generic: drop 5.15 support
authorMieczyslaw Nalewaj <[email protected]>
Tue, 17 Sep 2024 20:02:06 +0000 (22:02 +0200)
committerRobert Marko <[email protected]>
Fri, 20 Sep 2024 09:16:02 +0000 (11:16 +0200)
Drop config and files for Linux 5.15.

Signed-off-by: Mieczyslaw Nalewaj <[email protected]>
Link: https://github.com/openwrt/openwrt/pull/16417
Signed-off-by: Robert Marko <[email protected]>
941 files changed:
include/kernel-5.15 [deleted file]
target/linux/generic/backport-5.15/005-v5.17-01-Kbuild-use-Wdeclaration-after-statement.patch [deleted file]
target/linux/generic/backport-5.15/005-v5.17-02-Kbuild-move-to-std-gnu11.patch [deleted file]
target/linux/generic/backport-5.15/005-v5.17-03-Kbuild-use-std-gnu11-for-KBUILD_USERCFLAGS.patch [deleted file]
target/linux/generic/backport-5.15/020-v6.1-01-mm-x86-arm64-add-arch_has_hw_pte_young.patch [deleted file]
target/linux/generic/backport-5.15/020-v6.1-02-mm-x86-add-CONFIG_ARCH_HAS_NONLEAF_PMD_YOUNG.patch [deleted file]
target/linux/generic/backport-5.15/020-v6.1-03-mm-vmscan.c-refactor-shrink_node.patch [deleted file]
target/linux/generic/backport-5.15/020-v6.1-04-Revert-include-linux-mm_inline.h-fold-__update_lru_s.patch [deleted file]
target/linux/generic/backport-5.15/020-v6.1-05-mm-multi-gen-LRU-groundwork.patch [deleted file]
target/linux/generic/backport-5.15/020-v6.1-06-mm-multi-gen-LRU-minimal-implementation.patch [deleted file]
target/linux/generic/backport-5.15/020-v6.1-07-mm-multi-gen-LRU-exploit-locality-in-rmap.patch [deleted file]
target/linux/generic/backport-5.15/020-v6.1-08-mm-multi-gen-LRU-support-page-table-walks.patch [deleted file]
target/linux/generic/backport-5.15/020-v6.1-09-mm-multi-gen-LRU-optimize-multiple-memcgs.patch [deleted file]
target/linux/generic/backport-5.15/020-v6.1-10-mm-multi-gen-LRU-kill-switch.patch [deleted file]
target/linux/generic/backport-5.15/020-v6.1-11-mm-multi-gen-LRU-thrashing-prevention.patch [deleted file]
target/linux/generic/backport-5.15/020-v6.1-12-mm-multi-gen-LRU-debugfs-interface.patch [deleted file]
target/linux/generic/backport-5.15/020-v6.1-13-mm-mglru-don-t-sync-disk-for-each-aging-cycle.patch [deleted file]
target/linux/generic/backport-5.15/020-v6.1-14-mm-multi-gen-LRU-retry-pages-written-back-while-isol.patch [deleted file]
target/linux/generic/backport-5.15/020-v6.1-15-mm-multi-gen-LRU-move-lru_gen_add_mm-out-of-IRQ-off-.patch [deleted file]
target/linux/generic/backport-5.15/020-v6.1-17-mm-add-dummy-pmd_young-for-architectures-not-having-.patch [deleted file]
target/linux/generic/backport-5.15/020-v6.1-18-mm-introduce-arch_has_hw_nonleaf_pmd_young.patch [deleted file]
target/linux/generic/backport-5.15/020-v6.2-16-mm-multi-gen-LRU-fix-crash-during-cgroup-migration.patch [deleted file]
target/linux/generic/backport-5.15/020-v6.3-19-mm-add-vma_has_recency.patch [deleted file]
target/linux/generic/backport-5.15/020-v6.3-20-mm-support-POSIX_FADV_NOREUSE.patch [deleted file]
target/linux/generic/backport-5.15/020-v6.3-21-mm-multi-gen-LRU-rename-lru_gen_struct-to-lru_gen_pa.patch [deleted file]
target/linux/generic/backport-5.15/020-v6.3-22-mm-multi-gen-LRU-rename-lrugen-lists-to-lrugen-pages.patch [deleted file]
target/linux/generic/backport-5.15/020-v6.3-23-mm-multi-gen-LRU-remove-eviction-fairness-safeguard.patch [deleted file]
target/linux/generic/backport-5.15/020-v6.3-24-mm-multi-gen-LRU-remove-aging-fairness-safeguard.patch [deleted file]
target/linux/generic/backport-5.15/020-v6.3-25-mm-multi-gen-LRU-shuffle-should_run_aging.patch [deleted file]
target/linux/generic/backport-5.15/020-v6.3-26-mm-multi-gen-LRU-per-node-lru_gen_page-lists.patch [deleted file]
target/linux/generic/backport-5.15/020-v6.3-27-mm-multi-gen-LRU-clarify-scan_control-flags.patch [deleted file]
target/linux/generic/backport-5.15/020-v6.3-28-mm-multi-gen-LRU-simplify-arch_has_hw_pte_young-chec.patch [deleted file]
target/linux/generic/backport-5.15/020-v6.3-29-mm-multi-gen-LRU-avoid-futile-retries.patch [deleted file]
target/linux/generic/backport-5.15/021-v6.4-mm-Multi-gen-LRU-remove-wait_event_killable.patch [deleted file]
target/linux/generic/backport-5.15/050-v5.16-00-MIPS-uasm-Enable-muhu-opcode-for-MIPS-R6.patch [deleted file]
target/linux/generic/backport-5.15/050-v5.16-01-mips-uasm-Add-workaround-for-Loongson-2F-nop-CPU-err.patch [deleted file]
target/linux/generic/backport-5.15/050-v5.16-02-mips-bpf-Add-eBPF-JIT-for-32-bit-MIPS.patch [deleted file]
target/linux/generic/backport-5.15/050-v5.16-03-mips-bpf-Add-new-eBPF-JIT-for-64-bit-MIPS.patch [deleted file]
target/linux/generic/backport-5.15/050-v5.16-04-mips-bpf-Add-JIT-workarounds-for-CPU-errata.patch [deleted file]
target/linux/generic/backport-5.15/050-v5.16-05-mips-bpf-Enable-eBPF-JITs.patch [deleted file]
target/linux/generic/backport-5.15/050-v5.16-06-mips-bpf-Remove-old-BPF-JIT-implementations.patch [deleted file]
target/linux/generic/backport-5.15/060-v5.18-01-bpf-selftests-Add-helpers-to-directly-use-the-capget.patch [deleted file]
target/linux/generic/backport-5.15/060-v5.18-02-bpf-selftests-Remove-libcap-usage-from-test_verifier.patch [deleted file]
target/linux/generic/backport-5.15/060-v5.18-03-bpf-selftests-Remove-libcap-usage-from-test_progs.patch [deleted file]
target/linux/generic/backport-5.15/080-v5.17-clk-gate-Add-devm_clk_hw_register_gate.patch [deleted file]
target/linux/generic/backport-5.15/100-v5.18-tty-serial-bcm63xx-use-more-precise-Kconfig-symbol.patch [deleted file]
target/linux/generic/backport-5.15/200-v5.18-tools-resolve_btfids-Build-with-host-flags.patch [deleted file]
target/linux/generic/backport-5.15/201-v5.16-scripts-dtc-Update-to-upstream-version-v1.6.1-19-g0a.patch [deleted file]
target/linux/generic/backport-5.15/202-v6.1-kallsyms-support-big-kernel-symbols.patch [deleted file]
target/linux/generic/backport-5.15/300-v5.18-pinctrl-qcom-Return--EINVAL-for-setting-affinity-if-no-IRQ-parent.patch [deleted file]
target/linux/generic/backport-5.15/301-v5.16-soc-qcom-smem-Support-reserved-memory-description.patch [deleted file]
target/linux/generic/backport-5.15/302-v5.16-watchdog-bcm63xx_wdt-fix-fallthrough-warning.patch [deleted file]
target/linux/generic/backport-5.15/303-v6.2-powerpc-suppress-some-linker-warnings-in-recent-link.patch [deleted file]
target/linux/generic/backport-5.15/330-v5.16-01-MIPS-kernel-proc-add-CPU-option-reporting.patch [deleted file]
target/linux/generic/backport-5.15/330-v5.16-02-MIPS-Fix-using-smp_processor_id-in-preemptible-in-sh.patch [deleted file]
target/linux/generic/backport-5.15/331-v5.19-mtd-spinand-Add-support-for-XTX-XT26G0xA.patch [deleted file]
target/linux/generic/backport-5.15/344-v5.18-01-phy-marvell-phy-mvebu-a3700-comphy-Remove-port-from-.patch [deleted file]
target/linux/generic/backport-5.15/344-v5.18-02-phy-marvell-phy-mvebu-a3700-comphy-Add-native-kernel.patch [deleted file]
target/linux/generic/backport-5.15/345-v5.17-arm64-dts-marvell-armada-37xx-Add-xtal-clock-to-comp.patch [deleted file]
target/linux/generic/backport-5.15/346-v5.18-01-Revert-ata-ahci-mvebu-Make-SATA-PHY-optional-for-Arm.patch [deleted file]
target/linux/generic/backport-5.15/346-v5.18-02-Revert-usb-host-xhci-mvebu-make-USB-3.0-PHY-optional.patch [deleted file]
target/linux/generic/backport-5.15/346-v5.18-03-Revert-PCI-aardvark-Fix-initialization-with-old-Marv.patch [deleted file]
target/linux/generic/backport-5.15/347-v6.0-phy-marvell-phy-mvebu-a3700-comphy-Remove-broken-res.patch [deleted file]
target/linux/generic/backport-5.15/350-v5.18-regmap-add-configurable-downshift-for-addresses.patch [deleted file]
target/linux/generic/backport-5.15/351-v5.18-regmap-allow-a-defined-reg_base-to-be-added-to-every.patch [deleted file]
target/linux/generic/backport-5.15/352-v6.3-regmap-apply-reg_base-and-reg_downshift-for-single-r.patch [deleted file]
target/linux/generic/backport-5.15/360-v6.1-powerpc-vdso-link-with-z-noexecstack.patch [deleted file]
target/linux/generic/backport-5.15/400-v5.19-mtd-call-of_platform_populate-for-MTD-partitions.patch [deleted file]
target/linux/generic/backport-5.15/401-v6.0-mtd-parsers-add-support-for-Sercomm-partitions.patch [deleted file]
target/linux/generic/backport-5.15/402-v6.0-mtd-next-mtd-core-introduce-of-support-for-dynamic-partitions.patch [deleted file]
target/linux/generic/backport-5.15/403-v6.1-mtd-allow-getting-MTD-device-associated-with-a-speci.patch [deleted file]
target/linux/generic/backport-5.15/404-v6.0-mtd-core-check-partition-before-dereference.patch [deleted file]
target/linux/generic/backport-5.15/405-v6.1-mtd-core-add-missing-of_node_get-in-dynamic-partitio.patch [deleted file]
target/linux/generic/backport-5.15/406-v6.2-0001-mtd-core-simplify-a-bit-code-find-partition-matching.patch [deleted file]
target/linux/generic/backport-5.15/406-v6.2-0002-mtd-core-try-to-find-OF-node-for-every-MTD-partition.patch [deleted file]
target/linux/generic/backport-5.15/407-v5.17-mtd-parsers-qcom-Don-t-print-error-message-on-EPROBE.patch [deleted file]
target/linux/generic/backport-5.15/408-v6.2-mtd-core-set-ROOT_DEV-for-partitions-marked-as-rootf.patch [deleted file]
target/linux/generic/backport-5.15/409-v6.3-mtd-mtdpart-Don-t-create-platform-device-that-ll-nev.patch [deleted file]
target/linux/generic/backport-5.15/410-v5.18-mtd-parsers-trx-allow-to-use-on-MediaTek-MIPS-SoCs.patch [deleted file]
target/linux/generic/backport-5.15/411-v6.9-mtd-rawnand-brcmnand-Support-write-protection-settin.patch [deleted file]
target/linux/generic/backport-5.15/412-v6.3-01-spidev-Add-Silicon-Labs-EM3581-device-compatible.patch [deleted file]
target/linux/generic/backport-5.15/412-v6.3-02-spidev-Add-Silicon-Labs-SI3210-device-compatible.patch [deleted file]
target/linux/generic/backport-5.15/420-v5.19-02-mtd-spinand-gigadevice-add-support-for-GD5FxGQ4xExxG.patch [deleted file]
target/linux/generic/backport-5.15/420-v5.19-03-mtd-spinand-gigadevice-add-support-for-GD5F1GQ5RExxG.patch [deleted file]
target/linux/generic/backport-5.15/420-v5.19-04-mtd-spinand-gigadevice-add-support-for-GD5F-2-4-GQ5x.patch [deleted file]
target/linux/generic/backport-5.15/420-v5.19-05-mtd-spinand-gigadevice-add-support-for-GD5FxGM7xExxG.patch [deleted file]
target/linux/generic/backport-5.15/421-v6.2-mtd-parsers-add-TP-Link-SafeLoader-partitions-table-.patch [deleted file]
target/linux/generic/backport-5.15/422-v5.19-mtd-spi-nor-support-eon-en25qh256a.patch [deleted file]
target/linux/generic/backport-5.15/423-v6.1-0001-mtd-track-maximum-number-of-bitflips-for-each-read-r.patch [deleted file]
target/linux/generic/backport-5.15/423-v6.1-0002-mtd-always-initialize-stats-in-struct-mtd_oob_ops.patch [deleted file]
target/linux/generic/backport-5.15/423-v6.1-0003-mtd-add-ECC-error-accounting-for-each-read-request.patch [deleted file]
target/linux/generic/backport-5.15/423-v6.1-0004-mtdchar-add-MEMREAD-ioctl.patch [deleted file]
target/linux/generic/backport-5.15/423-v6.3-mtd-spinand-macronix-use-scratch-buffer-for-DMA-oper.patch [deleted file]
target/linux/generic/backport-5.15/424-v6.4-0004-mtd-core-prepare-mtd_otp_nvmem_add-to-handle-EPROBE_.patch [deleted file]
target/linux/generic/backport-5.15/600-v5.18-page_pool-Add-allocation-stats.patch [deleted file]
target/linux/generic/backport-5.15/601-v5.18-page_pool-Add-recycle-stats.patch [deleted file]
target/linux/generic/backport-5.15/602-v5.18-page_pool-Add-function-to-batch-and-return-stats.patch [deleted file]
target/linux/generic/backport-5.15/603-v5.19-page_pool-Add-recycle-stats-to-page_pool_put_page_bu.patch [deleted file]
target/linux/generic/backport-5.15/604-v5.19-net-page_pool-introduce-ethtool-stats.patch [deleted file]
target/linux/generic/backport-5.15/605-v5.18-xdp-introduce-flags-field-in-xdp_buff-xdp_frame.patch [deleted file]
target/linux/generic/backport-5.15/606-v5.18-xdp-add-frags-support-to-xdp_return_-buff-frame.patch [deleted file]
target/linux/generic/backport-5.15/607-v5.18-net-skbuff-add-size-metadata-to-skb_shared_info-for-.patch [deleted file]
target/linux/generic/backport-5.15/608-v5.18-net-veth-Account-total-xdp_frame-len-running-ndo_xdp.patch [deleted file]
target/linux/generic/backport-5.15/609-v5.18-veth-Allow-jumbo-frames-in-xdp-mode.patch [deleted file]
target/linux/generic/backport-5.15/611-v6.3-net-add-helper-eth_addr_add.patch [deleted file]
target/linux/generic/backport-5.15/700-v5.17-net-dsa-introduce-tagger-owned-storage-for-private.patch [deleted file]
target/linux/generic/backport-5.15/701-v5.17-dsa-make-tagging-protocols-connect-to-individual-switches.patch [deleted file]
target/linux/generic/backport-5.15/702-v5.19-00-net-ethernet-mtk_eth_soc-add-support-for-coherent-DM.patch [deleted file]
target/linux/generic/backport-5.15/702-v5.19-02-net-ethernet-mtk_eth_soc-add-support-for-Wireless-Et.patch [deleted file]
target/linux/generic/backport-5.15/702-v5.19-03-net-ethernet-mtk_eth_soc-implement-flow-offloading-t.patch [deleted file]
target/linux/generic/backport-5.15/702-v5.19-05-net-ethernet-mtk_eth_soc-add-ipv6-flow-offload-suppo.patch [deleted file]
target/linux/generic/backport-5.15/702-v5.19-06-net-ethernet-mtk_eth_soc-support-TC_SETUP_BLOCK-for-.patch [deleted file]
target/linux/generic/backport-5.15/702-v5.19-07-net-ethernet-mtk_eth_soc-allocate-struct-mtk_ppe-sep.patch [deleted file]
target/linux/generic/backport-5.15/702-v5.19-08-net-ethernet-mtk_eth_soc-rework-hardware-flow-table-.patch [deleted file]
target/linux/generic/backport-5.15/702-v5.19-09-net-ethernet-mtk_eth_soc-remove-bridge-flow-offload-.patch [deleted file]
target/linux/generic/backport-5.15/702-v5.19-10-net-ethernet-mtk_eth_soc-support-creating-mac-addres.patch [deleted file]
target/linux/generic/backport-5.15/702-v5.19-11-net-ethernet-mtk_eth_soc-wed-fix-sparse-endian-warni.patch [deleted file]
target/linux/generic/backport-5.15/702-v5.19-12-net-ethernet-mtk_eth_soc-fix-return-value-check-in-m.patch [deleted file]
target/linux/generic/backport-5.15/702-v5.19-13-net-ethernet-mtk_eth_soc-use-standard-property-for-c.patch [deleted file]
target/linux/generic/backport-5.15/702-v5.19-14-net-ethernet-mtk_eth_soc-use-after-free-in-__mtk_ppe.patch [deleted file]
target/linux/generic/backport-5.15/702-v5.19-15-net-ethernet-mtk_eth_soc-add-check-for-allocation-fa.patch [deleted file]
target/linux/generic/backport-5.15/702-v5.19-16-eth-mtk_eth_soc-silence-the-GCC-12-array-bounds-warn.patch [deleted file]
target/linux/generic/backport-5.15/702-v5.19-17-net-ethernet-mtk_eth_soc-rely-on-GFP_KERNEL-for-dma_.patch [deleted file]
target/linux/generic/backport-5.15/702-v5.19-18-net-ethernet-mtk_eth_soc-move-tx-dma-desc-configurat.patch [deleted file]
target/linux/generic/backport-5.15/702-v5.19-19-net-ethernet-mtk_eth_soc-add-txd_size-to-mtk_soc_dat.patch [deleted file]
target/linux/generic/backport-5.15/702-v5.19-20-net-ethernet-mtk_eth_soc-rely-on-txd_size-in-mtk_tx_.patch [deleted file]
target/linux/generic/backport-5.15/702-v5.19-21-net-ethernet-mtk_eth_soc-rely-on-txd_size-in-mtk_des.patch [deleted file]
target/linux/generic/backport-5.15/702-v5.19-22-net-ethernet-mtk_eth_soc-rely-on-txd_size-in-txd_to_.patch [deleted file]
target/linux/generic/backport-5.15/702-v5.19-23-net-ethernet-mtk_eth_soc-add-rxd_size-to-mtk_soc_dat.patch [deleted file]
target/linux/generic/backport-5.15/702-v5.19-24-net-ethernet-mtk_eth_soc-rely-on-txd_size-field-in-m.patch [deleted file]
target/linux/generic/backport-5.15/702-v5.19-25-net-ethernet-mtk_eth_soc-rely-on-rxd_size-field-in-m.patch [deleted file]
target/linux/generic/backport-5.15/702-v5.19-26-net-ethernet-mtk_eth_soc-introduce-device-register-m.patch [deleted file]
target/linux/generic/backport-5.15/702-v5.19-27-net-ethernet-mtk_eth_soc-introduce-MTK_NETSYS_V2-sup.patch [deleted file]
target/linux/generic/backport-5.15/702-v5.19-28-net-ethernet-mtk_eth_soc-convert-ring-dma-pointer-to.patch [deleted file]
target/linux/generic/backport-5.15/702-v5.19-29-net-ethernet-mtk_eth_soc-convert-scratch_ring-pointe.patch [deleted file]
target/linux/generic/backport-5.15/702-v5.19-30-net-ethernet-mtk_eth_soc-introduce-support-for-mt798.patch [deleted file]
target/linux/generic/backport-5.15/702-v5.19-31-net-ethernet-mtk_eth_soc-fix-error-code-in-mtk_flow_.patch [deleted file]
target/linux/generic/backport-5.15/702-v5.19-33-net-ethernet-mtk_eth_soc-enable-rx-cksum-offload-for.patch [deleted file]
target/linux/generic/backport-5.15/702-v5.19-34-eth-mtk_ppe-fix-up-after-merge.patch [deleted file]
target/linux/generic/backport-5.15/703-00-v5.16-net-convert-users-of-bitmap_foo-to-linkmode_foo.patch [deleted file]
target/linux/generic/backport-5.15/703-01-v5.16-net-phylink-add-MAC-phy_interface_t-bitmap.patch [deleted file]
target/linux/generic/backport-5.15/703-02-v5.16-net-phylink-use-supported_interfaces-for-phylink-val.patch [deleted file]
target/linux/generic/backport-5.15/703-03-v5.16-net-dsa-populate-supported_interfaces-member.patch [deleted file]
target/linux/generic/backport-5.15/703-04-v5.17-net-dsa-consolidate-phylink-creation.patch [deleted file]
target/linux/generic/backport-5.15/703-05-v5.17-net-dsa-replace-phylink_get_interfaces-with-phylink_.patch [deleted file]
target/linux/generic/backport-5.15/703-06-v5.18-net-dsa-add-support-for-phylink-mac_select_pcs.patch [deleted file]
target/linux/generic/backport-5.15/703-07-v5.16-net-phy-add-phy_interface_t-bitmap-support.patch [deleted file]
target/linux/generic/backport-5.15/703-08-v5.17-net-phylink-add-mac_select_pcs-method-to-phylink_mac.patch [deleted file]
target/linux/generic/backport-5.15/703-09-v5.17-net-phylink-add-generic-validate-implementation.patch [deleted file]
target/linux/generic/backport-5.15/703-11-v5.17-net-phylink-add-pcs_validate-method.patch [deleted file]
target/linux/generic/backport-5.15/703-12-v5.17-net-phylink-add-legacy_pre_march2020-indicator.patch [deleted file]
target/linux/generic/backport-5.15/703-13-v5.17-net-dsa-mark-DSA-phylink-as-legacy_pre_march2020.patch [deleted file]
target/linux/generic/backport-5.15/703-14-v5.17-net-phylink-use-legacy_pre_march2020.patch [deleted file]
target/linux/generic/backport-5.15/703-15-v5.18-net-phy-phylink-fix-DSA-mac_select_pcs-introduction.patch [deleted file]
target/linux/generic/backport-5.15/703-16-v5.16-net-mvneta-populate-supported_interfaces-member.patch [deleted file]
target/linux/generic/backport-5.15/703-17-v5.16-net-mvneta-remove-interface-checks-in-mvneta_validat.patch [deleted file]
target/linux/generic/backport-5.15/703-18-v5.16-net-mvneta-drop-use-of-phylink_helper_basex_speed.patch [deleted file]
target/linux/generic/backport-5.15/703-19-v5.17-net-mvneta-use-phylink_generic_validate.patch [deleted file]
target/linux/generic/backport-5.15/703-20-v5.17-net-mvneta-mark-as-a-legacy_pre_march2020-driver.patch [deleted file]
target/linux/generic/backport-5.15/704-01-v5.17-net-mtk_eth_soc-populate-supported_interfaces-member.patch [deleted file]
target/linux/generic/backport-5.15/704-02-v5.17-net-mtk_eth_soc-remove-interface-checks-in-mtk_valid.patch [deleted file]
target/linux/generic/backport-5.15/704-03-v5.17-net-mtk_eth_soc-drop-use-of-phylink_helper_basex_spe.patch [deleted file]
target/linux/generic/backport-5.15/704-04-v5.17-net-mtk_eth_soc-use-phylink_generic_validate.patch [deleted file]
target/linux/generic/backport-5.15/704-05-v5.17-net-mtk_eth_soc-mark-as-a-legacy_pre_march2020-drive.patch [deleted file]
target/linux/generic/backport-5.15/704-06-v5.19-eth-mtk_eth_soc-remove-a-copy-of-the-NAPI_POLL_WEIGH.patch [deleted file]
target/linux/generic/backport-5.15/704-07-v5.19-mtk_eth_soc-remove-unused-mac-mode.patch [deleted file]
target/linux/generic/backport-5.15/704-08-v5.19-net-mtk_eth_soc-remove-unused-sgmii-flags.patch [deleted file]
target/linux/generic/backport-5.15/704-09-v5.19-net-mtk_eth_soc-add-mask-and-update-PCS-speed-defini.patch [deleted file]
target/linux/generic/backport-5.15/704-10-v5.19-net-mtk_eth_soc-correct-802.3z-speed-setting.patch [deleted file]
target/linux/generic/backport-5.15/704-11-v5.19-net-mtk_eth_soc-correct-802.3z-duplex-setting.patch [deleted file]
target/linux/generic/backport-5.15/704-12-v5.19-net-mtk_eth_soc-stop-passing-phylink-state-to-sgmii-.patch [deleted file]
target/linux/generic/backport-5.15/704-13-v5.19-net-mtk_eth_soc-provide-mtk_sgmii_config.patch [deleted file]
target/linux/generic/backport-5.15/704-14-v5.19-net-mtk_eth_soc-add-fixme-comment-for-state-speed-us.patch [deleted file]
target/linux/generic/backport-5.15/704-16-v5.19-net-mtk_eth_soc-move-restoration-of-SYSCFG0-to-mac_f.patch [deleted file]
target/linux/generic/backport-5.15/704-17-v5.19-net-mtk_eth_soc-convert-code-structure-to-suit-split.patch [deleted file]
target/linux/generic/backport-5.15/704-18-v5.19-net-mtk_eth_soc-partially-convert-to-phylink_pcs.patch [deleted file]
target/linux/generic/backport-5.15/705-01-v5.17-net-dsa-mt7530-iterate-using-dsa_switch_for_each_use.patch [deleted file]
target/linux/generic/backport-5.15/705-02-v5.19-net-dsa-mt7530-populate-supported_interfaces-and-mac.patch [deleted file]
target/linux/generic/backport-5.15/705-03-v5.19-net-dsa-mt7530-remove-interface-checks.patch [deleted file]
target/linux/generic/backport-5.15/705-04-v5.19-net-dsa-mt7530-drop-use-of-phylink_helper_basex_spee.patch [deleted file]
target/linux/generic/backport-5.15/705-05-v5.19-net-dsa-mt7530-only-indicate-linkmodes-that-can-be-s.patch [deleted file]
target/linux/generic/backport-5.15/705-06-v5.19-net-dsa-mt7530-switch-to-use-phylink_get_linkmodes.patch [deleted file]
target/linux/generic/backport-5.15/705-07-v5.19-net-dsa-mt7530-partially-convert-to-phylink_pcs.patch [deleted file]
target/linux/generic/backport-5.15/705-08-v5.19-net-dsa-mt7530-move-autoneg-handling-to-PCS-validati.patch [deleted file]
target/linux/generic/backport-5.15/705-09-v5.19-net-dsa-mt7530-mark-as-non-legacy.patch [deleted file]
target/linux/generic/backport-5.15/705-10-v5.19-net-dsa-mt753x-fix-pcs-conversion-regression.patch [deleted file]
target/linux/generic/backport-5.15/705-11-v6.0-net-dsa-mt7530-rework-mt7530_hw_vlan_-add-del.patch [deleted file]
target/linux/generic/backport-5.15/705-13-v6.0-net-dsa-mt7530-get-cpu-port-via-dp-cpu_dp-instead-of.patch [deleted file]
target/linux/generic/backport-5.15/706-00-v6.0-net-ethernet-mtk_eth_soc-rely-on-page_pool-for-singl.patch [deleted file]
target/linux/generic/backport-5.15/706-01-v6.0-net-ethernet-mtk_eth_soc-add-basic-XDP-support.patch [deleted file]
target/linux/generic/backport-5.15/706-02-v6.0-net-ethernet-mtk_eth_soc-introduce-xdp-ethtool-count.patch [deleted file]
target/linux/generic/backport-5.15/706-03-v6.0-net-ethernet-mtk_eth_soc-add-xmit-XDP-support.patch [deleted file]
target/linux/generic/backport-5.15/706-04-v6.0-net-ethernet-mtk_eth_soc-add-support-for-page_pool_g.patch [deleted file]
target/linux/generic/backport-5.15/706-05-v6.0-net-ethernet-mtk_eth_soc-introduce-mtk_xdp_frame_map.patch [deleted file]
target/linux/generic/backport-5.15/706-06-v6.0-net-ethernet-mtk_eth_soc-introduce-xdp-multi-frag-su.patch [deleted file]
target/linux/generic/backport-5.15/707-v6.3-net-pcs-add-driver-for-MediaTek-SGMII-PCS.patch [deleted file]
target/linux/generic/backport-5.15/708-01-v5.16-net-mvneta-Delete-unused-variable.patch [deleted file]
target/linux/generic/backport-5.15/708-02-v6.3-net-mvneta-fix-potential-double-frees-in-mvneta_txq_.patch [deleted file]
target/linux/generic/backport-5.15/710-v6.0-net-ethernet-mtk_eth_soc-fix-hw-hash-reporting-for-M.patch [deleted file]
target/linux/generic/backport-5.15/711-v6.0-01-net-ethernet-mtk_eth_soc-fix-off-by-one-check-of-ARR.patch [deleted file]
target/linux/generic/backport-5.15/711-v6.0-02-net-ethernet-mtk_ppe-fix-possible-NULL-pointer-deref.patch [deleted file]
target/linux/generic/backport-5.15/711-v6.0-03-net-ethernet-mtk-ppe-fix-traffic-offload-with-bridge.patch [deleted file]
target/linux/generic/backport-5.15/711-v6.0-04-net-ethernet-mtk_eth_soc-remove-mtk_foe_entry_timest.patch [deleted file]
target/linux/generic/backport-5.15/712-v6.0-net-ethernet-mtk_eth_soc-enable-XDP-support-just-for.patch [deleted file]
target/linux/generic/backport-5.15/713-v6.0-net-ethernet-mtk_eth_soc-move-gdma_to_ppe-and-ppe_ba.patch [deleted file]
target/linux/generic/backport-5.15/714-v6.0-net-ethernet-mtk_eth_soc-move-ppe-table-hash-offset-.patch [deleted file]
target/linux/generic/backport-5.15/715-v6.0-net-ethernet-mtk_eth_soc-add-the-capability-to-run-m.patch [deleted file]
target/linux/generic/backport-5.15/716-v6.0-net-ethernet-mtk_eth_soc-move-wdma_base-definitions-.patch [deleted file]
target/linux/generic/backport-5.15/717-v6.0-net-ethernet-mtk_eth_soc-add-foe_entry_size-to-mtk_e.patch [deleted file]
target/linux/generic/backport-5.15/718-v6.0-net-ethernet-mtk_eth_soc-fix-typo-in-__mtk_foe_entry.patch [deleted file]
target/linux/generic/backport-5.15/719-v6.0-net-ethernet-mtk_eth_soc-check-max-allowed-value-in-.patch [deleted file]
target/linux/generic/backport-5.15/720-v6.0-net-ethernet-mtk_eth_wed-add-mtk_wed_configure_irq-a.patch [deleted file]
target/linux/generic/backport-5.15/721-v6.0-net-ethernet-mtk_eth_wed-add-wed-support-for-mt7986-.patch [deleted file]
target/linux/generic/backport-5.15/722-v6.0-net-ethernet-mtk_eth_wed-add-axi-bus-support.patch [deleted file]
target/linux/generic/backport-5.15/723-v6.0-net-ethernet-mtk_eth_soc-introduce-flow-offloading-s.patch [deleted file]
target/linux/generic/backport-5.15/724-v6.0-net-ethernet-mtk_eth_soc-fix-wrong-use-of-new-helper.patch [deleted file]
target/linux/generic/backport-5.15/724-v6.2-net-ethernet-mtk_eth_soc-enable-flow-offloading-supp.patch [deleted file]
target/linux/generic/backport-5.15/725-v6.0-net-ethernet-mtk_eth_soc-fix-usage-of-foe_entry_size.patch [deleted file]
target/linux/generic/backport-5.15/726-v6.0-net-ethernet-mtk_eth_soc-fix-mask-of-RX_DMA_GET_SPOR.patch [deleted file]
target/linux/generic/backport-5.15/727-v6.1-net-ethernet-mtk_eth_soc-fix-state-in-__mtk_foe_entr.patch [deleted file]
target/linux/generic/backport-5.15/728-v6.1-01-net-ethernet-mtk_eth_soc-fix-possible-memory-leak-in.patch [deleted file]
target/linux/generic/backport-5.15/728-v6.1-02-net-ethernet-mtk_eth_wed-add-missing-put_device-in-m.patch [deleted file]
target/linux/generic/backport-5.15/728-v6.1-03-net-ethernet-mtk_eth_wed-add-missing-of_node_put.patch [deleted file]
target/linux/generic/backport-5.15/728-v6.1-04-net-ethernet-mtk_eth_soc-fix-resource-leak-in-error-.patch [deleted file]
target/linux/generic/backport-5.15/728-v6.1-05-net-ethernet-mtk_eth_soc-fix-memory-leak-in-error-pa.patch [deleted file]
target/linux/generic/backport-5.15/729-01-v6.1-net-ethernet-mtk_wed-introduce-wed-mcu-support.patch [deleted file]
target/linux/generic/backport-5.15/729-02-v6.1-net-ethernet-mtk_wed-introduce-wed-wo-support.patch [deleted file]
target/linux/generic/backport-5.15/729-03-v6.1-net-ethernet-mtk_wed-rename-tx_wdma-array-in-rx_wdma.patch [deleted file]
target/linux/generic/backport-5.15/729-04-v6.1-net-ethernet-mtk_wed-add-configure-wed-wo-support.patch [deleted file]
target/linux/generic/backport-5.15/729-05-v6.1-net-ethernet-mtk_wed-add-rx-mib-counters.patch [deleted file]
target/linux/generic/backport-5.15/729-06-v6.1-net-ethernet-mtk_eth_soc-do-not-overwrite-mtu-config.patch [deleted file]
target/linux/generic/backport-5.15/729-07-v6.1-net-ethernet-mtk_eth_soc-remove-cpu_relax-in-mtk_pen.patch [deleted file]
target/linux/generic/backport-5.15/729-08-v6.2-net-ethernet-mtk_eth_soc-fix-RSTCTRL_PPE-0-1-definit.patch [deleted file]
target/linux/generic/backport-5.15/729-09-v6.2-net-ethernet-mtk_wed-add-wcid-overwritten-support-fo.patch [deleted file]
target/linux/generic/backport-5.15/729-10-v6.2-net-ethernet-mtk_wed-return-status-value-in-mtk_wdma.patch [deleted file]
target/linux/generic/backport-5.15/729-11-v6.2-net-ethernet-mtk_wed-move-MTK_WDMA_RESET_IDX_TX-conf.patch [deleted file]
target/linux/generic/backport-5.15/729-12-v6.2-net-ethernet-mtk_wed-update-mtk_wed_stop.patch [deleted file]
target/linux/generic/backport-5.15/729-13-v6.2-net-ethernet-mtk_wed-add-mtk_wed_rx_reset-routine.patch [deleted file]
target/linux/generic/backport-5.15/729-14-v6.2-net-ethernet-mtk_wed-add-reset-to-tx_ring_setup-call.patch [deleted file]
target/linux/generic/backport-5.15/729-15-v6.2-net-ethernet-mtk_wed-fix-sleep-while-atomic-in-mtk_w.patch [deleted file]
target/linux/generic/backport-5.15/729-16-v6.3-net-ethernet-mtk_wed-get-rid-of-queue-lock-for-rx-qu.patch [deleted file]
target/linux/generic/backport-5.15/729-17-v6.3-net-ethernet-mtk_wed-get-rid-of-queue-lock-for-tx-qu.patch [deleted file]
target/linux/generic/backport-5.15/729-18-v6.3-net-ethernet-mtk_eth_soc-introduce-mtk_hw_reset-util.patch [deleted file]
target/linux/generic/backport-5.15/729-19-v6.3-net-ethernet-mtk_eth_soc-introduce-mtk_hw_warm_reset.patch [deleted file]
target/linux/generic/backport-5.15/729-20-v6.3-net-ethernet-mtk_eth_soc-align-reset-procedure-to-ve.patch [deleted file]
target/linux/generic/backport-5.15/729-21-v6.3-net-ethernet-mtk_eth_soc-add-dma-checks-to-mtk_hw_re.patch [deleted file]
target/linux/generic/backport-5.15/729-22-v6.3-net-ethernet-mtk_wed-add-reset-reset_complete-callba.patch [deleted file]
target/linux/generic/backport-5.15/729-23-v6.3-net-ethernet-mtk_wed-add-reset-to-rx_ring_setup-call.patch [deleted file]
target/linux/generic/backport-5.15/730-01-v6.3-net-ethernet-mtk_eth_soc-account-for-vlan-in-rx-head.patch [deleted file]
target/linux/generic/backport-5.15/730-02-v6.3-net-ethernet-mtk_eth_soc-increase-tx-ring-side-for-Q.patch [deleted file]
target/linux/generic/backport-5.15/730-03-v6.3-net-ethernet-mtk_eth_soc-avoid-port_mg-assignment-on.patch [deleted file]
target/linux/generic/backport-5.15/730-04-v6.3-net-ethernet-mtk_eth_soc-implement-multi-queue-suppo.patch [deleted file]
target/linux/generic/backport-5.15/730-05-v6.3-net-dsa-tag_mtk-assign-per-port-queues.patch [deleted file]
target/linux/generic/backport-5.15/730-06-v6.3-net-ethernet-mediatek-ppe-assign-per-port-queues-for.patch [deleted file]
target/linux/generic/backport-5.15/730-08-v6.3-net-dsa-add-support-for-DSA-rx-offloading-via-metada.patch [deleted file]
target/linux/generic/backport-5.15/730-09-v6.3-net-ethernet-mtk_eth_soc-fix-VLAN-rx-hardware-accele.patch [deleted file]
target/linux/generic/backport-5.15/730-10-v6.3-net-ethernet-mtk_eth_soc-drop-packets-to-WDMA-if-the.patch [deleted file]
target/linux/generic/backport-5.15/730-12-v6.3-net-ethernet-mtk_eth_soc-disable-hardware-DSA-untagg.patch [deleted file]
target/linux/generic/backport-5.15/730-13-v6.3-net-ethernet-mtk_eth_soc-enable-special-tag-when-any.patch [deleted file]
target/linux/generic/backport-5.15/730-14-v6.3-net-ethernet-mtk_eth_soc-fix-DSA-TX-tag-hwaccel-for-.patch [deleted file]
target/linux/generic/backport-5.15/730-15-v6.3-net-ethernet-mtk_wed-No-need-to-clear-memory-after-a.patch [deleted file]
target/linux/generic/backport-5.15/730-16-v6.3-net-ethernet-mtk_wed-fix-some-possible-NULL-pointer-.patch [deleted file]
target/linux/generic/backport-5.15/730-17-v6.3-net-ethernet-mtk_wed-fix-possible-deadlock-if-mtk_we.patch [deleted file]
target/linux/generic/backport-5.15/730-18-v6.3-net-ethernet-mtk_eth_soc-fix-tx-throughput-regressio.patch [deleted file]
target/linux/generic/backport-5.15/731-v6.1-0001-net-phy-Introduce-QUSGMII-PHY-mode.patch [deleted file]
target/linux/generic/backport-5.15/731-v6.1-0002-net-phy-Add-helper-to-derive-the-number-of-ports-fro.patch [deleted file]
target/linux/generic/backport-5.15/731-v6.1-0003-net-phy-Add-1000BASE-KX-interface-mode.patch [deleted file]
target/linux/generic/backport-5.15/731-v6.1-0004-net-phy-Add-support-for-rate-matching.patch [deleted file]
target/linux/generic/backport-5.15/733-v6.2-01-net-ethernet-mtk_eth_soc-Avoid-truncating-allocation.patch [deleted file]
target/linux/generic/backport-5.15/733-v6.2-02-net-mtk_eth_soc-add-definitions-for-PCS.patch [deleted file]
target/linux/generic/backport-5.15/733-v6.2-03-net-mtk_eth_soc-eliminate-unnecessary-error-handling.patch [deleted file]
target/linux/generic/backport-5.15/733-v6.2-04-net-mtk_eth_soc-add-pcs_get_state-implementation.patch [deleted file]
target/linux/generic/backport-5.15/733-v6.2-05-net-mtk_eth_soc-convert-mtk_sgmii-to-use-regmap_upda.patch [deleted file]
target/linux/generic/backport-5.15/733-v6.2-06-net-mtk_eth_soc-add-out-of-band-forcing-of-speed-and.patch [deleted file]
target/linux/generic/backport-5.15/733-v6.2-07-net-mtk_eth_soc-move-PHY-power-up.patch [deleted file]
target/linux/generic/backport-5.15/733-v6.2-08-net-mtk_eth_soc-move-interface-speed-selection.patch [deleted file]
target/linux/generic/backport-5.15/733-v6.2-09-net-mtk_eth_soc-add-advertisement-programming.patch [deleted file]
target/linux/generic/backport-5.15/733-v6.2-10-net-mtk_eth_soc-move-and-correct-link-timer-programm.patch [deleted file]
target/linux/generic/backport-5.15/733-v6.2-11-net-mtk_eth_soc-add-support-for-in-band-802.3z-negot.patch [deleted file]
target/linux/generic/backport-5.15/733-v6.2-12-net-mediatek-sgmii-ensure-the-SGMII-PHY-is-powered-d.patch [deleted file]
target/linux/generic/backport-5.15/733-v6.2-13-net-mediatek-sgmii-fix-duplex-configuration.patch [deleted file]
target/linux/generic/backport-5.15/733-v6.2-14-mtk_sgmii-enable-PCS-polling-to-allow-SFP-work.patch [deleted file]
target/linux/generic/backport-5.15/733-v6.3-15-net-ethernet-mtk_eth_soc-reset-PCS-state.patch [deleted file]
target/linux/generic/backport-5.15/733-v6.3-16-net-ethernet-mtk_eth_soc-only-write-values-if-needed.patch [deleted file]
target/linux/generic/backport-5.15/733-v6.3-18-net-ethernet-mtk_eth_soc-add-support-for-MT7981.patch [deleted file]
target/linux/generic/backport-5.15/733-v6.3-19-net-ethernet-mtk_eth_soc-set-MDIO-bus-clock-frequenc.patch [deleted file]
target/linux/generic/backport-5.15/733-v6.3-20-net-ethernet-mtk_eth_soc-switch-to-external-PCS-driv.patch [deleted file]
target/linux/generic/backport-5.15/733-v6.3-21-net-ethernet-mtk_eth_soc-add-missing-ppe-cache-flush.patch [deleted file]
target/linux/generic/backport-5.15/733-v6.4-22-net-mtk_eth_soc-use-WO-firmware-for-MT7981.patch [deleted file]
target/linux/generic/backport-5.15/733-v6.4-23-net-ethernet-mtk_eth_soc-fix-NULL-pointer-dereferenc.patch [deleted file]
target/linux/generic/backport-5.15/733-v6.4-24-net-ethernet-mtk_eth_soc-ppe-add-support-for-flow-ac.patch [deleted file]
target/linux/generic/backport-5.15/733-v6.4-25-net-ethernet-mediatek-fix-ppe-flow-accounting-for-v1.patch [deleted file]
target/linux/generic/backport-5.15/733-v6.4-26-net-ethernet-mtk_eth_soc-drop-generic-vlan-rx-offloa.patch [deleted file]
target/linux/generic/backport-5.15/733-v6.5-27-net-ethernet-mtk_eth_soc-always-mtk_get_ib1_pkt_type.patch [deleted file]
target/linux/generic/backport-5.15/734-v5.16-0001-net-bgmac-improve-handling-PHY.patch [deleted file]
target/linux/generic/backport-5.15/734-v5.16-0002-net-bgmac-support-MDIO-described-in-DT.patch [deleted file]
target/linux/generic/backport-5.15/735-v6.0-0001-net-phy-Add-support-for-AQR113C-EPHY.patch [deleted file]
target/linux/generic/backport-5.15/736-v6.1-0001-net-phy-aquantia-Add-some-additional-phy-interfaces.patch [deleted file]
target/linux/generic/backport-5.15/736-v6.1-0002-net-phy-aquantia-Add-support-for-rate-matching.patch [deleted file]
target/linux/generic/backport-5.15/737-01-v6.7-net-phy-aquantia-move-to-separate-directory.patch [deleted file]
target/linux/generic/backport-5.15/737-02-v6.7-net-phy-aquantia-move-MMD_VEND-define-to-header.patch [deleted file]
target/linux/generic/backport-5.15/737-03-v6.7-net-phy-aquantia-add-firmware-load-support.patch [deleted file]
target/linux/generic/backport-5.15/738-v6.9-net-phy-aquantia-add-AQR111-and-AQR111B0-PHY-ID.patch [deleted file]
target/linux/generic/backport-5.15/739-v6.9-net-phy-aquantia-add-AQR113-PHY-ID.patch [deleted file]
target/linux/generic/backport-5.15/740-v6.9-net-phy-aquantia-add-AQR813-PHY-ID.patch [deleted file]
target/linux/generic/backport-5.15/742-v5.16-net-phy-at803x-add-support-for-qca-8327-internal-phy.patch [deleted file]
target/linux/generic/backport-5.15/743-v5.16-0001-net-dsa-b53-Include-all-ports-in-enabled_ports.patch [deleted file]
target/linux/generic/backport-5.15/743-v5.16-0002-net-dsa-b53-Drop-BCM5301x-workaround-for-a-wrong-CPU.patch [deleted file]
target/linux/generic/backport-5.15/743-v5.16-0003-net-dsa-b53-Improve-flow-control-setup-on-BCM5301x.patch [deleted file]
target/linux/generic/backport-5.15/743-v5.16-0004-net-dsa-b53-Drop-unused-cpu_port-field.patch [deleted file]
target/linux/generic/backport-5.15/745-v5.16-01-net-phy-at803x-add-support-for-qca-8327-A-variant.patch [deleted file]
target/linux/generic/backport-5.15/745-v5.16-02-net-phy-at803x-add-resume-suspend-function-to-qca83x.patch [deleted file]
target/linux/generic/backport-5.15/745-v5.16-03-net-phy-at803x-fix-spacing-and-improve-name-for-83xx.patch [deleted file]
target/linux/generic/backport-5.15/746-v5.16-01-net-phy-at803x-fix-resume-for-QCA8327-phy.patch [deleted file]
target/linux/generic/backport-5.15/746-v5.16-02-net-phy-at803x-add-DAC-amplitude-fix-for-8327-phy.patch [deleted file]
target/linux/generic/backport-5.15/746-v5.16-03-net-phy-at803x-enable-prefer-master-for-83xx-interna.patch [deleted file]
target/linux/generic/backport-5.15/746-v5.16-04-net-phy-at803x-better-describe-debug-regs.patch [deleted file]
target/linux/generic/backport-5.15/747-v5.16-01-dsa-qca8k-add-mac-power-sel-support.patch [deleted file]
target/linux/generic/backport-5.15/747-v5.16-02-dt-bindings-net-dsa-qca8k-Add-SGMII-clock-phase-prop.patch [deleted file]
target/linux/generic/backport-5.15/747-v5.16-03-net-dsa-qca8k-add-support-for-sgmii-falling-edge.patch [deleted file]
target/linux/generic/backport-5.15/747-v5.16-04-dt-bindings-net-dsa-qca8k-Document-support-for-CPU-p.patch [deleted file]
target/linux/generic/backport-5.15/747-v5.16-05-net-dsa-qca8k-add-support-for-cpu-port-6.patch [deleted file]
target/linux/generic/backport-5.15/747-v5.16-06-net-dsa-qca8k-rework-rgmii-delay-logic-and-scan-for-.patch [deleted file]
target/linux/generic/backport-5.15/747-v5.16-07-dt-bindings-net-dsa-qca8k-Document-qca-sgmii-enable-.patch [deleted file]
target/linux/generic/backport-5.15/747-v5.16-08-net-dsa-qca8k-add-explicit-SGMII-PLL-enable.patch [deleted file]
target/linux/generic/backport-5.15/747-v5.16-09-dt-bindings-net-dsa-qca8k-Document-qca-led-open-drai.patch [deleted file]
target/linux/generic/backport-5.15/747-v5.16-10-net-dsa-qca8k-add-support-for-pws-config-reg.patch [deleted file]
target/linux/generic/backport-5.15/747-v5.16-11-dt-bindings-net-dsa-qca8k-document-support-for-qca83.patch [deleted file]
target/linux/generic/backport-5.15/747-v5.16-12-net-dsa-qca8k-add-support-for-QCA8328.patch [deleted file]
target/linux/generic/backport-5.15/747-v5.16-13-net-dsa-qca8k-set-internal-delay-also-for-sgmii.patch [deleted file]
target/linux/generic/backport-5.15/747-v5.16-14-net-dsa-qca8k-move-port-config-to-dedicated-struct.patch [deleted file]
target/linux/generic/backport-5.15/747-v5.16-15-dt-bindings-net-ipq8064-mdio-fix-warning-with-new-qc.patch [deleted file]
target/linux/generic/backport-5.15/747-v5.16-16-dt-bindings-net-dsa-qca8k-convert-to-YAML-schema.patch [deleted file]
target/linux/generic/backport-5.15/748-v5.16-net-dsa-qca8k-fix-delay-applied-to-wrong-cpu-in-parse-p.patch [deleted file]
target/linux/generic/backport-5.15/749-v5.16-net-dsa-qca8k-tidy-for-loop-in-setup-and-add-cpu-port-c.patch [deleted file]
target/linux/generic/backport-5.15/750-v5.16-net-dsa-qca8k-make-sure-pad0-mac06-exchange-is-disabled.patch [deleted file]
target/linux/generic/backport-5.15/750-v6.5-01-net-ethernet-mtk_ppe-add-MTK_FOE_ENTRY_V-1-2-_SIZE-m.patch [deleted file]
target/linux/generic/backport-5.15/750-v6.5-02-net-ethernet-mtk_eth_soc-remove-incorrect-PLL-config.patch [deleted file]
target/linux/generic/backport-5.15/750-v6.5-03-net-ethernet-mtk_eth_soc-remove-mac_pcs_get_state-an.patch [deleted file]
target/linux/generic/backport-5.15/750-v6.5-05-net-ethernet-mtk_eth_soc-add-version-in-mtk_soc_data.patch [deleted file]
target/linux/generic/backport-5.15/750-v6.5-06-net-ethernet-mtk_eth_soc-increase-MAX_DEVS-to-3.patch [deleted file]
target/linux/generic/backport-5.15/750-v6.5-07-net-ethernet-mtk_eth_soc-rely-on-MTK_MAX_DEVS-and-re.patch [deleted file]
target/linux/generic/backport-5.15/750-v6.5-08-net-ethernet-mtk_eth_soc-add-NETSYS_V3-version-suppo.patch [deleted file]
target/linux/generic/backport-5.15/750-v6.5-09-net-ethernet-mtk_eth_soc-convert-caps-in-mtk_soc_dat.patch [deleted file]
target/linux/generic/backport-5.15/750-v6.5-10-net-ethernet-mtk_eth_soc-convert-clock-bitmap-to-u64.patch [deleted file]
target/linux/generic/backport-5.15/750-v6.5-11-net-ethernet-mtk_eth_soc-add-basic-support-for-MT798.patch [deleted file]
target/linux/generic/backport-5.15/750-v6.5-12-net-ethernet-mtk_eth_soc-enable-page_pool-support-fo.patch [deleted file]
target/linux/generic/backport-5.15/750-v6.5-13-net-ethernet-mtk_eth_soc-enable-nft-hw-flowtable_off.patch [deleted file]
target/linux/generic/backport-5.15/750-v6.5-14-net-ethernet-mtk_eth_soc-support-per-flow-accounting.patch [deleted file]
target/linux/generic/backport-5.15/750-v6.5-15-net-ethernet-mtk_eth_soc-fix-NULL-pointer-on-hw-rese.patch [deleted file]
target/linux/generic/backport-5.15/750-v6.5-16-net-ethernet-mtk_eth_soc-fix-register-definitions-fo.patch [deleted file]
target/linux/generic/backport-5.15/750-v6.5-17-net-ethernet-mtk_eth_soc-add-reset-bits-for-MT7988.patch [deleted file]
target/linux/generic/backport-5.15/750-v6.5-18-net-ethernet-mtk_eth_soc-add-support-for-in-SoC-SRAM.patch [deleted file]
target/linux/generic/backport-5.15/750-v6.5-19-net-ethernet-mtk_eth_soc-support-36-bit-DMA-addressi.patch [deleted file]
target/linux/generic/backport-5.15/750-v6.5-20-net-ethernet-mtk_eth_soc-fix-uninitialized-variable.patch [deleted file]
target/linux/generic/backport-5.15/750-v6.5-21-net-ethernet-mtk_eth_soc-fix-pse_port-configuration-.patch [deleted file]
target/linux/generic/backport-5.15/751-01-v6.4-net-ethernet-mtk_eth_soc-add-code-for-offloading-flo.patch [deleted file]
target/linux/generic/backport-5.15/751-02-v6.4-net-ethernet-mediatek-mtk_ppe-prefer-newly-added-l2-.patch [deleted file]
target/linux/generic/backport-5.15/751-03-v6.4-net-ethernet-mtk_eth_soc-improve-keeping-track-of-of.patch [deleted file]
target/linux/generic/backport-5.15/751-04-v6.4-net-ethernet-mediatek-fix-ppe-flow-accounting-for-L2.patch [deleted file]
target/linux/generic/backport-5.15/752-01-v6.6-net-ethernet-mtk_wed-add-some-more-info-in-wed_txinf.patch [deleted file]
target/linux/generic/backport-5.15/752-02-v6.6-net-ethernet-mtk_wed-minor-change-in-wed_-tx-rx-info.patch [deleted file]
target/linux/generic/backport-5.15/752-03-v6.6-net-ethernet-mtk_eth_soc-rely-on-mtk_pse_port-defini.patch [deleted file]
target/linux/generic/backport-5.15/752-04-v6.6-net-ethernet-mtk_wed-check-update_wo_rx_stats-in-mtk.patch [deleted file]
target/linux/generic/backport-5.15/752-05-v6.7-net-ethernet-mtk_wed-do-not-assume-offload-callbacks.patch [deleted file]
target/linux/generic/backport-5.15/752-06-v6.7-net-ethernet-mtk_wed-introduce-versioning-utility-ro.patch [deleted file]
target/linux/generic/backport-5.15/752-07-v6.7-net-ethernet-mtk_wed-do-not-configure-rx-offload-if-.patch [deleted file]
target/linux/generic/backport-5.15/752-08-v6.7-net-ethernet-mtk_wed-rename-mtk_rxbm_desc-in-mtk_wed.patch [deleted file]
target/linux/generic/backport-5.15/752-09-v6.7-net-ethernet-mtk_wed-introduce-mtk_wed_buf-structure.patch [deleted file]
target/linux/generic/backport-5.15/752-10-v6.7-net-ethernet-mtk_wed-move-mem_region-array-out-of-mt.patch [deleted file]
target/linux/generic/backport-5.15/752-11-v6.7-net-ethernet-mtk_wed-make-memory-region-optional.patch [deleted file]
target/linux/generic/backport-5.15/752-12-v6.7-net-ethernet-mtk_wed-fix-EXT_INT_STATUS_RX_FBUF-defi.patch [deleted file]
target/linux/generic/backport-5.15/752-13-v6.7-net-ethernet-mtk_wed-add-mtk_wed_soc_data-structure.patch [deleted file]
target/linux/generic/backport-5.15/752-14-v6.7-net-ethernet-mtk_wed-introduce-WED-support-for-MT798.patch [deleted file]
target/linux/generic/backport-5.15/752-15-v6.7-net-ethernet-mtk_wed-refactor-mtk_wed_check_wfdma_rx.patch [deleted file]
target/linux/generic/backport-5.15/752-16-v6.7-net-ethernet-mtk_wed-introduce-partial-AMSDU-offload.patch [deleted file]
target/linux/generic/backport-5.15/752-17-v6.7-net-ethernet-mtk_wed-introduce-hw_rro-support-for-MT.patch [deleted file]
target/linux/generic/backport-5.15/752-18-v6.7-net-ethernet-mtk_wed-debugfs-move-wed_v2-specific-re.patch [deleted file]
target/linux/generic/backport-5.15/752-19-v6.7-net-ethernet-mtk_wed-debugfs-add-WED-3.0-debugfs-ent.patch [deleted file]
target/linux/generic/backport-5.15/752-20-v6.7-net-ethernet-mtk_wed-add-wed-3.0-reset-support.patch [deleted file]
target/linux/generic/backport-5.15/764-01-v5.16-net-dsa-qca8k-fix-internal-delay-applied-to-the-wrong-PAD.patch [deleted file]
target/linux/generic/backport-5.15/764-02-v5.16-net-dsa-qca8k-fix-MTU-calculation.patch [deleted file]
target/linux/generic/backport-5.15/764-03-v5.17-net-next-net-dsa-qca8k-remove-redundant-check-in-parse_port_config.patch [deleted file]
target/linux/generic/backport-5.15/764-04-v5.17-net-next-net-dsa-qca8k-convert-to-GENMASK_FIELD_PREP_FIELD_GET.patch [deleted file]
target/linux/generic/backport-5.15/764-05-v5.17-net-next-net-dsa-qca8k-remove-extra-mutex_init-in-qca8k_setup.patch [deleted file]
target/linux/generic/backport-5.15/764-06-v5.17-net-next-net-dsa-qca8k-move-regmap-init-in-probe-and-set-it.patch [deleted file]
target/linux/generic/backport-5.15/764-07-v5.17-net-next-net-dsa-qca8k-initial-conversion-to-regmap-heper.patch [deleted file]
target/linux/generic/backport-5.15/764-08-v5.17-net-next-net-dsa-qca8k-add-additional-MIB-counter-and-.patch [deleted file]
target/linux/generic/backport-5.15/764-09-v5.17-net-next-net-dsa-qca8k-add-support-for-port-fast-aging.patch [deleted file]
target/linux/generic/backport-5.15/764-10-v5.17-net-next-net-dsa-qca8k-add-set_ageing_time-support.patch [deleted file]
target/linux/generic/backport-5.15/764-11-v5.17-net-next-net-dsa-qca8k-add-support-for-mdb_add-del.patch [deleted file]
target/linux/generic/backport-5.15/764-12-v5.17-net-next-net-dsa-qca8k-add-support-for-mirror-mode.patch [deleted file]
target/linux/generic/backport-5.15/764-13-v5.17-net-next-net-dsa-qca8k-add-LAG-support.patch [deleted file]
target/linux/generic/backport-5.15/764-14-v5.17-net-next-net-dsa-qca8k-fix-warning-in-LAG-feature.patch [deleted file]
target/linux/generic/backport-5.15/765-v5.17-01-net-next-net-dsa-reorder-PHY-initialization-with-MTU-setup-in.patch [deleted file]
target/linux/generic/backport-5.15/765-v5.17-02-net-next-net-dsa-merge-rtnl_lock-sections-in-dsa_slave_create.patch [deleted file]
target/linux/generic/backport-5.15/765-v5.17-03-net-next-net-dsa-stop-updating-master-MTU-from-master.c.patch [deleted file]
target/linux/generic/backport-5.15/765-v5.17-04-net-next-net-dsa-hold-rtnl_mutex-when-calling-dsa_master_-set.patch [deleted file]
target/linux/generic/backport-5.15/765-v5.17-05-net-next-net-dsa-first-set-up-shared-ports-then-non-shared-po.patch [deleted file]
target/linux/generic/backport-5.15/765-v5.17-06-net-next-net-dsa-setup-master-before-ports.patch [deleted file]
target/linux/generic/backport-5.15/766-v5.18-01-net-dsa-provide-switch-operations-for-tracking-the-m.patch [deleted file]
target/linux/generic/backport-5.15/766-v5.18-02-net-dsa-replay-master-state-events-in-dsa_tree_-setu.patch [deleted file]
target/linux/generic/backport-5.15/766-v5.18-03-net-dsa-tag_qca-convert-to-FIELD-macro.patch [deleted file]
target/linux/generic/backport-5.15/766-v5.18-04-net-dsa-tag_qca-move-define-to-include-linux-dsa.patch [deleted file]
target/linux/generic/backport-5.15/766-v5.18-05-net-dsa-tag_qca-enable-promisc_on_master-flag.patch [deleted file]
target/linux/generic/backport-5.15/766-v5.18-06-net-dsa-tag_qca-add-define-for-handling-mgmt-Etherne.patch [deleted file]
target/linux/generic/backport-5.15/766-v5.18-07-net-dsa-tag_qca-add-define-for-handling-MIB-packet.patch [deleted file]
target/linux/generic/backport-5.15/766-v5.18-08-net-dsa-tag_qca-add-support-for-handling-mgmt-and-MI.patch [deleted file]
target/linux/generic/backport-5.15/766-v5.18-09-net-dsa-qca8k-add-tracking-state-of-master-port.patch [deleted file]
target/linux/generic/backport-5.15/766-v5.18-10-net-dsa-qca8k-add-support-for-mgmt-read-write-in-Eth.patch [deleted file]
target/linux/generic/backport-5.15/766-v5.18-11-net-dsa-qca8k-add-support-for-mib-autocast-in-Ethern.patch [deleted file]
target/linux/generic/backport-5.15/766-v5.18-12-net-dsa-qca8k-add-support-for-phy-read-write-with-mg.patch [deleted file]
target/linux/generic/backport-5.15/766-v5.18-13-net-dsa-qca8k-move-page-cache-to-driver-priv.patch [deleted file]
target/linux/generic/backport-5.15/766-v5.18-14-net-dsa-qca8k-cache-lo-and-hi-for-mdio-write.patch [deleted file]
target/linux/generic/backport-5.15/766-v5.18-15-net-dsa-qca8k-add-support-for-larger-read-write-size.patch [deleted file]
target/linux/generic/backport-5.15/766-v5.18-16-net-dsa-qca8k-introduce-qca8k_bulk_read-write-functi.patch [deleted file]
target/linux/generic/backport-5.15/767-v5.18-net-dsa-qca8k-check-correct-variable-in-qca8k_phy_et.patch [deleted file]
target/linux/generic/backport-5.15/768-v5.18-net-dsa-qca8k-fix-noderef.cocci-warnings.patch [deleted file]
target/linux/generic/backport-5.15/769-v5.19-01-net-dsa-qca8k-drop-MTU-tracking-from-qca8k_priv.patch [deleted file]
target/linux/generic/backport-5.15/769-v5.19-02-net-dsa-qca8k-drop-port_sts-from-qca8k_priv.patch [deleted file]
target/linux/generic/backport-5.15/769-v5.19-03-net-dsa-qca8k-rework-and-simplify-mdiobus-logic.patch [deleted file]
target/linux/generic/backport-5.15/769-v5.19-04-net-dsa-qca8k-drop-dsa_switch_ops-from-qca8k_priv.patch [deleted file]
target/linux/generic/backport-5.15/769-v5.19-05-net-dsa-qca8k-correctly-handle-mdio-read-error.patch [deleted file]
target/linux/generic/backport-5.15/769-v5.19-06-net-dsa-qca8k-unify-bus-id-naming-with-legacy-and-OF.patch [deleted file]
target/linux/generic/backport-5.15/770-v6.0-net-dsa-qca8k-move-driver-to-qca-dir.patch [deleted file]
target/linux/generic/backport-5.15/771-v6.0-01-net-dsa-qca8k-cache-match-data-to-speed-up-access.patch [deleted file]
target/linux/generic/backport-5.15/771-v6.0-02-net-dsa-qca8k-make-mib-autocast-feature-optional.patch [deleted file]
target/linux/generic/backport-5.15/771-v6.0-03-net-dsa-qca8k-move-mib-struct-to-common-code.patch [deleted file]
target/linux/generic/backport-5.15/771-v6.0-04-net-dsa-qca8k-move-qca8k-read-write-rmw-and-reg-tabl.patch [deleted file]
target/linux/generic/backport-5.15/771-v6.0-05-net-dsa-qca8k-move-qca8k-bulk-read-write-helper-to-c.patch [deleted file]
target/linux/generic/backport-5.15/771-v6.0-06-net-dsa-qca8k-move-mib-init-function-to-common-code.patch [deleted file]
target/linux/generic/backport-5.15/771-v6.0-07-net-dsa-qca8k-move-port-set-status-eee-ethtool-stats.patch [deleted file]
target/linux/generic/backport-5.15/771-v6.0-08-net-dsa-qca8k-move-bridge-functions-to-common-code.patch [deleted file]
target/linux/generic/backport-5.15/771-v6.0-09-net-dsa-qca8k-move-set-age-MTU-port-enable-disable-f.patch [deleted file]
target/linux/generic/backport-5.15/771-v6.0-10-net-dsa-qca8k-move-port-FDB-MDB-function-to-common-c.patch [deleted file]
target/linux/generic/backport-5.15/771-v6.0-11-net-dsa-qca8k-move-port-mirror-functions-to-common-c.patch [deleted file]
target/linux/generic/backport-5.15/771-v6.0-12-net-dsa-qca8k-move-port-VLAN-functions-to-common-cod.patch [deleted file]
target/linux/generic/backport-5.15/771-v6.0-13-net-dsa-qca8k-move-port-LAG-functions-to-common-code.patch [deleted file]
target/linux/generic/backport-5.15/771-v6.0-14-net-dsa-qca8k-move-read_switch_id-function-to-common.patch [deleted file]
target/linux/generic/backport-5.15/772-v6.0-net-dsa-qca8k-fix-NULL-pointer-dereference-for-of_de.patch [deleted file]
target/linux/generic/backport-5.15/773-v5.18-1-net-dsa-Move-VLAN-filtering-syncing-out-of-dsa_switc.patch [deleted file]
target/linux/generic/backport-5.15/773-v5.18-2-net-dsa-Avoid-cross-chip-syncing-of-VLAN-filtering.patch [deleted file]
target/linux/generic/backport-5.15/774-v5.16-01-net-dsa-rtl8366rb-Support-bridge-offloading.patch [deleted file]
target/linux/generic/backport-5.15/774-v5.16-02-net-dsa-rtl8366-Drop-custom-VLAN-set-up.patch [deleted file]
target/linux/generic/backport-5.15/774-v5.16-03-net-dsa-rtl8366rb-Rewrite-weird-VLAN-filering-enable.patch [deleted file]
target/linux/generic/backport-5.15/774-v5.16-06-net-dsa-rtl8366-Drop-and-depromote-pointless-prints.patch [deleted file]
target/linux/generic/backport-5.15/774-v5.16-07-net-dsa-rtl8366rb-Use-core-filtering-tracking.patch [deleted file]
target/linux/generic/backport-5.15/774-v5.16-08-net-dsa-rtl8366rb-Support-disabling-learning.patch [deleted file]
target/linux/generic/backport-5.15/774-v5.16-09-net-dsa-rtl8366rb-Support-fast-aging.patch [deleted file]
target/linux/generic/backport-5.15/774-v5.16-10-net-dsa-rtl8366rb-Support-setting-STP-state.patch [deleted file]
target/linux/generic/backport-5.15/775-v6.0-01-net-ethernet-stmicro-stmmac-move-queue-reset-to-dedi.patch [deleted file]
target/linux/generic/backport-5.15/775-v6.0-02-net-ethernet-stmicro-stmmac-first-disable-all-queues.patch [deleted file]
target/linux/generic/backport-5.15/775-v6.0-03-net-ethernet-stmicro-stmmac-move-dma-conf-to-dedicat.patch [deleted file]
target/linux/generic/backport-5.15/775-v6.0-04-net-ethernet-stmicro-stmmac-generate-stmmac-dma-conf.patch [deleted file]
target/linux/generic/backport-5.15/775-v6.0-05-net-ethernet-stmicro-stmmac-permit-MTU-change-with-i.patch [deleted file]
target/linux/generic/backport-5.15/776-v6.1-01-net-dsa-qca8k-fix-inband-mgmt-for-big-endian-systems.patch [deleted file]
target/linux/generic/backport-5.15/776-v6.1-02-net-dsa-qca8k-fix-ethtool-autocast-mib-for-big-endia.patch [deleted file]
target/linux/generic/backport-5.15/777-v6.2-01-net-dsa-qca8k-fix-wrong-length-value-for-mgmt-eth-pa.patch [deleted file]
target/linux/generic/backport-5.15/777-v6.2-02-net-dsa-tag_qca-fix-wrong-MGMT_DATA2-size.patch [deleted file]
target/linux/generic/backport-5.15/777-v6.2-03-Revert-net-dsa-qca8k-cache-lo-and-hi-for-mdio-write.patch [deleted file]
target/linux/generic/backport-5.15/777-v6.2-04-net-dsa-qca8k-introduce-single-mii-read-write-lo-hi.patch [deleted file]
target/linux/generic/backport-5.15/777-v6.2-05-net-dsa-qca8k-improve-mdio-master-read-write-by-usin.patch [deleted file]
target/linux/generic/backport-5.15/778-v5.18-01-net-phy-at803x-add-fiber-support.patch [deleted file]
target/linux/generic/backport-5.15/778-v5.18-02-net-phy-at803x-support-downstream-SFP-cage.patch [deleted file]
target/linux/generic/backport-5.15/778-v5.18-03-net-phy-at803x-fix-NULL-pointer-dereference-on-AR9331-PHY.patch [deleted file]
target/linux/generic/backport-5.15/778-v5.18-04-net-phy-at803x-fix-error-return-code-in-at803x_probe.patch [deleted file]
target/linux/generic/backport-5.15/780-v5.16-bus-mhi-pci_generic-Introduce-Sierra-EM919X-support.patch [deleted file]
target/linux/generic/backport-5.15/781-v6.1-bus-mhi-host-always-print-detected-modem-name.patch [deleted file]
target/linux/generic/backport-5.15/782-v6.1-net-dsa-mt7530-add-support-for-in-band-link-status.patch [deleted file]
target/linux/generic/backport-5.15/783-v6.1-net-sfp-re-implement-soft-state-polling-setup.patch [deleted file]
target/linux/generic/backport-5.15/784-v6.1-net-sfp-move-quirk-handling-into-sfp.c.patch [deleted file]
target/linux/generic/backport-5.15/785-v6.1-net-sfp-move-Alcatel-Lucent-3FE46541AA-fixup.patch [deleted file]
target/linux/generic/backport-5.15/786-v6.1-net-sfp-move-Huawei-MA5671A-fixup.patch [deleted file]
target/linux/generic/backport-5.15/787-v6.1-net-sfp-add-support-for-HALNy-GPON-SFP.patch [deleted file]
target/linux/generic/backport-5.15/788-v6.3-net-dsa-mt7530-use-external-PCS-driver.patch [deleted file]
target/linux/generic/backport-5.15/789-v6.3-net-sfp-add-quirk-enabling-2500Base-x-for-HG-MXPD-48.patch [deleted file]
target/linux/generic/backport-5.15/790-v6.0-net-mii-add-mii_bmcr_encode_fixed.patch [deleted file]
target/linux/generic/backport-5.15/790-v6.4-0001-net-dsa-mt7530-make-some-noise-if-register-read-fail.patch [deleted file]
target/linux/generic/backport-5.15/790-v6.4-0002-net-dsa-mt7530-refactor-SGMII-PCS-creation.patch [deleted file]
target/linux/generic/backport-5.15/790-v6.4-0003-net-dsa-mt7530-use-unlocked-regmap-accessors.patch [deleted file]
target/linux/generic/backport-5.15/790-v6.4-0004-net-dsa-mt7530-use-regmap-to-access-switch-register-.patch [deleted file]
target/linux/generic/backport-5.15/790-v6.4-0005-net-dsa-mt7530-move-SGMII-PCS-creation-to-mt7530_pro.patch [deleted file]
target/linux/generic/backport-5.15/790-v6.4-0006-net-dsa-mt7530-introduce-mutex-helpers.patch [deleted file]
target/linux/generic/backport-5.15/790-v6.4-0007-net-dsa-mt7530-move-p5_intf_modes-function-to-mt7530.patch [deleted file]
target/linux/generic/backport-5.15/790-v6.4-0008-net-dsa-mt7530-introduce-mt7530_probe_common-helper-.patch [deleted file]
target/linux/generic/backport-5.15/790-v6.4-0009-net-dsa-mt7530-introduce-mt7530_remove_common-helper.patch [deleted file]
target/linux/generic/backport-5.15/790-v6.4-0011-net-dsa-mt7530-introduce-separate-MDIO-driver.patch [deleted file]
target/linux/generic/backport-5.15/790-v6.4-0012-net-dsa-mt7530-skip-locking-if-MDIO-bus-isn-t-presen.patch [deleted file]
target/linux/generic/backport-5.15/790-v6.4-0013-net-dsa-mt7530-introduce-driver-for-MT7988-built-in-.patch [deleted file]
target/linux/generic/backport-5.15/790-v6.4-0014-net-dsa-mt7530-fix-support-for-MT7531BE.patch [deleted file]
target/linux/generic/backport-5.15/791-v6.2-01-net-phy-Add-driver-for-Motorcomm-yt8521-gigabit-ethernet.patch [deleted file]
target/linux/generic/backport-5.15/791-v6.2-02-net-phy-fix-yt8521-duplicated-argument-to-or.patch [deleted file]
target/linux/generic/backport-5.15/791-v6.2-03-net-phy-add-Motorcomm-YT8531S-phy-id.patch [deleted file]
target/linux/generic/backport-5.15/791-v6.3-04-net-phy-fix-the-spelling-problem-of-Sentinel.patch [deleted file]
target/linux/generic/backport-5.15/791-v6.3-05-net-phy-motorcomm-change-the-phy-id-of-yt8521-and-yt8531s.patch [deleted file]
target/linux/generic/backport-5.15/791-v6.3-06-net-phy-Add-BIT-macro-for-Motorcomm-yt8521-yt8531-gigabit.patch [deleted file]
target/linux/generic/backport-5.15/791-v6.3-07-net-phy-Add-dts-support-for-Motorcomm-yt8521-gigabit.patch [deleted file]
target/linux/generic/backport-5.15/791-v6.3-08-net-phy-Add-dts-support-for-Motorcomm-yt8531s-gigabit.patch [deleted file]
target/linux/generic/backport-5.15/791-v6.3-09-net-phy-Add-driver-for-Motorcomm-yt8531-gigabit-ethernet.patch [deleted file]
target/linux/generic/backport-5.15/791-v6.3-10-net-phy-motorcomm-uninitialized-variables-in.patch [deleted file]
target/linux/generic/backport-5.15/791-v6.6-11-net-phy-motorcomm-Add-pad-drive-strength-cfg-support.patch [deleted file]
target/linux/generic/backport-5.15/792-01-v6.0-net-phylink-disable-PCS-polling-over-major-configura.patch [deleted file]
target/linux/generic/backport-5.15/792-02-v6.0-net-phylink-fix-NULL-pl-pcs-dereference-during-phyli.patch [deleted file]
target/linux/generic/backport-5.15/792-03-v6.6-net-phylink-add-pcs_enable-pcs_disable-methods.patch [deleted file]
target/linux/generic/backport-5.15/793-v6.6-net-pcs-lynxi-implement-pcs_disable-op.patch [deleted file]
target/linux/generic/backport-5.15/794-v6.2-net-core-Allow-live-renaming-when-an-interface-is-up.patch [deleted file]
target/linux/generic/backport-5.15/795-v6.3-02-cdc_ether-no-need-to-blacklist-any-r8152-devices.patch [deleted file]
target/linux/generic/backport-5.15/795-v6.3-05-r8152-reduce-the-control-transfer-of-rtl8152_get_ver.patch [deleted file]
target/linux/generic/backport-5.15/795-v6.3-06-r8152-Add-__GFP_NOWARN-to-big-allocations.patch [deleted file]
target/linux/generic/backport-5.15/795-v6.6-08-r8152-adjust-generic_ocp_write-function.patch [deleted file]
target/linux/generic/backport-5.15/795-v6.6-09-r8152-set-bp-in-bulk.patch [deleted file]
target/linux/generic/backport-5.15/795-v6.6-13-r8152-Block-future-register-access-if-register-acces.patch [deleted file]
target/linux/generic/backport-5.15/795-v6.6-14-r8152-break-the-loop-when-the-budget-is-exhausted.patch [deleted file]
target/linux/generic/backport-5.15/795-v6.6-15-net-usb-cdc_ether-add-u-blox-0x1313-composition.patch [deleted file]
target/linux/generic/backport-5.15/796-v6.5-01-usbnet-ipheth-fix-risk-of-NULL-pointer-deallocation.patch [deleted file]
target/linux/generic/backport-5.15/796-v6.5-02-usbnet-ipheth-transmit-URBs-without-trailing-padding.patch [deleted file]
target/linux/generic/backport-5.15/796-v6.5-03-usbnet-ipheth-add-CDC-NCM-support.patch [deleted file]
target/linux/generic/backport-5.15/796-v6.5-04-usbnet-ipheth-update-Kconfig-description.patch [deleted file]
target/linux/generic/backport-5.15/797-v5.17-net-usb-ax88179_178a-add-TSO-feature.patch [deleted file]
target/linux/generic/backport-5.15/798-net-next-net-sfp-add-quirk-for-Fiberstone-GPON-ONU-34-20BI.patch [deleted file]
target/linux/generic/backport-5.15/800-v6.0-0001-dt-bindings-leds-add-Broadcom-s-BCM63138-controller.patch [deleted file]
target/linux/generic/backport-5.15/800-v6.0-0002-leds-bcm63138-add-support-for-BCM63138-controller.patch [deleted file]
target/linux/generic/backport-5.15/801-v6.0-0001-dt-bindings-leds-leds-bcm63138-unify-full-stops-in-d.patch [deleted file]
target/linux/generic/backport-5.15/801-v6.0-0002-leds-add-help-info-about-BCM63138-module-name.patch [deleted file]
target/linux/generic/backport-5.15/801-v6.0-0003-leds-leds-bcm63138-get-rid-of-LED_OFF.patch [deleted file]
target/linux/generic/backport-5.15/802-v5.16-0001-nvmem-core-rework-nvmem-cell-instance-creation.patch [deleted file]
target/linux/generic/backport-5.15/802-v5.16-0002-nvmem-core-add-nvmem-cell-post-processing-callback.patch [deleted file]
target/linux/generic/backport-5.15/802-v5.16-0003-nvmem-imx-ocotp-add-support-for-post-processing.patch [deleted file]
target/linux/generic/backport-5.15/803-v5.17-0002-nvmem-mtk-efuse-support-minimum-one-byte-access-stri.patch [deleted file]
target/linux/generic/backport-5.15/804-v5.18-0001-nvmem-core-Remove-unused-devm_nvmem_unregister.patch [deleted file]
target/linux/generic/backport-5.15/804-v5.18-0002-nvmem-core-Use-devm_add_action_or_reset.patch [deleted file]
target/linux/generic/backport-5.15/804-v5.18-0003-nvmem-core-Check-input-parameter-for-NULL-in-nvmem_u.patch [deleted file]
target/linux/generic/backport-5.15/804-v5.18-0004-nvmem-qfprom-fix-kerneldoc-warning.patch [deleted file]
target/linux/generic/backport-5.15/804-v5.18-0005-nvmem-sunxi_sid-Add-support-for-D1-variant.patch [deleted file]
target/linux/generic/backport-5.15/804-v5.18-0006-nvmem-meson-mx-efuse-replace-unnecessary-devm_kstrdu.patch [deleted file]
target/linux/generic/backport-5.15/804-v5.18-0007-nvmem-add-driver-for-Layerscape-SFP-Security-Fuse-Pr.patch [deleted file]
target/linux/generic/backport-5.15/804-v5.18-0008-nvmem-qfprom-Increase-fuse-blow-timeout-to-prevent-w.patch [deleted file]
target/linux/generic/backport-5.15/804-v5.18-0009-nvmem-Add-driver-for-OCOTP-in-Sunplus-SP7021.patch [deleted file]
target/linux/generic/backport-5.15/804-v5.18-0010-nvmem-brcm_nvram-parse-NVRAM-content-into-NVMEM-cell.patch [deleted file]
target/linux/generic/backport-5.15/805-v5.19-0001-nvmem-bcm-ocotp-mark-ACPI-device-ID-table-as-maybe-u.patch [deleted file]
target/linux/generic/backport-5.15/805-v5.19-0002-nvmem-sunplus-ocotp-staticize-sp_otp_v0.patch [deleted file]
target/linux/generic/backport-5.15/805-v5.19-0003-nvmem-sunplus-ocotp-drop-useless-probe-confirmation.patch [deleted file]
target/linux/generic/backport-5.15/805-v5.19-0004-nvmem-core-support-passing-DT-node-in-cell-info.patch [deleted file]
target/linux/generic/backport-5.15/805-v5.19-0005-nvmem-brcm_nvram-find-Device-Tree-nodes-for-NVMEM-ce.patch [deleted file]
target/linux/generic/backport-5.15/805-v5.19-0006-nvmem-Add-Apple-eFuse-driver.patch [deleted file]
target/linux/generic/backport-5.15/805-v5.19-0007-nvmem-qfprom-using-pm_runtime_resume_and_get-instead.patch [deleted file]
target/linux/generic/backport-5.15/805-v5.19-0008-nvmem-sfp-Use-regmap.patch [deleted file]
target/linux/generic/backport-5.15/805-v5.19-0009-nvmem-sfp-Add-support-for-TA-2.1-devices.patch [deleted file]
target/linux/generic/backport-5.15/806-v6.0-0001-nvmem-microchip-otpc-add-support.patch [deleted file]
target/linux/generic/backport-5.15/806-v6.0-0002-nvmem-mtk-efuse-Simplify-with-devm_platform_get_and_.patch [deleted file]
target/linux/generic/backport-5.15/807-v6.1-0002-nvmem-add-driver-handling-U-Boot-environment-variabl.patch [deleted file]
target/linux/generic/backport-5.15/807-v6.1-0004-nvmem-brcm_nvram-Use-kzalloc-for-allocating-only-one.patch [deleted file]
target/linux/generic/backport-5.15/807-v6.1-0005-nvmem-prefix-all-symbols-with-NVMEM_.patch [deleted file]
target/linux/generic/backport-5.15/807-v6.1-0006-nvmem-sort-config-symbols-alphabetically.patch [deleted file]
target/linux/generic/backport-5.15/807-v6.1-0007-nvmem-u-boot-env-find-Device-Tree-nodes-for-NVMEM-ce.patch [deleted file]
target/linux/generic/backport-5.15/807-v6.1-0008-nvmem-lan9662-otp-add-support.patch [deleted file]
target/linux/generic/backport-5.15/807-v6.1-0009-nvmem-u-boot-env-fix-crc32-casting-type.patch [deleted file]
target/linux/generic/backport-5.15/807-v6.1-0010-nvmem-lan9662-otp-Fix-compatible-string.patch [deleted file]
target/linux/generic/backport-5.15/807-v6.1-0011-nvmem-u-boot-env-fix-crc32_data_offset-on-redundant-.patch [deleted file]
target/linux/generic/backport-5.15/807-v6.1-0013-nvmem-lan9662-otp-Change-return-type-of-lan9662_otp_.patch [deleted file]
target/linux/generic/backport-5.15/808-v6.2-0001-nvmem-stm32-move-STM32MP15_BSEC_NUM_LOWER-in-config.patch [deleted file]
target/linux/generic/backport-5.15/808-v6.2-0002-nvmem-stm32-add-warning-when-upper-OTPs-are-updated.patch [deleted file]
target/linux/generic/backport-5.15/808-v6.2-0003-nvmem-stm32-add-nvmem-type-attribute.patch [deleted file]
target/linux/generic/backport-5.15/808-v6.2-0004-nvmem-stm32-fix-spelling-typo-in-comment.patch [deleted file]
target/linux/generic/backport-5.15/808-v6.2-0005-nvmem-Kconfig-Fix-spelling-mistake-controlls-control.patch [deleted file]
target/linux/generic/backport-5.15/808-v6.2-0006-nvmem-u-boot-env-add-Broadcom-format-support.patch [deleted file]
target/linux/generic/backport-5.15/808-v6.2-0007-nvmem-brcm_nvram-Add-check-for-kzalloc.patch [deleted file]
target/linux/generic/backport-5.15/808-v6.2-0008-nvmem-sunxi_sid-Always-use-32-bit-MMIO-reads.patch [deleted file]
target/linux/generic/backport-5.15/808-v6.2-0013-nvmem-core-fix-device-node-refcounting.patch [deleted file]
target/linux/generic/backport-5.15/809-v6.3-0001-nvmem-core-remove-spurious-white-space.patch [deleted file]
target/linux/generic/backport-5.15/809-v6.3-0002-nvmem-core-add-an-index-parameter-to-the-cell.patch [deleted file]
target/linux/generic/backport-5.15/809-v6.3-0003-nvmem-core-move-struct-nvmem_cell_info-to-nvmem-prov.patch [deleted file]
target/linux/generic/backport-5.15/809-v6.3-0004-nvmem-core-drop-the-removal-of-the-cells-in-nvmem_ad.patch [deleted file]
target/linux/generic/backport-5.15/809-v6.3-0005-nvmem-core-add-nvmem_add_one_cell.patch [deleted file]
target/linux/generic/backport-5.15/809-v6.3-0006-nvmem-core-use-nvmem_add_one_cell-in-nvmem_add_cells.patch [deleted file]
target/linux/generic/backport-5.15/809-v6.3-0007-nvmem-stm32-add-OP-TEE-support-for-STM32MP13x.patch [deleted file]
target/linux/generic/backport-5.15/809-v6.3-0008-nvmem-stm32-detect-bsec-pta-presence-for-STM32MP15x.patch [deleted file]
target/linux/generic/backport-5.15/809-v6.3-0009-nvmem-rave-sp-eeprm-fix-kernel-doc-bad-line-warning.patch [deleted file]
target/linux/generic/backport-5.15/809-v6.3-0010-nvmem-qcom-spmi-sdam-register-at-device-init-time.patch [deleted file]
target/linux/generic/backport-5.15/809-v6.3-0011-nvmem-stm32-fix-OPTEE-dependency.patch [deleted file]
target/linux/generic/backport-5.15/810-v5.17-net-qmi_wwan-add-ZTE-MF286D-modem-19d2-1485.patch [deleted file]
target/linux/generic/backport-5.15/811-v6.4-0001-nvmem-xilinx-zynqmp-make-modular.patch [deleted file]
target/linux/generic/backport-5.15/811-v6.4-0002-nvmem-core-introduce-NVMEM-layouts.patch [deleted file]
target/linux/generic/backport-5.15/811-v6.4-0003-nvmem-core-handle-the-absence-of-expected-layouts.patch [deleted file]
target/linux/generic/backport-5.15/811-v6.4-0004-nvmem-core-request-layout-modules-loading.patch [deleted file]
target/linux/generic/backport-5.15/811-v6.4-0005-nvmem-core-add-per-cell-post-processing.patch [deleted file]
target/linux/generic/backport-5.15/811-v6.4-0006-nvmem-core-allow-to-modify-a-cell-before-adding-it.patch [deleted file]
target/linux/generic/backport-5.15/811-v6.4-0007-nvmem-imx-ocotp-replace-global-post-processing-with-.patch [deleted file]
target/linux/generic/backport-5.15/811-v6.4-0008-nvmem-cell-drop-global-cell_post_process.patch [deleted file]
target/linux/generic/backport-5.15/811-v6.4-0009-nvmem-core-provide-own-priv-pointer-in-post-process-.patch [deleted file]
target/linux/generic/backport-5.15/811-v6.4-0010-nvmem-layouts-sl28vpd-Add-new-layout-driver.patch [deleted file]
target/linux/generic/backport-5.15/811-v6.4-0011-nvmem-layouts-onie-tlv-Add-new-layout-driver.patch [deleted file]
target/linux/generic/backport-5.15/811-v6.4-0012-nvmem-stm32-romem-mark-OF-related-data-as-maybe-unus.patch [deleted file]
target/linux/generic/backport-5.15/811-v6.4-0013-nvmem-mtk-efuse-Support-postprocessing-for-GPU-speed.patch [deleted file]
target/linux/generic/backport-5.15/811-v6.4-0014-nvmem-bcm-ocotp-Use-devm_platform_ioremap_resource.patch [deleted file]
target/linux/generic/backport-5.15/811-v6.4-0015-nvmem-nintendo-otp-Use-devm_platform_ioremap_resourc.patch [deleted file]
target/linux/generic/backport-5.15/811-v6.4-0016-nvmem-vf610-ocotp-Use-devm_platform_get_and_ioremap_.patch [deleted file]
target/linux/generic/backport-5.15/811-v6.4-0017-nvmem-core-support-specifying-both-cell-raw-data-pos.patch [deleted file]
target/linux/generic/backport-5.15/811-v6.4-0018-nvmem-u-boot-env-post-process-ethaddr-env-variable.patch [deleted file]
target/linux/generic/backport-5.15/811-v6.4-0019-nvmem-Add-macro-to-register-nvmem-layout-drivers.patch [deleted file]
target/linux/generic/backport-5.15/811-v6.4-0020-nvmem-layouts-sl28vpd-Use-module_nvmem_layout_driver.patch [deleted file]
target/linux/generic/backport-5.15/811-v6.4-0021-nvmem-layouts-onie-tlv-Use-module_nvmem_layout_drive.patch [deleted file]
target/linux/generic/backport-5.15/811-v6.4-0022-nvmem-layouts-onie-tlv-Drop-wrong-module-alias.patch [deleted file]
target/linux/generic/backport-5.15/811-v6.4-0023-nvmem-layouts-sl28vpd-set-varaiable-sl28vpd_layout-s.patch [deleted file]
target/linux/generic/backport-5.15/812-v6.2-firmware-nvram-bcm47xx-support-init-from-IO-memory.patch [deleted file]
target/linux/generic/backport-5.15/813-v6.5-0001-nvmem-imx-ocotp-set-varaiable-imx_ocotp_layout-stora.patch [deleted file]
target/linux/generic/backport-5.15/813-v6.5-0002-nvmem-imx-ocotp-Reverse-MAC-addresses-on-all-i.MX-de.patch [deleted file]
target/linux/generic/backport-5.15/813-v6.5-0003-nvmem-brcm_nvram-add-.read_post_process-for-MACs.patch [deleted file]
target/linux/generic/backport-5.15/813-v6.5-0004-nvmem-rockchip-otp-Add-clks-and-reg_read-to-rockchip.patch [deleted file]
target/linux/generic/backport-5.15/813-v6.5-0005-nvmem-rockchip-otp-Generalize-rockchip_otp_wait_stat.patch [deleted file]
target/linux/generic/backport-5.15/813-v6.5-0006-nvmem-rockchip-otp-Use-devm_reset_control_array_get_.patch [deleted file]
target/linux/generic/backport-5.15/813-v6.5-0007-nvmem-rockchip-otp-Improve-probe-error-handling.patch [deleted file]
target/linux/generic/backport-5.15/813-v6.5-0008-nvmem-rockchip-otp-Add-support-for-RK3588.patch [deleted file]
target/linux/generic/backport-5.15/813-v6.5-0009-nvmem-zynqmp-Switch-xilinx.com-emails-to-amd.com.patch [deleted file]
target/linux/generic/backport-5.15/813-v6.5-0010-nvmem-imx-support-i.MX93-OCOTP.patch [deleted file]
target/linux/generic/backport-5.15/813-v6.5-0011-nvmem-core-add-support-for-fixed-cells-layout.patch [deleted file]
target/linux/generic/backport-5.15/814-v6.3-leds-Move-led_init_default_state_get-to-the-global-h.patch [deleted file]
target/linux/generic/backport-5.15/815-v6.4-01-net-dsa-qca8k-move-qca8k_port_to_phy-to-header.patch [deleted file]
target/linux/generic/backport-5.15/815-v6.4-02-net-dsa-qca8k-add-LEDs-basic-support.patch [deleted file]
target/linux/generic/backport-5.15/815-v6.4-03-net-dsa-qca8k-add-LEDs-blink_set-support.patch [deleted file]
target/linux/generic/backport-5.15/815-v6.4-04-leds-Provide-stubs-for-when-CLASS_LED-NEW_LEDS-are-d.patch [deleted file]
target/linux/generic/backport-5.15/815-v6.4-05-net-phy-Add-a-binding-for-PHY-LEDs.patch [deleted file]
target/linux/generic/backport-5.15/815-v6.4-06-net-phy-phy_device-Call-into-the-PHY-driver-to-set-L.patch [deleted file]
target/linux/generic/backport-5.15/815-v6.4-07-net-phy-marvell-Add-software-control-of-the-LEDs.patch [deleted file]
target/linux/generic/backport-5.15/815-v6.4-08-net-phy-phy_device-Call-into-the-PHY-driver-to-set-L.patch [deleted file]
target/linux/generic/backport-5.15/815-v6.4-09-net-phy-marvell-Implement-led_blink_set.patch [deleted file]
target/linux/generic/backport-5.15/816-v6.4-net-phy-marvell-Fix-inconsistent-indenting-in-led_bl.patch [deleted file]
target/linux/generic/backport-5.15/817-v6.5-02-leds-trigger-netdev-Drop-NETDEV_LED_MODE_LINKUP-from.patch [deleted file]
target/linux/generic/backport-5.15/817-v6.5-03-leds-trigger-netdev-Rename-add-namespace-to-netdev-t.patch [deleted file]
target/linux/generic/backport-5.15/817-v6.5-04-leds-trigger-netdev-Convert-device-attr-to-macro.patch [deleted file]
target/linux/generic/backport-5.15/817-v6.5-05-leds-trigger-netdev-Use-mutex-instead-of-spinlocks.patch [deleted file]
target/linux/generic/backport-5.15/818-v6.5-01-leds-add-APIs-for-LEDs-hw-control.patch [deleted file]
target/linux/generic/backport-5.15/818-v6.5-02-leds-add-API-to-get-attached-device-for-LED-hw-contr.patch [deleted file]
target/linux/generic/backport-5.15/818-v6.5-03-Documentation-leds-leds-class-Document-new-Hardware-.patch [deleted file]
target/linux/generic/backport-5.15/818-v6.5-04-leds-trigger-netdev-refactor-code-setting-device-nam.patch [deleted file]
target/linux/generic/backport-5.15/818-v6.5-05-leds-trigger-netdev-introduce-check-for-possible-hw-.patch [deleted file]
target/linux/generic/backport-5.15/818-v6.5-06-leds-trigger-netdev-add-basic-check-for-hw-control-s.patch [deleted file]
target/linux/generic/backport-5.15/818-v6.5-07-leds-trigger-netdev-reject-interval-store-for-hw_con.patch [deleted file]
target/linux/generic/backport-5.15/818-v6.5-08-leds-trigger-netdev-add-support-for-LED-hw-control.patch [deleted file]
target/linux/generic/backport-5.15/818-v6.5-09-leds-trigger-netdev-validate-configured-netdev.patch [deleted file]
target/linux/generic/backport-5.15/818-v6.5-10-leds-trigger-netdev-init-mode-if-hw-control-already-.patch [deleted file]
target/linux/generic/backport-5.15/818-v6.5-11-leds-trigger-netdev-expose-netdev-trigger-modes-in-l.patch [deleted file]
target/linux/generic/backport-5.15/818-v6.5-12-net-dsa-qca8k-implement-hw_control-ops.patch [deleted file]
target/linux/generic/backport-5.15/818-v6.5-13-net-dsa-qca8k-add-op-to-get-ports-netdev.patch [deleted file]
target/linux/generic/backport-5.15/819-v6.6-0001-nvmem-sunxi_sid-Convert-to-devm_platform_ioremap_res.patch [deleted file]
target/linux/generic/backport-5.15/819-v6.6-0002-nvmem-brcm_nvram-Use-devm_platform_get_and_ioremap_r.patch [deleted file]
target/linux/generic/backport-5.15/819-v6.6-0003-nvmem-lpc18xx_otp-Convert-to-devm_platform_ioremap_r.patch [deleted file]
target/linux/generic/backport-5.15/819-v6.6-0004-nvmem-meson-mx-efuse-Convert-to-devm_platform_iorema.patch [deleted file]
target/linux/generic/backport-5.15/819-v6.6-0005-nvmem-rockchip-efuse-Use-devm_platform_get_and_iorem.patch [deleted file]
target/linux/generic/backport-5.15/819-v6.6-0006-nvmem-stm32-romem-Use-devm_platform_get_and_ioremap_.patch [deleted file]
target/linux/generic/backport-5.15/819-v6.6-0007-nvmem-qfprom-do-some-cleanup.patch [deleted file]
target/linux/generic/backport-5.15/819-v6.6-0008-nvmem-uniphier-Use-devm_platform_get_and_ioremap_res.patch [deleted file]
target/linux/generic/backport-5.15/819-v6.6-0009-nvmem-add-new-NXP-QorIQ-eFuse-driver.patch [deleted file]
target/linux/generic/backport-5.15/819-v6.6-0011-nvmem-Kconfig-Fix-typo-drive-driver.patch [deleted file]
target/linux/generic/backport-5.15/819-v6.6-0012-nvmem-sec-qfprom-Add-Qualcomm-secure-QFPROM-support.patch [deleted file]
target/linux/generic/backport-5.15/819-v6.6-0013-nvmem-u-boot-env-Replace-zero-length-array-with-DECL.patch [deleted file]
target/linux/generic/backport-5.15/819-v6.6-0014-nvmem-core-Create-all-cells-before-adding-the-nvmem-.patch [deleted file]
target/linux/generic/backport-5.15/819-v6.6-0015-nvmem-core-Return-NULL-when-no-nvmem-layout-is-found.patch [deleted file]
target/linux/generic/backport-5.15/819-v6.6-0016-nvmem-core-Do-not-open-code-existing-functions.patch [deleted file]
target/linux/generic/backport-5.15/819-v6.6-0017-nvmem-core-Notify-when-a-new-layout-is-registered.patch [deleted file]
target/linux/generic/backport-5.15/820-v6.7-0001-nvmem-qfprom-Mark-core-clk-as-optional.patch [deleted file]
target/linux/generic/backport-5.15/820-v6.7-0002-nvmem-add-explicit-config-option-to-read-old-syntax-.patch [deleted file]
target/linux/generic/backport-5.15/820-v6.7-0003-nvmem-Use-device_get_match_data.patch [deleted file]
target/linux/generic/backport-5.15/820-v6.7-0004-Revert-nvmem-add-new-config-option.patch [deleted file]
target/linux/generic/backport-5.15/820-v6.7-0005-nvmem-Do-not-expect-fixed-layouts-to-grab-a-layout-d.patch [deleted file]
target/linux/generic/backport-5.15/820-v6.7-0006-nvmem-brcm_nvram-store-a-copy-of-NVRAM-content.patch [deleted file]
target/linux/generic/backport-5.15/821-v5.16-Bluetooth-btusb-Support-public-address-configuration.patch [deleted file]
target/linux/generic/backport-5.15/822-v5.17-Bluetooth-btusb-Fix-application-of-sizeof-to-pointer.patch [deleted file]
target/linux/generic/backport-5.15/823-v5.18-Bluetooth-btusb-Add-a-new-PID-VID-13d3-3567-for-MT79.patch [deleted file]
target/linux/generic/backport-5.15/824-v5.19-Bluetooth-btusb-Add-a-new-PID-VID-0489-e0c8-for-MT79.patch [deleted file]
target/linux/generic/backport-5.15/825-v6.1-Bluetooth-btusb-Add-a-new-VID-PID-0e8d-0608-for-MT79.patch [deleted file]
target/linux/generic/backport-5.15/826-v5.17-of-base-make-small-of_parse_phandle-variants-static-.patch [deleted file]
target/linux/generic/backport-5.15/827-v6.3-0001-of-base-add-of_parse_phandle_with_optional_args.patch [deleted file]
target/linux/generic/backport-5.15/827-v6.3-0002-of-property-make-.-cells-optional-for-simple-props.patch [deleted file]
target/linux/generic/backport-5.15/827-v6.3-0003-of-property-add-nvmem-cell-cells-property.patch [deleted file]
target/linux/generic/backport-5.15/827-v6.3-0004-of-device-Ignore-modalias-of-reused-nodes.patch [deleted file]
target/linux/generic/backport-5.15/827-v6.3-0005-of-device-Do-not-ignore-error-code-in-of_device_ueve.patch [deleted file]
target/linux/generic/backport-5.15/828-v6.4-0002-of-Update-of_device_get_modalias.patch [deleted file]
target/linux/generic/backport-5.15/828-v6.4-0003-of-Rename-of_modalias_node.patch [deleted file]
target/linux/generic/backport-5.15/828-v6.4-0004-of-Move-of_modalias-to-module.c.patch [deleted file]
target/linux/generic/backport-5.15/828-v6.4-0005-of-Move-the-request-module-helper-logic-to-module.c.patch [deleted file]
target/linux/generic/backport-5.15/829-v6.3-i915-Move-list_count-to-list.h-as-list_count_nodes-f.patch [deleted file]
target/linux/generic/backport-5.15/830-v6.0-leds-turris-omnia-convert-to-use-dev_groups.patch [deleted file]
target/linux/generic/backport-5.15/830-v6.6-1-leds-turris-omnia-Use-sysfs_emit-instead-of-sprintf.patch [deleted file]
target/linux/generic/backport-5.15/830-v6.7-2-leds-turris-omnia-Make-set_brightness-more-efficient.patch [deleted file]
target/linux/generic/backport-5.15/830-v6.7-3-leds-turris-omnia-Support-HW-controlled-mode-via-pri.patch [deleted file]
target/linux/generic/backport-5.15/830-v6.7-4-leds-turris-omnia-Add-support-for-enabling-disabling.patch [deleted file]
target/linux/generic/backport-5.15/830-v6.7-5-leds-turris-omnia-Fix-brightness-setting-and-trigger.patch [deleted file]
target/linux/generic/backport-5.15/831-v6.1-dt-bindings-leds-Expand-LED_COLOR_ID-definitions.patch [deleted file]
target/linux/generic/backport-5.15/832-v6.8-of-device-Export-of_device_make_bus_id.patch [deleted file]
target/linux/generic/backport-5.15/833-v6.8-leds-core-Add-more-colors-from-DT-bindings-to-led_co.patch.patch [deleted file]
target/linux/generic/backport-5.15/834-v6.8-0001-nvmem-Move-of_nvmem_layout_get_container-in-another-.patch [deleted file]
target/linux/generic/backport-5.15/834-v6.8-0002-nvmem-Create-a-header-for-internal-sharing.patch [deleted file]
target/linux/generic/backport-5.15/834-v6.8-0003-nvmem-Simplify-the-add_cells-hook.patch [deleted file]
target/linux/generic/backport-5.15/834-v6.8-0004-nvmem-Move-and-rename-fixup_cell_info.patch [deleted file]
target/linux/generic/backport-5.15/834-v6.8-0005-nvmem-core-Rework-layouts-to-become-regular-devices.patch [deleted file]
target/linux/generic/backport-5.15/834-v6.8-0006-nvmem-core-Expose-cells-through-sysfs.patch [deleted file]
target/linux/generic/backport-5.15/834-v6.8-0007-nvmem-stm32-add-support-for-STM32MP25-BSEC-to-contro.patch [deleted file]
target/linux/generic/backport-5.15/834-v6.8-0008-nvmem-layouts-refactor-.add_cells-callback-arguments.patch [deleted file]
target/linux/generic/backport-5.15/834-v6.8-0009-nvmem-drop-nvmem_layout_get_match_data.patch [deleted file]
target/linux/generic/backport-5.15/834-v6.8-0010-nvmem-core-add-nvmem_dev_size-helper.patch [deleted file]
target/linux/generic/backport-5.15/834-v6.8-0011-nvmem-u-boot-env-use-nvmem_add_one_cell-nvmem-subsys.patch [deleted file]
target/linux/generic/backport-5.15/834-v6.8-0012-nvmem-u-boot-env-use-nvmem-device-helpers.patch [deleted file]
target/linux/generic/backport-5.15/834-v6.8-0013-nvmem-u-boot-env-improve-coding-style.patch [deleted file]
target/linux/generic/backport-5.15/835-v6.9-0001-dt-bindings-leds-Add-FUNCTION-defines-for-per-band-W.patch [deleted file]
target/linux/generic/backport-5.15/835-v6.9-0002-dt-bindings-leds-Add-LED_FUNCTION_WAN_ONLINE-for-Int.patch [deleted file]
target/linux/generic/backport-5.15/836-v6.9-0002-nvmem-mtk-efuse-Register-MediaTek-socinfo-driver-fro.patch [deleted file]
target/linux/generic/backport-5.15/836-v6.9-0003-nvmem-zynqmp_nvmem-zynqmp_nvmem_probe-cleanup.patch [deleted file]
target/linux/generic/backport-5.15/836-v6.9-0004-nvmem-zynqmp_nvmem-Add-support-to-access-efuse.patch [deleted file]
target/linux/generic/backport-5.15/836-v6.9-0005-nvmem-mtk-efuse-Drop-NVMEM-device-name.patch [deleted file]
target/linux/generic/backport-5.15/836-v6.9-0007-nvmem-core-Print-error-on-wrong-bits-DT-property.patch [deleted file]
target/linux/generic/backport-5.15/837-v6.10-0001-nvmem-layouts-store-owner-from-modules-with-nvmem_la.patch [deleted file]
target/linux/generic/backport-5.15/837-v6.10-0002-nvmem-layouts-onie-tlv-drop-driver-owner-initializat.patch [deleted file]
target/linux/generic/backport-5.15/837-v6.10-0003-nvmem-layouts-sl28vpd-drop-driver-owner-initializati.patch [deleted file]
target/linux/generic/backport-5.15/837-v6.10-0004-nvmem-sc27xx-fix-module-autoloading.patch [deleted file]
target/linux/generic/backport-5.15/837-v6.10-0005-nvmem-sprd-fix-module-autoloading.patch [deleted file]
target/linux/generic/backport-5.15/837-v6.10-0006-nvmem-core-switch-to-use-device_add_groups.patch [deleted file]
target/linux/generic/backport-5.15/837-v6.10-0007-nvmem-lpc18xx_eeprom-Convert-to-platform-remove-call.patch [deleted file]
target/linux/generic/backport-5.15/837-v6.10-0008-nvmem-meson-mx-efuse-Remove-nvmem_device-from-efuse-.patch [deleted file]
target/linux/generic/backport-5.15/837-v6.10-0009-nvmem-rmem-Fix-return-value-of-rmem_read.patch [deleted file]
target/linux/generic/backport-5.15/837-v6.10-0010-nvmem-meson-efuse-Fix-return-value-of-nvmem-callback.patch [deleted file]
target/linux/generic/backport-5.15/837-v6.10-0011-nvmem-core-only-change-name-to-fram-for-current-attr.patch [deleted file]
target/linux/generic/backport-5.15/837-v6.10-0012-nvmem-core-limit-cell-sysfs-permissions-to-main-attr.patch [deleted file]
target/linux/generic/backport-5.15/838-v6.11-0001-nvmem-add-missing-MODULE_DESCRIPTION-macros.patch [deleted file]
target/linux/generic/backport-5.15/838-v6.11-0002-nvmem-meson-efuse-Replacing-the-use-of-of_node_put-t.patch [deleted file]
target/linux/generic/backport-5.15/838-v6.11-0003-nvmem-rockchip-otp-set-add_legacy_fixed_of_cells-con.patch [deleted file]
target/linux/generic/backport-5.15/838-v6.11-0004-nvmem-rockchip-otp-Set-type-to-OTP.patch [deleted file]
target/linux/generic/backport-5.15/838-v6.11-0005-nvmem-rockchip-efuse-set-type-to-OTP.patch [deleted file]
target/linux/generic/backport-5.15/838-v6.11-0006-nvmem-core-add-single-sysfs-group.patch [deleted file]
target/linux/generic/backport-5.15/838-v6.11-0007-nvmem-core-remove-global-nvmem_cells_group.patch [deleted file]
target/linux/generic/backport-5.15/838-v6.11-0008-nvmem-core-drop-unnecessary-range-checks-in-sysfs-ca.patch [deleted file]
target/linux/generic/backport-5.15/838-v6.11-0009-nvmem-Use-sysfs_emit-for-type-attribute.patch [deleted file]
target/linux/generic/backport-5.15/838-v6.11-0010-nvmem-core-Implement-force_ro-sysfs-attribute.patch [deleted file]
target/linux/generic/backport-5.15/838-v6.11-0011-nvmem-u-boot-env-error-if-NVMEM-device-is-too-small.patch [deleted file]
target/linux/generic/backport-5.15/838-v6.11-0012-nvmem-Fix-return-type-of-devm_nvmem_device_get-in-ke.patch [deleted file]
target/linux/generic/backport-5.15/839-v6.12-0001-nvmem-imx-ocotp-ele-support-i.MX95.patch [deleted file]
target/linux/generic/backport-5.15/839-v6.12-0002-nvmem-sunplus-ocotp-Use-devm_platform_ioremap_resour.patch [deleted file]
target/linux/generic/backport-5.15/839-v6.12-0003-nvmem-layouts-add-U-Boot-env-layout.patch [deleted file]
target/linux/generic/backport-5.15/860-v5.17-MIPS-ath79-drop-_machine_restart-again.patch [deleted file]
target/linux/generic/backport-5.15/870-v5.18-hwmon-lm70-Add-ti-tmp125-support.patch [deleted file]
target/linux/generic/backport-5.15/880-v5.19-cdc_ether-export-usbnet_cdc_zte_rx_fixup.patch [deleted file]
target/linux/generic/backport-5.15/881-v5.19-rndis_host-enable-the-bogus-MAC-fixup-for-ZTE-device.patch [deleted file]
target/linux/generic/backport-5.15/882-v5.19-rndis_host-limit-scope-of-bogus-MAC-address-detectio.patch [deleted file]
target/linux/generic/backport-5.15/890-v6.2-mtd-spinand-winbond-fix-flash-detection.patch [deleted file]
target/linux/generic/backport-5.15/891-v6.2-mtd-spinand-winbond-add-W25N02KV.patch [deleted file]
target/linux/generic/backport-5.15/892-v6.5-mtd-spinand-winbond-Fix-ecc_get_status.patch [deleted file]
target/linux/generic/backport-5.15/893-v6.5-01-net-dsa-mv88e6xxx-pass-directly-chip-structure-to-mv.patch [deleted file]
target/linux/generic/backport-5.15/893-v6.5-02-net-dsa-mv88e6xxx-use-mv88e6xxx_phy_is_internal-in-m.patch [deleted file]
target/linux/generic/backport-5.15/893-v6.5-03-net-dsa-mv88e6xxx-add-field-to-specify-internal-phys.patch [deleted file]
target/linux/generic/backport-5.15/893-v6.5-04-net-dsa-mv88e6xxx-fix-88E6393X-family-internal-phys-.patch [deleted file]
target/linux/generic/backport-5.15/893-v6.5-05-net-dsa-mv88e6xxx-pass-mv88e6xxx_chip-structure-to-p.patch [deleted file]
target/linux/generic/backport-5.15/893-v6.5-06-net-dsa-mv88e6xxx-enable-support-for-88E6361-switch.patch [deleted file]
target/linux/generic/backport-5.15/894-v6.8-net-ethtool-implement-ethtool_puts.patch [deleted file]
target/linux/generic/config-5.15 [deleted file]
target/linux/generic/hack-5.15/204-module_strip.patch [deleted file]
target/linux/generic/hack-5.15/205-kconfig-abort-configuration-on-unset-symbol.patch [deleted file]
target/linux/generic/hack-5.15/210-darwin_scripts_include.patch [deleted file]
target/linux/generic/hack-5.15/211-darwin-uuid-typedef-clash.patch [deleted file]
target/linux/generic/hack-5.15/212-tools_portability.patch [deleted file]
target/linux/generic/hack-5.15/214-spidev_h_portability.patch [deleted file]
target/linux/generic/hack-5.15/220-arm-gc_sections.patch [deleted file]
target/linux/generic/hack-5.15/221-module_exports.patch [deleted file]
target/linux/generic/hack-5.15/230-openwrt_lzma_options.patch [deleted file]
target/linux/generic/hack-5.15/250-netfilter_depends.patch [deleted file]
target/linux/generic/hack-5.15/251-kconfig.patch [deleted file]
target/linux/generic/hack-5.15/253-ksmbd-config.patch [deleted file]
target/linux/generic/hack-5.15/259-regmap_dynamic.patch [deleted file]
target/linux/generic/hack-5.15/260-crypto_test_dependencies.patch [deleted file]
target/linux/generic/hack-5.15/261-lib-arc4-unhide.patch [deleted file]
target/linux/generic/hack-5.15/280-rfkill-stubs.patch [deleted file]
target/linux/generic/hack-5.15/300-MIPS-r4k_cache-use-more-efficient-cache-blast.patch [deleted file]
target/linux/generic/hack-5.15/402-mtd-blktrans-call-add-disks-after-mtd-device.patch [deleted file]
target/linux/generic/hack-5.15/420-mtd-support-OpenWrt-s-MTD_ROOTFS_ROOT_DEV.patch [deleted file]
target/linux/generic/hack-5.15/421-drivers-mtd-parsers-add-nvmem-support-to-cmdlinepart.patch [deleted file]
target/linux/generic/hack-5.15/430-mtk-bmt-support.patch [deleted file]
target/linux/generic/hack-5.15/645-netfilter-connmark-introduce-set-dscpmark.patch [deleted file]
target/linux/generic/hack-5.15/650-netfilter-add-xt_FLOWOFFLOAD-target.patch [deleted file]
target/linux/generic/hack-5.15/651-wireless_mesh_header.patch [deleted file]
target/linux/generic/hack-5.15/660-fq_codel_defaults.patch [deleted file]
target/linux/generic/hack-5.15/661-kernel-ct-size-the-hashtable-more-adequately.patch [deleted file]
target/linux/generic/hack-5.15/700-swconfig_switch_drivers.patch [deleted file]
target/linux/generic/hack-5.15/711-net-dsa-mv88e6xxx-disable-ATU-violation.patch [deleted file]
target/linux/generic/hack-5.15/721-net-add-packet-mangeling.patch [deleted file]
target/linux/generic/hack-5.15/722-net-phy-aquantia-enable-AQR112-and-AQR412.patch [deleted file]
target/linux/generic/hack-5.15/723-net-phy-aquantia-fix-system-side-protocol-mi.patch [deleted file]
target/linux/generic/hack-5.15/725-net-phy-aquantia-add-PHY_IDs-for-AQR112-variants.patch [deleted file]
target/linux/generic/hack-5.15/750-net-pcs-mtk-lynxi-workaround-2500BaseX-no-an.patch [deleted file]
target/linux/generic/hack-5.15/760-net-usb-r8152-add-LED-configuration-from-OF.patch [deleted file]
target/linux/generic/hack-5.15/761-dt-bindings-net-add-RTL8152-binding-documentation.patch [deleted file]
target/linux/generic/hack-5.15/765-mxl-gpy-control-LED-reg-from-DT.patch [deleted file]
target/linux/generic/hack-5.15/766-net-phy-mediatek-ge-add-LED-configuration-interface.patch [deleted file]
target/linux/generic/hack-5.15/773-bgmac-add-srab-switch.patch [deleted file]
target/linux/generic/hack-5.15/780-usb-net-MeigLink_modem_support.patch [deleted file]
target/linux/generic/hack-5.15/781-usb-net-rndis-support-asr.patch [deleted file]
target/linux/generic/hack-5.15/790-SFP-GE-T-ignore-TX_FAULT.patch [deleted file]
target/linux/generic/hack-5.15/795-backport-phylink_pcs-helpers.patch [deleted file]
target/linux/generic/hack-5.15/800-GPIO-add-named-gpio-exports.patch [deleted file]
target/linux/generic/hack-5.15/810-bcma-ssb-fallback-sprom.patch [deleted file]
target/linux/generic/hack-5.15/901-debloat_sock_diag.patch [deleted file]
target/linux/generic/hack-5.15/902-debloat_proc.patch [deleted file]
target/linux/generic/hack-5.15/904-debloat_dma_buf.patch [deleted file]
target/linux/generic/hack-5.15/910-kobject_uevent.patch [deleted file]
target/linux/generic/hack-5.15/911-kobject_add_broadcast_uevent.patch [deleted file]
target/linux/generic/hack-5.15/920-device_tree_cmdline.patch [deleted file]
target/linux/generic/hack-5.15/930-Revert-Revert-Revert-driver-core-Set-fw_devlink-on-b.patch [deleted file]
target/linux/generic/pending-5.15/100-compiler.h-only-include-asm-rwonce.h-for-kernel-code.patch [deleted file]
target/linux/generic/pending-5.15/102-MIPS-only-process-negative-stack-offsets-on-stack-tr.patch [deleted file]
target/linux/generic/pending-5.15/103-kbuild-export-SUBARCH.patch [deleted file]
target/linux/generic/pending-5.15/111-watchdog-max63xx_wdt-Add-support-for-specifying-WDI-.patch [deleted file]
target/linux/generic/pending-5.15/120-Fix-alloc_node_mem_map-with-ARCH_PFN_OFFSET-calcu.patch [deleted file]
target/linux/generic/pending-5.15/140-jffs2-use-.rename2-and-add-RENAME_WHITEOUT-support.patch [deleted file]
target/linux/generic/pending-5.15/141-jffs2-add-RENAME_EXCHANGE-support.patch [deleted file]
target/linux/generic/pending-5.15/142-jffs2-add-splice-ops.patch [deleted file]
target/linux/generic/pending-5.15/150-bridge_allow_receiption_on_disabled_port.patch [deleted file]
target/linux/generic/pending-5.15/151-net-bridge-do-not-send-arp-replies-if-src-and-target.patch [deleted file]
target/linux/generic/pending-5.15/190-rtc-rs5c372-support_alarms_up_to_1_week.patch [deleted file]
target/linux/generic/pending-5.15/191-rtc-rs5c372-let_the_alarm_to_be_used_as_wakeup_source.patch [deleted file]
target/linux/generic/pending-5.15/203-kallsyms_uncompressed.patch [deleted file]
target/linux/generic/pending-5.15/205-backtrace_module_info.patch [deleted file]
target/linux/generic/pending-5.15/240-remove-unsane-filenames-from-deps_initramfs-list.patch [deleted file]
target/linux/generic/pending-5.15/261-enable_wilink_platform_without_drivers.patch [deleted file]
target/linux/generic/pending-5.15/270-platform-mikrotik-build-bits.patch [deleted file]
target/linux/generic/pending-5.15/300-mips_expose_boot_raw.patch [deleted file]
target/linux/generic/pending-5.15/301-MIPS-Add-barriers-between-dcache-icache-flushes.patch [deleted file]
target/linux/generic/pending-5.15/302-mips_no_branch_likely.patch [deleted file]
target/linux/generic/pending-5.15/305-mips_module_reloc.patch [deleted file]
target/linux/generic/pending-5.15/308-mips32r2_tune.patch [deleted file]
target/linux/generic/pending-5.15/310-arm_module_unresolved_weak_sym.patch [deleted file]
target/linux/generic/pending-5.15/330-MIPS-kexec-Accept-command-line-parameters-from-users.patch [deleted file]
target/linux/generic/pending-5.15/332-arc-add-OWRTDTB-section.patch [deleted file]
target/linux/generic/pending-5.15/333-arc-enable-unaligned-access-in-kernel-mode.patch [deleted file]
target/linux/generic/pending-5.15/342-powerpc-Enable-kernel-XZ-compression-option-on-PPC_8.patch [deleted file]
target/linux/generic/pending-5.15/351-irqchip-bcm-6345-l1-request-memory-region.patch [deleted file]
target/linux/generic/pending-5.15/400-mtd-mtdsplit-support.patch [deleted file]
target/linux/generic/pending-5.15/401-mtd-don-t-register-NVMEM-devices-for-partitions-with.patch [deleted file]
target/linux/generic/pending-5.15/402-mtd-spi-nor-write-support-for-minor-aligned-partitions.patch [deleted file]
target/linux/generic/pending-5.15/405-mtd-spi-nor-Add-support-for-BoHong-bh25q128as.patch [deleted file]
target/linux/generic/pending-5.15/420-mtd-redboot_space.patch [deleted file]
target/linux/generic/pending-5.15/430-mtd-add-myloader-partition-parser.patch [deleted file]
target/linux/generic/pending-5.15/431-mtd-bcm47xxpart-check-for-bad-blocks-when-calculatin.patch [deleted file]
target/linux/generic/pending-5.15/432-mtd-bcm47xxpart-detect-T_Meter-partition.patch [deleted file]
target/linux/generic/pending-5.15/435-mtd-add-routerbootpart-parser-config.patch [deleted file]
target/linux/generic/pending-5.15/460-mtd-cfi_cmdset_0002-no-erase_suspend.patch [deleted file]
target/linux/generic/pending-5.15/461-mtd-cfi_cmdset_0002-add-buffer-write-cmd-timeout.patch [deleted file]
target/linux/generic/pending-5.15/465-m25p80-mx-disable-software-protection.patch [deleted file]
target/linux/generic/pending-5.15/476-mtd-spi-nor-add-eon-en25q128.patch [deleted file]
target/linux/generic/pending-5.15/477-mtd-spi-nor-add-eon-en25qx128a.patch [deleted file]
target/linux/generic/pending-5.15/479-mtd-spi-nor-add-xtx-xt25f128b.patch [deleted file]
target/linux/generic/pending-5.15/481-mtd-spi-nor-add-support-for-Gigadevice-GD25D05.patch [deleted file]
target/linux/generic/pending-5.15/482-mtd-spi-nor-add-gd25q512.patch [deleted file]
target/linux/generic/pending-5.15/484-mtd-spi-nor-add-esmt-f25l16pa.patch [deleted file]
target/linux/generic/pending-5.15/485-mtd-spi-nor-add-xmc-xm25qh128c.patch [deleted file]
target/linux/generic/pending-5.15/486-01-mtd-spinand-add-support-for-ESMT-F50x1G41LB.patch [deleted file]
target/linux/generic/pending-5.15/487-mtd-spinand-Add-support-for-Etron-EM73D044VCx.patch [deleted file]
target/linux/generic/pending-5.15/488-mtd-spi-nor-add-xmc-xm25qh64c.patch [deleted file]
target/linux/generic/pending-5.15/490-ubi-auto-attach-mtd-device-named-ubi-or-data-on-boot.patch [deleted file]
target/linux/generic/pending-5.15/491-ubi-auto-create-ubiblock-device-for-rootfs.patch [deleted file]
target/linux/generic/pending-5.15/492-try-auto-mounting-ubi0-rootfs-in-init-do_mounts.c.patch [deleted file]
target/linux/generic/pending-5.15/493-ubi-set-ROOT_DEV-to-ubiblock-rootfs-if-unset.patch [deleted file]
target/linux/generic/pending-5.15/494-mtd-ubi-add-EOF-marker-support.patch [deleted file]
target/linux/generic/pending-5.15/496-dt-bindings-add-bindings-for-mtd-concat-devices.patch [deleted file]
target/linux/generic/pending-5.15/497-mtd-mtdconcat-add-dt-driver-for-concat-devices.patch [deleted file]
target/linux/generic/pending-5.15/498-mtd-spi-nor-locking-support-for-MX25L6405D.patch [deleted file]
target/linux/generic/pending-5.15/499-mtd-spi-nor-disable-16-bit-sr-for-macronix.patch [deleted file]
target/linux/generic/pending-5.15/500-fs_cdrom_dependencies.patch [deleted file]
target/linux/generic/pending-5.15/530-jffs2_make_lzma_available.patch [deleted file]
target/linux/generic/pending-5.15/532-jffs2_eofdetect.patch [deleted file]
target/linux/generic/pending-5.15/600-netfilter_conntrack_flush.patch [deleted file]
target/linux/generic/pending-5.15/610-netfilter_match_bypass_default_checks.patch [deleted file]
target/linux/generic/pending-5.15/611-netfilter_match_bypass_default_table.patch [deleted file]
target/linux/generic/pending-5.15/612-netfilter_match_reduce_memory_access.patch [deleted file]
target/linux/generic/pending-5.15/620-net_sched-codel-do-not-defer-queue-length-update.patch [deleted file]
target/linux/generic/pending-5.15/630-packet_socket_type.patch [deleted file]
target/linux/generic/pending-5.15/655-increase_skb_pad.patch [deleted file]
target/linux/generic/pending-5.15/666-Add-support-for-MAP-E-FMRs-mesh-mode.patch [deleted file]
target/linux/generic/pending-5.15/670-ipv6-allow-rejecting-with-source-address-failed-policy.patch [deleted file]
target/linux/generic/pending-5.15/671-net-provide-defines-for-_POLICY_FAILED-until-all-cod.patch [deleted file]
target/linux/generic/pending-5.15/680-NET-skip-GRO-for-foreign-MAC-addresses.patch [deleted file]
target/linux/generic/pending-5.15/683-of_net-add-mac-address-to-of-tree.patch [deleted file]
target/linux/generic/pending-5.15/700-netfilter-nft_flow_offload-handle-netdevice-events-f.patch [deleted file]
target/linux/generic/pending-5.15/701-netfilter-nf_tables-ignore-EOPNOTSUPP-on-flowtable-d.patch [deleted file]
target/linux/generic/pending-5.15/702-net-ethernet-mtk_eth_soc-enable-threaded-NAPI.patch [deleted file]
target/linux/generic/pending-5.15/703-phy-add-detach-callback-to-struct-phy_driver.patch [deleted file]
target/linux/generic/pending-5.15/704-01-v6.4-net-mvneta-fix-transmit-path-dma-unmapping-on-error.patch [deleted file]
target/linux/generic/pending-5.15/704-02-v6.4-net-mvneta-mark-mapped-and-tso-buffers-separately.patch [deleted file]
target/linux/generic/pending-5.15/704-03-v6.4-net-mvneta-use-buf-type-to-determine-whether-to-dma-.patch [deleted file]
target/linux/generic/pending-5.15/704-04-v6.4-net-mvneta-move-tso_build_hdr-into-mvneta_tso_put_hd.patch [deleted file]
target/linux/generic/pending-5.15/704-05-v6.4-net-mvneta-allocate-TSO-header-DMA-memory-in-chunks.patch [deleted file]
target/linux/generic/pending-5.15/705-net-dsa-tag_mtk-add-padding-for-tx-packets.patch [deleted file]
target/linux/generic/pending-5.15/710-bridge-add-knob-for-filtering-rx-tx-BPDU-pack.patch [deleted file]
target/linux/generic/pending-5.15/721-net-phy-realtek-rtl8221-allow-to-configure-SERDES-mo.patch [deleted file]
target/linux/generic/pending-5.15/722-net-phy-realtek-support-switching-between-SGMII-and-.patch [deleted file]
target/linux/generic/pending-5.15/723-net-mt7531-ensure-all-MACs-are-powered-down-before-r.patch [deleted file]
target/linux/generic/pending-5.15/724-net-phy-realtek-use-genphy_soft_reset-for-2.5G-PHYs.patch [deleted file]
target/linux/generic/pending-5.15/725-net-phy-realtek-disable-SGMII-in-band-AN-for-2-5G-PHYs.patch [deleted file]
target/linux/generic/pending-5.15/726-net-phy-realtek-make-sure-paged-read-is-protected-by.patch [deleted file]
target/linux/generic/pending-5.15/727-net-phy-realtek-use-inline-functions-for-10GbE-adver.patch [deleted file]
target/linux/generic/pending-5.15/728-net-phy-realtek-check-validity-of-10GbE-link-partner.patch [deleted file]
target/linux/generic/pending-5.15/729-net-phy-realtek-introduce-rtl822x_probe.patch [deleted file]
target/linux/generic/pending-5.15/730-net-phy-realtek-detect-early-version-of-RTL8221B.patch [deleted file]
target/linux/generic/pending-5.15/731-net-phy-realtek-support-interrupt-of-RTL8221B.patch [deleted file]
target/linux/generic/pending-5.15/732-00-net-ethernet-mtk_eth_soc-compile-out-netsys-v2-code-.patch [deleted file]
target/linux/generic/pending-5.15/732-01-net-ethernet-mtk_eth_soc-work-around-issue-with-send.patch [deleted file]
target/linux/generic/pending-5.15/732-02-net-ethernet-mtk_eth_soc-set-NETIF_F_ALL_TSO.patch [deleted file]
target/linux/generic/pending-5.15/732-03-net-ethernet-mtk_eth_soc-fix-remaining-throughput-re.patch [deleted file]
target/linux/generic/pending-5.15/734-net-ethernet-mtk_eth_soc-ppe-fix-L2-offloading-with-.patch [deleted file]
target/linux/generic/pending-5.15/737-net-ethernet-mtk_eth_soc-add-paths-and-SerDes-modes-.patch [deleted file]
target/linux/generic/pending-5.15/738-net-ethernet-mtk_eth_soc-set-coherent-mask-to-get-PP.patch [deleted file]
target/linux/generic/pending-5.15/740-net-phy-motorcomm-Add-missing-include.patch [deleted file]
target/linux/generic/pending-5.15/750-skb-Do-mix-page-pool-and-page-referenced-frags-in-GR.patch [deleted file]
target/linux/generic/pending-5.15/760-net-core-add-optional-threading-for-backlog-processi.patch [deleted file]
target/linux/generic/pending-5.15/768-net-dsa-mv88e6xxx-Request-assisted-learning-on-CPU-port.patch [deleted file]
target/linux/generic/pending-5.15/772-net-dsa-b53-add-support-for-BCM63xx-RGMIIs.patch [deleted file]
target/linux/generic/pending-5.15/773-net-dsa-b53-mmap-add-more-63xx-SoCs.patch [deleted file]
target/linux/generic/pending-5.15/774-net-dsa-b53-mmap-allow-passing-a-chip-ID.patch [deleted file]
target/linux/generic/pending-5.15/775-net-dsa-b53-add-BCM63268-RGMII-configuration.patch [deleted file]
target/linux/generic/pending-5.15/777-net-dsa-b53-mdio-add-support-for-BCM53134.patch [deleted file]
target/linux/generic/pending-5.15/779-net-vxlan-don-t-learn-non-unicast-L2-destinations.patch [deleted file]
target/linux/generic/pending-5.15/780-ARM-kirkwood-add-missing-linux-if_ether.h-for-ETH_AL.patch [deleted file]
target/linux/generic/pending-5.15/790-bus-mhi-core-add-SBL-state-callback.patch [deleted file]
target/linux/generic/pending-5.15/795-mt7530-register-OF-node-for-internal-MDIO-bus.patch [deleted file]
target/linux/generic/pending-5.15/796-net-dsa-mt7530-fix-10M-100M-speed-on-MT7988-switch.patch [deleted file]
target/linux/generic/pending-5.15/800-bcma-get-SoC-device-struct-copy-its-DMA-params-to-th.patch [deleted file]
target/linux/generic/pending-5.15/801-gpio-gpio-cascade-add-generic-GPIO-cascade.patch [deleted file]
target/linux/generic/pending-5.15/802-nvmem-u-boot-env-align-endianness-of-crc32-values.patch [deleted file]
target/linux/generic/pending-5.15/804-nvmem-core-support-mac-base-fixed-layout-cells.patch [deleted file]
target/linux/generic/pending-5.15/810-pci_disable_common_quirks.patch [deleted file]
target/linux/generic/pending-5.15/811-pci_disable_usb_common_quirks.patch [deleted file]
target/linux/generic/pending-5.15/820-w1-gpio-fix-problem-with-platfom-data-in-w1-gpio.patch [deleted file]
target/linux/generic/pending-5.15/834-ledtrig-libata.patch [deleted file]
target/linux/generic/pending-5.15/840-hwrng-bcm2835-set-quality-to-1000.patch [deleted file]
target/linux/generic/pending-5.15/850-0023-PCI-aardvark-Make-main-irq_chip-structure-a-static-d.patch [deleted file]
target/linux/generic/pending-5.15/850-dt-bindings-clk-add-BCM63268-timer-clock-definitions.patch [deleted file]
target/linux/generic/pending-5.15/851-dt-bindings-reset-add-BCM63268-timer-reset-definitions.patch [deleted file]
target/linux/generic/pending-5.15/852-clk-bcm-Add-BCM63268-timer-clock-and-reset-driver.patch [deleted file]
target/linux/generic/pending-5.15/860-serial-8250_mtk-track-busclk-state-to-avoid-bus-error.patch [deleted file]
target/linux/generic/pending-5.15/870-ARM-dts-nxp-imx7d-pico-add-cpu-supply-nodes.patch [deleted file]
target/linux/generic/pending-5.15/880-01-dt-bindings-leds-add-LED_FUNCTION_MOBILE-for-mobile-.patch [deleted file]
target/linux/generic/pending-5.15/880-02-dt-bindings-leds-add-LED_FUNCTION_SPEED_-for-link-sp.patch [deleted file]
target/linux/generic/pending-5.15/920-mangle_bootargs.patch [deleted file]
target/linux/generic/pending-5.15/980-tools-thermal-tmon-Fix-compilation-warning-for-wrong.patch [deleted file]

diff --git a/include/kernel-5.15 b/include/kernel-5.15
deleted file mode 100644 (file)
index a03ed80..0000000
+++ /dev/null
@@ -1,2 +0,0 @@
-LINUX_VERSION-5.15 = .161
-LINUX_KERNEL_HASH-5.15.161 = d629f78680dc4b65e3d78b61406fb7757b960c83c206e63ad8c2606b3e3c474c
diff --git a/target/linux/generic/backport-5.15/005-v5.17-01-Kbuild-use-Wdeclaration-after-statement.patch b/target/linux/generic/backport-5.15/005-v5.17-01-Kbuild-use-Wdeclaration-after-statement.patch
deleted file mode 100644 (file)
index b481dd3..0000000
+++ /dev/null
@@ -1,73 +0,0 @@
-From 2fd7e7f9317d3048a14026816d081b08ba98ea8e Mon Sep 17 00:00:00 2001
-From: Mark Rutland <[email protected]>
-Date: Tue, 8 Mar 2022 22:56:13 +0100
-Subject: [PATCH 1/3] Kbuild: use -Wdeclaration-after-statement
-
-The kernel is moving from using `-std=gnu89` to `-std=gnu11`, permitting
-the use of additional C11 features such as for-loop initial declarations.
-
-One contentious aspect of C99 is that it permits mixed declarations and
-code, and for now at least, it seems preferable to enforce that
-declarations must come first.
-
-These warnings were already enabled in the kernel itself, but not
-for KBUILD_USERCFLAGS or the compat VDSO on arch/arm64, which uses
-a separate set of CFLAGS.
-
-This patch fixes an existing violation in modpost.c, which is not
-reported because of the missing flag in KBUILD_USERCFLAGS:
-
-| scripts/mod/modpost.c: In function ‘match’:
-| scripts/mod/modpost.c:837:3: warning: ISO C90 forbids mixed declarations and code [-Wdeclaration-after-statement]
-|   837 |   const char *endp = p + strlen(p) - 1;
-|       |   ^~~~~
-
-Signed-off-by: Mark Rutland <[email protected]>
-[arnd: don't add a duplicate flag to the default set, update changelog]
-Signed-off-by: Arnd Bergmann <[email protected]>
-Reviewed-by: Nathan Chancellor <[email protected]>
-Reviewed-by: Nick Desaulniers <[email protected]>
-Tested-by: Sedat Dilek <[email protected]> # LLVM/Clang v13.0.0 (x86-64)
-Signed-off-by: Masahiro Yamada <[email protected]>
----
- Makefile                          | 3 ++-
- arch/arm64/kernel/vdso32/Makefile | 1 +
- scripts/mod/modpost.c             | 4 +++-
- 3 files changed, 6 insertions(+), 2 deletions(-)
-
---- a/Makefile
-+++ b/Makefile
-@@ -440,7 +440,8 @@ endif
- HOSTPKG_CONFIG        = pkg-config
- export KBUILD_USERCFLAGS := -Wall -Wmissing-prototypes -Wstrict-prototypes \
--                            -O2 -fomit-frame-pointer -std=gnu89
-+                            -O2 -fomit-frame-pointer -std=gnu89 \
-+                            -Wdeclaration-after-statement
- export KBUILD_USERLDFLAGS :=
- KBUILD_HOSTCFLAGS   := $(KBUILD_USERCFLAGS) $(HOST_LFS_CFLAGS) $(HOSTCFLAGS)
---- a/arch/arm64/kernel/vdso32/Makefile
-+++ b/arch/arm64/kernel/vdso32/Makefile
-@@ -76,6 +76,7 @@ VDSO_CFLAGS += -Wall -Wundef -Wstrict-pr
-                -fno-strict-aliasing -fno-common \
-                -Werror-implicit-function-declaration \
-                -Wno-format-security \
-+               -Wdeclaration-after-statement \
-                -std=gnu89
- VDSO_CFLAGS  += -O2
- # Some useful compiler-dependent flags from top-level Makefile
---- a/scripts/mod/modpost.c
-+++ b/scripts/mod/modpost.c
-@@ -833,8 +833,10 @@ static int match(const char *sym, const
- {
-       const char *p;
-       while (*pat) {
-+              const char *endp;
-+
-               p = *pat++;
--              const char *endp = p + strlen(p) - 1;
-+              endp = p + strlen(p) - 1;
-               /* "*foo*" */
-               if (*p == '*' && *endp == '*') {
diff --git a/target/linux/generic/backport-5.15/005-v5.17-02-Kbuild-move-to-std-gnu11.patch b/target/linux/generic/backport-5.15/005-v5.17-02-Kbuild-move-to-std-gnu11.patch
deleted file mode 100644 (file)
index 94fc52f..0000000
+++ /dev/null
@@ -1,60 +0,0 @@
-From b810c8e719ea082e47c7a8f7cf878bc84fa2455d Mon Sep 17 00:00:00 2001
-From: Arnd Bergmann <[email protected]>
-Date: Tue, 8 Mar 2022 22:56:14 +0100
-Subject: [PATCH 2/3] Kbuild: move to -std=gnu11
-
-During a patch discussion, Linus brought up the option of changing
-the C standard version from gnu89 to gnu99, which allows using variable
-declaration inside of a for() loop. While the C99, C11 and later standards
-introduce many other features, most of these are already available in
-gnu89 as GNU extensions as well.
-
-An earlier attempt to do this when gcc-5 started defaulting to
--std=gnu11 failed because at the time that caused warnings about
-designated initializers with older compilers. Now that gcc-5.1 is
-the minimum compiler version used for building kernels, that is no
-longer a concern. Similarly, the behavior of 'inline' functions changes
-between gnu89 using gnu_inline behavior and gnu11 using standard c99+
-behavior, but this was taken care of by defining 'inline' to include
-__attribute__((gnu_inline)) in order to allow building with clang a
-while ago.
-
-Nathan Chancellor reported a new -Wdeclaration-after-statement
-warning that appears in a system header on arm, this still needs a
-workaround.
-
-The differences between gnu99, gnu11, gnu1x and gnu17 are fairly
-minimal and mainly impact warnings at the -Wpedantic level that the
-kernel never enables. Between these, gnu11 is the newest version
-that is supported by all supported compiler versions, though it is
-only the default on gcc-5, while all other supported versions of
-gcc or clang default to gnu1x/gnu17.
-
-Link: https://lore.kernel.org/lkml/CAHk-=wiyCH7xeHcmiFJ-YgXUy2Jaj7pnkdKpcovt8fYbVFW3TA@mail.gmail.com/
-Link: https://github.com/ClangBuiltLinux/linux/issues/1603
-Suggested-by: Linus Torvalds <[email protected]>
-Acked-by: Marco Elver <[email protected]>
-Acked-by: Jani Nikula <[email protected]>
-Acked-by: David Sterba <[email protected]>
-Tested-by: Sedat Dilek <[email protected]>
-Reviewed-by: Alex Shi <[email protected]>
-Reviewed-by: Nick Desaulniers <[email protected]>
-Reviewed-by: Miguel Ojeda <[email protected]>
-Signed-off-by: Arnd Bergmann <[email protected]>
-Reviewed-by: Nathan Chancellor <[email protected]>
-Signed-off-by: Masahiro Yamada <[email protected]>
----
- Makefile | 2 +-
- 1 file changed, 1 insertion(+), 1 deletion(-)
-
---- a/Makefile
-+++ b/Makefile
-@@ -524,7 +524,7 @@ KBUILD_CFLAGS   := -Wall -Wundef -Werror
-                  -fno-strict-aliasing -fno-common -fshort-wchar -fno-PIE \
-                  -Werror=implicit-function-declaration -Werror=implicit-int \
-                  -Werror=return-type -Wno-format-security \
--                 -std=gnu89
-+                 -std=gnu11
- KBUILD_CPPFLAGS := -D__KERNEL__
- KBUILD_AFLAGS_KERNEL :=
- KBUILD_CFLAGS_KERNEL :=
diff --git a/target/linux/generic/backport-5.15/005-v5.17-03-Kbuild-use-std-gnu11-for-KBUILD_USERCFLAGS.patch b/target/linux/generic/backport-5.15/005-v5.17-03-Kbuild-use-std-gnu11-for-KBUILD_USERCFLAGS.patch
deleted file mode 100644 (file)
index e34acbb..0000000
+++ /dev/null
@@ -1,43 +0,0 @@
-From 40337d6f3d677aee7ad3052ae662d3f53dd4d5cb Mon Sep 17 00:00:00 2001
-From: Arnd Bergmann <[email protected]>
-Date: Tue, 8 Mar 2022 22:56:15 +0100
-Subject: [PATCH 3/3] Kbuild: use -std=gnu11 for KBUILD_USERCFLAGS
-
-As we change the C language standard for the kernel from gnu89 to
-gnu11, it makes sense to also update the version for user space
-compilation.
-
-Some users have older native compilers than what they use for
-kernel builds, so I considered using gnu99 as the default version
-for wider compatibility with gcc-4.6 and earlier.
-
-However, testing with older compilers showed that we already require
-HOSTCC version 5.1 as well because a lot of host tools include
-linux/compiler.h that uses __has_attribute():
-
-  CC      tools/objtool/exec-cmd.o
-In file included from tools/include/linux/compiler_types.h:36:0,
-                 from tools/include/linux/compiler.h:5,
-                 from exec-cmd.c:2:
-tools/include/linux/compiler-gcc.h:19:5: error: "__has_attribute" is not defined [-Werror=undef]
-
-Signed-off-by: Arnd Bergmann <[email protected]>
-Reviewed-by: Nathan Chancellor <[email protected]>
-Reviewed-by: Nick Desaulniers <[email protected]>
-Tested-by: Sedat Dilek <[email protected]>
-Signed-off-by: Masahiro Yamada <[email protected]>
----
- Makefile | 2 +-
- 1 file changed, 1 insertion(+), 1 deletion(-)
-
---- a/Makefile
-+++ b/Makefile
-@@ -440,7 +440,7 @@ endif
- HOSTPKG_CONFIG        = pkg-config
- export KBUILD_USERCFLAGS := -Wall -Wmissing-prototypes -Wstrict-prototypes \
--                            -O2 -fomit-frame-pointer -std=gnu89 \
-+                            -O2 -fomit-frame-pointer -std=gnu11 \
-                             -Wdeclaration-after-statement
- export KBUILD_USERLDFLAGS :=
diff --git a/target/linux/generic/backport-5.15/020-v6.1-01-mm-x86-arm64-add-arch_has_hw_pte_young.patch b/target/linux/generic/backport-5.15/020-v6.1-01-mm-x86-arm64-add-arch_has_hw_pte_young.patch
deleted file mode 100644 (file)
index 865da6b..0000000
+++ /dev/null
@@ -1,425 +0,0 @@
-From a4103262b01a1b8704b37c01c7c813df91b7b119 Mon Sep 17 00:00:00 2001
-From: Yu Zhao <[email protected]>
-Date: Sun, 18 Sep 2022 01:59:58 -0600
-Subject: [PATCH 01/29] mm: x86, arm64: add arch_has_hw_pte_young()
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-Patch series "Multi-Gen LRU Framework", v14.
-
-What's new
-==========
-1. OpenWrt, in addition to Android, Arch Linux Zen, Armbian, ChromeOS,
-   Liquorix, post-factum and XanMod, is now shipping MGLRU on 5.15.
-2. Fixed long-tailed direct reclaim latency seen on high-memory (TBs)
-   machines. The old direct reclaim backoff, which tries to enforce a
-   minimum fairness among all eligible memcgs, over-swapped by about
-   (total_mem>>DEF_PRIORITY)-nr_to_reclaim. The new backoff, which
-   pulls the plug on swapping once the target is met, trades some
-   fairness for curtailed latency:
-   https://lore.kernel.org/r/[email protected]/
-3. Fixed minior build warnings and conflicts. More comments and nits.
-
-TLDR
-====
-The current page reclaim is too expensive in terms of CPU usage and it
-often makes poor choices about what to evict. This patchset offers an
-alternative solution that is performant, versatile and
-straightforward.
-
-Patchset overview
-=================
-The design and implementation overview is in patch 14:
-https://lore.kernel.org/r/[email protected]/
-
-01. mm: x86, arm64: add arch_has_hw_pte_young()
-02. mm: x86: add CONFIG_ARCH_HAS_NONLEAF_PMD_YOUNG
-Take advantage of hardware features when trying to clear the accessed
-bit in many PTEs.
-
-03. mm/vmscan.c: refactor shrink_node()
-04. Revert "include/linux/mm_inline.h: fold __update_lru_size() into
-    its sole caller"
-Minor refactors to improve readability for the following patches.
-
-05. mm: multi-gen LRU: groundwork
-Adds the basic data structure and the functions that insert pages to
-and remove pages from the multi-gen LRU (MGLRU) lists.
-
-06. mm: multi-gen LRU: minimal implementation
-A minimal implementation without optimizations.
-
-07. mm: multi-gen LRU: exploit locality in rmap
-Exploits spatial locality to improve efficiency when using the rmap.
-
-08. mm: multi-gen LRU: support page table walks
-Further exploits spatial locality by optionally scanning page tables.
-
-09. mm: multi-gen LRU: optimize multiple memcgs
-Optimizes the overall performance for multiple memcgs running mixed
-types of workloads.
-
-10. mm: multi-gen LRU: kill switch
-Adds a kill switch to enable or disable MGLRU at runtime.
-
-11. mm: multi-gen LRU: thrashing prevention
-12. mm: multi-gen LRU: debugfs interface
-Provide userspace with features like thrashing prevention, working set
-estimation and proactive reclaim.
-
-13. mm: multi-gen LRU: admin guide
-14. mm: multi-gen LRU: design doc
-Add an admin guide and a design doc.
-
-Benchmark results
-=================
-Independent lab results
------------------------
-Based on the popularity of searches [01] and the memory usage in
-Google's public cloud, the most popular open-source memory-hungry
-applications, in alphabetical order, are:
-      Apache Cassandra      Memcached
-      Apache Hadoop         MongoDB
-      Apache Spark          PostgreSQL
-      MariaDB (MySQL)       Redis
-
-An independent lab evaluated MGLRU with the most widely used benchmark
-suites for the above applications. They posted 960 data points along
-with kernel metrics and perf profiles collected over more than 500
-hours of total benchmark time. Their final reports show that, with 95%
-confidence intervals (CIs), the above applications all performed
-significantly better for at least part of their benchmark matrices.
-
-On 5.14:
-1. Apache Spark [02] took 95% CIs [9.28, 11.19]% and [12.20, 14.93]%
-   less wall time to sort three billion random integers, respectively,
-   under the medium- and the high-concurrency conditions, when
-   overcommitting memory. There were no statistically significant
-   changes in wall time for the rest of the benchmark matrix.
-2. MariaDB [03] achieved 95% CIs [5.24, 10.71]% and [20.22, 25.97]%
-   more transactions per minute (TPM), respectively, under the medium-
-   and the high-concurrency conditions, when overcommitting memory.
-   There were no statistically significant changes in TPM for the rest
-   of the benchmark matrix.
-3. Memcached [04] achieved 95% CIs [23.54, 32.25]%, [20.76, 41.61]%
-   and [21.59, 30.02]% more operations per second (OPS), respectively,
-   for sequential access, random access and Gaussian (distribution)
-   access, when THP=always; 95% CIs [13.85, 15.97]% and
-   [23.94, 29.92]% more OPS, respectively, for random access and
-   Gaussian access, when THP=never. There were no statistically
-   significant changes in OPS for the rest of the benchmark matrix.
-4. MongoDB [05] achieved 95% CIs [2.23, 3.44]%, [6.97, 9.73]% and
-   [2.16, 3.55]% more operations per second (OPS), respectively, for
-   exponential (distribution) access, random access and Zipfian
-   (distribution) access, when underutilizing memory; 95% CIs
-   [8.83, 10.03]%, [21.12, 23.14]% and [5.53, 6.46]% more OPS,
-   respectively, for exponential access, random access and Zipfian
-   access, when overcommitting memory.
-
-On 5.15:
-5. Apache Cassandra [06] achieved 95% CIs [1.06, 4.10]%, [1.94, 5.43]%
-   and [4.11, 7.50]% more operations per second (OPS), respectively,
-   for exponential (distribution) access, random access and Zipfian
-   (distribution) access, when swap was off; 95% CIs [0.50, 2.60]%,
-   [6.51, 8.77]% and [3.29, 6.75]% more OPS, respectively, for
-   exponential access, random access and Zipfian access, when swap was
-   on.
-6. Apache Hadoop [07] took 95% CIs [5.31, 9.69]% and [2.02, 7.86]%
-   less average wall time to finish twelve parallel TeraSort jobs,
-   respectively, under the medium- and the high-concurrency
-   conditions, when swap was on. There were no statistically
-   significant changes in average wall time for the rest of the
-   benchmark matrix.
-7. PostgreSQL [08] achieved 95% CI [1.75, 6.42]% more transactions per
-   minute (TPM) under the high-concurrency condition, when swap was
-   off; 95% CIs [12.82, 18.69]% and [22.70, 46.86]% more TPM,
-   respectively, under the medium- and the high-concurrency
-   conditions, when swap was on. There were no statistically
-   significant changes in TPM for the rest of the benchmark matrix.
-8. Redis [09] achieved 95% CIs [0.58, 5.94]%, [6.55, 14.58]% and
-   [11.47, 19.36]% more total operations per second (OPS),
-   respectively, for sequential access, random access and Gaussian
-   (distribution) access, when THP=always; 95% CIs [1.27, 3.54]%,
-   [10.11, 14.81]% and [8.75, 13.64]% more total OPS, respectively,
-   for sequential access, random access and Gaussian access, when
-   THP=never.
-
-Our lab results
----------------
-To supplement the above results, we ran the following benchmark suites
-on 5.16-rc7 and found no regressions [10].
-      fs_fio_bench_hdd_mq      pft
-      fs_lmbench               pgsql-hammerdb
-      fs_parallelio            redis
-      fs_postmark              stream
-      hackbench                sysbenchthread
-      kernbench                tpcc_spark
-      memcached                unixbench
-      multichase               vm-scalability
-      mutilate                 will-it-scale
-      nginx
-
-[01] https://trends.google.com
-[02] https://lore.kernel.org/r/[email protected]/
-[03] https://lore.kernel.org/r/[email protected]/
-[04] https://lore.kernel.org/r/[email protected]/
-[05] https://lore.kernel.org/r/[email protected]/
-[06] https://lore.kernel.org/r/[email protected]/
-[07] https://lore.kernel.org/r/[email protected]/
-[08] https://lore.kernel.org/r/[email protected]/
-[09] https://lore.kernel.org/r/[email protected]/
-[10] https://lore.kernel.org/r/[email protected]/
-
-Read-world applications
-=======================
-Third-party testimonials
-------------------------
-Konstantin reported [11]:
-   I have Archlinux with 8G RAM + zswap + swap. While developing, I
-   have lots of apps opened such as multiple LSP-servers for different
-   langs, chats, two browsers, etc... Usually, my system gets quickly
-   to a point of SWAP-storms, where I have to kill LSP-servers,
-   restart browsers to free memory, etc, otherwise the system lags
-   heavily and is barely usable.
-
-   1.5 day ago I migrated from 5.11.15 kernel to 5.12 + the LRU
-   patchset, and I started up by opening lots of apps to create memory
-   pressure, and worked for a day like this. Till now I had not a
-   single SWAP-storm, and mind you I got 3.4G in SWAP. I was never
-   getting to the point of 3G in SWAP before without a single
-   SWAP-storm.
-
-Vaibhav from IBM reported [12]:
-   In a synthetic MongoDB Benchmark, seeing an average of ~19%
-   throughput improvement on POWER10(Radix MMU + 64K Page Size) with
-   MGLRU patches on top of 5.16 kernel for MongoDB + YCSB across
-   three different request distributions, namely, Exponential, Uniform
-   and Zipfan.
-
-Shuang from U of Rochester reported [13]:
-   With the MGLRU, fio achieved 95% CIs [38.95, 40.26]%, [4.12, 6.64]%
-   and [9.26, 10.36]% higher throughput, respectively, for random
-   access, Zipfian (distribution) access and Gaussian (distribution)
-   access, when the average number of jobs per CPU is 1; 95% CIs
-   [42.32, 49.15]%, [9.44, 9.89]% and [20.99, 22.86]% higher
-   throughput, respectively, for random access, Zipfian access and
-   Gaussian access, when the average number of jobs per CPU is 2.
-
-Daniel from Michigan Tech reported [14]:
-   With Memcached allocating ~100GB of byte-addressable Optante,
-   performance improvement in terms of throughput (measured as queries
-   per second) was about 10% for a series of workloads.
-
-Large-scale deployments
------------------------
-We've rolled out MGLRU to tens of millions of ChromeOS users and
-about a million Android users. Google's fleetwide profiling [15] shows
-an overall 40% decrease in kswapd CPU usage, in addition to
-improvements in other UX metrics, e.g., an 85% decrease in the number
-of low-memory kills at the 75th percentile and an 18% decrease in
-app launch time at the 50th percentile.
-
-The downstream kernels that have been using MGLRU include:
-1. Android [16]
-2. Arch Linux Zen [17]
-3. Armbian [18]
-4. ChromeOS [19]
-5. Liquorix [20]
-6. OpenWrt [21]
-7. post-factum [22]
-8. XanMod [23]
-
-[11] https://lore.kernel.org/r/[email protected]/
-[12] https://lore.kernel.org/r/[email protected]/
-[13] https://lore.kernel.org/r/[email protected]/
-[14] https://lore.kernel.org/r/CA+4-3vksGvKd18FgRinxhqHetBS1hQekJE2gwco8Ja-bJWKtFw@mail.gmail.com/
-[15] https://dl.acm.org/doi/10.1145/2749469.2750392
-[16] https://android.com
-[17] https://archlinux.org
-[18] https://armbian.com
-[19] https://chromium.org
-[20] https://liquorix.net
-[21] https://openwrt.org
-[22] https://codeberg.org/pf-kernel
-[23] https://xanmod.org
-
-Summary
-=======
-The facts are:
-1. The independent lab results and the real-world applications
-   indicate substantial improvements; there are no known regressions.
-2. Thrashing prevention, working set estimation and proactive reclaim
-   work out of the box; there are no equivalent solutions.
-3. There is a lot of new code; no smaller changes have been
-   demonstrated similar effects.
-
-Our options, accordingly, are:
-1. Given the amount of evidence, the reported improvements will likely
-   materialize for a wide range of workloads.
-2. Gauging the interest from the past discussions, the new features
-   will likely be put to use for both personal computers and data
-   centers.
-3. Based on Google's track record, the new code will likely be well
-   maintained in the long term. It'd be more difficult if not
-   impossible to achieve similar effects with other approaches.
-
-This patch (of 14):
-
-Some architectures automatically set the accessed bit in PTEs, e.g., x86
-and arm64 v8.2.  On architectures that do not have this capability,
-clearing the accessed bit in a PTE usually triggers a page fault following
-the TLB miss of this PTE (to emulate the accessed bit).
-
-Being aware of this capability can help make better decisions, e.g.,
-whether to spread the work out over a period of time to reduce bursty page
-faults when trying to clear the accessed bit in many PTEs.
-
-Note that theoretically this capability can be unreliable, e.g.,
-hotplugged CPUs might be different from builtin ones.  Therefore it should
-not be used in architecture-independent code that involves correctness,
-e.g., to determine whether TLB flushes are required (in combination with
-the accessed bit).
-
-Link: https://lkml.kernel.org/r/[email protected]
-Link: https://lkml.kernel.org/r/[email protected]
-Signed-off-by: Yu Zhao <[email protected]>
-Reviewed-by: Barry Song <[email protected]>
-Acked-by: Brian Geffon <[email protected]>
-Acked-by: Jan Alexander Steffens (heftig) <[email protected]>
-Acked-by: Oleksandr Natalenko <[email protected]>
-Acked-by: Steven Barrett <[email protected]>
-Acked-by: Suleiman Souhlal <[email protected]>
-Acked-by: Will Deacon <[email protected]>
-Tested-by: Daniel Byrne <[email protected]>
-Tested-by: Donald Carr <[email protected]>
-Tested-by: Holger Hoffstätte <[email protected]>
-Tested-by: Konstantin Kharlamov <[email protected]>
-Tested-by: Shuang Zhai <[email protected]>
-Tested-by: Sofia Trinh <[email protected]>
-Tested-by: Vaibhav Jain <[email protected]>
-Cc: Andi Kleen <[email protected]>
-Cc: Aneesh Kumar K.V <[email protected]>
-Cc: Catalin Marinas <[email protected]>
-Cc: Dave Hansen <[email protected]>
-Cc: Hillf Danton <[email protected]>
-Cc: Jens Axboe <[email protected]>
-Cc: Johannes Weiner <[email protected]>
-Cc: Jonathan Corbet <[email protected]>
-Cc: Linus Torvalds <[email protected]>
-Cc: Matthew Wilcox <[email protected]>
-Cc: Mel Gorman <[email protected]>
-Cc: Michael Larabel <[email protected]>
-Cc: Michal Hocko <[email protected]>
-Cc: Mike Rapoport <[email protected]>
-Cc: Peter Zijlstra <[email protected]>
-Cc: Tejun Heo <[email protected]>
-Cc: Vlastimil Babka <[email protected]>
-Cc: Miaohe Lin <[email protected]>
-Cc: Mike Rapoport <[email protected]>
-Cc: Qi Zheng <[email protected]>
-Signed-off-by: Andrew Morton <[email protected]>
----
- arch/arm64/include/asm/pgtable.h | 14 ++------------
- arch/x86/include/asm/pgtable.h   |  6 +++---
- include/linux/pgtable.h          | 13 +++++++++++++
- mm/memory.c                      | 14 +-------------
- 4 files changed, 19 insertions(+), 28 deletions(-)
-
---- a/arch/arm64/include/asm/pgtable.h
-+++ b/arch/arm64/include/asm/pgtable.h
-@@ -1005,23 +1005,13 @@ static inline void update_mmu_cache(stru
-  * page after fork() + CoW for pfn mappings. We don't always have a
-  * hardware-managed access flag on arm64.
-  */
--static inline bool arch_faults_on_old_pte(void)
--{
--      WARN_ON(preemptible());
--
--      return !cpu_has_hw_af();
--}
--#define arch_faults_on_old_pte                arch_faults_on_old_pte
-+#define arch_has_hw_pte_young         cpu_has_hw_af
- /*
-  * Experimentally, it's cheap to set the access flag in hardware and we
-  * benefit from prefaulting mappings as 'old' to start with.
-  */
--static inline bool arch_wants_old_prefaulted_pte(void)
--{
--      return !arch_faults_on_old_pte();
--}
--#define arch_wants_old_prefaulted_pte arch_wants_old_prefaulted_pte
-+#define arch_wants_old_prefaulted_pte cpu_has_hw_af
- #endif /* !__ASSEMBLY__ */
---- a/arch/x86/include/asm/pgtable.h
-+++ b/arch/x86/include/asm/pgtable.h
-@@ -1397,10 +1397,10 @@ static inline bool arch_has_pfn_modify_c
-       return boot_cpu_has_bug(X86_BUG_L1TF);
- }
--#define arch_faults_on_old_pte arch_faults_on_old_pte
--static inline bool arch_faults_on_old_pte(void)
-+#define arch_has_hw_pte_young arch_has_hw_pte_young
-+static inline bool arch_has_hw_pte_young(void)
- {
--      return false;
-+      return true;
- }
- #endif        /* __ASSEMBLY__ */
---- a/include/linux/pgtable.h
-+++ b/include/linux/pgtable.h
-@@ -259,6 +259,19 @@ static inline int pmdp_clear_flush_young
- #endif /* CONFIG_TRANSPARENT_HUGEPAGE */
- #endif
-+#ifndef arch_has_hw_pte_young
-+/*
-+ * Return whether the accessed bit is supported on the local CPU.
-+ *
-+ * This stub assumes accessing through an old PTE triggers a page fault.
-+ * Architectures that automatically set the access bit should overwrite it.
-+ */
-+static inline bool arch_has_hw_pte_young(void)
-+{
-+      return false;
-+}
-+#endif
-+
- #ifndef __HAVE_ARCH_PTEP_GET_AND_CLEAR
- static inline pte_t ptep_get_and_clear(struct mm_struct *mm,
-                                      unsigned long address,
---- a/mm/memory.c
-+++ b/mm/memory.c
-@@ -121,18 +121,6 @@ int randomize_va_space __read_mostly =
-                                       2;
- #endif
--#ifndef arch_faults_on_old_pte
--static inline bool arch_faults_on_old_pte(void)
--{
--      /*
--       * Those arches which don't have hw access flag feature need to
--       * implement their own helper. By default, "true" means pagefault
--       * will be hit on old pte.
--       */
--      return true;
--}
--#endif
--
- #ifndef arch_wants_old_prefaulted_pte
- static inline bool arch_wants_old_prefaulted_pte(void)
- {
-@@ -2791,7 +2779,7 @@ static inline int cow_user_page(struct p
-        * On architectures with software "accessed" bits, we would
-        * take a double page fault, so mark it accessed here.
-        */
--      if (arch_faults_on_old_pte() && !pte_young(vmf->orig_pte)) {
-+      if (!arch_has_hw_pte_young() && !pte_young(vmf->orig_pte)) {
-               pte_t entry;
-               vmf->pte = pte_offset_map_lock(mm, vmf->pmd, addr, &vmf->ptl);
diff --git a/target/linux/generic/backport-5.15/020-v6.1-02-mm-x86-add-CONFIG_ARCH_HAS_NONLEAF_PMD_YOUNG.patch b/target/linux/generic/backport-5.15/020-v6.1-02-mm-x86-add-CONFIG_ARCH_HAS_NONLEAF_PMD_YOUNG.patch
deleted file mode 100644 (file)
index 8e4de36..0000000
+++ /dev/null
@@ -1,153 +0,0 @@
-From 493de1c4b0f2cd909169401da8c445f6c8a7e29d Mon Sep 17 00:00:00 2001
-From: Yu Zhao <[email protected]>
-Date: Sun, 18 Sep 2022 01:59:59 -0600
-Subject: [PATCH 02/29] mm: x86: add CONFIG_ARCH_HAS_NONLEAF_PMD_YOUNG
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-Some architectures support the accessed bit in non-leaf PMD entries, e.g.,
-x86 sets the accessed bit in a non-leaf PMD entry when using it as part of
-linear address translation [1].  Page table walkers that clear the
-accessed bit may use this capability to reduce their search space.
-
-Note that:
-1. Although an inline function is preferable, this capability is added
-   as a configuration option for consistency with the existing macros.
-2. Due to the little interest in other varieties, this capability was
-   only tested on Intel and AMD CPUs.
-
-Thanks to the following developers for their efforts [2][3].
-  Randy Dunlap <[email protected]>
-  Stephen Rothwell <[email protected]>
-
-[1]: Intel 64 and IA-32 Architectures Software Developer's Manual
-     Volume 3 (June 2021), section 4.8
-[2] https://lore.kernel.org/r/[email protected]/
-[3] https://lore.kernel.org/r/[email protected]/
-
-Link: https://lkml.kernel.org/r/[email protected]
-Signed-off-by: Yu Zhao <[email protected]>
-Reviewed-by: Barry Song <[email protected]>
-Acked-by: Brian Geffon <[email protected]>
-Acked-by: Jan Alexander Steffens (heftig) <[email protected]>
-Acked-by: Oleksandr Natalenko <[email protected]>
-Acked-by: Steven Barrett <[email protected]>
-Acked-by: Suleiman Souhlal <[email protected]>
-Tested-by: Daniel Byrne <[email protected]>
-Tested-by: Donald Carr <[email protected]>
-Tested-by: Holger Hoffstätte <[email protected]>
-Tested-by: Konstantin Kharlamov <[email protected]>
-Tested-by: Shuang Zhai <[email protected]>
-Tested-by: Sofia Trinh <[email protected]>
-Tested-by: Vaibhav Jain <[email protected]>
-Cc: Andi Kleen <[email protected]>
-Cc: Aneesh Kumar K.V <[email protected]>
-Cc: Catalin Marinas <[email protected]>
-Cc: Dave Hansen <[email protected]>
-Cc: Hillf Danton <[email protected]>
-Cc: Jens Axboe <[email protected]>
-Cc: Johannes Weiner <[email protected]>
-Cc: Jonathan Corbet <[email protected]>
-Cc: Linus Torvalds <[email protected]>
-Cc: Matthew Wilcox <[email protected]>
-Cc: Mel Gorman <[email protected]>
-Cc: Miaohe Lin <[email protected]>
-Cc: Michael Larabel <[email protected]>
-Cc: Michal Hocko <[email protected]>
-Cc: Mike Rapoport <[email protected]>
-Cc: Mike Rapoport <[email protected]>
-Cc: Peter Zijlstra <[email protected]>
-Cc: Qi Zheng <[email protected]>
-Cc: Tejun Heo <[email protected]>
-Cc: Vlastimil Babka <[email protected]>
-Cc: Will Deacon <[email protected]>
-Signed-off-by: Andrew Morton <[email protected]>
----
- arch/Kconfig                   | 8 ++++++++
- arch/x86/Kconfig               | 1 +
- arch/x86/include/asm/pgtable.h | 3 ++-
- arch/x86/mm/pgtable.c          | 5 ++++-
- include/linux/pgtable.h        | 4 ++--
- 5 files changed, 17 insertions(+), 4 deletions(-)
-
---- a/arch/Kconfig
-+++ b/arch/Kconfig
-@@ -1307,6 +1307,14 @@ config ARCH_HAS_ELFCORE_COMPAT
- config ARCH_HAS_PARANOID_L1D_FLUSH
-       bool
-+config ARCH_HAS_NONLEAF_PMD_YOUNG
-+      bool
-+      help
-+        Architectures that select this option are capable of setting the
-+        accessed bit in non-leaf PMD entries when using them as part of linear
-+        address translations. Page table walkers that clear the accessed bit
-+        may use this capability to reduce their search space.
-+
- source "kernel/gcov/Kconfig"
- source "scripts/gcc-plugins/Kconfig"
---- a/arch/x86/Kconfig
-+++ b/arch/x86/Kconfig
-@@ -86,6 +86,7 @@ config X86
-       select ARCH_HAS_PMEM_API                if X86_64
-       select ARCH_HAS_PTE_DEVMAP              if X86_64
-       select ARCH_HAS_PTE_SPECIAL
-+      select ARCH_HAS_NONLEAF_PMD_YOUNG       if PGTABLE_LEVELS > 2
-       select ARCH_HAS_UACCESS_FLUSHCACHE      if X86_64
-       select ARCH_HAS_COPY_MC                 if X86_64
-       select ARCH_HAS_SET_MEMORY
---- a/arch/x86/include/asm/pgtable.h
-+++ b/arch/x86/include/asm/pgtable.h
-@@ -817,7 +817,8 @@ static inline unsigned long pmd_page_vad
- static inline int pmd_bad(pmd_t pmd)
- {
--      return (pmd_flags(pmd) & ~_PAGE_USER) != _KERNPG_TABLE;
-+      return (pmd_flags(pmd) & ~(_PAGE_USER | _PAGE_ACCESSED)) !=
-+             (_KERNPG_TABLE & ~_PAGE_ACCESSED);
- }
- static inline unsigned long pages_to_mb(unsigned long npg)
---- a/arch/x86/mm/pgtable.c
-+++ b/arch/x86/mm/pgtable.c
-@@ -550,7 +550,7 @@ int ptep_test_and_clear_young(struct vm_
-       return ret;
- }
--#ifdef CONFIG_TRANSPARENT_HUGEPAGE
-+#if defined(CONFIG_TRANSPARENT_HUGEPAGE) || defined(CONFIG_ARCH_HAS_NONLEAF_PMD_YOUNG)
- int pmdp_test_and_clear_young(struct vm_area_struct *vma,
-                             unsigned long addr, pmd_t *pmdp)
- {
-@@ -562,6 +562,9 @@ int pmdp_test_and_clear_young(struct vm_
-       return ret;
- }
-+#endif
-+
-+#ifdef CONFIG_TRANSPARENT_HUGEPAGE
- int pudp_test_and_clear_young(struct vm_area_struct *vma,
-                             unsigned long addr, pud_t *pudp)
- {
---- a/include/linux/pgtable.h
-+++ b/include/linux/pgtable.h
-@@ -212,7 +212,7 @@ static inline int ptep_test_and_clear_yo
- #endif
- #ifndef __HAVE_ARCH_PMDP_TEST_AND_CLEAR_YOUNG
--#ifdef CONFIG_TRANSPARENT_HUGEPAGE
-+#if defined(CONFIG_TRANSPARENT_HUGEPAGE) || defined(CONFIG_ARCH_HAS_NONLEAF_PMD_YOUNG)
- static inline int pmdp_test_and_clear_young(struct vm_area_struct *vma,
-                                           unsigned long address,
-                                           pmd_t *pmdp)
-@@ -233,7 +233,7 @@ static inline int pmdp_test_and_clear_yo
-       BUILD_BUG();
-       return 0;
- }
--#endif /* CONFIG_TRANSPARENT_HUGEPAGE */
-+#endif /* CONFIG_TRANSPARENT_HUGEPAGE || CONFIG_ARCH_HAS_NONLEAF_PMD_YOUNG */
- #endif
- #ifndef __HAVE_ARCH_PTEP_CLEAR_YOUNG_FLUSH
diff --git a/target/linux/generic/backport-5.15/020-v6.1-03-mm-vmscan.c-refactor-shrink_node.patch b/target/linux/generic/backport-5.15/020-v6.1-03-mm-vmscan.c-refactor-shrink_node.patch
deleted file mode 100644 (file)
index b8d2917..0000000
+++ /dev/null
@@ -1,275 +0,0 @@
-From 9e17efd11450d3d2069adaa3c58db9ac8ebd1c66 Mon Sep 17 00:00:00 2001
-From: Yu Zhao <[email protected]>
-Date: Sun, 18 Sep 2022 02:00:00 -0600
-Subject: [PATCH 03/29] mm/vmscan.c: refactor shrink_node()
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-This patch refactors shrink_node() to improve readability for the upcoming
-changes to mm/vmscan.c.
-
-Link: https://lkml.kernel.org/r/[email protected]
-Signed-off-by: Yu Zhao <[email protected]>
-Reviewed-by: Barry Song <[email protected]>
-Reviewed-by: Miaohe Lin <[email protected]>
-Acked-by: Brian Geffon <[email protected]>
-Acked-by: Jan Alexander Steffens (heftig) <[email protected]>
-Acked-by: Oleksandr Natalenko <[email protected]>
-Acked-by: Steven Barrett <[email protected]>
-Acked-by: Suleiman Souhlal <[email protected]>
-Tested-by: Daniel Byrne <[email protected]>
-Tested-by: Donald Carr <[email protected]>
-Tested-by: Holger Hoffstätte <[email protected]>
-Tested-by: Konstantin Kharlamov <[email protected]>
-Tested-by: Shuang Zhai <[email protected]>
-Tested-by: Sofia Trinh <[email protected]>
-Tested-by: Vaibhav Jain <[email protected]>
-Cc: Andi Kleen <[email protected]>
-Cc: Aneesh Kumar K.V <[email protected]>
-Cc: Catalin Marinas <[email protected]>
-Cc: Dave Hansen <[email protected]>
-Cc: Hillf Danton <[email protected]>
-Cc: Jens Axboe <[email protected]>
-Cc: Johannes Weiner <[email protected]>
-Cc: Jonathan Corbet <[email protected]>
-Cc: Linus Torvalds <[email protected]>
-Cc: Matthew Wilcox <[email protected]>
-Cc: Mel Gorman <[email protected]>
-Cc: Michael Larabel <[email protected]>
-Cc: Michal Hocko <[email protected]>
-Cc: Mike Rapoport <[email protected]>
-Cc: Mike Rapoport <[email protected]>
-Cc: Peter Zijlstra <[email protected]>
-Cc: Qi Zheng <[email protected]>
-Cc: Tejun Heo <[email protected]>
-Cc: Vlastimil Babka <[email protected]>
-Cc: Will Deacon <[email protected]>
-Signed-off-by: Andrew Morton <[email protected]>
----
- mm/vmscan.c | 198 +++++++++++++++++++++++++++-------------------------
- 1 file changed, 104 insertions(+), 94 deletions(-)
-
---- a/mm/vmscan.c
-+++ b/mm/vmscan.c
-@@ -2497,6 +2497,109 @@ enum scan_balance {
-       SCAN_FILE,
- };
-+static void prepare_scan_count(pg_data_t *pgdat, struct scan_control *sc)
-+{
-+      unsigned long file;
-+      struct lruvec *target_lruvec;
-+
-+      target_lruvec = mem_cgroup_lruvec(sc->target_mem_cgroup, pgdat);
-+
-+      /*
-+       * Flush the memory cgroup stats, so that we read accurate per-memcg
-+       * lruvec stats for heuristics.
-+       */
-+      mem_cgroup_flush_stats();
-+
-+      /*
-+       * Determine the scan balance between anon and file LRUs.
-+       */
-+      spin_lock_irq(&target_lruvec->lru_lock);
-+      sc->anon_cost = target_lruvec->anon_cost;
-+      sc->file_cost = target_lruvec->file_cost;
-+      spin_unlock_irq(&target_lruvec->lru_lock);
-+
-+      /*
-+       * Target desirable inactive:active list ratios for the anon
-+       * and file LRU lists.
-+       */
-+      if (!sc->force_deactivate) {
-+              unsigned long refaults;
-+
-+              refaults = lruvec_page_state(target_lruvec,
-+                              WORKINGSET_ACTIVATE_ANON);
-+              if (refaults != target_lruvec->refaults[0] ||
-+                      inactive_is_low(target_lruvec, LRU_INACTIVE_ANON))
-+                      sc->may_deactivate |= DEACTIVATE_ANON;
-+              else
-+                      sc->may_deactivate &= ~DEACTIVATE_ANON;
-+
-+              /*
-+               * When refaults are being observed, it means a new
-+               * workingset is being established. Deactivate to get
-+               * rid of any stale active pages quickly.
-+               */
-+              refaults = lruvec_page_state(target_lruvec,
-+                              WORKINGSET_ACTIVATE_FILE);
-+              if (refaults != target_lruvec->refaults[1] ||
-+                  inactive_is_low(target_lruvec, LRU_INACTIVE_FILE))
-+                      sc->may_deactivate |= DEACTIVATE_FILE;
-+              else
-+                      sc->may_deactivate &= ~DEACTIVATE_FILE;
-+      } else
-+              sc->may_deactivate = DEACTIVATE_ANON | DEACTIVATE_FILE;
-+
-+      /*
-+       * If we have plenty of inactive file pages that aren't
-+       * thrashing, try to reclaim those first before touching
-+       * anonymous pages.
-+       */
-+      file = lruvec_page_state(target_lruvec, NR_INACTIVE_FILE);
-+      if (file >> sc->priority && !(sc->may_deactivate & DEACTIVATE_FILE))
-+              sc->cache_trim_mode = 1;
-+      else
-+              sc->cache_trim_mode = 0;
-+
-+      /*
-+       * Prevent the reclaimer from falling into the cache trap: as
-+       * cache pages start out inactive, every cache fault will tip
-+       * the scan balance towards the file LRU.  And as the file LRU
-+       * shrinks, so does the window for rotation from references.
-+       * This means we have a runaway feedback loop where a tiny
-+       * thrashing file LRU becomes infinitely more attractive than
-+       * anon pages.  Try to detect this based on file LRU size.
-+       */
-+      if (!cgroup_reclaim(sc)) {
-+              unsigned long total_high_wmark = 0;
-+              unsigned long free, anon;
-+              int z;
-+
-+              free = sum_zone_node_page_state(pgdat->node_id, NR_FREE_PAGES);
-+              file = node_page_state(pgdat, NR_ACTIVE_FILE) +
-+                         node_page_state(pgdat, NR_INACTIVE_FILE);
-+
-+              for (z = 0; z < MAX_NR_ZONES; z++) {
-+                      struct zone *zone = &pgdat->node_zones[z];
-+
-+                      if (!managed_zone(zone))
-+                              continue;
-+
-+                      total_high_wmark += high_wmark_pages(zone);
-+              }
-+
-+              /*
-+               * Consider anon: if that's low too, this isn't a
-+               * runaway file reclaim problem, but rather just
-+               * extreme pressure. Reclaim as per usual then.
-+               */
-+              anon = node_page_state(pgdat, NR_INACTIVE_ANON);
-+
-+              sc->file_is_tiny =
-+                      file + free <= total_high_wmark &&
-+                      !(sc->may_deactivate & DEACTIVATE_ANON) &&
-+                      anon >> sc->priority;
-+      }
-+}
-+
- /*
-  * Determine how aggressively the anon and file LRU lists should be
-  * scanned.  The relative value of each set of LRU lists is determined
-@@ -2965,109 +3068,16 @@ static void shrink_node(pg_data_t *pgdat
-       unsigned long nr_reclaimed, nr_scanned;
-       struct lruvec *target_lruvec;
-       bool reclaimable = false;
--      unsigned long file;
-       target_lruvec = mem_cgroup_lruvec(sc->target_mem_cgroup, pgdat);
- again:
--      /*
--       * Flush the memory cgroup stats, so that we read accurate per-memcg
--       * lruvec stats for heuristics.
--       */
--      mem_cgroup_flush_stats();
--
-       memset(&sc->nr, 0, sizeof(sc->nr));
-       nr_reclaimed = sc->nr_reclaimed;
-       nr_scanned = sc->nr_scanned;
--      /*
--       * Determine the scan balance between anon and file LRUs.
--       */
--      spin_lock_irq(&target_lruvec->lru_lock);
--      sc->anon_cost = target_lruvec->anon_cost;
--      sc->file_cost = target_lruvec->file_cost;
--      spin_unlock_irq(&target_lruvec->lru_lock);
--
--      /*
--       * Target desirable inactive:active list ratios for the anon
--       * and file LRU lists.
--       */
--      if (!sc->force_deactivate) {
--              unsigned long refaults;
--
--              refaults = lruvec_page_state(target_lruvec,
--                              WORKINGSET_ACTIVATE_ANON);
--              if (refaults != target_lruvec->refaults[0] ||
--                      inactive_is_low(target_lruvec, LRU_INACTIVE_ANON))
--                      sc->may_deactivate |= DEACTIVATE_ANON;
--              else
--                      sc->may_deactivate &= ~DEACTIVATE_ANON;
--
--              /*
--               * When refaults are being observed, it means a new
--               * workingset is being established. Deactivate to get
--               * rid of any stale active pages quickly.
--               */
--              refaults = lruvec_page_state(target_lruvec,
--                              WORKINGSET_ACTIVATE_FILE);
--              if (refaults != target_lruvec->refaults[1] ||
--                  inactive_is_low(target_lruvec, LRU_INACTIVE_FILE))
--                      sc->may_deactivate |= DEACTIVATE_FILE;
--              else
--                      sc->may_deactivate &= ~DEACTIVATE_FILE;
--      } else
--              sc->may_deactivate = DEACTIVATE_ANON | DEACTIVATE_FILE;
--
--      /*
--       * If we have plenty of inactive file pages that aren't
--       * thrashing, try to reclaim those first before touching
--       * anonymous pages.
--       */
--      file = lruvec_page_state(target_lruvec, NR_INACTIVE_FILE);
--      if (file >> sc->priority && !(sc->may_deactivate & DEACTIVATE_FILE))
--              sc->cache_trim_mode = 1;
--      else
--              sc->cache_trim_mode = 0;
--
--      /*
--       * Prevent the reclaimer from falling into the cache trap: as
--       * cache pages start out inactive, every cache fault will tip
--       * the scan balance towards the file LRU.  And as the file LRU
--       * shrinks, so does the window for rotation from references.
--       * This means we have a runaway feedback loop where a tiny
--       * thrashing file LRU becomes infinitely more attractive than
--       * anon pages.  Try to detect this based on file LRU size.
--       */
--      if (!cgroup_reclaim(sc)) {
--              unsigned long total_high_wmark = 0;
--              unsigned long free, anon;
--              int z;
--
--              free = sum_zone_node_page_state(pgdat->node_id, NR_FREE_PAGES);
--              file = node_page_state(pgdat, NR_ACTIVE_FILE) +
--                         node_page_state(pgdat, NR_INACTIVE_FILE);
--
--              for (z = 0; z < MAX_NR_ZONES; z++) {
--                      struct zone *zone = &pgdat->node_zones[z];
--                      if (!managed_zone(zone))
--                              continue;
--
--                      total_high_wmark += high_wmark_pages(zone);
--              }
--
--              /*
--               * Consider anon: if that's low too, this isn't a
--               * runaway file reclaim problem, but rather just
--               * extreme pressure. Reclaim as per usual then.
--               */
--              anon = node_page_state(pgdat, NR_INACTIVE_ANON);
--
--              sc->file_is_tiny =
--                      file + free <= total_high_wmark &&
--                      !(sc->may_deactivate & DEACTIVATE_ANON) &&
--                      anon >> sc->priority;
--      }
-+      prepare_scan_count(pgdat, sc);
-       shrink_node_memcgs(pgdat, sc);
diff --git a/target/linux/generic/backport-5.15/020-v6.1-04-Revert-include-linux-mm_inline.h-fold-__update_lru_s.patch b/target/linux/generic/backport-5.15/020-v6.1-04-Revert-include-linux-mm_inline.h-fold-__update_lru_s.patch
deleted file mode 100644 (file)
index 2f277a5..0000000
+++ /dev/null
@@ -1,82 +0,0 @@
-From 03705be42114db7cc5bd6eb7bf7e8703c94d4880 Mon Sep 17 00:00:00 2001
-From: Yu Zhao <[email protected]>
-Date: Sun, 18 Sep 2022 02:00:01 -0600
-Subject: [PATCH 04/29] Revert "include/linux/mm_inline.h: fold
- __update_lru_size() into its sole caller"
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-This patch undoes the following refactor: commit 289ccba18af4
-("include/linux/mm_inline.h: fold __update_lru_size() into its sole
-caller")
-
-The upcoming changes to include/linux/mm_inline.h will reuse
-__update_lru_size().
-
-Link: https://lkml.kernel.org/r/[email protected]
-Signed-off-by: Yu Zhao <[email protected]>
-Reviewed-by: Miaohe Lin <[email protected]>
-Acked-by: Brian Geffon <[email protected]>
-Acked-by: Jan Alexander Steffens (heftig) <[email protected]>
-Acked-by: Oleksandr Natalenko <[email protected]>
-Acked-by: Steven Barrett <[email protected]>
-Acked-by: Suleiman Souhlal <[email protected]>
-Tested-by: Daniel Byrne <[email protected]>
-Tested-by: Donald Carr <[email protected]>
-Tested-by: Holger Hoffstätte <[email protected]>
-Tested-by: Konstantin Kharlamov <[email protected]>
-Tested-by: Shuang Zhai <[email protected]>
-Tested-by: Sofia Trinh <[email protected]>
-Tested-by: Vaibhav Jain <[email protected]>
-Cc: Andi Kleen <[email protected]>
-Cc: Aneesh Kumar K.V <[email protected]>
-Cc: Barry Song <[email protected]>
-Cc: Catalin Marinas <[email protected]>
-Cc: Dave Hansen <[email protected]>
-Cc: Hillf Danton <[email protected]>
-Cc: Jens Axboe <[email protected]>
-Cc: Johannes Weiner <[email protected]>
-Cc: Jonathan Corbet <[email protected]>
-Cc: Linus Torvalds <[email protected]>
-Cc: Matthew Wilcox <[email protected]>
-Cc: Mel Gorman <[email protected]>
-Cc: Michael Larabel <[email protected]>
-Cc: Michal Hocko <[email protected]>
-Cc: Mike Rapoport <[email protected]>
-Cc: Mike Rapoport <[email protected]>
-Cc: Peter Zijlstra <[email protected]>
-Cc: Qi Zheng <[email protected]>
-Cc: Tejun Heo <[email protected]>
-Cc: Vlastimil Babka <[email protected]>
-Cc: Will Deacon <[email protected]>
-Signed-off-by: Andrew Morton <[email protected]>
----
- include/linux/mm_inline.h | 9 ++++++++-
- 1 file changed, 8 insertions(+), 1 deletion(-)
-
---- a/include/linux/mm_inline.h
-+++ b/include/linux/mm_inline.h
-@@ -24,7 +24,7 @@ static inline int page_is_file_lru(struc
-       return !PageSwapBacked(page);
- }
--static __always_inline void update_lru_size(struct lruvec *lruvec,
-+static __always_inline void __update_lru_size(struct lruvec *lruvec,
-                               enum lru_list lru, enum zone_type zid,
-                               int nr_pages)
- {
-@@ -33,6 +33,13 @@ static __always_inline void update_lru_s
-       __mod_lruvec_state(lruvec, NR_LRU_BASE + lru, nr_pages);
-       __mod_zone_page_state(&pgdat->node_zones[zid],
-                               NR_ZONE_LRU_BASE + lru, nr_pages);
-+}
-+
-+static __always_inline void update_lru_size(struct lruvec *lruvec,
-+                              enum lru_list lru, enum zone_type zid,
-+                              long nr_pages)
-+{
-+      __update_lru_size(lruvec, lru, zid, nr_pages);
- #ifdef CONFIG_MEMCG
-       mem_cgroup_update_lru_size(lruvec, lru, zid, nr_pages);
- #endif
diff --git a/target/linux/generic/backport-5.15/020-v6.1-05-mm-multi-gen-LRU-groundwork.patch b/target/linux/generic/backport-5.15/020-v6.1-05-mm-multi-gen-LRU-groundwork.patch
deleted file mode 100644 (file)
index ff4bb4d..0000000
+++ /dev/null
@@ -1,807 +0,0 @@
-From a9b328add8422921a0dbbef162730800e16e8cfd Mon Sep 17 00:00:00 2001
-From: Yu Zhao <[email protected]>
-Date: Sun, 18 Sep 2022 02:00:02 -0600
-Subject: [PATCH 05/29] mm: multi-gen LRU: groundwork
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-Evictable pages are divided into multiple generations for each lruvec.
-The youngest generation number is stored in lrugen->max_seq for both
-anon and file types as they are aged on an equal footing. The oldest
-generation numbers are stored in lrugen->min_seq[] separately for anon
-and file types as clean file pages can be evicted regardless of swap
-constraints. These three variables are monotonically increasing.
-
-Generation numbers are truncated into order_base_2(MAX_NR_GENS+1) bits
-in order to fit into the gen counter in page->flags. Each truncated
-generation number is an index to lrugen->lists[]. The sliding window
-technique is used to track at least MIN_NR_GENS and at most
-MAX_NR_GENS generations. The gen counter stores a value within [1,
-MAX_NR_GENS] while a page is on one of lrugen->lists[]. Otherwise it
-stores 0.
-
-There are two conceptually independent procedures: "the aging", which
-produces young generations, and "the eviction", which consumes old
-generations.  They form a closed-loop system, i.e., "the page reclaim".
-Both procedures can be invoked from userspace for the purposes of working
-set estimation and proactive reclaim.  These techniques are commonly used
-to optimize job scheduling (bin packing) in data centers [1][2].
-
-To avoid confusion, the terms "hot" and "cold" will be applied to the
-multi-gen LRU, as a new convention; the terms "active" and "inactive" will
-be applied to the active/inactive LRU, as usual.
-
-The protection of hot pages and the selection of cold pages are based
-on page access channels and patterns. There are two access channels:
-one through page tables and the other through file descriptors. The
-protection of the former channel is by design stronger because:
-1. The uncertainty in determining the access patterns of the former
-   channel is higher due to the approximation of the accessed bit.
-2. The cost of evicting the former channel is higher due to the TLB
-   flushes required and the likelihood of encountering the dirty bit.
-3. The penalty of underprotecting the former channel is higher because
-   applications usually do not prepare themselves for major page
-   faults like they do for blocked I/O. E.g., GUI applications
-   commonly use dedicated I/O threads to avoid blocking rendering
-   threads.
-
-There are also two access patterns: one with temporal locality and the
-other without.  For the reasons listed above, the former channel is
-assumed to follow the former pattern unless VM_SEQ_READ or VM_RAND_READ is
-present; the latter channel is assumed to follow the latter pattern unless
-outlying refaults have been observed [3][4].
-
-The next patch will address the "outlying refaults".  Three macros, i.e.,
-LRU_REFS_WIDTH, LRU_REFS_PGOFF and LRU_REFS_MASK, used later are added in
-this patch to make the entire patchset less diffy.
-
-A page is added to the youngest generation on faulting.  The aging needs
-to check the accessed bit at least twice before handing this page over to
-the eviction.  The first check takes care of the accessed bit set on the
-initial fault; the second check makes sure this page has not been used
-since then.  This protocol, AKA second chance, requires a minimum of two
-generations, hence MIN_NR_GENS.
-
-[1] https://dl.acm.org/doi/10.1145/3297858.3304053
-[2] https://dl.acm.org/doi/10.1145/3503222.3507731
-[3] https://lwn.net/Articles/495543/
-[4] https://lwn.net/Articles/815342/
-
-Link: https://lkml.kernel.org/r/[email protected]
-Signed-off-by: Yu Zhao <[email protected]>
-Acked-by: Brian Geffon <[email protected]>
-Acked-by: Jan Alexander Steffens (heftig) <[email protected]>
-Acked-by: Oleksandr Natalenko <[email protected]>
-Acked-by: Steven Barrett <[email protected]>
-Acked-by: Suleiman Souhlal <[email protected]>
-Tested-by: Daniel Byrne <[email protected]>
-Tested-by: Donald Carr <[email protected]>
-Tested-by: Holger Hoffstätte <[email protected]>
-Tested-by: Konstantin Kharlamov <[email protected]>
-Tested-by: Shuang Zhai <[email protected]>
-Tested-by: Sofia Trinh <[email protected]>
-Tested-by: Vaibhav Jain <[email protected]>
-Cc: Andi Kleen <[email protected]>
-Cc: Aneesh Kumar K.V <[email protected]>
-Cc: Barry Song <[email protected]>
-Cc: Catalin Marinas <[email protected]>
-Cc: Dave Hansen <[email protected]>
-Cc: Hillf Danton <[email protected]>
-Cc: Jens Axboe <[email protected]>
-Cc: Johannes Weiner <[email protected]>
-Cc: Jonathan Corbet <[email protected]>
-Cc: Linus Torvalds <[email protected]>
-Cc: Matthew Wilcox <[email protected]>
-Cc: Mel Gorman <[email protected]>
-Cc: Miaohe Lin <[email protected]>
-Cc: Michael Larabel <[email protected]>
-Cc: Michal Hocko <[email protected]>
-Cc: Mike Rapoport <[email protected]>
-Cc: Mike Rapoport <[email protected]>
-Cc: Peter Zijlstra <[email protected]>
-Cc: Qi Zheng <[email protected]>
-Cc: Tejun Heo <[email protected]>
-Cc: Vlastimil Babka <[email protected]>
-Cc: Will Deacon <[email protected]>
-Signed-off-by: Andrew Morton <[email protected]>
----
- fs/fuse/dev.c                     |   3 +-
- include/linux/mm.h                |   2 +
- include/linux/mm_inline.h         | 177 +++++++++++++++++++++++++++++-
- include/linux/mmzone.h            | 100 +++++++++++++++++
- include/linux/page-flags-layout.h |  13 ++-
- include/linux/page-flags.h        |   4 +-
- include/linux/sched.h             |   4 +
- kernel/bounds.c                   |   5 +
- mm/Kconfig                        |   8 ++
- mm/huge_memory.c                  |   3 +-
- mm/memcontrol.c                   |   2 +
- mm/memory.c                       |  25 +++++
- mm/mm_init.c                      |   6 +-
- mm/mmzone.c                       |   2 +
- mm/swap.c                         |  10 +-
- mm/vmscan.c                       |  75 +++++++++++++
- 16 files changed, 425 insertions(+), 14 deletions(-)
-
---- a/fs/fuse/dev.c
-+++ b/fs/fuse/dev.c
-@@ -785,7 +785,8 @@ static int fuse_check_page(struct page *
-              1 << PG_active |
-              1 << PG_workingset |
-              1 << PG_reclaim |
--             1 << PG_waiters))) {
-+             1 << PG_waiters |
-+             LRU_GEN_MASK | LRU_REFS_MASK))) {
-               dump_page(page, "fuse: trying to steal weird page");
-               return 1;
-       }
---- a/include/linux/mm.h
-+++ b/include/linux/mm.h
-@@ -1093,6 +1093,8 @@ vm_fault_t finish_mkwrite_fault(struct v
- #define ZONES_PGOFF           (NODES_PGOFF - ZONES_WIDTH)
- #define LAST_CPUPID_PGOFF     (ZONES_PGOFF - LAST_CPUPID_WIDTH)
- #define KASAN_TAG_PGOFF               (LAST_CPUPID_PGOFF - KASAN_TAG_WIDTH)
-+#define LRU_GEN_PGOFF         (KASAN_TAG_PGOFF - LRU_GEN_WIDTH)
-+#define LRU_REFS_PGOFF                (LRU_GEN_PGOFF - LRU_REFS_WIDTH)
- /*
-  * Define the bit shifts to access each section.  For non-existent
---- a/include/linux/mm_inline.h
-+++ b/include/linux/mm_inline.h
-@@ -26,10 +26,13 @@ static inline int page_is_file_lru(struc
- static __always_inline void __update_lru_size(struct lruvec *lruvec,
-                               enum lru_list lru, enum zone_type zid,
--                              int nr_pages)
-+                              long nr_pages)
- {
-       struct pglist_data *pgdat = lruvec_pgdat(lruvec);
-+      lockdep_assert_held(&lruvec->lru_lock);
-+      WARN_ON_ONCE(nr_pages != (int)nr_pages);
-+
-       __mod_lruvec_state(lruvec, NR_LRU_BASE + lru, nr_pages);
-       __mod_zone_page_state(&pgdat->node_zones[zid],
-                               NR_ZONE_LRU_BASE + lru, nr_pages);
-@@ -86,11 +89,177 @@ static __always_inline enum lru_list pag
-       return lru;
- }
-+#ifdef CONFIG_LRU_GEN
-+
-+static inline bool lru_gen_enabled(void)
-+{
-+      return true;
-+}
-+
-+static inline bool lru_gen_in_fault(void)
-+{
-+      return current->in_lru_fault;
-+}
-+
-+static inline int lru_gen_from_seq(unsigned long seq)
-+{
-+      return seq % MAX_NR_GENS;
-+}
-+
-+static inline int page_lru_gen(struct page *page)
-+{
-+      unsigned long flags = READ_ONCE(page->flags);
-+
-+      return ((flags & LRU_GEN_MASK) >> LRU_GEN_PGOFF) - 1;
-+}
-+
-+static inline bool lru_gen_is_active(struct lruvec *lruvec, int gen)
-+{
-+      unsigned long max_seq = lruvec->lrugen.max_seq;
-+
-+      VM_WARN_ON_ONCE(gen >= MAX_NR_GENS);
-+
-+      /* see the comment on MIN_NR_GENS */
-+      return gen == lru_gen_from_seq(max_seq) || gen == lru_gen_from_seq(max_seq - 1);
-+}
-+
-+static inline void lru_gen_update_size(struct lruvec *lruvec, struct page *page,
-+                                     int old_gen, int new_gen)
-+{
-+      int type = page_is_file_lru(page);
-+      int zone = page_zonenum(page);
-+      int delta = thp_nr_pages(page);
-+      enum lru_list lru = type * LRU_INACTIVE_FILE;
-+      struct lru_gen_struct *lrugen = &lruvec->lrugen;
-+
-+      VM_WARN_ON_ONCE(old_gen != -1 && old_gen >= MAX_NR_GENS);
-+      VM_WARN_ON_ONCE(new_gen != -1 && new_gen >= MAX_NR_GENS);
-+      VM_WARN_ON_ONCE(old_gen == -1 && new_gen == -1);
-+
-+      if (old_gen >= 0)
-+              WRITE_ONCE(lrugen->nr_pages[old_gen][type][zone],
-+                         lrugen->nr_pages[old_gen][type][zone] - delta);
-+      if (new_gen >= 0)
-+              WRITE_ONCE(lrugen->nr_pages[new_gen][type][zone],
-+                         lrugen->nr_pages[new_gen][type][zone] + delta);
-+
-+      /* addition */
-+      if (old_gen < 0) {
-+              if (lru_gen_is_active(lruvec, new_gen))
-+                      lru += LRU_ACTIVE;
-+              __update_lru_size(lruvec, lru, zone, delta);
-+              return;
-+      }
-+
-+      /* deletion */
-+      if (new_gen < 0) {
-+              if (lru_gen_is_active(lruvec, old_gen))
-+                      lru += LRU_ACTIVE;
-+              __update_lru_size(lruvec, lru, zone, -delta);
-+              return;
-+      }
-+}
-+
-+static inline bool lru_gen_add_page(struct lruvec *lruvec, struct page *page, bool reclaiming)
-+{
-+      unsigned long seq;
-+      unsigned long flags;
-+      int gen = page_lru_gen(page);
-+      int type = page_is_file_lru(page);
-+      int zone = page_zonenum(page);
-+      struct lru_gen_struct *lrugen = &lruvec->lrugen;
-+
-+      VM_WARN_ON_ONCE_PAGE(gen != -1, page);
-+
-+      if (PageUnevictable(page))
-+              return false;
-+      /*
-+       * There are three common cases for this page:
-+       * 1. If it's hot, e.g., freshly faulted in or previously hot and
-+       *    migrated, add it to the youngest generation.
-+       * 2. If it's cold but can't be evicted immediately, i.e., an anon page
-+       *    not in swapcache or a dirty page pending writeback, add it to the
-+       *    second oldest generation.
-+       * 3. Everything else (clean, cold) is added to the oldest generation.
-+       */
-+      if (PageActive(page))
-+              seq = lrugen->max_seq;
-+      else if ((type == LRU_GEN_ANON && !PageSwapCache(page)) ||
-+               (PageReclaim(page) &&
-+                (PageDirty(page) || PageWriteback(page))))
-+              seq = lrugen->min_seq[type] + 1;
-+      else
-+              seq = lrugen->min_seq[type];
-+
-+      gen = lru_gen_from_seq(seq);
-+      flags = (gen + 1UL) << LRU_GEN_PGOFF;
-+      /* see the comment on MIN_NR_GENS about PG_active */
-+      set_mask_bits(&page->flags, LRU_GEN_MASK | BIT(PG_active), flags);
-+
-+      lru_gen_update_size(lruvec, page, -1, gen);
-+      /* for rotate_reclaimable_page() */
-+      if (reclaiming)
-+              list_add_tail(&page->lru, &lrugen->lists[gen][type][zone]);
-+      else
-+              list_add(&page->lru, &lrugen->lists[gen][type][zone]);
-+
-+      return true;
-+}
-+
-+static inline bool lru_gen_del_page(struct lruvec *lruvec, struct page *page, bool reclaiming)
-+{
-+      unsigned long flags;
-+      int gen = page_lru_gen(page);
-+
-+      if (gen < 0)
-+              return false;
-+
-+      VM_WARN_ON_ONCE_PAGE(PageActive(page), page);
-+      VM_WARN_ON_ONCE_PAGE(PageUnevictable(page), page);
-+
-+      /* for migrate_page_states() */
-+      flags = !reclaiming && lru_gen_is_active(lruvec, gen) ? BIT(PG_active) : 0;
-+      flags = set_mask_bits(&page->flags, LRU_GEN_MASK, flags);
-+      gen = ((flags & LRU_GEN_MASK) >> LRU_GEN_PGOFF) - 1;
-+
-+      lru_gen_update_size(lruvec, page, gen, -1);
-+      list_del(&page->lru);
-+
-+      return true;
-+}
-+
-+#else /* !CONFIG_LRU_GEN */
-+
-+static inline bool lru_gen_enabled(void)
-+{
-+      return false;
-+}
-+
-+static inline bool lru_gen_in_fault(void)
-+{
-+      return false;
-+}
-+
-+static inline bool lru_gen_add_page(struct lruvec *lruvec, struct page *page, bool reclaiming)
-+{
-+      return false;
-+}
-+
-+static inline bool lru_gen_del_page(struct lruvec *lruvec, struct page *page, bool reclaiming)
-+{
-+      return false;
-+}
-+
-+#endif /* CONFIG_LRU_GEN */
-+
- static __always_inline void add_page_to_lru_list(struct page *page,
-                               struct lruvec *lruvec)
- {
-       enum lru_list lru = page_lru(page);
-+      if (lru_gen_add_page(lruvec, page, false))
-+              return;
-+
-       update_lru_size(lruvec, lru, page_zonenum(page), thp_nr_pages(page));
-       list_add(&page->lru, &lruvec->lists[lru]);
- }
-@@ -100,6 +269,9 @@ static __always_inline void add_page_to_
- {
-       enum lru_list lru = page_lru(page);
-+      if (lru_gen_add_page(lruvec, page, true))
-+              return;
-+
-       update_lru_size(lruvec, lru, page_zonenum(page), thp_nr_pages(page));
-       list_add_tail(&page->lru, &lruvec->lists[lru]);
- }
-@@ -107,6 +279,9 @@ static __always_inline void add_page_to_
- static __always_inline void del_page_from_lru_list(struct page *page,
-                               struct lruvec *lruvec)
- {
-+      if (lru_gen_del_page(lruvec, page, false))
-+              return;
-+
-       list_del(&page->lru);
-       update_lru_size(lruvec, page_lru(page), page_zonenum(page),
-                       -thp_nr_pages(page));
---- a/include/linux/mmzone.h
-+++ b/include/linux/mmzone.h
-@@ -294,6 +294,102 @@ enum lruvec_flags {
-                                        */
- };
-+#endif /* !__GENERATING_BOUNDS_H */
-+
-+/*
-+ * Evictable pages are divided into multiple generations. The youngest and the
-+ * oldest generation numbers, max_seq and min_seq, are monotonically increasing.
-+ * They form a sliding window of a variable size [MIN_NR_GENS, MAX_NR_GENS]. An
-+ * offset within MAX_NR_GENS, i.e., gen, indexes the LRU list of the
-+ * corresponding generation. The gen counter in page->flags stores gen+1 while
-+ * a page is on one of lrugen->lists[]. Otherwise it stores 0.
-+ *
-+ * A page is added to the youngest generation on faulting. The aging needs to
-+ * check the accessed bit at least twice before handing this page over to the
-+ * eviction. The first check takes care of the accessed bit set on the initial
-+ * fault; the second check makes sure this page hasn't been used since then.
-+ * This process, AKA second chance, requires a minimum of two generations,
-+ * hence MIN_NR_GENS. And to maintain ABI compatibility with the active/inactive
-+ * LRU, e.g., /proc/vmstat, these two generations are considered active; the
-+ * rest of generations, if they exist, are considered inactive. See
-+ * lru_gen_is_active().
-+ *
-+ * PG_active is always cleared while a page is on one of lrugen->lists[] so that
-+ * the aging needs not to worry about it. And it's set again when a page
-+ * considered active is isolated for non-reclaiming purposes, e.g., migration.
-+ * See lru_gen_add_page() and lru_gen_del_page().
-+ *
-+ * MAX_NR_GENS is set to 4 so that the multi-gen LRU can support twice the
-+ * number of categories of the active/inactive LRU when keeping track of
-+ * accesses through page tables. This requires order_base_2(MAX_NR_GENS+1) bits
-+ * in page->flags.
-+ */
-+#define MIN_NR_GENS           2U
-+#define MAX_NR_GENS           4U
-+
-+#ifndef __GENERATING_BOUNDS_H
-+
-+struct lruvec;
-+
-+#define LRU_GEN_MASK          ((BIT(LRU_GEN_WIDTH) - 1) << LRU_GEN_PGOFF)
-+#define LRU_REFS_MASK         ((BIT(LRU_REFS_WIDTH) - 1) << LRU_REFS_PGOFF)
-+
-+#ifdef CONFIG_LRU_GEN
-+
-+enum {
-+      LRU_GEN_ANON,
-+      LRU_GEN_FILE,
-+};
-+
-+/*
-+ * The youngest generation number is stored in max_seq for both anon and file
-+ * types as they are aged on an equal footing. The oldest generation numbers are
-+ * stored in min_seq[] separately for anon and file types as clean file pages
-+ * can be evicted regardless of swap constraints.
-+ *
-+ * Normally anon and file min_seq are in sync. But if swapping is constrained,
-+ * e.g., out of swap space, file min_seq is allowed to advance and leave anon
-+ * min_seq behind.
-+ *
-+ * The number of pages in each generation is eventually consistent and therefore
-+ * can be transiently negative.
-+ */
-+struct lru_gen_struct {
-+      /* the aging increments the youngest generation number */
-+      unsigned long max_seq;
-+      /* the eviction increments the oldest generation numbers */
-+      unsigned long min_seq[ANON_AND_FILE];
-+      /* the multi-gen LRU lists, lazily sorted on eviction */
-+      struct list_head lists[MAX_NR_GENS][ANON_AND_FILE][MAX_NR_ZONES];
-+      /* the multi-gen LRU sizes, eventually consistent */
-+      long nr_pages[MAX_NR_GENS][ANON_AND_FILE][MAX_NR_ZONES];
-+};
-+
-+void lru_gen_init_lruvec(struct lruvec *lruvec);
-+
-+#ifdef CONFIG_MEMCG
-+void lru_gen_init_memcg(struct mem_cgroup *memcg);
-+void lru_gen_exit_memcg(struct mem_cgroup *memcg);
-+#endif
-+
-+#else /* !CONFIG_LRU_GEN */
-+
-+static inline void lru_gen_init_lruvec(struct lruvec *lruvec)
-+{
-+}
-+
-+#ifdef CONFIG_MEMCG
-+static inline void lru_gen_init_memcg(struct mem_cgroup *memcg)
-+{
-+}
-+
-+static inline void lru_gen_exit_memcg(struct mem_cgroup *memcg)
-+{
-+}
-+#endif
-+
-+#endif /* CONFIG_LRU_GEN */
-+
- struct lruvec {
-       struct list_head                lists[NR_LRU_LISTS];
-       /* per lruvec lru_lock for memcg */
-@@ -311,6 +407,10 @@ struct lruvec {
-       unsigned long                   refaults[ANON_AND_FILE];
-       /* Various lruvec state flags (enum lruvec_flags) */
-       unsigned long                   flags;
-+#ifdef CONFIG_LRU_GEN
-+      /* evictable pages divided into generations */
-+      struct lru_gen_struct           lrugen;
-+#endif
- #ifdef CONFIG_MEMCG
-       struct pglist_data *pgdat;
- #endif
---- a/include/linux/page-flags-layout.h
-+++ b/include/linux/page-flags-layout.h
-@@ -55,7 +55,8 @@
- #define SECTIONS_WIDTH                0
- #endif
--#if ZONES_WIDTH + SECTIONS_WIDTH + NODES_SHIFT <= BITS_PER_LONG - NR_PAGEFLAGS
-+#if ZONES_WIDTH + LRU_GEN_WIDTH + SECTIONS_WIDTH + NODES_SHIFT \
-+      <= BITS_PER_LONG - NR_PAGEFLAGS
- #define NODES_WIDTH           NODES_SHIFT
- #elif defined(CONFIG_SPARSEMEM_VMEMMAP)
- #error "Vmemmap: No space for nodes field in page flags"
-@@ -89,8 +90,8 @@
- #define LAST_CPUPID_SHIFT 0
- #endif
--#if ZONES_WIDTH + SECTIONS_WIDTH + NODES_WIDTH + KASAN_TAG_WIDTH + LAST_CPUPID_SHIFT \
--      <= BITS_PER_LONG - NR_PAGEFLAGS
-+#if ZONES_WIDTH + LRU_GEN_WIDTH + SECTIONS_WIDTH + NODES_WIDTH + \
-+      KASAN_TAG_WIDTH + LAST_CPUPID_SHIFT <= BITS_PER_LONG - NR_PAGEFLAGS
- #define LAST_CPUPID_WIDTH LAST_CPUPID_SHIFT
- #else
- #define LAST_CPUPID_WIDTH 0
-@@ -100,10 +101,12 @@
- #define LAST_CPUPID_NOT_IN_PAGE_FLAGS
- #endif
--#if ZONES_WIDTH + SECTIONS_WIDTH + NODES_WIDTH + KASAN_TAG_WIDTH + LAST_CPUPID_WIDTH \
--      > BITS_PER_LONG - NR_PAGEFLAGS
-+#if ZONES_WIDTH + LRU_GEN_WIDTH + SECTIONS_WIDTH + NODES_WIDTH + \
-+      KASAN_TAG_WIDTH + LAST_CPUPID_WIDTH > BITS_PER_LONG - NR_PAGEFLAGS
- #error "Not enough bits in page flags"
- #endif
-+#define LRU_REFS_WIDTH        0
-+
- #endif
- #endif /* _LINUX_PAGE_FLAGS_LAYOUT */
---- a/include/linux/page-flags.h
-+++ b/include/linux/page-flags.h
-@@ -845,7 +845,7 @@ static inline void ClearPageSlabPfmemall
-        1UL << PG_private      | 1UL << PG_private_2   |       \
-        1UL << PG_writeback    | 1UL << PG_reserved    |       \
-        1UL << PG_slab         | 1UL << PG_active      |       \
--       1UL << PG_unevictable  | __PG_MLOCKED)
-+       1UL << PG_unevictable  | __PG_MLOCKED | LRU_GEN_MASK)
- /*
-  * Flags checked when a page is prepped for return by the page allocator.
-@@ -856,7 +856,7 @@ static inline void ClearPageSlabPfmemall
-  * alloc-free cycle to prevent from reusing the page.
-  */
- #define PAGE_FLAGS_CHECK_AT_PREP      \
--      (PAGEFLAGS_MASK & ~__PG_HWPOISON)
-+      ((PAGEFLAGS_MASK & ~__PG_HWPOISON) | LRU_GEN_MASK | LRU_REFS_MASK)
- #define PAGE_FLAGS_PRIVATE                            \
-       (1UL << PG_private | 1UL << PG_private_2)
---- a/include/linux/sched.h
-+++ b/include/linux/sched.h
-@@ -907,6 +907,10 @@ struct task_struct {
- #ifdef CONFIG_MEMCG
-       unsigned                        in_user_fault:1;
- #endif
-+#ifdef CONFIG_LRU_GEN
-+      /* whether the LRU algorithm may apply to this access */
-+      unsigned                        in_lru_fault:1;
-+#endif
- #ifdef CONFIG_COMPAT_BRK
-       unsigned                        brk_randomized:1;
- #endif
---- a/kernel/bounds.c
-+++ b/kernel/bounds.c
-@@ -22,6 +22,11 @@ int main(void)
-       DEFINE(NR_CPUS_BITS, order_base_2(CONFIG_NR_CPUS));
- #endif
-       DEFINE(SPINLOCK_SIZE, sizeof(spinlock_t));
-+#ifdef CONFIG_LRU_GEN
-+      DEFINE(LRU_GEN_WIDTH, order_base_2(MAX_NR_GENS + 1));
-+#else
-+      DEFINE(LRU_GEN_WIDTH, 0);
-+#endif
-       /* End of constants */
-       return 0;
---- a/mm/Kconfig
-+++ b/mm/Kconfig
-@@ -897,6 +897,14 @@ config IO_MAPPING
- config SECRETMEM
-       def_bool ARCH_HAS_SET_DIRECT_MAP && !EMBEDDED
-+config LRU_GEN
-+      bool "Multi-Gen LRU"
-+      depends on MMU
-+      # make sure page->flags has enough spare bits
-+      depends on 64BIT || !SPARSEMEM || SPARSEMEM_VMEMMAP
-+      help
-+        A high performance LRU implementation to overcommit memory.
-+
- source "mm/damon/Kconfig"
- endmenu
---- a/mm/huge_memory.c
-+++ b/mm/huge_memory.c
-@@ -2366,7 +2366,8 @@ static void __split_huge_page_tail(struc
- #ifdef CONFIG_64BIT
-                        (1L << PG_arch_2) |
- #endif
--                       (1L << PG_dirty)));
-+                       (1L << PG_dirty) |
-+                       LRU_GEN_MASK | LRU_REFS_MASK));
-       /* ->mapping in first tail page is compound_mapcount */
-       VM_BUG_ON_PAGE(tail > 2 && page_tail->mapping != TAIL_MAPPING,
---- a/mm/memcontrol.c
-+++ b/mm/memcontrol.c
-@@ -5179,6 +5179,7 @@ static void __mem_cgroup_free(struct mem
- static void mem_cgroup_free(struct mem_cgroup *memcg)
- {
-+      lru_gen_exit_memcg(memcg);
-       memcg_wb_domain_exit(memcg);
-       __mem_cgroup_free(memcg);
- }
-@@ -5242,6 +5243,7 @@ static struct mem_cgroup *mem_cgroup_all
-       memcg->deferred_split_queue.split_queue_len = 0;
- #endif
-       idr_replace(&mem_cgroup_idr, memcg, memcg->id.id);
-+      lru_gen_init_memcg(memcg);
-       return memcg;
- fail:
-       mem_cgroup_id_remove(memcg);
---- a/mm/memory.c
-+++ b/mm/memory.c
-@@ -4805,6 +4805,27 @@ static inline void mm_account_fault(stru
-               perf_sw_event(PERF_COUNT_SW_PAGE_FAULTS_MIN, 1, regs, address);
- }
-+#ifdef CONFIG_LRU_GEN
-+static void lru_gen_enter_fault(struct vm_area_struct *vma)
-+{
-+      /* the LRU algorithm doesn't apply to sequential or random reads */
-+      current->in_lru_fault = !(vma->vm_flags & (VM_SEQ_READ | VM_RAND_READ));
-+}
-+
-+static void lru_gen_exit_fault(void)
-+{
-+      current->in_lru_fault = false;
-+}
-+#else
-+static void lru_gen_enter_fault(struct vm_area_struct *vma)
-+{
-+}
-+
-+static void lru_gen_exit_fault(void)
-+{
-+}
-+#endif /* CONFIG_LRU_GEN */
-+
- /*
-  * By the time we get here, we already hold the mm semaphore
-  *
-@@ -4836,11 +4857,15 @@ vm_fault_t handle_mm_fault(struct vm_are
-       if (flags & FAULT_FLAG_USER)
-               mem_cgroup_enter_user_fault();
-+      lru_gen_enter_fault(vma);
-+
-       if (unlikely(is_vm_hugetlb_page(vma)))
-               ret = hugetlb_fault(vma->vm_mm, vma, address, flags);
-       else
-               ret = __handle_mm_fault(vma, address, flags);
-+      lru_gen_exit_fault();
-+
-       if (flags & FAULT_FLAG_USER) {
-               mem_cgroup_exit_user_fault();
-               /*
---- a/mm/mm_init.c
-+++ b/mm/mm_init.c
-@@ -65,14 +65,16 @@ void __init mminit_verify_pageflags_layo
-       shift = 8 * sizeof(unsigned long);
-       width = shift - SECTIONS_WIDTH - NODES_WIDTH - ZONES_WIDTH
--              - LAST_CPUPID_SHIFT - KASAN_TAG_WIDTH;
-+              - LAST_CPUPID_SHIFT - KASAN_TAG_WIDTH - LRU_GEN_WIDTH - LRU_REFS_WIDTH;
-       mminit_dprintk(MMINIT_TRACE, "pageflags_layout_widths",
--              "Section %d Node %d Zone %d Lastcpupid %d Kasantag %d Flags %d\n",
-+              "Section %d Node %d Zone %d Lastcpupid %d Kasantag %d Gen %d Tier %d Flags %d\n",
-               SECTIONS_WIDTH,
-               NODES_WIDTH,
-               ZONES_WIDTH,
-               LAST_CPUPID_WIDTH,
-               KASAN_TAG_WIDTH,
-+              LRU_GEN_WIDTH,
-+              LRU_REFS_WIDTH,
-               NR_PAGEFLAGS);
-       mminit_dprintk(MMINIT_TRACE, "pageflags_layout_shifts",
-               "Section %d Node %d Zone %d Lastcpupid %d Kasantag %d\n",
---- a/mm/mmzone.c
-+++ b/mm/mmzone.c
-@@ -81,6 +81,8 @@ void lruvec_init(struct lruvec *lruvec)
-       for_each_lru(lru)
-               INIT_LIST_HEAD(&lruvec->lists[lru]);
-+
-+      lru_gen_init_lruvec(lruvec);
- }
- #if defined(CONFIG_NUMA_BALANCING) && !defined(LAST_CPUPID_NOT_IN_PAGE_FLAGS)
---- a/mm/swap.c
-+++ b/mm/swap.c
-@@ -446,6 +446,11 @@ void lru_cache_add(struct page *page)
-       VM_BUG_ON_PAGE(PageActive(page) && PageUnevictable(page), page);
-       VM_BUG_ON_PAGE(PageLRU(page), page);
-+      /* see the comment in lru_gen_add_page() */
-+      if (lru_gen_enabled() && !PageUnevictable(page) &&
-+          lru_gen_in_fault() && !(current->flags & PF_MEMALLOC))
-+              SetPageActive(page);
-+
-       get_page(page);
-       local_lock(&lru_pvecs.lock);
-       pvec = this_cpu_ptr(&lru_pvecs.lru_add);
-@@ -547,7 +552,7 @@ static void lru_deactivate_file_fn(struc
- static void lru_deactivate_fn(struct page *page, struct lruvec *lruvec)
- {
--      if (PageActive(page) && !PageUnevictable(page)) {
-+      if (!PageUnevictable(page) && (PageActive(page) || lru_gen_enabled())) {
-               int nr_pages = thp_nr_pages(page);
-               del_page_from_lru_list(page, lruvec);
-@@ -661,7 +666,8 @@ void deactivate_file_page(struct page *p
-  */
- void deactivate_page(struct page *page)
- {
--      if (PageLRU(page) && PageActive(page) && !PageUnevictable(page)) {
-+      if (PageLRU(page) && !PageUnevictable(page) &&
-+          (PageActive(page) || lru_gen_enabled())) {
-               struct pagevec *pvec;
-               local_lock(&lru_pvecs.lock);
---- a/mm/vmscan.c
-+++ b/mm/vmscan.c
-@@ -2821,6 +2821,81 @@ static bool can_age_anon_pages(struct pg
-       return can_demote(pgdat->node_id, sc);
- }
-+#ifdef CONFIG_LRU_GEN
-+
-+/******************************************************************************
-+ *                          shorthand helpers
-+ ******************************************************************************/
-+
-+#define for_each_gen_type_zone(gen, type, zone)                               \
-+      for ((gen) = 0; (gen) < MAX_NR_GENS; (gen)++)                   \
-+              for ((type) = 0; (type) < ANON_AND_FILE; (type)++)      \
-+                      for ((zone) = 0; (zone) < MAX_NR_ZONES; (zone)++)
-+
-+static struct lruvec __maybe_unused *get_lruvec(struct mem_cgroup *memcg, int nid)
-+{
-+      struct pglist_data *pgdat = NODE_DATA(nid);
-+
-+#ifdef CONFIG_MEMCG
-+      if (memcg) {
-+              struct lruvec *lruvec = &memcg->nodeinfo[nid]->lruvec;
-+
-+              /* for hotadd_new_pgdat() */
-+              if (!lruvec->pgdat)
-+                      lruvec->pgdat = pgdat;
-+
-+              return lruvec;
-+      }
-+#endif
-+      VM_WARN_ON_ONCE(!mem_cgroup_disabled());
-+
-+      return pgdat ? &pgdat->__lruvec : NULL;
-+}
-+
-+/******************************************************************************
-+ *                          initialization
-+ ******************************************************************************/
-+
-+void lru_gen_init_lruvec(struct lruvec *lruvec)
-+{
-+      int gen, type, zone;
-+      struct lru_gen_struct *lrugen = &lruvec->lrugen;
-+
-+      lrugen->max_seq = MIN_NR_GENS + 1;
-+
-+      for_each_gen_type_zone(gen, type, zone)
-+              INIT_LIST_HEAD(&lrugen->lists[gen][type][zone]);
-+}
-+
-+#ifdef CONFIG_MEMCG
-+void lru_gen_init_memcg(struct mem_cgroup *memcg)
-+{
-+}
-+
-+void lru_gen_exit_memcg(struct mem_cgroup *memcg)
-+{
-+      int nid;
-+
-+      for_each_node(nid) {
-+              struct lruvec *lruvec = get_lruvec(memcg, nid);
-+
-+              VM_WARN_ON_ONCE(memchr_inv(lruvec->lrugen.nr_pages, 0,
-+                                         sizeof(lruvec->lrugen.nr_pages)));
-+      }
-+}
-+#endif
-+
-+static int __init init_lru_gen(void)
-+{
-+      BUILD_BUG_ON(MIN_NR_GENS + 1 >= MAX_NR_GENS);
-+      BUILD_BUG_ON(BIT(LRU_GEN_WIDTH) <= MAX_NR_GENS);
-+
-+      return 0;
-+};
-+late_initcall(init_lru_gen);
-+
-+#endif /* CONFIG_LRU_GEN */
-+
- static void shrink_lruvec(struct lruvec *lruvec, struct scan_control *sc)
- {
-       unsigned long nr[NR_LRU_LISTS];
diff --git a/target/linux/generic/backport-5.15/020-v6.1-06-mm-multi-gen-LRU-minimal-implementation.patch b/target/linux/generic/backport-5.15/020-v6.1-06-mm-multi-gen-LRU-minimal-implementation.patch
deleted file mode 100644 (file)
index 14fc73f..0000000
+++ /dev/null
@@ -1,1447 +0,0 @@
-From b564b9471cd60ef1ee3961a224898ce4a9620d84 Mon Sep 17 00:00:00 2001
-From: Yu Zhao <[email protected]>
-Date: Sun, 18 Sep 2022 02:00:03 -0600
-Subject: [PATCH 06/29] mm: multi-gen LRU: minimal implementation
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-To avoid confusion, the terms "promotion" and "demotion" will be applied
-to the multi-gen LRU, as a new convention; the terms "activation" and
-"deactivation" will be applied to the active/inactive LRU, as usual.
-
-The aging produces young generations.  Given an lruvec, it increments
-max_seq when max_seq-min_seq+1 approaches MIN_NR_GENS.  The aging promotes
-hot pages to the youngest generation when it finds them accessed through
-page tables; the demotion of cold pages happens consequently when it
-increments max_seq.  Promotion in the aging path does not involve any LRU
-list operations, only the updates of the gen counter and
-lrugen->nr_pages[]; demotion, unless as the result of the increment of
-max_seq, requires LRU list operations, e.g., lru_deactivate_fn().  The
-aging has the complexity O(nr_hot_pages), since it is only interested in
-hot pages.
-
-The eviction consumes old generations.  Given an lruvec, it increments
-min_seq when lrugen->lists[] indexed by min_seq%MAX_NR_GENS becomes empty.
-A feedback loop modeled after the PID controller monitors refaults over
-anon and file types and decides which type to evict when both types are
-available from the same generation.
-
-The protection of pages accessed multiple times through file descriptors
-takes place in the eviction path.  Each generation is divided into
-multiple tiers.  A page accessed N times through file descriptors is in
-tier order_base_2(N).  Tiers do not have dedicated lrugen->lists[], only
-bits in page->flags.  The aforementioned feedback loop also monitors
-refaults over all tiers and decides when to protect pages in which tiers
-(N>1), using the first tier (N=0,1) as a baseline.  The first tier
-contains single-use unmapped clean pages, which are most likely the best
-choices.  In contrast to promotion in the aging path, the protection of a
-page in the eviction path is achieved by moving this page to the next
-generation, i.e., min_seq+1, if the feedback loop decides so.  This
-approach has the following advantages:
-
-1. It removes the cost of activation in the buffered access path by
-   inferring whether pages accessed multiple times through file
-   descriptors are statistically hot and thus worth protecting in the
-   eviction path.
-2. It takes pages accessed through page tables into account and avoids
-   overprotecting pages accessed multiple times through file
-   descriptors. (Pages accessed through page tables are in the first
-   tier, since N=0.)
-3. More tiers provide better protection for pages accessed more than
-   twice through file descriptors, when under heavy buffered I/O
-   workloads.
-
-Server benchmark results:
-  Single workload:
-    fio (buffered I/O): +[30, 32]%
-                IOPS         BW
-      5.19-rc1: 2673k        10.2GiB/s
-      patch1-6: 3491k        13.3GiB/s
-
-  Single workload:
-    memcached (anon): -[4, 6]%
-                Ops/sec      KB/sec
-      5.19-rc1: 1161501.04   45177.25
-      patch1-6: 1106168.46   43025.04
-
-  Configurations:
-    CPU: two Xeon 6154
-    Mem: total 256G
-
-    Node 1 was only used as a ram disk to reduce the variance in the
-    results.
-
-    patch drivers/block/brd.c <<EOF
-    99,100c99,100
-    <  gfp_flags = GFP_NOIO | __GFP_ZERO | __GFP_HIGHMEM;
-    <  page = alloc_page(gfp_flags);
-    ---
-    >  gfp_flags = GFP_NOIO | __GFP_ZERO | __GFP_HIGHMEM | __GFP_THISNODE;
-    >  page = alloc_pages_node(1, gfp_flags, 0);
-    EOF
-
-    cat >>/etc/systemd/system.conf <<EOF
-    CPUAffinity=numa
-    NUMAPolicy=bind
-    NUMAMask=0
-    EOF
-
-    cat >>/etc/memcached.conf <<EOF
-    -m 184320
-    -s /var/run/memcached/memcached.sock
-    -a 0766
-    -t 36
-    -B binary
-    EOF
-
-    cat fio.sh
-    modprobe brd rd_nr=1 rd_size=113246208
-    swapoff -a
-    mkfs.ext4 /dev/ram0
-    mount -t ext4 /dev/ram0 /mnt
-
-    mkdir /sys/fs/cgroup/user.slice/test
-    echo 38654705664 >/sys/fs/cgroup/user.slice/test/memory.max
-    echo $$ >/sys/fs/cgroup/user.slice/test/cgroup.procs
-    fio -name=mglru --numjobs=72 --directory=/mnt --size=1408m \
-      --buffered=1 --ioengine=io_uring --iodepth=128 \
-      --iodepth_batch_submit=32 --iodepth_batch_complete=32 \
-      --rw=randread --random_distribution=random --norandommap \
-      --time_based --ramp_time=10m --runtime=5m --group_reporting
-
-    cat memcached.sh
-    modprobe brd rd_nr=1 rd_size=113246208
-    swapoff -a
-    mkswap /dev/ram0
-    swapon /dev/ram0
-
-    memtier_benchmark -S /var/run/memcached/memcached.sock \
-      -P memcache_binary -n allkeys --key-minimum=1 \
-      --key-maximum=65000000 --key-pattern=P:P -c 1 -t 36 \
-      --ratio 1:0 --pipeline 8 -d 2000
-
-    memtier_benchmark -S /var/run/memcached/memcached.sock \
-      -P memcache_binary -n allkeys --key-minimum=1 \
-      --key-maximum=65000000 --key-pattern=R:R -c 1 -t 36 \
-      --ratio 0:1 --pipeline 8 --randomize --distinct-client-seed
-
-Client benchmark results:
-  kswapd profiles:
-    5.19-rc1
-      40.33%  page_vma_mapped_walk (overhead)
-      21.80%  lzo1x_1_do_compress (real work)
-       7.53%  do_raw_spin_lock
-       3.95%  _raw_spin_unlock_irq
-       2.52%  vma_interval_tree_iter_next
-       2.37%  page_referenced_one
-       2.28%  vma_interval_tree_subtree_search
-       1.97%  anon_vma_interval_tree_iter_first
-       1.60%  ptep_clear_flush
-       1.06%  __zram_bvec_write
-
-    patch1-6
-      39.03%  lzo1x_1_do_compress (real work)
-      18.47%  page_vma_mapped_walk (overhead)
-       6.74%  _raw_spin_unlock_irq
-       3.97%  do_raw_spin_lock
-       2.49%  ptep_clear_flush
-       2.48%  anon_vma_interval_tree_iter_first
-       1.92%  page_referenced_one
-       1.88%  __zram_bvec_write
-       1.48%  memmove
-       1.31%  vma_interval_tree_iter_next
-
-  Configurations:
-    CPU: single Snapdragon 7c
-    Mem: total 4G
-
-    ChromeOS MemoryPressure [1]
-
-[1] https://chromium.googlesource.com/chromiumos/platform/tast-tests/
-
-Link: https://lkml.kernel.org/r/[email protected]
-Signed-off-by: Yu Zhao <[email protected]>
-Acked-by: Brian Geffon <[email protected]>
-Acked-by: Jan Alexander Steffens (heftig) <[email protected]>
-Acked-by: Oleksandr Natalenko <[email protected]>
-Acked-by: Steven Barrett <[email protected]>
-Acked-by: Suleiman Souhlal <[email protected]>
-Tested-by: Daniel Byrne <[email protected]>
-Tested-by: Donald Carr <[email protected]>
-Tested-by: Holger Hoffstätte <[email protected]>
-Tested-by: Konstantin Kharlamov <[email protected]>
-Tested-by: Shuang Zhai <[email protected]>
-Tested-by: Sofia Trinh <[email protected]>
-Tested-by: Vaibhav Jain <[email protected]>
-Cc: Andi Kleen <[email protected]>
-Cc: Aneesh Kumar K.V <[email protected]>
-Cc: Barry Song <[email protected]>
-Cc: Catalin Marinas <[email protected]>
-Cc: Dave Hansen <[email protected]>
-Cc: Hillf Danton <[email protected]>
-Cc: Jens Axboe <[email protected]>
-Cc: Johannes Weiner <[email protected]>
-Cc: Jonathan Corbet <[email protected]>
-Cc: Linus Torvalds <[email protected]>
-Cc: Matthew Wilcox <[email protected]>
-Cc: Mel Gorman <[email protected]>
-Cc: Miaohe Lin <[email protected]>
-Cc: Michael Larabel <[email protected]>
-Cc: Michal Hocko <[email protected]>
-Cc: Mike Rapoport <[email protected]>
-Cc: Mike Rapoport <[email protected]>
-Cc: Peter Zijlstra <[email protected]>
-Cc: Qi Zheng <[email protected]>
-Cc: Tejun Heo <[email protected]>
-Cc: Vlastimil Babka <[email protected]>
-Cc: Will Deacon <[email protected]>
-Signed-off-by: Andrew Morton <[email protected]>
----
- include/linux/mm_inline.h         |  36 ++
- include/linux/mmzone.h            |  41 ++
- include/linux/page-flags-layout.h |   5 +-
- kernel/bounds.c                   |   2 +
- mm/Kconfig                        |  11 +
- mm/swap.c                         |  39 ++
- mm/vmscan.c                       | 792 +++++++++++++++++++++++++++++-
- mm/workingset.c                   | 110 ++++-
- 8 files changed, 1025 insertions(+), 11 deletions(-)
-
---- a/include/linux/mm_inline.h
-+++ b/include/linux/mm_inline.h
-@@ -106,6 +106,33 @@ static inline int lru_gen_from_seq(unsig
-       return seq % MAX_NR_GENS;
- }
-+static inline int lru_hist_from_seq(unsigned long seq)
-+{
-+      return seq % NR_HIST_GENS;
-+}
-+
-+static inline int lru_tier_from_refs(int refs)
-+{
-+      VM_WARN_ON_ONCE(refs > BIT(LRU_REFS_WIDTH));
-+
-+      /* see the comment in page_lru_refs() */
-+      return order_base_2(refs + 1);
-+}
-+
-+static inline int page_lru_refs(struct page *page)
-+{
-+      unsigned long flags = READ_ONCE(page->flags);
-+      bool workingset = flags & BIT(PG_workingset);
-+
-+      /*
-+       * Return the number of accesses beyond PG_referenced, i.e., N-1 if the
-+       * total number of accesses is N>1, since N=0,1 both map to the first
-+       * tier. lru_tier_from_refs() will account for this off-by-one. Also see
-+       * the comment on MAX_NR_TIERS.
-+       */
-+      return ((flags & LRU_REFS_MASK) >> LRU_REFS_PGOFF) + workingset;
-+}
-+
- static inline int page_lru_gen(struct page *page)
- {
-       unsigned long flags = READ_ONCE(page->flags);
-@@ -158,6 +185,15 @@ static inline void lru_gen_update_size(s
-               __update_lru_size(lruvec, lru, zone, -delta);
-               return;
-       }
-+
-+      /* promotion */
-+      if (!lru_gen_is_active(lruvec, old_gen) && lru_gen_is_active(lruvec, new_gen)) {
-+              __update_lru_size(lruvec, lru, zone, -delta);
-+              __update_lru_size(lruvec, lru + LRU_ACTIVE, zone, delta);
-+      }
-+
-+      /* demotion requires isolation, e.g., lru_deactivate_fn() */
-+      VM_WARN_ON_ONCE(lru_gen_is_active(lruvec, old_gen) && !lru_gen_is_active(lruvec, new_gen));
- }
- static inline bool lru_gen_add_page(struct lruvec *lruvec, struct page *page, bool reclaiming)
---- a/include/linux/mmzone.h
-+++ b/include/linux/mmzone.h
-@@ -327,6 +327,28 @@ enum lruvec_flags {
- #define MIN_NR_GENS           2U
- #define MAX_NR_GENS           4U
-+/*
-+ * Each generation is divided into multiple tiers. A page accessed N times
-+ * through file descriptors is in tier order_base_2(N). A page in the first tier
-+ * (N=0,1) is marked by PG_referenced unless it was faulted in through page
-+ * tables or read ahead. A page in any other tier (N>1) is marked by
-+ * PG_referenced and PG_workingset. This implies a minimum of two tiers is
-+ * supported without using additional bits in page->flags.
-+ *
-+ * In contrast to moving across generations which requires the LRU lock, moving
-+ * across tiers only involves atomic operations on page->flags and therefore
-+ * has a negligible cost in the buffered access path. In the eviction path,
-+ * comparisons of refaulted/(evicted+protected) from the first tier and the
-+ * rest infer whether pages accessed multiple times through file descriptors
-+ * are statistically hot and thus worth protecting.
-+ *
-+ * MAX_NR_TIERS is set to 4 so that the multi-gen LRU can support twice the
-+ * number of categories of the active/inactive LRU when keeping track of
-+ * accesses through file descriptors. This uses MAX_NR_TIERS-2 spare bits in
-+ * page->flags.
-+ */
-+#define MAX_NR_TIERS          4U
-+
- #ifndef __GENERATING_BOUNDS_H
- struct lruvec;
-@@ -341,6 +363,16 @@ enum {
-       LRU_GEN_FILE,
- };
-+#define MIN_LRU_BATCH         BITS_PER_LONG
-+#define MAX_LRU_BATCH         (MIN_LRU_BATCH * 64)
-+
-+/* whether to keep historical stats from evicted generations */
-+#ifdef CONFIG_LRU_GEN_STATS
-+#define NR_HIST_GENS          MAX_NR_GENS
-+#else
-+#define NR_HIST_GENS          1U
-+#endif
-+
- /*
-  * The youngest generation number is stored in max_seq for both anon and file
-  * types as they are aged on an equal footing. The oldest generation numbers are
-@@ -363,6 +395,15 @@ struct lru_gen_struct {
-       struct list_head lists[MAX_NR_GENS][ANON_AND_FILE][MAX_NR_ZONES];
-       /* the multi-gen LRU sizes, eventually consistent */
-       long nr_pages[MAX_NR_GENS][ANON_AND_FILE][MAX_NR_ZONES];
-+      /* the exponential moving average of refaulted */
-+      unsigned long avg_refaulted[ANON_AND_FILE][MAX_NR_TIERS];
-+      /* the exponential moving average of evicted+protected */
-+      unsigned long avg_total[ANON_AND_FILE][MAX_NR_TIERS];
-+      /* the first tier doesn't need protection, hence the minus one */
-+      unsigned long protected[NR_HIST_GENS][ANON_AND_FILE][MAX_NR_TIERS - 1];
-+      /* can be modified without holding the LRU lock */
-+      atomic_long_t evicted[NR_HIST_GENS][ANON_AND_FILE][MAX_NR_TIERS];
-+      atomic_long_t refaulted[NR_HIST_GENS][ANON_AND_FILE][MAX_NR_TIERS];
- };
- void lru_gen_init_lruvec(struct lruvec *lruvec);
---- a/include/linux/page-flags-layout.h
-+++ b/include/linux/page-flags-layout.h
-@@ -106,7 +106,10 @@
- #error "Not enough bits in page flags"
- #endif
--#define LRU_REFS_WIDTH        0
-+/* see the comment on MAX_NR_TIERS */
-+#define LRU_REFS_WIDTH        min(__LRU_REFS_WIDTH, BITS_PER_LONG - NR_PAGEFLAGS - \
-+                          ZONES_WIDTH - LRU_GEN_WIDTH - SECTIONS_WIDTH - \
-+                          NODES_WIDTH - KASAN_TAG_WIDTH - LAST_CPUPID_WIDTH)
- #endif
- #endif /* _LINUX_PAGE_FLAGS_LAYOUT */
---- a/kernel/bounds.c
-+++ b/kernel/bounds.c
-@@ -24,8 +24,10 @@ int main(void)
-       DEFINE(SPINLOCK_SIZE, sizeof(spinlock_t));
- #ifdef CONFIG_LRU_GEN
-       DEFINE(LRU_GEN_WIDTH, order_base_2(MAX_NR_GENS + 1));
-+      DEFINE(__LRU_REFS_WIDTH, MAX_NR_TIERS - 2);
- #else
-       DEFINE(LRU_GEN_WIDTH, 0);
-+      DEFINE(__LRU_REFS_WIDTH, 0);
- #endif
-       /* End of constants */
---- a/mm/Kconfig
-+++ b/mm/Kconfig
-@@ -897,6 +897,7 @@ config IO_MAPPING
- config SECRETMEM
-       def_bool ARCH_HAS_SET_DIRECT_MAP && !EMBEDDED
-+# multi-gen LRU {
- config LRU_GEN
-       bool "Multi-Gen LRU"
-       depends on MMU
-@@ -905,6 +906,16 @@ config LRU_GEN
-       help
-         A high performance LRU implementation to overcommit memory.
-+config LRU_GEN_STATS
-+      bool "Full stats for debugging"
-+      depends on LRU_GEN
-+      help
-+        Do not enable this option unless you plan to look at historical stats
-+        from evicted generations for debugging purpose.
-+
-+        This option has a per-memcg and per-node memory overhead.
-+# }
-+
- source "mm/damon/Kconfig"
- endmenu
---- a/mm/swap.c
-+++ b/mm/swap.c
-@@ -389,6 +389,40 @@ static void __lru_cache_activate_page(st
-       local_unlock(&lru_pvecs.lock);
- }
-+#ifdef CONFIG_LRU_GEN
-+static void page_inc_refs(struct page *page)
-+{
-+      unsigned long new_flags, old_flags = READ_ONCE(page->flags);
-+
-+      if (PageUnevictable(page))
-+              return;
-+
-+      if (!PageReferenced(page)) {
-+              SetPageReferenced(page);
-+              return;
-+      }
-+
-+      if (!PageWorkingset(page)) {
-+              SetPageWorkingset(page);
-+              return;
-+      }
-+
-+      /* see the comment on MAX_NR_TIERS */
-+      do {
-+              new_flags = old_flags & LRU_REFS_MASK;
-+              if (new_flags == LRU_REFS_MASK)
-+                      break;
-+
-+              new_flags += BIT(LRU_REFS_PGOFF);
-+              new_flags |= old_flags & ~LRU_REFS_MASK;
-+      } while (!try_cmpxchg(&page->flags, &old_flags, new_flags));
-+}
-+#else
-+static void page_inc_refs(struct page *page)
-+{
-+}
-+#endif /* CONFIG_LRU_GEN */
-+
- /*
-  * Mark a page as having seen activity.
-  *
-@@ -403,6 +437,11 @@ void mark_page_accessed(struct page *pag
- {
-       page = compound_head(page);
-+      if (lru_gen_enabled()) {
-+              page_inc_refs(page);
-+              return;
-+      }
-+
-       if (!PageReferenced(page)) {
-               SetPageReferenced(page);
-       } else if (PageUnevictable(page)) {
---- a/mm/vmscan.c
-+++ b/mm/vmscan.c
-@@ -1142,9 +1142,11 @@ static int __remove_mapping(struct addre
-       if (PageSwapCache(page)) {
-               swp_entry_t swap = { .val = page_private(page) };
--              mem_cgroup_swapout(page, swap);
-+
-+              /* get a shadow entry before mem_cgroup_swapout() clears page_memcg() */
-               if (reclaimed && !mapping_exiting(mapping))
-                       shadow = workingset_eviction(page, target_memcg);
-+              mem_cgroup_swapout(page, swap);
-               __delete_from_swap_cache(page, swap, shadow);
-               xa_unlock_irq(&mapping->i_pages);
-               put_swap_page(page, swap);
-@@ -2502,6 +2504,9 @@ static void prepare_scan_count(pg_data_t
-       unsigned long file;
-       struct lruvec *target_lruvec;
-+      if (lru_gen_enabled())
-+              return;
-+
-       target_lruvec = mem_cgroup_lruvec(sc->target_mem_cgroup, pgdat);
-       /*
-@@ -2827,6 +2832,17 @@ static bool can_age_anon_pages(struct pg
-  *                          shorthand helpers
-  ******************************************************************************/
-+#define LRU_REFS_FLAGS        (BIT(PG_referenced) | BIT(PG_workingset))
-+
-+#define DEFINE_MAX_SEQ(lruvec)                                                \
-+      unsigned long max_seq = READ_ONCE((lruvec)->lrugen.max_seq)
-+
-+#define DEFINE_MIN_SEQ(lruvec)                                                \
-+      unsigned long min_seq[ANON_AND_FILE] = {                        \
-+              READ_ONCE((lruvec)->lrugen.min_seq[LRU_GEN_ANON]),      \
-+              READ_ONCE((lruvec)->lrugen.min_seq[LRU_GEN_FILE]),      \
-+      }
-+
- #define for_each_gen_type_zone(gen, type, zone)                               \
-       for ((gen) = 0; (gen) < MAX_NR_GENS; (gen)++)                   \
-               for ((type) = 0; (type) < ANON_AND_FILE; (type)++)      \
-@@ -2852,6 +2868,745 @@ static struct lruvec __maybe_unused *get
-       return pgdat ? &pgdat->__lruvec : NULL;
- }
-+static int get_swappiness(struct lruvec *lruvec, struct scan_control *sc)
-+{
-+      struct mem_cgroup *memcg = lruvec_memcg(lruvec);
-+      struct pglist_data *pgdat = lruvec_pgdat(lruvec);
-+
-+      if (!can_demote(pgdat->node_id, sc) &&
-+          mem_cgroup_get_nr_swap_pages(memcg) < MIN_LRU_BATCH)
-+              return 0;
-+
-+      return mem_cgroup_swappiness(memcg);
-+}
-+
-+static int get_nr_gens(struct lruvec *lruvec, int type)
-+{
-+      return lruvec->lrugen.max_seq - lruvec->lrugen.min_seq[type] + 1;
-+}
-+
-+static bool __maybe_unused seq_is_valid(struct lruvec *lruvec)
-+{
-+      /* see the comment on lru_gen_struct */
-+      return get_nr_gens(lruvec, LRU_GEN_FILE) >= MIN_NR_GENS &&
-+             get_nr_gens(lruvec, LRU_GEN_FILE) <= get_nr_gens(lruvec, LRU_GEN_ANON) &&
-+             get_nr_gens(lruvec, LRU_GEN_ANON) <= MAX_NR_GENS;
-+}
-+
-+/******************************************************************************
-+ *                          refault feedback loop
-+ ******************************************************************************/
-+
-+/*
-+ * A feedback loop based on Proportional-Integral-Derivative (PID) controller.
-+ *
-+ * The P term is refaulted/(evicted+protected) from a tier in the generation
-+ * currently being evicted; the I term is the exponential moving average of the
-+ * P term over the generations previously evicted, using the smoothing factor
-+ * 1/2; the D term isn't supported.
-+ *
-+ * The setpoint (SP) is always the first tier of one type; the process variable
-+ * (PV) is either any tier of the other type or any other tier of the same
-+ * type.
-+ *
-+ * The error is the difference between the SP and the PV; the correction is to
-+ * turn off protection when SP>PV or turn on protection when SP<PV.
-+ *
-+ * For future optimizations:
-+ * 1. The D term may discount the other two terms over time so that long-lived
-+ *    generations can resist stale information.
-+ */
-+struct ctrl_pos {
-+      unsigned long refaulted;
-+      unsigned long total;
-+      int gain;
-+};
-+
-+static void read_ctrl_pos(struct lruvec *lruvec, int type, int tier, int gain,
-+                        struct ctrl_pos *pos)
-+{
-+      struct lru_gen_struct *lrugen = &lruvec->lrugen;
-+      int hist = lru_hist_from_seq(lrugen->min_seq[type]);
-+
-+      pos->refaulted = lrugen->avg_refaulted[type][tier] +
-+                       atomic_long_read(&lrugen->refaulted[hist][type][tier]);
-+      pos->total = lrugen->avg_total[type][tier] +
-+                   atomic_long_read(&lrugen->evicted[hist][type][tier]);
-+      if (tier)
-+              pos->total += lrugen->protected[hist][type][tier - 1];
-+      pos->gain = gain;
-+}
-+
-+static void reset_ctrl_pos(struct lruvec *lruvec, int type, bool carryover)
-+{
-+      int hist, tier;
-+      struct lru_gen_struct *lrugen = &lruvec->lrugen;
-+      bool clear = carryover ? NR_HIST_GENS == 1 : NR_HIST_GENS > 1;
-+      unsigned long seq = carryover ? lrugen->min_seq[type] : lrugen->max_seq + 1;
-+
-+      lockdep_assert_held(&lruvec->lru_lock);
-+
-+      if (!carryover && !clear)
-+              return;
-+
-+      hist = lru_hist_from_seq(seq);
-+
-+      for (tier = 0; tier < MAX_NR_TIERS; tier++) {
-+              if (carryover) {
-+                      unsigned long sum;
-+
-+                      sum = lrugen->avg_refaulted[type][tier] +
-+                            atomic_long_read(&lrugen->refaulted[hist][type][tier]);
-+                      WRITE_ONCE(lrugen->avg_refaulted[type][tier], sum / 2);
-+
-+                      sum = lrugen->avg_total[type][tier] +
-+                            atomic_long_read(&lrugen->evicted[hist][type][tier]);
-+                      if (tier)
-+                              sum += lrugen->protected[hist][type][tier - 1];
-+                      WRITE_ONCE(lrugen->avg_total[type][tier], sum / 2);
-+              }
-+
-+              if (clear) {
-+                      atomic_long_set(&lrugen->refaulted[hist][type][tier], 0);
-+                      atomic_long_set(&lrugen->evicted[hist][type][tier], 0);
-+                      if (tier)
-+                              WRITE_ONCE(lrugen->protected[hist][type][tier - 1], 0);
-+              }
-+      }
-+}
-+
-+static bool positive_ctrl_err(struct ctrl_pos *sp, struct ctrl_pos *pv)
-+{
-+      /*
-+       * Return true if the PV has a limited number of refaults or a lower
-+       * refaulted/total than the SP.
-+       */
-+      return pv->refaulted < MIN_LRU_BATCH ||
-+             pv->refaulted * (sp->total + MIN_LRU_BATCH) * sp->gain <=
-+             (sp->refaulted + 1) * pv->total * pv->gain;
-+}
-+
-+/******************************************************************************
-+ *                          the aging
-+ ******************************************************************************/
-+
-+/* protect pages accessed multiple times through file descriptors */
-+static int page_inc_gen(struct lruvec *lruvec, struct page *page, bool reclaiming)
-+{
-+      int type = page_is_file_lru(page);
-+      struct lru_gen_struct *lrugen = &lruvec->lrugen;
-+      int new_gen, old_gen = lru_gen_from_seq(lrugen->min_seq[type]);
-+      unsigned long new_flags, old_flags = READ_ONCE(page->flags);
-+
-+      VM_WARN_ON_ONCE_PAGE(!(old_flags & LRU_GEN_MASK), page);
-+
-+      do {
-+              new_gen = (old_gen + 1) % MAX_NR_GENS;
-+
-+              new_flags = old_flags & ~(LRU_GEN_MASK | LRU_REFS_MASK | LRU_REFS_FLAGS);
-+              new_flags |= (new_gen + 1UL) << LRU_GEN_PGOFF;
-+              /* for end_page_writeback() */
-+              if (reclaiming)
-+                      new_flags |= BIT(PG_reclaim);
-+      } while (!try_cmpxchg(&page->flags, &old_flags, new_flags));
-+
-+      lru_gen_update_size(lruvec, page, old_gen, new_gen);
-+
-+      return new_gen;
-+}
-+
-+static void inc_min_seq(struct lruvec *lruvec, int type)
-+{
-+      struct lru_gen_struct *lrugen = &lruvec->lrugen;
-+
-+      reset_ctrl_pos(lruvec, type, true);
-+      WRITE_ONCE(lrugen->min_seq[type], lrugen->min_seq[type] + 1);
-+}
-+
-+static bool try_to_inc_min_seq(struct lruvec *lruvec, bool can_swap)
-+{
-+      int gen, type, zone;
-+      bool success = false;
-+      struct lru_gen_struct *lrugen = &lruvec->lrugen;
-+      DEFINE_MIN_SEQ(lruvec);
-+
-+      VM_WARN_ON_ONCE(!seq_is_valid(lruvec));
-+
-+      /* find the oldest populated generation */
-+      for (type = !can_swap; type < ANON_AND_FILE; type++) {
-+              while (min_seq[type] + MIN_NR_GENS <= lrugen->max_seq) {
-+                      gen = lru_gen_from_seq(min_seq[type]);
-+
-+                      for (zone = 0; zone < MAX_NR_ZONES; zone++) {
-+                              if (!list_empty(&lrugen->lists[gen][type][zone]))
-+                                      goto next;
-+                      }
-+
-+                      min_seq[type]++;
-+              }
-+next:
-+              ;
-+      }
-+
-+      /* see the comment on lru_gen_struct */
-+      if (can_swap) {
-+              min_seq[LRU_GEN_ANON] = min(min_seq[LRU_GEN_ANON], min_seq[LRU_GEN_FILE]);
-+              min_seq[LRU_GEN_FILE] = max(min_seq[LRU_GEN_ANON], lrugen->min_seq[LRU_GEN_FILE]);
-+      }
-+
-+      for (type = !can_swap; type < ANON_AND_FILE; type++) {
-+              if (min_seq[type] == lrugen->min_seq[type])
-+                      continue;
-+
-+              reset_ctrl_pos(lruvec, type, true);
-+              WRITE_ONCE(lrugen->min_seq[type], min_seq[type]);
-+              success = true;
-+      }
-+
-+      return success;
-+}
-+
-+static void inc_max_seq(struct lruvec *lruvec, unsigned long max_seq, bool can_swap)
-+{
-+      int prev, next;
-+      int type, zone;
-+      struct lru_gen_struct *lrugen = &lruvec->lrugen;
-+
-+      spin_lock_irq(&lruvec->lru_lock);
-+
-+      VM_WARN_ON_ONCE(!seq_is_valid(lruvec));
-+
-+      if (max_seq != lrugen->max_seq)
-+              goto unlock;
-+
-+      for (type = ANON_AND_FILE - 1; type >= 0; type--) {
-+              if (get_nr_gens(lruvec, type) != MAX_NR_GENS)
-+                      continue;
-+
-+              VM_WARN_ON_ONCE(type == LRU_GEN_FILE || can_swap);
-+
-+              inc_min_seq(lruvec, type);
-+      }
-+
-+      /*
-+       * Update the active/inactive LRU sizes for compatibility. Both sides of
-+       * the current max_seq need to be covered, since max_seq+1 can overlap
-+       * with min_seq[LRU_GEN_ANON] if swapping is constrained. And if they do
-+       * overlap, cold/hot inversion happens.
-+       */
-+      prev = lru_gen_from_seq(lrugen->max_seq - 1);
-+      next = lru_gen_from_seq(lrugen->max_seq + 1);
-+
-+      for (type = 0; type < ANON_AND_FILE; type++) {
-+              for (zone = 0; zone < MAX_NR_ZONES; zone++) {
-+                      enum lru_list lru = type * LRU_INACTIVE_FILE;
-+                      long delta = lrugen->nr_pages[prev][type][zone] -
-+                                   lrugen->nr_pages[next][type][zone];
-+
-+                      if (!delta)
-+                              continue;
-+
-+                      __update_lru_size(lruvec, lru, zone, delta);
-+                      __update_lru_size(lruvec, lru + LRU_ACTIVE, zone, -delta);
-+              }
-+      }
-+
-+      for (type = 0; type < ANON_AND_FILE; type++)
-+              reset_ctrl_pos(lruvec, type, false);
-+
-+      /* make sure preceding modifications appear */
-+      smp_store_release(&lrugen->max_seq, lrugen->max_seq + 1);
-+unlock:
-+      spin_unlock_irq(&lruvec->lru_lock);
-+}
-+
-+static bool should_run_aging(struct lruvec *lruvec, unsigned long max_seq, unsigned long *min_seq,
-+                           struct scan_control *sc, bool can_swap, unsigned long *nr_to_scan)
-+{
-+      int gen, type, zone;
-+      unsigned long old = 0;
-+      unsigned long young = 0;
-+      unsigned long total = 0;
-+      struct lru_gen_struct *lrugen = &lruvec->lrugen;
-+      struct mem_cgroup *memcg = lruvec_memcg(lruvec);
-+
-+      for (type = !can_swap; type < ANON_AND_FILE; type++) {
-+              unsigned long seq;
-+
-+              for (seq = min_seq[type]; seq <= max_seq; seq++) {
-+                      unsigned long size = 0;
-+
-+                      gen = lru_gen_from_seq(seq);
-+
-+                      for (zone = 0; zone < MAX_NR_ZONES; zone++)
-+                              size += max(READ_ONCE(lrugen->nr_pages[gen][type][zone]), 0L);
-+
-+                      total += size;
-+                      if (seq == max_seq)
-+                              young += size;
-+                      else if (seq + MIN_NR_GENS == max_seq)
-+                              old += size;
-+              }
-+      }
-+
-+      /* try to scrape all its memory if this memcg was deleted */
-+      *nr_to_scan = mem_cgroup_online(memcg) ? (total >> sc->priority) : total;
-+
-+      /*
-+       * The aging tries to be lazy to reduce the overhead, while the eviction
-+       * stalls when the number of generations reaches MIN_NR_GENS. Hence, the
-+       * ideal number of generations is MIN_NR_GENS+1.
-+       */
-+      if (min_seq[!can_swap] + MIN_NR_GENS > max_seq)
-+              return true;
-+      if (min_seq[!can_swap] + MIN_NR_GENS < max_seq)
-+              return false;
-+
-+      /*
-+       * It's also ideal to spread pages out evenly, i.e., 1/(MIN_NR_GENS+1)
-+       * of the total number of pages for each generation. A reasonable range
-+       * for this average portion is [1/MIN_NR_GENS, 1/(MIN_NR_GENS+2)]. The
-+       * aging cares about the upper bound of hot pages, while the eviction
-+       * cares about the lower bound of cold pages.
-+       */
-+      if (young * MIN_NR_GENS > total)
-+              return true;
-+      if (old * (MIN_NR_GENS + 2) < total)
-+              return true;
-+
-+      return false;
-+}
-+
-+static void age_lruvec(struct lruvec *lruvec, struct scan_control *sc)
-+{
-+      bool need_aging;
-+      unsigned long nr_to_scan;
-+      int swappiness = get_swappiness(lruvec, sc);
-+      struct mem_cgroup *memcg = lruvec_memcg(lruvec);
-+      DEFINE_MAX_SEQ(lruvec);
-+      DEFINE_MIN_SEQ(lruvec);
-+
-+      VM_WARN_ON_ONCE(sc->memcg_low_reclaim);
-+
-+      mem_cgroup_calculate_protection(NULL, memcg);
-+
-+      if (mem_cgroup_below_min(memcg))
-+              return;
-+
-+      need_aging = should_run_aging(lruvec, max_seq, min_seq, sc, swappiness, &nr_to_scan);
-+      if (need_aging)
-+              inc_max_seq(lruvec, max_seq, swappiness);
-+}
-+
-+static void lru_gen_age_node(struct pglist_data *pgdat, struct scan_control *sc)
-+{
-+      struct mem_cgroup *memcg;
-+
-+      VM_WARN_ON_ONCE(!current_is_kswapd());
-+
-+      memcg = mem_cgroup_iter(NULL, NULL, NULL);
-+      do {
-+              struct lruvec *lruvec = mem_cgroup_lruvec(memcg, pgdat);
-+
-+              age_lruvec(lruvec, sc);
-+
-+              cond_resched();
-+      } while ((memcg = mem_cgroup_iter(NULL, memcg, NULL)));
-+}
-+
-+/******************************************************************************
-+ *                          the eviction
-+ ******************************************************************************/
-+
-+static bool sort_page(struct lruvec *lruvec, struct page *page, int tier_idx)
-+{
-+      bool success;
-+      int gen = page_lru_gen(page);
-+      int type = page_is_file_lru(page);
-+      int zone = page_zonenum(page);
-+      int delta = thp_nr_pages(page);
-+      int refs = page_lru_refs(page);
-+      int tier = lru_tier_from_refs(refs);
-+      struct lru_gen_struct *lrugen = &lruvec->lrugen;
-+
-+      VM_WARN_ON_ONCE_PAGE(gen >= MAX_NR_GENS, page);
-+
-+      /* unevictable */
-+      if (!page_evictable(page)) {
-+              success = lru_gen_del_page(lruvec, page, true);
-+              VM_WARN_ON_ONCE_PAGE(!success, page);
-+              SetPageUnevictable(page);
-+              add_page_to_lru_list(page, lruvec);
-+              __count_vm_events(UNEVICTABLE_PGCULLED, delta);
-+              return true;
-+      }
-+
-+      /* dirty lazyfree */
-+      if (type == LRU_GEN_FILE && PageAnon(page) && PageDirty(page)) {
-+              success = lru_gen_del_page(lruvec, page, true);
-+              VM_WARN_ON_ONCE_PAGE(!success, page);
-+              SetPageSwapBacked(page);
-+              add_page_to_lru_list_tail(page, lruvec);
-+              return true;
-+      }
-+
-+      /* protected */
-+      if (tier > tier_idx) {
-+              int hist = lru_hist_from_seq(lrugen->min_seq[type]);
-+
-+              gen = page_inc_gen(lruvec, page, false);
-+              list_move_tail(&page->lru, &lrugen->lists[gen][type][zone]);
-+
-+              WRITE_ONCE(lrugen->protected[hist][type][tier - 1],
-+                         lrugen->protected[hist][type][tier - 1] + delta);
-+              __mod_lruvec_state(lruvec, WORKINGSET_ACTIVATE_BASE + type, delta);
-+              return true;
-+      }
-+
-+      /* waiting for writeback */
-+      if (PageLocked(page) || PageWriteback(page) ||
-+          (type == LRU_GEN_FILE && PageDirty(page))) {
-+              gen = page_inc_gen(lruvec, page, true);
-+              list_move(&page->lru, &lrugen->lists[gen][type][zone]);
-+              return true;
-+      }
-+
-+      return false;
-+}
-+
-+static bool isolate_page(struct lruvec *lruvec, struct page *page, struct scan_control *sc)
-+{
-+      bool success;
-+
-+      /* unmapping inhibited */
-+      if (!sc->may_unmap && page_mapped(page))
-+              return false;
-+
-+      /* swapping inhibited */
-+      if (!(sc->may_writepage && (sc->gfp_mask & __GFP_IO)) &&
-+          (PageDirty(page) ||
-+           (PageAnon(page) && !PageSwapCache(page))))
-+              return false;
-+
-+      /* raced with release_pages() */
-+      if (!get_page_unless_zero(page))
-+              return false;
-+
-+      /* raced with another isolation */
-+      if (!TestClearPageLRU(page)) {
-+              put_page(page);
-+              return false;
-+      }
-+
-+      /* see the comment on MAX_NR_TIERS */
-+      if (!PageReferenced(page))
-+              set_mask_bits(&page->flags, LRU_REFS_MASK | LRU_REFS_FLAGS, 0);
-+
-+      /* for shrink_page_list() */
-+      ClearPageReclaim(page);
-+      ClearPageReferenced(page);
-+
-+      success = lru_gen_del_page(lruvec, page, true);
-+      VM_WARN_ON_ONCE_PAGE(!success, page);
-+
-+      return true;
-+}
-+
-+static int scan_pages(struct lruvec *lruvec, struct scan_control *sc,
-+                    int type, int tier, struct list_head *list)
-+{
-+      int gen, zone;
-+      enum vm_event_item item;
-+      int sorted = 0;
-+      int scanned = 0;
-+      int isolated = 0;
-+      int remaining = MAX_LRU_BATCH;
-+      struct lru_gen_struct *lrugen = &lruvec->lrugen;
-+      struct mem_cgroup *memcg = lruvec_memcg(lruvec);
-+
-+      VM_WARN_ON_ONCE(!list_empty(list));
-+
-+      if (get_nr_gens(lruvec, type) == MIN_NR_GENS)
-+              return 0;
-+
-+      gen = lru_gen_from_seq(lrugen->min_seq[type]);
-+
-+      for (zone = sc->reclaim_idx; zone >= 0; zone--) {
-+              LIST_HEAD(moved);
-+              int skipped = 0;
-+              struct list_head *head = &lrugen->lists[gen][type][zone];
-+
-+              while (!list_empty(head)) {
-+                      struct page *page = lru_to_page(head);
-+                      int delta = thp_nr_pages(page);
-+
-+                      VM_WARN_ON_ONCE_PAGE(PageUnevictable(page), page);
-+                      VM_WARN_ON_ONCE_PAGE(PageActive(page), page);
-+                      VM_WARN_ON_ONCE_PAGE(page_is_file_lru(page) != type, page);
-+                      VM_WARN_ON_ONCE_PAGE(page_zonenum(page) != zone, page);
-+
-+                      scanned += delta;
-+
-+                      if (sort_page(lruvec, page, tier))
-+                              sorted += delta;
-+                      else if (isolate_page(lruvec, page, sc)) {
-+                              list_add(&page->lru, list);
-+                              isolated += delta;
-+                      } else {
-+                              list_move(&page->lru, &moved);
-+                              skipped += delta;
-+                      }
-+
-+                      if (!--remaining || max(isolated, skipped) >= MIN_LRU_BATCH)
-+                              break;
-+              }
-+
-+              if (skipped) {
-+                      list_splice(&moved, head);
-+                      __count_zid_vm_events(PGSCAN_SKIP, zone, skipped);
-+              }
-+
-+              if (!remaining || isolated >= MIN_LRU_BATCH)
-+                      break;
-+      }
-+
-+      item = current_is_kswapd() ? PGSCAN_KSWAPD : PGSCAN_DIRECT;
-+      if (!cgroup_reclaim(sc)) {
-+              __count_vm_events(item, isolated);
-+              __count_vm_events(PGREFILL, sorted);
-+      }
-+      __count_memcg_events(memcg, item, isolated);
-+      __count_memcg_events(memcg, PGREFILL, sorted);
-+      __count_vm_events(PGSCAN_ANON + type, isolated);
-+
-+      /*
-+       * There might not be eligible pages due to reclaim_idx, may_unmap and
-+       * may_writepage. Check the remaining to prevent livelock if it's not
-+       * making progress.
-+       */
-+      return isolated || !remaining ? scanned : 0;
-+}
-+
-+static int get_tier_idx(struct lruvec *lruvec, int type)
-+{
-+      int tier;
-+      struct ctrl_pos sp, pv;
-+
-+      /*
-+       * To leave a margin for fluctuations, use a larger gain factor (1:2).
-+       * This value is chosen because any other tier would have at least twice
-+       * as many refaults as the first tier.
-+       */
-+      read_ctrl_pos(lruvec, type, 0, 1, &sp);
-+      for (tier = 1; tier < MAX_NR_TIERS; tier++) {
-+              read_ctrl_pos(lruvec, type, tier, 2, &pv);
-+              if (!positive_ctrl_err(&sp, &pv))
-+                      break;
-+      }
-+
-+      return tier - 1;
-+}
-+
-+static int get_type_to_scan(struct lruvec *lruvec, int swappiness, int *tier_idx)
-+{
-+      int type, tier;
-+      struct ctrl_pos sp, pv;
-+      int gain[ANON_AND_FILE] = { swappiness, 200 - swappiness };
-+
-+      /*
-+       * Compare the first tier of anon with that of file to determine which
-+       * type to scan. Also need to compare other tiers of the selected type
-+       * with the first tier of the other type to determine the last tier (of
-+       * the selected type) to evict.
-+       */
-+      read_ctrl_pos(lruvec, LRU_GEN_ANON, 0, gain[LRU_GEN_ANON], &sp);
-+      read_ctrl_pos(lruvec, LRU_GEN_FILE, 0, gain[LRU_GEN_FILE], &pv);
-+      type = positive_ctrl_err(&sp, &pv);
-+
-+      read_ctrl_pos(lruvec, !type, 0, gain[!type], &sp);
-+      for (tier = 1; tier < MAX_NR_TIERS; tier++) {
-+              read_ctrl_pos(lruvec, type, tier, gain[type], &pv);
-+              if (!positive_ctrl_err(&sp, &pv))
-+                      break;
-+      }
-+
-+      *tier_idx = tier - 1;
-+
-+      return type;
-+}
-+
-+static int isolate_pages(struct lruvec *lruvec, struct scan_control *sc, int swappiness,
-+                       int *type_scanned, struct list_head *list)
-+{
-+      int i;
-+      int type;
-+      int scanned;
-+      int tier = -1;
-+      DEFINE_MIN_SEQ(lruvec);
-+
-+      /*
-+       * Try to make the obvious choice first. When anon and file are both
-+       * available from the same generation, interpret swappiness 1 as file
-+       * first and 200 as anon first.
-+       */
-+      if (!swappiness)
-+              type = LRU_GEN_FILE;
-+      else if (min_seq[LRU_GEN_ANON] < min_seq[LRU_GEN_FILE])
-+              type = LRU_GEN_ANON;
-+      else if (swappiness == 1)
-+              type = LRU_GEN_FILE;
-+      else if (swappiness == 200)
-+              type = LRU_GEN_ANON;
-+      else
-+              type = get_type_to_scan(lruvec, swappiness, &tier);
-+
-+      for (i = !swappiness; i < ANON_AND_FILE; i++) {
-+              if (tier < 0)
-+                      tier = get_tier_idx(lruvec, type);
-+
-+              scanned = scan_pages(lruvec, sc, type, tier, list);
-+              if (scanned)
-+                      break;
-+
-+              type = !type;
-+              tier = -1;
-+      }
-+
-+      *type_scanned = type;
-+
-+      return scanned;
-+}
-+
-+static int evict_pages(struct lruvec *lruvec, struct scan_control *sc, int swappiness)
-+{
-+      int type;
-+      int scanned;
-+      int reclaimed;
-+      LIST_HEAD(list);
-+      struct page *page;
-+      enum vm_event_item item;
-+      struct reclaim_stat stat;
-+      struct mem_cgroup *memcg = lruvec_memcg(lruvec);
-+      struct pglist_data *pgdat = lruvec_pgdat(lruvec);
-+
-+      spin_lock_irq(&lruvec->lru_lock);
-+
-+      scanned = isolate_pages(lruvec, sc, swappiness, &type, &list);
-+
-+      scanned += try_to_inc_min_seq(lruvec, swappiness);
-+
-+      if (get_nr_gens(lruvec, !swappiness) == MIN_NR_GENS)
-+              scanned = 0;
-+
-+      spin_unlock_irq(&lruvec->lru_lock);
-+
-+      if (list_empty(&list))
-+              return scanned;
-+
-+      reclaimed = shrink_page_list(&list, pgdat, sc, &stat, false);
-+
-+      list_for_each_entry(page, &list, lru) {
-+              /* restore LRU_REFS_FLAGS cleared by isolate_page() */
-+              if (PageWorkingset(page))
-+                      SetPageReferenced(page);
-+
-+              /* don't add rejected pages to the oldest generation */
-+              if (PageReclaim(page) &&
-+                  (PageDirty(page) || PageWriteback(page)))
-+                      ClearPageActive(page);
-+              else
-+                      SetPageActive(page);
-+      }
-+
-+      spin_lock_irq(&lruvec->lru_lock);
-+
-+      move_pages_to_lru(lruvec, &list);
-+
-+      item = current_is_kswapd() ? PGSTEAL_KSWAPD : PGSTEAL_DIRECT;
-+      if (!cgroup_reclaim(sc))
-+              __count_vm_events(item, reclaimed);
-+      __count_memcg_events(memcg, item, reclaimed);
-+      __count_vm_events(PGSTEAL_ANON + type, reclaimed);
-+
-+      spin_unlock_irq(&lruvec->lru_lock);
-+
-+      mem_cgroup_uncharge_list(&list);
-+      free_unref_page_list(&list);
-+
-+      sc->nr_reclaimed += reclaimed;
-+
-+      return scanned;
-+}
-+
-+static unsigned long get_nr_to_scan(struct lruvec *lruvec, struct scan_control *sc,
-+                                  bool can_swap)
-+{
-+      bool need_aging;
-+      unsigned long nr_to_scan;
-+      struct mem_cgroup *memcg = lruvec_memcg(lruvec);
-+      DEFINE_MAX_SEQ(lruvec);
-+      DEFINE_MIN_SEQ(lruvec);
-+
-+      if (mem_cgroup_below_min(memcg) ||
-+          (mem_cgroup_below_low(memcg) && !sc->memcg_low_reclaim))
-+              return 0;
-+
-+      need_aging = should_run_aging(lruvec, max_seq, min_seq, sc, can_swap, &nr_to_scan);
-+      if (!need_aging)
-+              return nr_to_scan;
-+
-+      /* skip the aging path at the default priority */
-+      if (sc->priority == DEF_PRIORITY)
-+              goto done;
-+
-+      /* leave the work to lru_gen_age_node() */
-+      if (current_is_kswapd())
-+              return 0;
-+
-+      inc_max_seq(lruvec, max_seq, can_swap);
-+done:
-+      return min_seq[!can_swap] + MIN_NR_GENS <= max_seq ? nr_to_scan : 0;
-+}
-+
-+static void lru_gen_shrink_lruvec(struct lruvec *lruvec, struct scan_control *sc)
-+{
-+      struct blk_plug plug;
-+      unsigned long scanned = 0;
-+
-+      lru_add_drain();
-+
-+      blk_start_plug(&plug);
-+
-+      while (true) {
-+              int delta;
-+              int swappiness;
-+              unsigned long nr_to_scan;
-+
-+              if (sc->may_swap)
-+                      swappiness = get_swappiness(lruvec, sc);
-+              else if (!cgroup_reclaim(sc) && get_swappiness(lruvec, sc))
-+                      swappiness = 1;
-+              else
-+                      swappiness = 0;
-+
-+              nr_to_scan = get_nr_to_scan(lruvec, sc, swappiness);
-+              if (!nr_to_scan)
-+                      break;
-+
-+              delta = evict_pages(lruvec, sc, swappiness);
-+              if (!delta)
-+                      break;
-+
-+              scanned += delta;
-+              if (scanned >= nr_to_scan)
-+                      break;
-+
-+              cond_resched();
-+      }
-+
-+      blk_finish_plug(&plug);
-+}
-+
- /******************************************************************************
-  *                          initialization
-  ******************************************************************************/
-@@ -2894,6 +3649,16 @@ static int __init init_lru_gen(void)
- };
- late_initcall(init_lru_gen);
-+#else /* !CONFIG_LRU_GEN */
-+
-+static void lru_gen_age_node(struct pglist_data *pgdat, struct scan_control *sc)
-+{
-+}
-+
-+static void lru_gen_shrink_lruvec(struct lruvec *lruvec, struct scan_control *sc)
-+{
-+}
-+
- #endif /* CONFIG_LRU_GEN */
- static void shrink_lruvec(struct lruvec *lruvec, struct scan_control *sc)
-@@ -2907,6 +3672,11 @@ static void shrink_lruvec(struct lruvec
-       bool proportional_reclaim;
-       struct blk_plug plug;
-+      if (lru_gen_enabled()) {
-+              lru_gen_shrink_lruvec(lruvec, sc);
-+              return;
-+      }
-+
-       get_scan_count(lruvec, sc, nr);
-       /* Record the original scan target for proportional adjustments later */
-@@ -3375,6 +4145,9 @@ static void snapshot_refaults(struct mem
-       struct lruvec *target_lruvec;
-       unsigned long refaults;
-+      if (lru_gen_enabled())
-+              return;
-+
-       target_lruvec = mem_cgroup_lruvec(target_memcg, pgdat);
-       refaults = lruvec_page_state(target_lruvec, WORKINGSET_ACTIVATE_ANON);
-       target_lruvec->refaults[0] = refaults;
-@@ -3739,12 +4512,16 @@ unsigned long try_to_free_mem_cgroup_pag
- }
- #endif
--static void age_active_anon(struct pglist_data *pgdat,
--                              struct scan_control *sc)
-+static void kswapd_age_node(struct pglist_data *pgdat, struct scan_control *sc)
- {
-       struct mem_cgroup *memcg;
-       struct lruvec *lruvec;
-+      if (lru_gen_enabled()) {
-+              lru_gen_age_node(pgdat, sc);
-+              return;
-+      }
-+
-       if (!can_age_anon_pages(pgdat, sc))
-               return;
-@@ -4061,12 +4838,11 @@ restart:
-               sc.may_swap = !nr_boost_reclaim;
-               /*
--               * Do some background aging of the anon list, to give
--               * pages a chance to be referenced before reclaiming. All
--               * pages are rotated regardless of classzone as this is
--               * about consistent aging.
-+               * Do some background aging, to give pages a chance to be
-+               * referenced before reclaiming. All pages are rotated
-+               * regardless of classzone as this is about consistent aging.
-                */
--              age_active_anon(pgdat, &sc);
-+              kswapd_age_node(pgdat, &sc);
-               /*
-                * If we're getting trouble reclaiming, start doing writepage
---- a/mm/workingset.c
-+++ b/mm/workingset.c
-@@ -187,7 +187,6 @@ static unsigned int bucket_order __read_
- static void *pack_shadow(int memcgid, pg_data_t *pgdat, unsigned long eviction,
-                        bool workingset)
- {
--      eviction >>= bucket_order;
-       eviction &= EVICTION_MASK;
-       eviction = (eviction << MEM_CGROUP_ID_SHIFT) | memcgid;
-       eviction = (eviction << NODES_SHIFT) | pgdat->node_id;
-@@ -212,10 +211,107 @@ static void unpack_shadow(void *shadow,
-       *memcgidp = memcgid;
-       *pgdat = NODE_DATA(nid);
--      *evictionp = entry << bucket_order;
-+      *evictionp = entry;
-       *workingsetp = workingset;
- }
-+#ifdef CONFIG_LRU_GEN
-+
-+static void *lru_gen_eviction(struct page *page)
-+{
-+      int hist;
-+      unsigned long token;
-+      unsigned long min_seq;
-+      struct lruvec *lruvec;
-+      struct lru_gen_struct *lrugen;
-+      int type = page_is_file_lru(page);
-+      int delta = thp_nr_pages(page);
-+      int refs = page_lru_refs(page);
-+      int tier = lru_tier_from_refs(refs);
-+      struct mem_cgroup *memcg = page_memcg(page);
-+      struct pglist_data *pgdat = page_pgdat(page);
-+
-+      BUILD_BUG_ON(LRU_GEN_WIDTH + LRU_REFS_WIDTH > BITS_PER_LONG - EVICTION_SHIFT);
-+
-+      lruvec = mem_cgroup_lruvec(memcg, pgdat);
-+      lrugen = &lruvec->lrugen;
-+      min_seq = READ_ONCE(lrugen->min_seq[type]);
-+      token = (min_seq << LRU_REFS_WIDTH) | max(refs - 1, 0);
-+
-+      hist = lru_hist_from_seq(min_seq);
-+      atomic_long_add(delta, &lrugen->evicted[hist][type][tier]);
-+
-+      return pack_shadow(mem_cgroup_id(memcg), pgdat, token, refs);
-+}
-+
-+static void lru_gen_refault(struct page *page, void *shadow)
-+{
-+      int hist, tier, refs;
-+      int memcg_id;
-+      bool workingset;
-+      unsigned long token;
-+      unsigned long min_seq;
-+      struct lruvec *lruvec;
-+      struct lru_gen_struct *lrugen;
-+      struct mem_cgroup *memcg;
-+      struct pglist_data *pgdat;
-+      int type = page_is_file_lru(page);
-+      int delta = thp_nr_pages(page);
-+
-+      unpack_shadow(shadow, &memcg_id, &pgdat, &token, &workingset);
-+
-+      if (pgdat != page_pgdat(page))
-+              return;
-+
-+      rcu_read_lock();
-+
-+      memcg = page_memcg_rcu(page);
-+      if (memcg_id != mem_cgroup_id(memcg))
-+              goto unlock;
-+
-+      lruvec = mem_cgroup_lruvec(memcg, pgdat);
-+      lrugen = &lruvec->lrugen;
-+
-+      min_seq = READ_ONCE(lrugen->min_seq[type]);
-+      if ((token >> LRU_REFS_WIDTH) != (min_seq & (EVICTION_MASK >> LRU_REFS_WIDTH)))
-+              goto unlock;
-+
-+      hist = lru_hist_from_seq(min_seq);
-+      /* see the comment in page_lru_refs() */
-+      refs = (token & (BIT(LRU_REFS_WIDTH) - 1)) + workingset;
-+      tier = lru_tier_from_refs(refs);
-+
-+      atomic_long_add(delta, &lrugen->refaulted[hist][type][tier]);
-+      mod_lruvec_state(lruvec, WORKINGSET_REFAULT_BASE + type, delta);
-+
-+      /*
-+       * Count the following two cases as stalls:
-+       * 1. For pages accessed through page tables, hotter pages pushed out
-+       *    hot pages which refaulted immediately.
-+       * 2. For pages accessed multiple times through file descriptors,
-+       *    numbers of accesses might have been out of the range.
-+       */
-+      if (lru_gen_in_fault() || refs == BIT(LRU_REFS_WIDTH)) {
-+              SetPageWorkingset(page);
-+              mod_lruvec_state(lruvec, WORKINGSET_RESTORE_BASE + type, delta);
-+      }
-+unlock:
-+      rcu_read_unlock();
-+}
-+
-+#else /* !CONFIG_LRU_GEN */
-+
-+static void *lru_gen_eviction(struct page *page)
-+{
-+      return NULL;
-+}
-+
-+static void lru_gen_refault(struct page *page, void *shadow)
-+{
-+}
-+
-+#endif /* CONFIG_LRU_GEN */
-+
- /**
-  * workingset_age_nonresident - age non-resident entries as LRU ages
-  * @lruvec: the lruvec that was aged
-@@ -264,10 +360,14 @@ void *workingset_eviction(struct page *p
-       VM_BUG_ON_PAGE(page_count(page), page);
-       VM_BUG_ON_PAGE(!PageLocked(page), page);
-+      if (lru_gen_enabled())
-+              return lru_gen_eviction(page);
-+
-       lruvec = mem_cgroup_lruvec(target_memcg, pgdat);
-       /* XXX: target_memcg can be NULL, go through lruvec */
-       memcgid = mem_cgroup_id(lruvec_memcg(lruvec));
-       eviction = atomic_long_read(&lruvec->nonresident_age);
-+      eviction >>= bucket_order;
-       workingset_age_nonresident(lruvec, thp_nr_pages(page));
-       return pack_shadow(memcgid, pgdat, eviction, PageWorkingset(page));
- }
-@@ -296,7 +396,13 @@ void workingset_refault(struct page *pag
-       bool workingset;
-       int memcgid;
-+      if (lru_gen_enabled()) {
-+              lru_gen_refault(page, shadow);
-+              return;
-+      }
-+
-       unpack_shadow(shadow, &memcgid, &pgdat, &eviction, &workingset);
-+      eviction <<= bucket_order;
-       rcu_read_lock();
-       /*
diff --git a/target/linux/generic/backport-5.15/020-v6.1-07-mm-multi-gen-LRU-exploit-locality-in-rmap.patch b/target/linux/generic/backport-5.15/020-v6.1-07-mm-multi-gen-LRU-exploit-locality-in-rmap.patch
deleted file mode 100644 (file)
index 40e51b4..0000000
+++ /dev/null
@@ -1,491 +0,0 @@
-From e4277535f6d6708bb19b88c4bad155832671d69b Mon Sep 17 00:00:00 2001
-From: Yu Zhao <[email protected]>
-Date: Sun, 18 Sep 2022 02:00:04 -0600
-Subject: [PATCH 07/29] mm: multi-gen LRU: exploit locality in rmap
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-Searching the rmap for PTEs mapping each page on an LRU list (to test and
-clear the accessed bit) can be expensive because pages from different VMAs
-(PA space) are not cache friendly to the rmap (VA space).  For workloads
-mostly using mapped pages, searching the rmap can incur the highest CPU
-cost in the reclaim path.
-
-This patch exploits spatial locality to reduce the trips into the rmap.
-When shrink_page_list() walks the rmap and finds a young PTE, a new
-function lru_gen_look_around() scans at most BITS_PER_LONG-1 adjacent
-PTEs.  On finding another young PTE, it clears the accessed bit and
-updates the gen counter of the page mapped by this PTE to
-(max_seq%MAX_NR_GENS)+1.
-
-Server benchmark results:
-  Single workload:
-    fio (buffered I/O): no change
-
-  Single workload:
-    memcached (anon): +[3, 5]%
-                Ops/sec      KB/sec
-      patch1-6: 1106168.46   43025.04
-      patch1-7: 1147696.57   44640.29
-
-  Configurations:
-    no change
-
-Client benchmark results:
-  kswapd profiles:
-    patch1-6
-      39.03%  lzo1x_1_do_compress (real work)
-      18.47%  page_vma_mapped_walk (overhead)
-       6.74%  _raw_spin_unlock_irq
-       3.97%  do_raw_spin_lock
-       2.49%  ptep_clear_flush
-       2.48%  anon_vma_interval_tree_iter_first
-       1.92%  page_referenced_one
-       1.88%  __zram_bvec_write
-       1.48%  memmove
-       1.31%  vma_interval_tree_iter_next
-
-    patch1-7
-      48.16%  lzo1x_1_do_compress (real work)
-       8.20%  page_vma_mapped_walk (overhead)
-       7.06%  _raw_spin_unlock_irq
-       2.92%  ptep_clear_flush
-       2.53%  __zram_bvec_write
-       2.11%  do_raw_spin_lock
-       2.02%  memmove
-       1.93%  lru_gen_look_around
-       1.56%  free_unref_page_list
-       1.40%  memset
-
-  Configurations:
-    no change
-
-Link: https://lkml.kernel.org/r/[email protected]
-Signed-off-by: Yu Zhao <[email protected]>
-Acked-by: Barry Song <[email protected]>
-Acked-by: Brian Geffon <[email protected]>
-Acked-by: Jan Alexander Steffens (heftig) <[email protected]>
-Acked-by: Oleksandr Natalenko <[email protected]>
-Acked-by: Steven Barrett <[email protected]>
-Acked-by: Suleiman Souhlal <[email protected]>
-Tested-by: Daniel Byrne <[email protected]>
-Tested-by: Donald Carr <[email protected]>
-Tested-by: Holger Hoffstätte <[email protected]>
-Tested-by: Konstantin Kharlamov <[email protected]>
-Tested-by: Shuang Zhai <[email protected]>
-Tested-by: Sofia Trinh <[email protected]>
-Tested-by: Vaibhav Jain <[email protected]>
-Cc: Andi Kleen <[email protected]>
-Cc: Aneesh Kumar K.V <[email protected]>
-Cc: Catalin Marinas <[email protected]>
-Cc: Dave Hansen <[email protected]>
-Cc: Hillf Danton <[email protected]>
-Cc: Jens Axboe <[email protected]>
-Cc: Johannes Weiner <[email protected]>
-Cc: Jonathan Corbet <[email protected]>
-Cc: Linus Torvalds <[email protected]>
-Cc: Matthew Wilcox <[email protected]>
-Cc: Mel Gorman <[email protected]>
-Cc: Miaohe Lin <[email protected]>
-Cc: Michael Larabel <[email protected]>
-Cc: Michal Hocko <[email protected]>
-Cc: Mike Rapoport <[email protected]>
-Cc: Mike Rapoport <[email protected]>
-Cc: Peter Zijlstra <[email protected]>
-Cc: Qi Zheng <[email protected]>
-Cc: Tejun Heo <[email protected]>
-Cc: Vlastimil Babka <[email protected]>
-Cc: Will Deacon <[email protected]>
-Signed-off-by: Andrew Morton <[email protected]>
----
- include/linux/memcontrol.h |  31 +++++++
- include/linux/mmzone.h     |   6 ++
- mm/internal.h              |   1 +
- mm/memcontrol.c            |   1 +
- mm/rmap.c                  |   7 ++
- mm/swap.c                  |   4 +-
- mm/vmscan.c                | 184 +++++++++++++++++++++++++++++++++++++
- 7 files changed, 232 insertions(+), 2 deletions(-)
-
---- a/include/linux/memcontrol.h
-+++ b/include/linux/memcontrol.h
-@@ -447,6 +447,7 @@ static inline struct obj_cgroup *__page_
-  * - LRU isolation
-  * - lock_page_memcg()
-  * - exclusive reference
-+ * - mem_cgroup_trylock_pages()
-  *
-  * For a kmem page a caller should hold an rcu read lock to protect memcg
-  * associated with a kmem page from being released.
-@@ -502,6 +503,7 @@ static inline struct mem_cgroup *page_me
-  * - LRU isolation
-  * - lock_page_memcg()
-  * - exclusive reference
-+ * - mem_cgroup_trylock_pages()
-  *
-  * For a kmem page a caller should hold an rcu read lock to protect memcg
-  * associated with a kmem page from being released.
-@@ -958,6 +960,23 @@ void unlock_page_memcg(struct page *page
- void __mod_memcg_state(struct mem_cgroup *memcg, int idx, int val);
-+/* try to stablize page_memcg() for all the pages in a memcg */
-+static inline bool mem_cgroup_trylock_pages(struct mem_cgroup *memcg)
-+{
-+      rcu_read_lock();
-+
-+      if (mem_cgroup_disabled() || !atomic_read(&memcg->moving_account))
-+              return true;
-+
-+      rcu_read_unlock();
-+      return false;
-+}
-+
-+static inline void mem_cgroup_unlock_pages(void)
-+{
-+      rcu_read_unlock();
-+}
-+
- /* idx can be of type enum memcg_stat_item or node_stat_item */
- static inline void mod_memcg_state(struct mem_cgroup *memcg,
-                                  int idx, int val)
-@@ -1374,6 +1393,18 @@ static inline void unlock_page_memcg(str
- {
- }
-+static inline bool mem_cgroup_trylock_pages(struct mem_cgroup *memcg)
-+{
-+      /* to match page_memcg_rcu() */
-+      rcu_read_lock();
-+      return true;
-+}
-+
-+static inline void mem_cgroup_unlock_pages(void)
-+{
-+      rcu_read_unlock();
-+}
-+
- static inline void mem_cgroup_handle_over_high(void)
- {
- }
---- a/include/linux/mmzone.h
-+++ b/include/linux/mmzone.h
-@@ -352,6 +352,7 @@ enum lruvec_flags {
- #ifndef __GENERATING_BOUNDS_H
- struct lruvec;
-+struct page_vma_mapped_walk;
- #define LRU_GEN_MASK          ((BIT(LRU_GEN_WIDTH) - 1) << LRU_GEN_PGOFF)
- #define LRU_REFS_MASK         ((BIT(LRU_REFS_WIDTH) - 1) << LRU_REFS_PGOFF)
-@@ -407,6 +408,7 @@ struct lru_gen_struct {
- };
- void lru_gen_init_lruvec(struct lruvec *lruvec);
-+void lru_gen_look_around(struct page_vma_mapped_walk *pvmw);
- #ifdef CONFIG_MEMCG
- void lru_gen_init_memcg(struct mem_cgroup *memcg);
-@@ -419,6 +421,10 @@ static inline void lru_gen_init_lruvec(s
- {
- }
-+static inline void lru_gen_look_around(struct page_vma_mapped_walk *pvmw)
-+{
-+}
-+
- #ifdef CONFIG_MEMCG
- static inline void lru_gen_init_memcg(struct mem_cgroup *memcg)
- {
---- a/mm/internal.h
-+++ b/mm/internal.h
-@@ -35,6 +35,7 @@
- void page_writeback_init(void);
- vm_fault_t do_swap_page(struct vm_fault *vmf);
-+void activate_page(struct page *page);
- void free_pgtables(struct mmu_gather *tlb, struct vm_area_struct *start_vma,
-               unsigned long floor, unsigned long ceiling);
---- a/mm/memcontrol.c
-+++ b/mm/memcontrol.c
-@@ -2798,6 +2798,7 @@ static void commit_charge(struct page *p
-        * - LRU isolation
-        * - lock_page_memcg()
-        * - exclusive reference
-+       * - mem_cgroup_trylock_pages()
-        */
-       page->memcg_data = (unsigned long)memcg;
- }
---- a/mm/rmap.c
-+++ b/mm/rmap.c
-@@ -73,6 +73,7 @@
- #include <linux/page_idle.h>
- #include <linux/memremap.h>
- #include <linux/userfaultfd_k.h>
-+#include <linux/mm_inline.h>
- #include <asm/tlbflush.h>
-@@ -793,6 +794,12 @@ static bool page_referenced_one(struct p
-               }
-               if (pvmw.pte) {
-+                      if (lru_gen_enabled() && pte_young(*pvmw.pte) &&
-+                          !(vma->vm_flags & (VM_SEQ_READ | VM_RAND_READ))) {
-+                              lru_gen_look_around(&pvmw);
-+                              referenced++;
-+                      }
-+
-                       if (ptep_clear_flush_young_notify(vma, address,
-                                               pvmw.pte)) {
-                               /*
---- a/mm/swap.c
-+++ b/mm/swap.c
-@@ -325,7 +325,7 @@ static bool need_activate_page_drain(int
-       return pagevec_count(&per_cpu(lru_pvecs.activate_page, cpu)) != 0;
- }
--static void activate_page(struct page *page)
-+void activate_page(struct page *page)
- {
-       page = compound_head(page);
-       if (PageLRU(page) && !PageActive(page) && !PageUnevictable(page)) {
-@@ -345,7 +345,7 @@ static inline void activate_page_drain(i
- {
- }
--static void activate_page(struct page *page)
-+void activate_page(struct page *page)
- {
-       struct lruvec *lruvec;
---- a/mm/vmscan.c
-+++ b/mm/vmscan.c
-@@ -1409,6 +1409,11 @@ retry:
-               if (!sc->may_unmap && page_mapped(page))
-                       goto keep_locked;
-+              /* page_update_gen() tried to promote this page? */
-+              if (lru_gen_enabled() && !ignore_references &&
-+                  page_mapped(page) && PageReferenced(page))
-+                      goto keep_locked;
-+
-               may_enter_fs = (sc->gfp_mask & __GFP_FS) ||
-                       (PageSwapCache(page) && (sc->gfp_mask & __GFP_IO));
-@@ -2990,6 +2995,29 @@ static bool positive_ctrl_err(struct ctr
-  *                          the aging
-  ******************************************************************************/
-+/* promote pages accessed through page tables */
-+static int page_update_gen(struct page *page, int gen)
-+{
-+      unsigned long new_flags, old_flags = READ_ONCE(page->flags);
-+
-+      VM_WARN_ON_ONCE(gen >= MAX_NR_GENS);
-+      VM_WARN_ON_ONCE(!rcu_read_lock_held());
-+
-+      do {
-+              /* lru_gen_del_page() has isolated this page? */
-+              if (!(old_flags & LRU_GEN_MASK)) {
-+                      /* for shrink_page_list() */
-+                      new_flags = old_flags | BIT(PG_referenced);
-+                      continue;
-+              }
-+
-+              new_flags = old_flags & ~(LRU_GEN_MASK | LRU_REFS_MASK | LRU_REFS_FLAGS);
-+              new_flags |= (gen + 1UL) << LRU_GEN_PGOFF;
-+      } while (!try_cmpxchg(&page->flags, &old_flags, new_flags));
-+
-+      return ((old_flags & LRU_GEN_MASK) >> LRU_GEN_PGOFF) - 1;
-+}
-+
- /* protect pages accessed multiple times through file descriptors */
- static int page_inc_gen(struct lruvec *lruvec, struct page *page, bool reclaiming)
- {
-@@ -3001,6 +3029,11 @@ static int page_inc_gen(struct lruvec *l
-       VM_WARN_ON_ONCE_PAGE(!(old_flags & LRU_GEN_MASK), page);
-       do {
-+              new_gen = ((old_flags & LRU_GEN_MASK) >> LRU_GEN_PGOFF) - 1;
-+              /* page_update_gen() has promoted this page? */
-+              if (new_gen >= 0 && new_gen != old_gen)
-+                      return new_gen;
-+
-               new_gen = (old_gen + 1) % MAX_NR_GENS;
-               new_flags = old_flags & ~(LRU_GEN_MASK | LRU_REFS_MASK | LRU_REFS_FLAGS);
-@@ -3015,6 +3048,43 @@ static int page_inc_gen(struct lruvec *l
-       return new_gen;
- }
-+static unsigned long get_pte_pfn(pte_t pte, struct vm_area_struct *vma, unsigned long addr)
-+{
-+      unsigned long pfn = pte_pfn(pte);
-+
-+      VM_WARN_ON_ONCE(addr < vma->vm_start || addr >= vma->vm_end);
-+
-+      if (!pte_present(pte) || is_zero_pfn(pfn))
-+              return -1;
-+
-+      if (WARN_ON_ONCE(pte_devmap(pte) || pte_special(pte)))
-+              return -1;
-+
-+      if (WARN_ON_ONCE(!pfn_valid(pfn)))
-+              return -1;
-+
-+      return pfn;
-+}
-+
-+static struct page *get_pfn_page(unsigned long pfn, struct mem_cgroup *memcg,
-+                               struct pglist_data *pgdat)
-+{
-+      struct page *page;
-+
-+      /* try to avoid unnecessary memory loads */
-+      if (pfn < pgdat->node_start_pfn || pfn >= pgdat_end_pfn(pgdat))
-+              return NULL;
-+
-+      page = compound_head(pfn_to_page(pfn));
-+      if (page_to_nid(page) != pgdat->node_id)
-+              return NULL;
-+
-+      if (page_memcg_rcu(page) != memcg)
-+              return NULL;
-+
-+      return page;
-+}
-+
- static void inc_min_seq(struct lruvec *lruvec, int type)
- {
-       struct lru_gen_struct *lrugen = &lruvec->lrugen;
-@@ -3214,6 +3284,114 @@ static void lru_gen_age_node(struct pgli
-       } while ((memcg = mem_cgroup_iter(NULL, memcg, NULL)));
- }
-+/*
-+ * This function exploits spatial locality when shrink_page_list() walks the
-+ * rmap. It scans the adjacent PTEs of a young PTE and promotes hot pages.
-+ */
-+void lru_gen_look_around(struct page_vma_mapped_walk *pvmw)
-+{
-+      int i;
-+      pte_t *pte;
-+      unsigned long start;
-+      unsigned long end;
-+      unsigned long addr;
-+      unsigned long bitmap[BITS_TO_LONGS(MIN_LRU_BATCH)] = {};
-+      struct page *page = pvmw->page;
-+      struct mem_cgroup *memcg = page_memcg(page);
-+      struct pglist_data *pgdat = page_pgdat(page);
-+      struct lruvec *lruvec = mem_cgroup_lruvec(memcg, pgdat);
-+      DEFINE_MAX_SEQ(lruvec);
-+      int old_gen, new_gen = lru_gen_from_seq(max_seq);
-+
-+      lockdep_assert_held(pvmw->ptl);
-+      VM_WARN_ON_ONCE_PAGE(PageLRU(page), page);
-+
-+      if (spin_is_contended(pvmw->ptl))
-+              return;
-+
-+      start = max(pvmw->address & PMD_MASK, pvmw->vma->vm_start);
-+      end = min(pvmw->address | ~PMD_MASK, pvmw->vma->vm_end - 1) + 1;
-+
-+      if (end - start > MIN_LRU_BATCH * PAGE_SIZE) {
-+              if (pvmw->address - start < MIN_LRU_BATCH * PAGE_SIZE / 2)
-+                      end = start + MIN_LRU_BATCH * PAGE_SIZE;
-+              else if (end - pvmw->address < MIN_LRU_BATCH * PAGE_SIZE / 2)
-+                      start = end - MIN_LRU_BATCH * PAGE_SIZE;
-+              else {
-+                      start = pvmw->address - MIN_LRU_BATCH * PAGE_SIZE / 2;
-+                      end = pvmw->address + MIN_LRU_BATCH * PAGE_SIZE / 2;
-+              }
-+      }
-+
-+      pte = pvmw->pte - (pvmw->address - start) / PAGE_SIZE;
-+
-+      rcu_read_lock();
-+      arch_enter_lazy_mmu_mode();
-+
-+      for (i = 0, addr = start; addr != end; i++, addr += PAGE_SIZE) {
-+              unsigned long pfn;
-+
-+              pfn = get_pte_pfn(pte[i], pvmw->vma, addr);
-+              if (pfn == -1)
-+                      continue;
-+
-+              if (!pte_young(pte[i]))
-+                      continue;
-+
-+              page = get_pfn_page(pfn, memcg, pgdat);
-+              if (!page)
-+                      continue;
-+
-+              if (!ptep_test_and_clear_young(pvmw->vma, addr, pte + i))
-+                      VM_WARN_ON_ONCE(true);
-+
-+              if (pte_dirty(pte[i]) && !PageDirty(page) &&
-+                  !(PageAnon(page) && PageSwapBacked(page) &&
-+                    !PageSwapCache(page)))
-+                      set_page_dirty(page);
-+
-+              old_gen = page_lru_gen(page);
-+              if (old_gen < 0)
-+                      SetPageReferenced(page);
-+              else if (old_gen != new_gen)
-+                      __set_bit(i, bitmap);
-+      }
-+
-+      arch_leave_lazy_mmu_mode();
-+      rcu_read_unlock();
-+
-+      if (bitmap_weight(bitmap, MIN_LRU_BATCH) < PAGEVEC_SIZE) {
-+              for_each_set_bit(i, bitmap, MIN_LRU_BATCH) {
-+                      page = pte_page(pte[i]);
-+                      activate_page(page);
-+              }
-+              return;
-+      }
-+
-+      /* page_update_gen() requires stable page_memcg() */
-+      if (!mem_cgroup_trylock_pages(memcg))
-+              return;
-+
-+      spin_lock_irq(&lruvec->lru_lock);
-+      new_gen = lru_gen_from_seq(lruvec->lrugen.max_seq);
-+
-+      for_each_set_bit(i, bitmap, MIN_LRU_BATCH) {
-+              page = compound_head(pte_page(pte[i]));
-+              if (page_memcg_rcu(page) != memcg)
-+                      continue;
-+
-+              old_gen = page_update_gen(page, new_gen);
-+              if (old_gen < 0 || old_gen == new_gen)
-+                      continue;
-+
-+              lru_gen_update_size(lruvec, page, old_gen, new_gen);
-+      }
-+
-+      spin_unlock_irq(&lruvec->lru_lock);
-+
-+      mem_cgroup_unlock_pages();
-+}
-+
- /******************************************************************************
-  *                          the eviction
-  ******************************************************************************/
-@@ -3250,6 +3428,12 @@ static bool sort_page(struct lruvec *lru
-               return true;
-       }
-+      /* promoted */
-+      if (gen != lru_gen_from_seq(lrugen->min_seq[type])) {
-+              list_move(&page->lru, &lrugen->lists[gen][type][zone]);
-+              return true;
-+      }
-+
-       /* protected */
-       if (tier > tier_idx) {
-               int hist = lru_hist_from_seq(lrugen->min_seq[type]);
diff --git a/target/linux/generic/backport-5.15/020-v6.1-08-mm-multi-gen-LRU-support-page-table-walks.patch b/target/linux/generic/backport-5.15/020-v6.1-08-mm-multi-gen-LRU-support-page-table-walks.patch
deleted file mode 100644 (file)
index 4cfd247..0000000
+++ /dev/null
@@ -1,1687 +0,0 @@
-From 05223c4e80b34e29f2255c04ffebc2c4475e7593 Mon Sep 17 00:00:00 2001
-From: Yu Zhao <[email protected]>
-Date: Sun, 18 Sep 2022 02:00:05 -0600
-Subject: [PATCH 08/29] mm: multi-gen LRU: support page table walks
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-To further exploit spatial locality, the aging prefers to walk page tables
-to search for young PTEs and promote hot pages.  A kill switch will be
-added in the next patch to disable this behavior.  When disabled, the
-aging relies on the rmap only.
-
-NB: this behavior has nothing similar with the page table scanning in the
-2.4 kernel [1], which searches page tables for old PTEs, adds cold pages
-to swapcache and unmaps them.
-
-To avoid confusion, the term "iteration" specifically means the traversal
-of an entire mm_struct list; the term "walk" will be applied to page
-tables and the rmap, as usual.
-
-An mm_struct list is maintained for each memcg, and an mm_struct follows
-its owner task to the new memcg when this task is migrated.  Given an
-lruvec, the aging iterates lruvec_memcg()->mm_list and calls
-walk_page_range() with each mm_struct on this list to promote hot pages
-before it increments max_seq.
-
-When multiple page table walkers iterate the same list, each of them gets
-a unique mm_struct; therefore they can run concurrently.  Page table
-walkers ignore any misplaced pages, e.g., if an mm_struct was migrated,
-pages it left in the previous memcg will not be promoted when its current
-memcg is under reclaim.  Similarly, page table walkers will not promote
-pages from nodes other than the one under reclaim.
-
-This patch uses the following optimizations when walking page tables:
-1. It tracks the usage of mm_struct's between context switches so that
-   page table walkers can skip processes that have been sleeping since
-   the last iteration.
-2. It uses generational Bloom filters to record populated branches so
-   that page table walkers can reduce their search space based on the
-   query results, e.g., to skip page tables containing mostly holes or
-   misplaced pages.
-3. It takes advantage of the accessed bit in non-leaf PMD entries when
-   CONFIG_ARCH_HAS_NONLEAF_PMD_YOUNG=y.
-4. It does not zigzag between a PGD table and the same PMD table
-   spanning multiple VMAs. IOW, it finishes all the VMAs within the
-   range of the same PMD table before it returns to a PGD table. This
-   improves the cache performance for workloads that have large
-   numbers of tiny VMAs [2], especially when CONFIG_PGTABLE_LEVELS=5.
-
-Server benchmark results:
-  Single workload:
-    fio (buffered I/O): no change
-
-  Single workload:
-    memcached (anon): +[8, 10]%
-                Ops/sec      KB/sec
-      patch1-7: 1147696.57   44640.29
-      patch1-8: 1245274.91   48435.66
-
-  Configurations:
-    no change
-
-Client benchmark results:
-  kswapd profiles:
-    patch1-7
-      48.16%  lzo1x_1_do_compress (real work)
-       8.20%  page_vma_mapped_walk (overhead)
-       7.06%  _raw_spin_unlock_irq
-       2.92%  ptep_clear_flush
-       2.53%  __zram_bvec_write
-       2.11%  do_raw_spin_lock
-       2.02%  memmove
-       1.93%  lru_gen_look_around
-       1.56%  free_unref_page_list
-       1.40%  memset
-
-    patch1-8
-      49.44%  lzo1x_1_do_compress (real work)
-       6.19%  page_vma_mapped_walk (overhead)
-       5.97%  _raw_spin_unlock_irq
-       3.13%  get_pfn_page
-       2.85%  ptep_clear_flush
-       2.42%  __zram_bvec_write
-       2.08%  do_raw_spin_lock
-       1.92%  memmove
-       1.44%  alloc_zspage
-       1.36%  memset
-
-  Configurations:
-    no change
-
-Thanks to the following developers for their efforts [3].
-  kernel test robot <[email protected]>
-
-[1] https://lwn.net/Articles/23732/
-[2] https://llvm.org/docs/ScudoHardenedAllocator.html
-[3] https://lore.kernel.org/r/[email protected]/
-
-Link: https://lkml.kernel.org/r/[email protected]
-Signed-off-by: Yu Zhao <[email protected]>
-Acked-by: Brian Geffon <[email protected]>
-Acked-by: Jan Alexander Steffens (heftig) <[email protected]>
-Acked-by: Oleksandr Natalenko <[email protected]>
-Acked-by: Steven Barrett <[email protected]>
-Acked-by: Suleiman Souhlal <[email protected]>
-Tested-by: Daniel Byrne <[email protected]>
-Tested-by: Donald Carr <[email protected]>
-Tested-by: Holger Hoffstätte <[email protected]>
-Tested-by: Konstantin Kharlamov <[email protected]>
-Tested-by: Shuang Zhai <[email protected]>
-Tested-by: Sofia Trinh <[email protected]>
-Tested-by: Vaibhav Jain <[email protected]>
-Cc: Andi Kleen <[email protected]>
-Cc: Aneesh Kumar K.V <[email protected]>
-Cc: Barry Song <[email protected]>
-Cc: Catalin Marinas <[email protected]>
-Cc: Dave Hansen <[email protected]>
-Cc: Hillf Danton <[email protected]>
-Cc: Jens Axboe <[email protected]>
-Cc: Johannes Weiner <[email protected]>
-Cc: Jonathan Corbet <[email protected]>
-Cc: Linus Torvalds <[email protected]>
-Cc: Matthew Wilcox <[email protected]>
-Cc: Mel Gorman <[email protected]>
-Cc: Miaohe Lin <[email protected]>
-Cc: Michael Larabel <[email protected]>
-Cc: Michal Hocko <[email protected]>
-Cc: Mike Rapoport <[email protected]>
-Cc: Mike Rapoport <[email protected]>
-Cc: Peter Zijlstra <[email protected]>
-Cc: Qi Zheng <[email protected]>
-Cc: Tejun Heo <[email protected]>
-Cc: Vlastimil Babka <[email protected]>
-Cc: Will Deacon <[email protected]>
-Signed-off-by: Andrew Morton <[email protected]>
----
- fs/exec.c                  |    2 +
- include/linux/memcontrol.h |    5 +
- include/linux/mm_types.h   |   76 +++
- include/linux/mmzone.h     |   56 +-
- include/linux/swap.h       |    4 +
- kernel/exit.c              |    1 +
- kernel/fork.c              |    9 +
- kernel/sched/core.c        |    1 +
- mm/memcontrol.c            |   25 +
- mm/vmscan.c                | 1010 +++++++++++++++++++++++++++++++++++-
- 10 files changed, 1172 insertions(+), 17 deletions(-)
-
---- a/fs/exec.c
-+++ b/fs/exec.c
-@@ -1014,6 +1014,7 @@ static int exec_mmap(struct mm_struct *m
-       active_mm = tsk->active_mm;
-       tsk->active_mm = mm;
-       tsk->mm = mm;
-+      lru_gen_add_mm(mm);
-       /*
-        * This prevents preemption while active_mm is being loaded and
-        * it and mm are being updated, which could cause problems for
-@@ -1029,6 +1030,7 @@ static int exec_mmap(struct mm_struct *m
-       tsk->mm->vmacache_seqnum = 0;
-       vmacache_flush(tsk);
-       task_unlock(tsk);
-+      lru_gen_use_mm(mm);
-       if (old_mm) {
-               mmap_read_unlock(old_mm);
-               BUG_ON(active_mm != old_mm);
---- a/include/linux/memcontrol.h
-+++ b/include/linux/memcontrol.h
-@@ -353,6 +353,11 @@ struct mem_cgroup {
-       struct deferred_split deferred_split_queue;
- #endif
-+#ifdef CONFIG_LRU_GEN
-+      /* per-memcg mm_struct list */
-+      struct lru_gen_mm_list mm_list;
-+#endif
-+
-       struct mem_cgroup_per_node *nodeinfo[];
- };
---- a/include/linux/mm_types.h
-+++ b/include/linux/mm_types.h
-@@ -580,6 +580,22 @@ struct mm_struct {
- #ifdef CONFIG_IOMMU_SUPPORT
-               u32 pasid;
- #endif
-+#ifdef CONFIG_LRU_GEN
-+              struct {
-+                      /* this mm_struct is on lru_gen_mm_list */
-+                      struct list_head list;
-+                      /*
-+                       * Set when switching to this mm_struct, as a hint of
-+                       * whether it has been used since the last time per-node
-+                       * page table walkers cleared the corresponding bits.
-+                       */
-+                      unsigned long bitmap;
-+#ifdef CONFIG_MEMCG
-+                      /* points to the memcg of "owner" above */
-+                      struct mem_cgroup *memcg;
-+#endif
-+              } lru_gen;
-+#endif /* CONFIG_LRU_GEN */
-       } __randomize_layout;
-       /*
-@@ -606,6 +622,66 @@ static inline cpumask_t *mm_cpumask(stru
-       return (struct cpumask *)&mm->cpu_bitmap;
- }
-+#ifdef CONFIG_LRU_GEN
-+
-+struct lru_gen_mm_list {
-+      /* mm_struct list for page table walkers */
-+      struct list_head fifo;
-+      /* protects the list above */
-+      spinlock_t lock;
-+};
-+
-+void lru_gen_add_mm(struct mm_struct *mm);
-+void lru_gen_del_mm(struct mm_struct *mm);
-+#ifdef CONFIG_MEMCG
-+void lru_gen_migrate_mm(struct mm_struct *mm);
-+#endif
-+
-+static inline void lru_gen_init_mm(struct mm_struct *mm)
-+{
-+      INIT_LIST_HEAD(&mm->lru_gen.list);
-+      mm->lru_gen.bitmap = 0;
-+#ifdef CONFIG_MEMCG
-+      mm->lru_gen.memcg = NULL;
-+#endif
-+}
-+
-+static inline void lru_gen_use_mm(struct mm_struct *mm)
-+{
-+      /*
-+       * When the bitmap is set, page reclaim knows this mm_struct has been
-+       * used since the last time it cleared the bitmap. So it might be worth
-+       * walking the page tables of this mm_struct to clear the accessed bit.
-+       */
-+      WRITE_ONCE(mm->lru_gen.bitmap, -1);
-+}
-+
-+#else /* !CONFIG_LRU_GEN */
-+
-+static inline void lru_gen_add_mm(struct mm_struct *mm)
-+{
-+}
-+
-+static inline void lru_gen_del_mm(struct mm_struct *mm)
-+{
-+}
-+
-+#ifdef CONFIG_MEMCG
-+static inline void lru_gen_migrate_mm(struct mm_struct *mm)
-+{
-+}
-+#endif
-+
-+static inline void lru_gen_init_mm(struct mm_struct *mm)
-+{
-+}
-+
-+static inline void lru_gen_use_mm(struct mm_struct *mm)
-+{
-+}
-+
-+#endif /* CONFIG_LRU_GEN */
-+
- struct mmu_gather;
- extern void tlb_gather_mmu(struct mmu_gather *tlb, struct mm_struct *mm);
- extern void tlb_gather_mmu_fullmm(struct mmu_gather *tlb, struct mm_struct *mm);
---- a/include/linux/mmzone.h
-+++ b/include/linux/mmzone.h
-@@ -385,7 +385,7 @@ enum {
-  * min_seq behind.
-  *
-  * The number of pages in each generation is eventually consistent and therefore
-- * can be transiently negative.
-+ * can be transiently negative when reset_batch_size() is pending.
-  */
- struct lru_gen_struct {
-       /* the aging increments the youngest generation number */
-@@ -407,6 +407,53 @@ struct lru_gen_struct {
-       atomic_long_t refaulted[NR_HIST_GENS][ANON_AND_FILE][MAX_NR_TIERS];
- };
-+enum {
-+      MM_LEAF_TOTAL,          /* total leaf entries */
-+      MM_LEAF_OLD,            /* old leaf entries */
-+      MM_LEAF_YOUNG,          /* young leaf entries */
-+      MM_NONLEAF_TOTAL,       /* total non-leaf entries */
-+      MM_NONLEAF_FOUND,       /* non-leaf entries found in Bloom filters */
-+      MM_NONLEAF_ADDED,       /* non-leaf entries added to Bloom filters */
-+      NR_MM_STATS
-+};
-+
-+/* double-buffering Bloom filters */
-+#define NR_BLOOM_FILTERS      2
-+
-+struct lru_gen_mm_state {
-+      /* set to max_seq after each iteration */
-+      unsigned long seq;
-+      /* where the current iteration continues (inclusive) */
-+      struct list_head *head;
-+      /* where the last iteration ended (exclusive) */
-+      struct list_head *tail;
-+      /* to wait for the last page table walker to finish */
-+      struct wait_queue_head wait;
-+      /* Bloom filters flip after each iteration */
-+      unsigned long *filters[NR_BLOOM_FILTERS];
-+      /* the mm stats for debugging */
-+      unsigned long stats[NR_HIST_GENS][NR_MM_STATS];
-+      /* the number of concurrent page table walkers */
-+      int nr_walkers;
-+};
-+
-+struct lru_gen_mm_walk {
-+      /* the lruvec under reclaim */
-+      struct lruvec *lruvec;
-+      /* unstable max_seq from lru_gen_struct */
-+      unsigned long max_seq;
-+      /* the next address within an mm to scan */
-+      unsigned long next_addr;
-+      /* to batch promoted pages */
-+      int nr_pages[MAX_NR_GENS][ANON_AND_FILE][MAX_NR_ZONES];
-+      /* to batch the mm stats */
-+      int mm_stats[NR_MM_STATS];
-+      /* total batched items */
-+      int batched;
-+      bool can_swap;
-+      bool force_scan;
-+};
-+
- void lru_gen_init_lruvec(struct lruvec *lruvec);
- void lru_gen_look_around(struct page_vma_mapped_walk *pvmw);
-@@ -457,6 +504,8 @@ struct lruvec {
- #ifdef CONFIG_LRU_GEN
-       /* evictable pages divided into generations */
-       struct lru_gen_struct           lrugen;
-+      /* to concurrently iterate lru_gen_mm_list */
-+      struct lru_gen_mm_state         mm_state;
- #endif
- #ifdef CONFIG_MEMCG
-       struct pglist_data *pgdat;
-@@ -1042,6 +1091,11 @@ typedef struct pglist_data {
-       unsigned long           flags;
-+#ifdef CONFIG_LRU_GEN
-+      /* kswap mm walk data */
-+      struct lru_gen_mm_walk  mm_walk;
-+#endif
-+
-       ZONE_PADDING(_pad2_)
-       /* Per-node vmstats */
---- a/include/linux/swap.h
-+++ b/include/linux/swap.h
-@@ -137,6 +137,10 @@ union swap_header {
-  */
- struct reclaim_state {
-       unsigned long reclaimed_slab;
-+#ifdef CONFIG_LRU_GEN
-+      /* per-thread mm walk data */
-+      struct lru_gen_mm_walk *mm_walk;
-+#endif
- };
- #ifdef __KERNEL__
---- a/kernel/exit.c
-+++ b/kernel/exit.c
-@@ -469,6 +469,7 @@ assign_new_owner:
-               goto retry;
-       }
-       WRITE_ONCE(mm->owner, c);
-+      lru_gen_migrate_mm(mm);
-       task_unlock(c);
-       put_task_struct(c);
- }
---- a/kernel/fork.c
-+++ b/kernel/fork.c
-@@ -1091,6 +1091,7 @@ static struct mm_struct *mm_init(struct
-               goto fail_nocontext;
-       mm->user_ns = get_user_ns(user_ns);
-+      lru_gen_init_mm(mm);
-       return mm;
- fail_nocontext:
-@@ -1133,6 +1134,7 @@ static inline void __mmput(struct mm_str
-       }
-       if (mm->binfmt)
-               module_put(mm->binfmt->module);
-+      lru_gen_del_mm(mm);
-       mmdrop(mm);
- }
-@@ -2625,6 +2627,13 @@ pid_t kernel_clone(struct kernel_clone_a
-               get_task_struct(p);
-       }
-+      if (IS_ENABLED(CONFIG_LRU_GEN) && !(clone_flags & CLONE_VM)) {
-+              /* lock the task to synchronize with memcg migration */
-+              task_lock(p);
-+              lru_gen_add_mm(p->mm);
-+              task_unlock(p);
-+      }
-+
-       wake_up_new_task(p);
-       /* forking complete and child started to run, tell ptracer */
---- a/kernel/sched/core.c
-+++ b/kernel/sched/core.c
-@@ -5014,6 +5014,7 @@ context_switch(struct rq *rq, struct tas
-                * finish_task_switch()'s mmdrop().
-                */
-               switch_mm_irqs_off(prev->active_mm, next->mm, next);
-+              lru_gen_use_mm(next->mm);
-               if (!prev->mm) {                        // from kernel
-                       /* will mmdrop() in finish_task_switch(). */
---- a/mm/memcontrol.c
-+++ b/mm/memcontrol.c
-@@ -6213,6 +6213,30 @@ static void mem_cgroup_move_task(void)
- }
- #endif
-+#ifdef CONFIG_LRU_GEN
-+static void mem_cgroup_attach(struct cgroup_taskset *tset)
-+{
-+      struct task_struct *task;
-+      struct cgroup_subsys_state *css;
-+
-+      /* find the first leader if there is any */
-+      cgroup_taskset_for_each_leader(task, css, tset)
-+              break;
-+
-+      if (!task)
-+              return;
-+
-+      task_lock(task);
-+      if (task->mm && READ_ONCE(task->mm->owner) == task)
-+              lru_gen_migrate_mm(task->mm);
-+      task_unlock(task);
-+}
-+#else
-+static void mem_cgroup_attach(struct cgroup_taskset *tset)
-+{
-+}
-+#endif /* CONFIG_LRU_GEN */
-+
- static int seq_puts_memcg_tunable(struct seq_file *m, unsigned long value)
- {
-       if (value == PAGE_COUNTER_MAX)
-@@ -6556,6 +6580,7 @@ struct cgroup_subsys memory_cgrp_subsys
-       .css_reset = mem_cgroup_css_reset,
-       .css_rstat_flush = mem_cgroup_css_rstat_flush,
-       .can_attach = mem_cgroup_can_attach,
-+      .attach = mem_cgroup_attach,
-       .cancel_attach = mem_cgroup_cancel_attach,
-       .post_attach = mem_cgroup_move_task,
-       .dfl_cftypes = memory_files,
---- a/mm/vmscan.c
-+++ b/mm/vmscan.c
-@@ -50,6 +50,8 @@
- #include <linux/printk.h>
- #include <linux/dax.h>
- #include <linux/psi.h>
-+#include <linux/pagewalk.h>
-+#include <linux/shmem_fs.h>
- #include <asm/tlbflush.h>
- #include <asm/div64.h>
-@@ -2853,7 +2855,7 @@ static bool can_age_anon_pages(struct pg
-               for ((type) = 0; (type) < ANON_AND_FILE; (type)++)      \
-                       for ((zone) = 0; (zone) < MAX_NR_ZONES; (zone)++)
--static struct lruvec __maybe_unused *get_lruvec(struct mem_cgroup *memcg, int nid)
-+static struct lruvec *get_lruvec(struct mem_cgroup *memcg, int nid)
- {
-       struct pglist_data *pgdat = NODE_DATA(nid);
-@@ -2899,6 +2901,371 @@ static bool __maybe_unused seq_is_valid(
- }
- /******************************************************************************
-+ *                          mm_struct list
-+ ******************************************************************************/
-+
-+static struct lru_gen_mm_list *get_mm_list(struct mem_cgroup *memcg)
-+{
-+      static struct lru_gen_mm_list mm_list = {
-+              .fifo = LIST_HEAD_INIT(mm_list.fifo),
-+              .lock = __SPIN_LOCK_UNLOCKED(mm_list.lock),
-+      };
-+
-+#ifdef CONFIG_MEMCG
-+      if (memcg)
-+              return &memcg->mm_list;
-+#endif
-+      VM_WARN_ON_ONCE(!mem_cgroup_disabled());
-+
-+      return &mm_list;
-+}
-+
-+void lru_gen_add_mm(struct mm_struct *mm)
-+{
-+      int nid;
-+      struct mem_cgroup *memcg = get_mem_cgroup_from_mm(mm);
-+      struct lru_gen_mm_list *mm_list = get_mm_list(memcg);
-+
-+      VM_WARN_ON_ONCE(!list_empty(&mm->lru_gen.list));
-+#ifdef CONFIG_MEMCG
-+      VM_WARN_ON_ONCE(mm->lru_gen.memcg);
-+      mm->lru_gen.memcg = memcg;
-+#endif
-+      spin_lock(&mm_list->lock);
-+
-+      for_each_node_state(nid, N_MEMORY) {
-+              struct lruvec *lruvec = get_lruvec(memcg, nid);
-+
-+              if (!lruvec)
-+                      continue;
-+
-+              /* the first addition since the last iteration */
-+              if (lruvec->mm_state.tail == &mm_list->fifo)
-+                      lruvec->mm_state.tail = &mm->lru_gen.list;
-+      }
-+
-+      list_add_tail(&mm->lru_gen.list, &mm_list->fifo);
-+
-+      spin_unlock(&mm_list->lock);
-+}
-+
-+void lru_gen_del_mm(struct mm_struct *mm)
-+{
-+      int nid;
-+      struct lru_gen_mm_list *mm_list;
-+      struct mem_cgroup *memcg = NULL;
-+
-+      if (list_empty(&mm->lru_gen.list))
-+              return;
-+
-+#ifdef CONFIG_MEMCG
-+      memcg = mm->lru_gen.memcg;
-+#endif
-+      mm_list = get_mm_list(memcg);
-+
-+      spin_lock(&mm_list->lock);
-+
-+      for_each_node(nid) {
-+              struct lruvec *lruvec = get_lruvec(memcg, nid);
-+
-+              if (!lruvec)
-+                      continue;
-+
-+              /* where the last iteration ended (exclusive) */
-+              if (lruvec->mm_state.tail == &mm->lru_gen.list)
-+                      lruvec->mm_state.tail = lruvec->mm_state.tail->next;
-+
-+              /* where the current iteration continues (inclusive) */
-+              if (lruvec->mm_state.head != &mm->lru_gen.list)
-+                      continue;
-+
-+              lruvec->mm_state.head = lruvec->mm_state.head->next;
-+              /* the deletion ends the current iteration */
-+              if (lruvec->mm_state.head == &mm_list->fifo)
-+                      WRITE_ONCE(lruvec->mm_state.seq, lruvec->mm_state.seq + 1);
-+      }
-+
-+      list_del_init(&mm->lru_gen.list);
-+
-+      spin_unlock(&mm_list->lock);
-+
-+#ifdef CONFIG_MEMCG
-+      mem_cgroup_put(mm->lru_gen.memcg);
-+      mm->lru_gen.memcg = NULL;
-+#endif
-+}
-+
-+#ifdef CONFIG_MEMCG
-+void lru_gen_migrate_mm(struct mm_struct *mm)
-+{
-+      struct mem_cgroup *memcg;
-+      struct task_struct *task = rcu_dereference_protected(mm->owner, true);
-+
-+      VM_WARN_ON_ONCE(task->mm != mm);
-+      lockdep_assert_held(&task->alloc_lock);
-+
-+      /* for mm_update_next_owner() */
-+      if (mem_cgroup_disabled())
-+              return;
-+
-+      rcu_read_lock();
-+      memcg = mem_cgroup_from_task(task);
-+      rcu_read_unlock();
-+      if (memcg == mm->lru_gen.memcg)
-+              return;
-+
-+      VM_WARN_ON_ONCE(!mm->lru_gen.memcg);
-+      VM_WARN_ON_ONCE(list_empty(&mm->lru_gen.list));
-+
-+      lru_gen_del_mm(mm);
-+      lru_gen_add_mm(mm);
-+}
-+#endif
-+
-+/*
-+ * Bloom filters with m=1<<15, k=2 and the false positive rates of ~1/5 when
-+ * n=10,000 and ~1/2 when n=20,000, where, conventionally, m is the number of
-+ * bits in a bitmap, k is the number of hash functions and n is the number of
-+ * inserted items.
-+ *
-+ * Page table walkers use one of the two filters to reduce their search space.
-+ * To get rid of non-leaf entries that no longer have enough leaf entries, the
-+ * aging uses the double-buffering technique to flip to the other filter each
-+ * time it produces a new generation. For non-leaf entries that have enough
-+ * leaf entries, the aging carries them over to the next generation in
-+ * walk_pmd_range(); the eviction also report them when walking the rmap
-+ * in lru_gen_look_around().
-+ *
-+ * For future optimizations:
-+ * 1. It's not necessary to keep both filters all the time. The spare one can be
-+ *    freed after the RCU grace period and reallocated if needed again.
-+ * 2. And when reallocating, it's worth scaling its size according to the number
-+ *    of inserted entries in the other filter, to reduce the memory overhead on
-+ *    small systems and false positives on large systems.
-+ * 3. Jenkins' hash function is an alternative to Knuth's.
-+ */
-+#define BLOOM_FILTER_SHIFT    15
-+
-+static inline int filter_gen_from_seq(unsigned long seq)
-+{
-+      return seq % NR_BLOOM_FILTERS;
-+}
-+
-+static void get_item_key(void *item, int *key)
-+{
-+      u32 hash = hash_ptr(item, BLOOM_FILTER_SHIFT * 2);
-+
-+      BUILD_BUG_ON(BLOOM_FILTER_SHIFT * 2 > BITS_PER_TYPE(u32));
-+
-+      key[0] = hash & (BIT(BLOOM_FILTER_SHIFT) - 1);
-+      key[1] = hash >> BLOOM_FILTER_SHIFT;
-+}
-+
-+static void reset_bloom_filter(struct lruvec *lruvec, unsigned long seq)
-+{
-+      unsigned long *filter;
-+      int gen = filter_gen_from_seq(seq);
-+
-+      filter = lruvec->mm_state.filters[gen];
-+      if (filter) {
-+              bitmap_clear(filter, 0, BIT(BLOOM_FILTER_SHIFT));
-+              return;
-+      }
-+
-+      filter = bitmap_zalloc(BIT(BLOOM_FILTER_SHIFT),
-+                             __GFP_HIGH | __GFP_NOMEMALLOC | __GFP_NOWARN);
-+      WRITE_ONCE(lruvec->mm_state.filters[gen], filter);
-+}
-+
-+static void update_bloom_filter(struct lruvec *lruvec, unsigned long seq, void *item)
-+{
-+      int key[2];
-+      unsigned long *filter;
-+      int gen = filter_gen_from_seq(seq);
-+
-+      filter = READ_ONCE(lruvec->mm_state.filters[gen]);
-+      if (!filter)
-+              return;
-+
-+      get_item_key(item, key);
-+
-+      if (!test_bit(key[0], filter))
-+              set_bit(key[0], filter);
-+      if (!test_bit(key[1], filter))
-+              set_bit(key[1], filter);
-+}
-+
-+static bool test_bloom_filter(struct lruvec *lruvec, unsigned long seq, void *item)
-+{
-+      int key[2];
-+      unsigned long *filter;
-+      int gen = filter_gen_from_seq(seq);
-+
-+      filter = READ_ONCE(lruvec->mm_state.filters[gen]);
-+      if (!filter)
-+              return true;
-+
-+      get_item_key(item, key);
-+
-+      return test_bit(key[0], filter) && test_bit(key[1], filter);
-+}
-+
-+static void reset_mm_stats(struct lruvec *lruvec, struct lru_gen_mm_walk *walk, bool last)
-+{
-+      int i;
-+      int hist;
-+
-+      lockdep_assert_held(&get_mm_list(lruvec_memcg(lruvec))->lock);
-+
-+      if (walk) {
-+              hist = lru_hist_from_seq(walk->max_seq);
-+
-+              for (i = 0; i < NR_MM_STATS; i++) {
-+                      WRITE_ONCE(lruvec->mm_state.stats[hist][i],
-+                                 lruvec->mm_state.stats[hist][i] + walk->mm_stats[i]);
-+                      walk->mm_stats[i] = 0;
-+              }
-+      }
-+
-+      if (NR_HIST_GENS > 1 && last) {
-+              hist = lru_hist_from_seq(lruvec->mm_state.seq + 1);
-+
-+              for (i = 0; i < NR_MM_STATS; i++)
-+                      WRITE_ONCE(lruvec->mm_state.stats[hist][i], 0);
-+      }
-+}
-+
-+static bool should_skip_mm(struct mm_struct *mm, struct lru_gen_mm_walk *walk)
-+{
-+      int type;
-+      unsigned long size = 0;
-+      struct pglist_data *pgdat = lruvec_pgdat(walk->lruvec);
-+      int key = pgdat->node_id % BITS_PER_TYPE(mm->lru_gen.bitmap);
-+
-+      if (!walk->force_scan && !test_bit(key, &mm->lru_gen.bitmap))
-+              return true;
-+
-+      clear_bit(key, &mm->lru_gen.bitmap);
-+
-+      for (type = !walk->can_swap; type < ANON_AND_FILE; type++) {
-+              size += type ? get_mm_counter(mm, MM_FILEPAGES) :
-+                             get_mm_counter(mm, MM_ANONPAGES) +
-+                             get_mm_counter(mm, MM_SHMEMPAGES);
-+      }
-+
-+      if (size < MIN_LRU_BATCH)
-+              return true;
-+
-+      return !mmget_not_zero(mm);
-+}
-+
-+static bool iterate_mm_list(struct lruvec *lruvec, struct lru_gen_mm_walk *walk,
-+                          struct mm_struct **iter)
-+{
-+      bool first = false;
-+      bool last = true;
-+      struct mm_struct *mm = NULL;
-+      struct mem_cgroup *memcg = lruvec_memcg(lruvec);
-+      struct lru_gen_mm_list *mm_list = get_mm_list(memcg);
-+      struct lru_gen_mm_state *mm_state = &lruvec->mm_state;
-+
-+      /*
-+       * There are four interesting cases for this page table walker:
-+       * 1. It tries to start a new iteration of mm_list with a stale max_seq;
-+       *    there is nothing left to do.
-+       * 2. It's the first of the current generation, and it needs to reset
-+       *    the Bloom filter for the next generation.
-+       * 3. It reaches the end of mm_list, and it needs to increment
-+       *    mm_state->seq; the iteration is done.
-+       * 4. It's the last of the current generation, and it needs to reset the
-+       *    mm stats counters for the next generation.
-+       */
-+      spin_lock(&mm_list->lock);
-+
-+      VM_WARN_ON_ONCE(mm_state->seq + 1 < walk->max_seq);
-+      VM_WARN_ON_ONCE(*iter && mm_state->seq > walk->max_seq);
-+      VM_WARN_ON_ONCE(*iter && !mm_state->nr_walkers);
-+
-+      if (walk->max_seq <= mm_state->seq) {
-+              if (!*iter)
-+                      last = false;
-+              goto done;
-+      }
-+
-+      if (!mm_state->nr_walkers) {
-+              VM_WARN_ON_ONCE(mm_state->head && mm_state->head != &mm_list->fifo);
-+
-+              mm_state->head = mm_list->fifo.next;
-+              first = true;
-+      }
-+
-+      while (!mm && mm_state->head != &mm_list->fifo) {
-+              mm = list_entry(mm_state->head, struct mm_struct, lru_gen.list);
-+
-+              mm_state->head = mm_state->head->next;
-+
-+              /* force scan for those added after the last iteration */
-+              if (!mm_state->tail || mm_state->tail == &mm->lru_gen.list) {
-+                      mm_state->tail = mm_state->head;
-+                      walk->force_scan = true;
-+              }
-+
-+              if (should_skip_mm(mm, walk))
-+                      mm = NULL;
-+      }
-+
-+      if (mm_state->head == &mm_list->fifo)
-+              WRITE_ONCE(mm_state->seq, mm_state->seq + 1);
-+done:
-+      if (*iter && !mm)
-+              mm_state->nr_walkers--;
-+      if (!*iter && mm)
-+              mm_state->nr_walkers++;
-+
-+      if (mm_state->nr_walkers)
-+              last = false;
-+
-+      if (*iter || last)
-+              reset_mm_stats(lruvec, walk, last);
-+
-+      spin_unlock(&mm_list->lock);
-+
-+      if (mm && first)
-+              reset_bloom_filter(lruvec, walk->max_seq + 1);
-+
-+      if (*iter)
-+              mmput_async(*iter);
-+
-+      *iter = mm;
-+
-+      return last;
-+}
-+
-+static bool iterate_mm_list_nowalk(struct lruvec *lruvec, unsigned long max_seq)
-+{
-+      bool success = false;
-+      struct mem_cgroup *memcg = lruvec_memcg(lruvec);
-+      struct lru_gen_mm_list *mm_list = get_mm_list(memcg);
-+      struct lru_gen_mm_state *mm_state = &lruvec->mm_state;
-+
-+      spin_lock(&mm_list->lock);
-+
-+      VM_WARN_ON_ONCE(mm_state->seq + 1 < max_seq);
-+
-+      if (max_seq > mm_state->seq && !mm_state->nr_walkers) {
-+              VM_WARN_ON_ONCE(mm_state->head && mm_state->head != &mm_list->fifo);
-+
-+              WRITE_ONCE(mm_state->seq, mm_state->seq + 1);
-+              reset_mm_stats(lruvec, NULL, true);
-+              success = true;
-+      }
-+
-+      spin_unlock(&mm_list->lock);
-+
-+      return success;
-+}
-+
-+/******************************************************************************
-  *                          refault feedback loop
-  ******************************************************************************/
-@@ -3048,6 +3415,118 @@ static int page_inc_gen(struct lruvec *l
-       return new_gen;
- }
-+static void update_batch_size(struct lru_gen_mm_walk *walk, struct page *page,
-+                            int old_gen, int new_gen)
-+{
-+      int type = page_is_file_lru(page);
-+      int zone = page_zonenum(page);
-+      int delta = thp_nr_pages(page);
-+
-+      VM_WARN_ON_ONCE(old_gen >= MAX_NR_GENS);
-+      VM_WARN_ON_ONCE(new_gen >= MAX_NR_GENS);
-+
-+      walk->batched++;
-+
-+      walk->nr_pages[old_gen][type][zone] -= delta;
-+      walk->nr_pages[new_gen][type][zone] += delta;
-+}
-+
-+static void reset_batch_size(struct lruvec *lruvec, struct lru_gen_mm_walk *walk)
-+{
-+      int gen, type, zone;
-+      struct lru_gen_struct *lrugen = &lruvec->lrugen;
-+
-+      walk->batched = 0;
-+
-+      for_each_gen_type_zone(gen, type, zone) {
-+              enum lru_list lru = type * LRU_INACTIVE_FILE;
-+              int delta = walk->nr_pages[gen][type][zone];
-+
-+              if (!delta)
-+                      continue;
-+
-+              walk->nr_pages[gen][type][zone] = 0;
-+              WRITE_ONCE(lrugen->nr_pages[gen][type][zone],
-+                         lrugen->nr_pages[gen][type][zone] + delta);
-+
-+              if (lru_gen_is_active(lruvec, gen))
-+                      lru += LRU_ACTIVE;
-+              __update_lru_size(lruvec, lru, zone, delta);
-+      }
-+}
-+
-+static int should_skip_vma(unsigned long start, unsigned long end, struct mm_walk *args)
-+{
-+      struct address_space *mapping;
-+      struct vm_area_struct *vma = args->vma;
-+      struct lru_gen_mm_walk *walk = args->private;
-+
-+      if (!vma_is_accessible(vma))
-+              return true;
-+
-+      if (is_vm_hugetlb_page(vma))
-+              return true;
-+
-+      if (vma->vm_flags & (VM_LOCKED | VM_SPECIAL | VM_SEQ_READ | VM_RAND_READ))
-+              return true;
-+
-+      if (vma == get_gate_vma(vma->vm_mm))
-+              return true;
-+
-+      if (vma_is_anonymous(vma))
-+              return !walk->can_swap;
-+
-+      if (WARN_ON_ONCE(!vma->vm_file || !vma->vm_file->f_mapping))
-+              return true;
-+
-+      mapping = vma->vm_file->f_mapping;
-+      if (mapping_unevictable(mapping))
-+              return true;
-+
-+      if (shmem_mapping(mapping))
-+              return !walk->can_swap;
-+
-+      /* to exclude special mappings like dax, etc. */
-+      return !mapping->a_ops->readpage;
-+}
-+
-+/*
-+ * Some userspace memory allocators map many single-page VMAs. Instead of
-+ * returning back to the PGD table for each of such VMAs, finish an entire PMD
-+ * table to reduce zigzags and improve cache performance.
-+ */
-+static bool get_next_vma(unsigned long mask, unsigned long size, struct mm_walk *args,
-+                       unsigned long *vm_start, unsigned long *vm_end)
-+{
-+      unsigned long start = round_up(*vm_end, size);
-+      unsigned long end = (start | ~mask) + 1;
-+
-+      VM_WARN_ON_ONCE(mask & size);
-+      VM_WARN_ON_ONCE((start & mask) != (*vm_start & mask));
-+
-+      while (args->vma) {
-+              if (start >= args->vma->vm_end) {
-+                      args->vma = args->vma->vm_next;
-+                      continue;
-+              }
-+
-+              if (end && end <= args->vma->vm_start)
-+                      return false;
-+
-+              if (should_skip_vma(args->vma->vm_start, args->vma->vm_end, args)) {
-+                      args->vma = args->vma->vm_next;
-+                      continue;
-+              }
-+
-+              *vm_start = max(start, args->vma->vm_start);
-+              *vm_end = min(end - 1, args->vma->vm_end - 1) + 1;
-+
-+              return true;
-+      }
-+
-+      return false;
-+}
-+
- static unsigned long get_pte_pfn(pte_t pte, struct vm_area_struct *vma, unsigned long addr)
- {
-       unsigned long pfn = pte_pfn(pte);
-@@ -3066,8 +3545,28 @@ static unsigned long get_pte_pfn(pte_t p
-       return pfn;
- }
-+#if defined(CONFIG_TRANSPARENT_HUGEPAGE) || defined(CONFIG_ARCH_HAS_NONLEAF_PMD_YOUNG)
-+static unsigned long get_pmd_pfn(pmd_t pmd, struct vm_area_struct *vma, unsigned long addr)
-+{
-+      unsigned long pfn = pmd_pfn(pmd);
-+
-+      VM_WARN_ON_ONCE(addr < vma->vm_start || addr >= vma->vm_end);
-+
-+      if (!pmd_present(pmd) || is_huge_zero_pmd(pmd))
-+              return -1;
-+
-+      if (WARN_ON_ONCE(pmd_devmap(pmd)))
-+              return -1;
-+
-+      if (WARN_ON_ONCE(!pfn_valid(pfn)))
-+              return -1;
-+
-+      return pfn;
-+}
-+#endif
-+
- static struct page *get_pfn_page(unsigned long pfn, struct mem_cgroup *memcg,
--                               struct pglist_data *pgdat)
-+                               struct pglist_data *pgdat, bool can_swap)
- {
-       struct page *page;
-@@ -3082,9 +3581,375 @@ static struct page *get_pfn_page(unsigne
-       if (page_memcg_rcu(page) != memcg)
-               return NULL;
-+      /* file VMAs can contain anon pages from COW */
-+      if (!page_is_file_lru(page) && !can_swap)
-+              return NULL;
-+
-       return page;
- }
-+static bool suitable_to_scan(int total, int young)
-+{
-+      int n = clamp_t(int, cache_line_size() / sizeof(pte_t), 2, 8);
-+
-+      /* suitable if the average number of young PTEs per cacheline is >=1 */
-+      return young * n >= total;
-+}
-+
-+static bool walk_pte_range(pmd_t *pmd, unsigned long start, unsigned long end,
-+                         struct mm_walk *args)
-+{
-+      int i;
-+      pte_t *pte;
-+      spinlock_t *ptl;
-+      unsigned long addr;
-+      int total = 0;
-+      int young = 0;
-+      struct lru_gen_mm_walk *walk = args->private;
-+      struct mem_cgroup *memcg = lruvec_memcg(walk->lruvec);
-+      struct pglist_data *pgdat = lruvec_pgdat(walk->lruvec);
-+      int old_gen, new_gen = lru_gen_from_seq(walk->max_seq);
-+
-+      VM_WARN_ON_ONCE(pmd_leaf(*pmd));
-+
-+      ptl = pte_lockptr(args->mm, pmd);
-+      if (!spin_trylock(ptl))
-+              return false;
-+
-+      arch_enter_lazy_mmu_mode();
-+
-+      pte = pte_offset_map(pmd, start & PMD_MASK);
-+restart:
-+      for (i = pte_index(start), addr = start; addr != end; i++, addr += PAGE_SIZE) {
-+              unsigned long pfn;
-+              struct page *page;
-+
-+              total++;
-+              walk->mm_stats[MM_LEAF_TOTAL]++;
-+
-+              pfn = get_pte_pfn(pte[i], args->vma, addr);
-+              if (pfn == -1)
-+                      continue;
-+
-+              if (!pte_young(pte[i])) {
-+                      walk->mm_stats[MM_LEAF_OLD]++;
-+                      continue;
-+              }
-+
-+              page = get_pfn_page(pfn, memcg, pgdat, walk->can_swap);
-+              if (!page)
-+                      continue;
-+
-+              if (!ptep_test_and_clear_young(args->vma, addr, pte + i))
-+                      VM_WARN_ON_ONCE(true);
-+
-+              young++;
-+              walk->mm_stats[MM_LEAF_YOUNG]++;
-+
-+              if (pte_dirty(pte[i]) && !PageDirty(page) &&
-+                  !(PageAnon(page) && PageSwapBacked(page) &&
-+                    !PageSwapCache(page)))
-+                      set_page_dirty(page);
-+
-+              old_gen = page_update_gen(page, new_gen);
-+              if (old_gen >= 0 && old_gen != new_gen)
-+                      update_batch_size(walk, page, old_gen, new_gen);
-+      }
-+
-+      if (i < PTRS_PER_PTE && get_next_vma(PMD_MASK, PAGE_SIZE, args, &start, &end))
-+              goto restart;
-+
-+      pte_unmap(pte);
-+
-+      arch_leave_lazy_mmu_mode();
-+      spin_unlock(ptl);
-+
-+      return suitable_to_scan(total, young);
-+}
-+
-+#if defined(CONFIG_TRANSPARENT_HUGEPAGE) || defined(CONFIG_ARCH_HAS_NONLEAF_PMD_YOUNG)
-+static void walk_pmd_range_locked(pud_t *pud, unsigned long next, struct vm_area_struct *vma,
-+                                struct mm_walk *args, unsigned long *bitmap, unsigned long *start)
-+{
-+      int i;
-+      pmd_t *pmd;
-+      spinlock_t *ptl;
-+      struct lru_gen_mm_walk *walk = args->private;
-+      struct mem_cgroup *memcg = lruvec_memcg(walk->lruvec);
-+      struct pglist_data *pgdat = lruvec_pgdat(walk->lruvec);
-+      int old_gen, new_gen = lru_gen_from_seq(walk->max_seq);
-+
-+      VM_WARN_ON_ONCE(pud_leaf(*pud));
-+
-+      /* try to batch at most 1+MIN_LRU_BATCH+1 entries */
-+      if (*start == -1) {
-+              *start = next;
-+              return;
-+      }
-+
-+      i = next == -1 ? 0 : pmd_index(next) - pmd_index(*start);
-+      if (i && i <= MIN_LRU_BATCH) {
-+              __set_bit(i - 1, bitmap);
-+              return;
-+      }
-+
-+      pmd = pmd_offset(pud, *start);
-+
-+      ptl = pmd_lockptr(args->mm, pmd);
-+      if (!spin_trylock(ptl))
-+              goto done;
-+
-+      arch_enter_lazy_mmu_mode();
-+
-+      do {
-+              unsigned long pfn;
-+              struct page *page;
-+              unsigned long addr = i ? (*start & PMD_MASK) + i * PMD_SIZE : *start;
-+
-+              pfn = get_pmd_pfn(pmd[i], vma, addr);
-+              if (pfn == -1)
-+                      goto next;
-+
-+              if (!pmd_trans_huge(pmd[i])) {
-+                      if (IS_ENABLED(CONFIG_ARCH_HAS_NONLEAF_PMD_YOUNG))
-+                              pmdp_test_and_clear_young(vma, addr, pmd + i);
-+                      goto next;
-+              }
-+
-+              page = get_pfn_page(pfn, memcg, pgdat, walk->can_swap);
-+              if (!page)
-+                      goto next;
-+
-+              if (!pmdp_test_and_clear_young(vma, addr, pmd + i))
-+                      goto next;
-+
-+              walk->mm_stats[MM_LEAF_YOUNG]++;
-+
-+              if (pmd_dirty(pmd[i]) && !PageDirty(page) &&
-+                  !(PageAnon(page) && PageSwapBacked(page) &&
-+                    !PageSwapCache(page)))
-+                      set_page_dirty(page);
-+
-+              old_gen = page_update_gen(page, new_gen);
-+              if (old_gen >= 0 && old_gen != new_gen)
-+                      update_batch_size(walk, page, old_gen, new_gen);
-+next:
-+              i = i > MIN_LRU_BATCH ? 0 : find_next_bit(bitmap, MIN_LRU_BATCH, i) + 1;
-+      } while (i <= MIN_LRU_BATCH);
-+
-+      arch_leave_lazy_mmu_mode();
-+      spin_unlock(ptl);
-+done:
-+      *start = -1;
-+      bitmap_zero(bitmap, MIN_LRU_BATCH);
-+}
-+#else
-+static void walk_pmd_range_locked(pud_t *pud, unsigned long next, struct vm_area_struct *vma,
-+                                struct mm_walk *args, unsigned long *bitmap, unsigned long *start)
-+{
-+}
-+#endif
-+
-+static void walk_pmd_range(pud_t *pud, unsigned long start, unsigned long end,
-+                         struct mm_walk *args)
-+{
-+      int i;
-+      pmd_t *pmd;
-+      unsigned long next;
-+      unsigned long addr;
-+      struct vm_area_struct *vma;
-+      unsigned long pos = -1;
-+      struct lru_gen_mm_walk *walk = args->private;
-+      unsigned long bitmap[BITS_TO_LONGS(MIN_LRU_BATCH)] = {};
-+
-+      VM_WARN_ON_ONCE(pud_leaf(*pud));
-+
-+      /*
-+       * Finish an entire PMD in two passes: the first only reaches to PTE
-+       * tables to avoid taking the PMD lock; the second, if necessary, takes
-+       * the PMD lock to clear the accessed bit in PMD entries.
-+       */
-+      pmd = pmd_offset(pud, start & PUD_MASK);
-+restart:
-+      /* walk_pte_range() may call get_next_vma() */
-+      vma = args->vma;
-+      for (i = pmd_index(start), addr = start; addr != end; i++, addr = next) {
-+              pmd_t val = pmd_read_atomic(pmd + i);
-+
-+              /* for pmd_read_atomic() */
-+              barrier();
-+
-+              next = pmd_addr_end(addr, end);
-+
-+              if (!pmd_present(val) || is_huge_zero_pmd(val)) {
-+                      walk->mm_stats[MM_LEAF_TOTAL]++;
-+                      continue;
-+              }
-+
-+#ifdef CONFIG_TRANSPARENT_HUGEPAGE
-+              if (pmd_trans_huge(val)) {
-+                      unsigned long pfn = pmd_pfn(val);
-+                      struct pglist_data *pgdat = lruvec_pgdat(walk->lruvec);
-+
-+                      walk->mm_stats[MM_LEAF_TOTAL]++;
-+
-+                      if (!pmd_young(val)) {
-+                              walk->mm_stats[MM_LEAF_OLD]++;
-+                              continue;
-+                      }
-+
-+                      /* try to avoid unnecessary memory loads */
-+                      if (pfn < pgdat->node_start_pfn || pfn >= pgdat_end_pfn(pgdat))
-+                              continue;
-+
-+                      walk_pmd_range_locked(pud, addr, vma, args, bitmap, &pos);
-+                      continue;
-+              }
-+#endif
-+              walk->mm_stats[MM_NONLEAF_TOTAL]++;
-+
-+#ifdef CONFIG_ARCH_HAS_NONLEAF_PMD_YOUNG
-+              if (!pmd_young(val))
-+                      continue;
-+
-+              walk_pmd_range_locked(pud, addr, vma, args, bitmap, &pos);
-+#endif
-+              if (!walk->force_scan && !test_bloom_filter(walk->lruvec, walk->max_seq, pmd + i))
-+                      continue;
-+
-+              walk->mm_stats[MM_NONLEAF_FOUND]++;
-+
-+              if (!walk_pte_range(&val, addr, next, args))
-+                      continue;
-+
-+              walk->mm_stats[MM_NONLEAF_ADDED]++;
-+
-+              /* carry over to the next generation */
-+              update_bloom_filter(walk->lruvec, walk->max_seq + 1, pmd + i);
-+      }
-+
-+      walk_pmd_range_locked(pud, -1, vma, args, bitmap, &pos);
-+
-+      if (i < PTRS_PER_PMD && get_next_vma(PUD_MASK, PMD_SIZE, args, &start, &end))
-+              goto restart;
-+}
-+
-+static int walk_pud_range(p4d_t *p4d, unsigned long start, unsigned long end,
-+                        struct mm_walk *args)
-+{
-+      int i;
-+      pud_t *pud;
-+      unsigned long addr;
-+      unsigned long next;
-+      struct lru_gen_mm_walk *walk = args->private;
-+
-+      VM_WARN_ON_ONCE(p4d_leaf(*p4d));
-+
-+      pud = pud_offset(p4d, start & P4D_MASK);
-+restart:
-+      for (i = pud_index(start), addr = start; addr != end; i++, addr = next) {
-+              pud_t val = READ_ONCE(pud[i]);
-+
-+              next = pud_addr_end(addr, end);
-+
-+              if (!pud_present(val) || WARN_ON_ONCE(pud_leaf(val)))
-+                      continue;
-+
-+              walk_pmd_range(&val, addr, next, args);
-+
-+              /* a racy check to curtail the waiting time */
-+              if (wq_has_sleeper(&walk->lruvec->mm_state.wait))
-+                      return 1;
-+
-+              if (need_resched() || walk->batched >= MAX_LRU_BATCH) {
-+                      end = (addr | ~PUD_MASK) + 1;
-+                      goto done;
-+              }
-+      }
-+
-+      if (i < PTRS_PER_PUD && get_next_vma(P4D_MASK, PUD_SIZE, args, &start, &end))
-+              goto restart;
-+
-+      end = round_up(end, P4D_SIZE);
-+done:
-+      if (!end || !args->vma)
-+              return 1;
-+
-+      walk->next_addr = max(end, args->vma->vm_start);
-+
-+      return -EAGAIN;
-+}
-+
-+static void walk_mm(struct lruvec *lruvec, struct mm_struct *mm, struct lru_gen_mm_walk *walk)
-+{
-+      static const struct mm_walk_ops mm_walk_ops = {
-+              .test_walk = should_skip_vma,
-+              .p4d_entry = walk_pud_range,
-+      };
-+
-+      int err;
-+      struct mem_cgroup *memcg = lruvec_memcg(lruvec);
-+
-+      walk->next_addr = FIRST_USER_ADDRESS;
-+
-+      do {
-+              err = -EBUSY;
-+
-+              /* page_update_gen() requires stable page_memcg() */
-+              if (!mem_cgroup_trylock_pages(memcg))
-+                      break;
-+
-+              /* the caller might be holding the lock for write */
-+              if (mmap_read_trylock(mm)) {
-+                      err = walk_page_range(mm, walk->next_addr, ULONG_MAX, &mm_walk_ops, walk);
-+
-+                      mmap_read_unlock(mm);
-+              }
-+
-+              mem_cgroup_unlock_pages();
-+
-+              if (walk->batched) {
-+                      spin_lock_irq(&lruvec->lru_lock);
-+                      reset_batch_size(lruvec, walk);
-+                      spin_unlock_irq(&lruvec->lru_lock);
-+              }
-+
-+              cond_resched();
-+      } while (err == -EAGAIN);
-+}
-+
-+static struct lru_gen_mm_walk *set_mm_walk(struct pglist_data *pgdat)
-+{
-+      struct lru_gen_mm_walk *walk = current->reclaim_state->mm_walk;
-+
-+      if (pgdat && current_is_kswapd()) {
-+              VM_WARN_ON_ONCE(walk);
-+
-+              walk = &pgdat->mm_walk;
-+      } else if (!pgdat && !walk) {
-+              VM_WARN_ON_ONCE(current_is_kswapd());
-+
-+              walk = kzalloc(sizeof(*walk), __GFP_HIGH | __GFP_NOMEMALLOC | __GFP_NOWARN);
-+      }
-+
-+      current->reclaim_state->mm_walk = walk;
-+
-+      return walk;
-+}
-+
-+static void clear_mm_walk(void)
-+{
-+      struct lru_gen_mm_walk *walk = current->reclaim_state->mm_walk;
-+
-+      VM_WARN_ON_ONCE(walk && memchr_inv(walk->nr_pages, 0, sizeof(walk->nr_pages)));
-+      VM_WARN_ON_ONCE(walk && memchr_inv(walk->mm_stats, 0, sizeof(walk->mm_stats)));
-+
-+      current->reclaim_state->mm_walk = NULL;
-+
-+      if (!current_is_kswapd())
-+              kfree(walk);
-+}
-+
- static void inc_min_seq(struct lruvec *lruvec, int type)
- {
-       struct lru_gen_struct *lrugen = &lruvec->lrugen;
-@@ -3136,7 +4001,7 @@ next:
-       return success;
- }
--static void inc_max_seq(struct lruvec *lruvec, unsigned long max_seq, bool can_swap)
-+static void inc_max_seq(struct lruvec *lruvec, bool can_swap)
- {
-       int prev, next;
-       int type, zone;
-@@ -3146,9 +4011,6 @@ static void inc_max_seq(struct lruvec *l
-       VM_WARN_ON_ONCE(!seq_is_valid(lruvec));
--      if (max_seq != lrugen->max_seq)
--              goto unlock;
--
-       for (type = ANON_AND_FILE - 1; type >= 0; type--) {
-               if (get_nr_gens(lruvec, type) != MAX_NR_GENS)
-                       continue;
-@@ -3186,10 +4048,76 @@ static void inc_max_seq(struct lruvec *l
-       /* make sure preceding modifications appear */
-       smp_store_release(&lrugen->max_seq, lrugen->max_seq + 1);
--unlock:
-+
-       spin_unlock_irq(&lruvec->lru_lock);
- }
-+static bool try_to_inc_max_seq(struct lruvec *lruvec, unsigned long max_seq,
-+                             struct scan_control *sc, bool can_swap)
-+{
-+      bool success;
-+      struct lru_gen_mm_walk *walk;
-+      struct mm_struct *mm = NULL;
-+      struct lru_gen_struct *lrugen = &lruvec->lrugen;
-+
-+      VM_WARN_ON_ONCE(max_seq > READ_ONCE(lrugen->max_seq));
-+
-+      /* see the comment in iterate_mm_list() */
-+      if (max_seq <= READ_ONCE(lruvec->mm_state.seq)) {
-+              success = false;
-+              goto done;
-+      }
-+
-+      /*
-+       * If the hardware doesn't automatically set the accessed bit, fallback
-+       * to lru_gen_look_around(), which only clears the accessed bit in a
-+       * handful of PTEs. Spreading the work out over a period of time usually
-+       * is less efficient, but it avoids bursty page faults.
-+       */
-+      if (!arch_has_hw_pte_young()) {
-+              success = iterate_mm_list_nowalk(lruvec, max_seq);
-+              goto done;
-+      }
-+
-+      walk = set_mm_walk(NULL);
-+      if (!walk) {
-+              success = iterate_mm_list_nowalk(lruvec, max_seq);
-+              goto done;
-+      }
-+
-+      walk->lruvec = lruvec;
-+      walk->max_seq = max_seq;
-+      walk->can_swap = can_swap;
-+      walk->force_scan = false;
-+
-+      do {
-+              success = iterate_mm_list(lruvec, walk, &mm);
-+              if (mm)
-+                      walk_mm(lruvec, mm, walk);
-+
-+              cond_resched();
-+      } while (mm);
-+done:
-+      if (!success) {
-+              if (sc->priority <= DEF_PRIORITY - 2)
-+                      wait_event_killable(lruvec->mm_state.wait,
-+                                          max_seq < READ_ONCE(lrugen->max_seq));
-+
-+              return max_seq < READ_ONCE(lrugen->max_seq);
-+      }
-+
-+      VM_WARN_ON_ONCE(max_seq != READ_ONCE(lrugen->max_seq));
-+
-+      inc_max_seq(lruvec, can_swap);
-+      /* either this sees any waiters or they will see updated max_seq */
-+      if (wq_has_sleeper(&lruvec->mm_state.wait))
-+              wake_up_all(&lruvec->mm_state.wait);
-+
-+      wakeup_flusher_threads(WB_REASON_VMSCAN);
-+
-+      return true;
-+}
-+
- static bool should_run_aging(struct lruvec *lruvec, unsigned long max_seq, unsigned long *min_seq,
-                            struct scan_control *sc, bool can_swap, unsigned long *nr_to_scan)
- {
-@@ -3265,7 +4193,7 @@ static void age_lruvec(struct lruvec *lr
-       need_aging = should_run_aging(lruvec, max_seq, min_seq, sc, swappiness, &nr_to_scan);
-       if (need_aging)
--              inc_max_seq(lruvec, max_seq, swappiness);
-+              try_to_inc_max_seq(lruvec, max_seq, sc, swappiness);
- }
- static void lru_gen_age_node(struct pglist_data *pgdat, struct scan_control *sc)
-@@ -3274,6 +4202,8 @@ static void lru_gen_age_node(struct pgli
-       VM_WARN_ON_ONCE(!current_is_kswapd());
-+      set_mm_walk(pgdat);
-+
-       memcg = mem_cgroup_iter(NULL, NULL, NULL);
-       do {
-               struct lruvec *lruvec = mem_cgroup_lruvec(memcg, pgdat);
-@@ -3282,11 +4212,16 @@ static void lru_gen_age_node(struct pgli
-               cond_resched();
-       } while ((memcg = mem_cgroup_iter(NULL, memcg, NULL)));
-+
-+      clear_mm_walk();
- }
- /*
-  * This function exploits spatial locality when shrink_page_list() walks the
-- * rmap. It scans the adjacent PTEs of a young PTE and promotes hot pages.
-+ * rmap. It scans the adjacent PTEs of a young PTE and promotes hot pages. If
-+ * the scan was done cacheline efficiently, it adds the PMD entry pointing to
-+ * the PTE table to the Bloom filter. This forms a feedback loop between the
-+ * eviction and the aging.
-  */
- void lru_gen_look_around(struct page_vma_mapped_walk *pvmw)
- {
-@@ -3295,6 +4230,8 @@ void lru_gen_look_around(struct page_vma
-       unsigned long start;
-       unsigned long end;
-       unsigned long addr;
-+      struct lru_gen_mm_walk *walk;
-+      int young = 0;
-       unsigned long bitmap[BITS_TO_LONGS(MIN_LRU_BATCH)] = {};
-       struct page *page = pvmw->page;
-       struct mem_cgroup *memcg = page_memcg(page);
-@@ -3309,6 +4246,9 @@ void lru_gen_look_around(struct page_vma
-       if (spin_is_contended(pvmw->ptl))
-               return;
-+      /* avoid taking the LRU lock under the PTL when possible */
-+      walk = current->reclaim_state ? current->reclaim_state->mm_walk : NULL;
-+
-       start = max(pvmw->address & PMD_MASK, pvmw->vma->vm_start);
-       end = min(pvmw->address | ~PMD_MASK, pvmw->vma->vm_end - 1) + 1;
-@@ -3338,13 +4278,15 @@ void lru_gen_look_around(struct page_vma
-               if (!pte_young(pte[i]))
-                       continue;
--              page = get_pfn_page(pfn, memcg, pgdat);
-+              page = get_pfn_page(pfn, memcg, pgdat, !walk || walk->can_swap);
-               if (!page)
-                       continue;
-               if (!ptep_test_and_clear_young(pvmw->vma, addr, pte + i))
-                       VM_WARN_ON_ONCE(true);
-+              young++;
-+
-               if (pte_dirty(pte[i]) && !PageDirty(page) &&
-                   !(PageAnon(page) && PageSwapBacked(page) &&
-                     !PageSwapCache(page)))
-@@ -3360,7 +4302,11 @@ void lru_gen_look_around(struct page_vma
-       arch_leave_lazy_mmu_mode();
-       rcu_read_unlock();
--      if (bitmap_weight(bitmap, MIN_LRU_BATCH) < PAGEVEC_SIZE) {
-+      /* feedback from rmap walkers to page table walkers */
-+      if (suitable_to_scan(i, young))
-+              update_bloom_filter(lruvec, max_seq, pvmw->pmd);
-+
-+      if (!walk && bitmap_weight(bitmap, MIN_LRU_BATCH) < PAGEVEC_SIZE) {
-               for_each_set_bit(i, bitmap, MIN_LRU_BATCH) {
-                       page = pte_page(pte[i]);
-                       activate_page(page);
-@@ -3372,8 +4318,10 @@ void lru_gen_look_around(struct page_vma
-       if (!mem_cgroup_trylock_pages(memcg))
-               return;
--      spin_lock_irq(&lruvec->lru_lock);
--      new_gen = lru_gen_from_seq(lruvec->lrugen.max_seq);
-+      if (!walk) {
-+              spin_lock_irq(&lruvec->lru_lock);
-+              new_gen = lru_gen_from_seq(lruvec->lrugen.max_seq);
-+      }
-       for_each_set_bit(i, bitmap, MIN_LRU_BATCH) {
-               page = compound_head(pte_page(pte[i]));
-@@ -3384,10 +4332,14 @@ void lru_gen_look_around(struct page_vma
-               if (old_gen < 0 || old_gen == new_gen)
-                       continue;
--              lru_gen_update_size(lruvec, page, old_gen, new_gen);
-+              if (walk)
-+                      update_batch_size(walk, page, old_gen, new_gen);
-+              else
-+                      lru_gen_update_size(lruvec, page, old_gen, new_gen);
-       }
--      spin_unlock_irq(&lruvec->lru_lock);
-+      if (!walk)
-+              spin_unlock_irq(&lruvec->lru_lock);
-       mem_cgroup_unlock_pages();
- }
-@@ -3670,6 +4622,7 @@ static int evict_pages(struct lruvec *lr
-       struct page *page;
-       enum vm_event_item item;
-       struct reclaim_stat stat;
-+      struct lru_gen_mm_walk *walk;
-       struct mem_cgroup *memcg = lruvec_memcg(lruvec);
-       struct pglist_data *pgdat = lruvec_pgdat(lruvec);
-@@ -3706,6 +4659,10 @@ static int evict_pages(struct lruvec *lr
-       move_pages_to_lru(lruvec, &list);
-+      walk = current->reclaim_state->mm_walk;
-+      if (walk && walk->batched)
-+              reset_batch_size(lruvec, walk);
-+
-       item = current_is_kswapd() ? PGSTEAL_KSWAPD : PGSTEAL_DIRECT;
-       if (!cgroup_reclaim(sc))
-               __count_vm_events(item, reclaimed);
-@@ -3722,6 +4679,11 @@ static int evict_pages(struct lruvec *lr
-       return scanned;
- }
-+/*
-+ * For future optimizations:
-+ * 1. Defer try_to_inc_max_seq() to workqueues to reduce latency for memcg
-+ *    reclaim.
-+ */
- static unsigned long get_nr_to_scan(struct lruvec *lruvec, struct scan_control *sc,
-                                   bool can_swap)
- {
-@@ -3747,7 +4709,8 @@ static unsigned long get_nr_to_scan(stru
-       if (current_is_kswapd())
-               return 0;
--      inc_max_seq(lruvec, max_seq, can_swap);
-+      if (try_to_inc_max_seq(lruvec, max_seq, sc, can_swap))
-+              return nr_to_scan;
- done:
-       return min_seq[!can_swap] + MIN_NR_GENS <= max_seq ? nr_to_scan : 0;
- }
-@@ -3761,6 +4724,8 @@ static void lru_gen_shrink_lruvec(struct
-       blk_start_plug(&plug);
-+      set_mm_walk(lruvec_pgdat(lruvec));
-+
-       while (true) {
-               int delta;
-               int swappiness;
-@@ -3788,6 +4753,8 @@ static void lru_gen_shrink_lruvec(struct
-               cond_resched();
-       }
-+      clear_mm_walk();
-+
-       blk_finish_plug(&plug);
- }
-@@ -3804,15 +4771,21 @@ void lru_gen_init_lruvec(struct lruvec *
-       for_each_gen_type_zone(gen, type, zone)
-               INIT_LIST_HEAD(&lrugen->lists[gen][type][zone]);
-+
-+      lruvec->mm_state.seq = MIN_NR_GENS;
-+      init_waitqueue_head(&lruvec->mm_state.wait);
- }
- #ifdef CONFIG_MEMCG
- void lru_gen_init_memcg(struct mem_cgroup *memcg)
- {
-+      INIT_LIST_HEAD(&memcg->mm_list.fifo);
-+      spin_lock_init(&memcg->mm_list.lock);
- }
- void lru_gen_exit_memcg(struct mem_cgroup *memcg)
- {
-+      int i;
-       int nid;
-       for_each_node(nid) {
-@@ -3820,6 +4793,11 @@ void lru_gen_exit_memcg(struct mem_cgrou
-               VM_WARN_ON_ONCE(memchr_inv(lruvec->lrugen.nr_pages, 0,
-                                          sizeof(lruvec->lrugen.nr_pages)));
-+
-+              for (i = 0; i < NR_BLOOM_FILTERS; i++) {
-+                      bitmap_free(lruvec->mm_state.filters[i]);
-+                      lruvec->mm_state.filters[i] = NULL;
-+              }
-       }
- }
- #endif
diff --git a/target/linux/generic/backport-5.15/020-v6.1-09-mm-multi-gen-LRU-optimize-multiple-memcgs.patch b/target/linux/generic/backport-5.15/020-v6.1-09-mm-multi-gen-LRU-optimize-multiple-memcgs.patch
deleted file mode 100644 (file)
index b5fb195..0000000
+++ /dev/null
@@ -1,315 +0,0 @@
-From 36a18a68ea458e8f4db2ca86b00091daf32c6c74 Mon Sep 17 00:00:00 2001
-From: Yu Zhao <[email protected]>
-Date: Sun, 18 Sep 2022 02:00:06 -0600
-Subject: [PATCH 09/29] mm: multi-gen LRU: optimize multiple memcgs
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-When multiple memcgs are available, it is possible to use generations as a
-frame of reference to make better choices and improve overall performance
-under global memory pressure.  This patch adds a basic optimization to
-select memcgs that can drop single-use unmapped clean pages first.  Doing
-so reduces the chance of going into the aging path or swapping, which can
-be costly.
-
-A typical example that benefits from this optimization is a server running
-mixed types of workloads, e.g., heavy anon workload in one memcg and heavy
-buffered I/O workload in the other.
-
-Though this optimization can be applied to both kswapd and direct reclaim,
-it is only added to kswapd to keep the patchset manageable.  Later
-improvements may cover the direct reclaim path.
-
-While ensuring certain fairness to all eligible memcgs, proportional scans
-of individual memcgs also require proper backoff to avoid overshooting
-their aggregate reclaim target by too much.  Otherwise it can cause high
-direct reclaim latency.  The conditions for backoff are:
-
-1. At low priorities, for direct reclaim, if aging fairness or direct
-   reclaim latency is at risk, i.e., aging one memcg multiple times or
-   swapping after the target is met.
-2. At high priorities, for global reclaim, if per-zone free pages are
-   above respective watermarks.
-
-Server benchmark results:
-  Mixed workloads:
-    fio (buffered I/O): +[19, 21]%
-                IOPS         BW
-      patch1-8: 1880k        7343MiB/s
-      patch1-9: 2252k        8796MiB/s
-
-    memcached (anon): +[119, 123]%
-                Ops/sec      KB/sec
-      patch1-8: 862768.65    33514.68
-      patch1-9: 1911022.12   74234.54
-
-  Mixed workloads:
-    fio (buffered I/O): +[75, 77]%
-                IOPS         BW
-      5.19-rc1: 1279k        4996MiB/s
-      patch1-9: 2252k        8796MiB/s
-
-    memcached (anon): +[13, 15]%
-                Ops/sec      KB/sec
-      5.19-rc1: 1673524.04   65008.87
-      patch1-9: 1911022.12   74234.54
-
-  Configurations:
-    (changes since patch 6)
-
-    cat mixed.sh
-    modprobe brd rd_nr=2 rd_size=56623104
-
-    swapoff -a
-    mkswap /dev/ram0
-    swapon /dev/ram0
-
-    mkfs.ext4 /dev/ram1
-    mount -t ext4 /dev/ram1 /mnt
-
-    memtier_benchmark -S /var/run/memcached/memcached.sock \
-      -P memcache_binary -n allkeys --key-minimum=1 \
-      --key-maximum=50000000 --key-pattern=P:P -c 1 -t 36 \
-      --ratio 1:0 --pipeline 8 -d 2000
-
-    fio -name=mglru --numjobs=36 --directory=/mnt --size=1408m \
-      --buffered=1 --ioengine=io_uring --iodepth=128 \
-      --iodepth_batch_submit=32 --iodepth_batch_complete=32 \
-      --rw=randread --random_distribution=random --norandommap \
-      --time_based --ramp_time=10m --runtime=90m --group_reporting &
-    pid=$!
-
-    sleep 200
-
-    memtier_benchmark -S /var/run/memcached/memcached.sock \
-      -P memcache_binary -n allkeys --key-minimum=1 \
-      --key-maximum=50000000 --key-pattern=R:R -c 1 -t 36 \
-      --ratio 0:1 --pipeline 8 --randomize --distinct-client-seed
-
-    kill -INT $pid
-    wait
-
-Client benchmark results:
-  no change (CONFIG_MEMCG=n)
-
-Link: https://lkml.kernel.org/r/[email protected]
-Signed-off-by: Yu Zhao <[email protected]>
-Acked-by: Brian Geffon <[email protected]>
-Acked-by: Jan Alexander Steffens (heftig) <[email protected]>
-Acked-by: Oleksandr Natalenko <[email protected]>
-Acked-by: Steven Barrett <[email protected]>
-Acked-by: Suleiman Souhlal <[email protected]>
-Tested-by: Daniel Byrne <[email protected]>
-Tested-by: Donald Carr <[email protected]>
-Tested-by: Holger Hoffstätte <[email protected]>
-Tested-by: Konstantin Kharlamov <[email protected]>
-Tested-by: Shuang Zhai <[email protected]>
-Tested-by: Sofia Trinh <[email protected]>
-Tested-by: Vaibhav Jain <[email protected]>
-Cc: Andi Kleen <[email protected]>
-Cc: Aneesh Kumar K.V <[email protected]>
-Cc: Barry Song <[email protected]>
-Cc: Catalin Marinas <[email protected]>
-Cc: Dave Hansen <[email protected]>
-Cc: Hillf Danton <[email protected]>
-Cc: Jens Axboe <[email protected]>
-Cc: Johannes Weiner <[email protected]>
-Cc: Jonathan Corbet <[email protected]>
-Cc: Linus Torvalds <[email protected]>
-Cc: Matthew Wilcox <[email protected]>
-Cc: Mel Gorman <[email protected]>
-Cc: Miaohe Lin <[email protected]>
-Cc: Michael Larabel <[email protected]>
-Cc: Michal Hocko <[email protected]>
-Cc: Mike Rapoport <[email protected]>
-Cc: Mike Rapoport <[email protected]>
-Cc: Peter Zijlstra <[email protected]>
-Cc: Qi Zheng <[email protected]>
-Cc: Tejun Heo <[email protected]>
-Cc: Vlastimil Babka <[email protected]>
-Cc: Will Deacon <[email protected]>
-Signed-off-by: Andrew Morton <[email protected]>
----
- mm/vmscan.c | 105 +++++++++++++++++++++++++++++++++++++++++++++++-----
- 1 file changed, 96 insertions(+), 9 deletions(-)
-
---- a/mm/vmscan.c
-+++ b/mm/vmscan.c
-@@ -127,6 +127,12 @@ struct scan_control {
-       /* Always discard instead of demoting to lower tier memory */
-       unsigned int no_demotion:1;
-+#ifdef CONFIG_LRU_GEN
-+      /* help kswapd make better choices among multiple memcgs */
-+      unsigned int memcgs_need_aging:1;
-+      unsigned long last_reclaimed;
-+#endif
-+
-       /* Allocation order */
-       s8 order;
-@@ -4202,6 +4208,19 @@ static void lru_gen_age_node(struct pgli
-       VM_WARN_ON_ONCE(!current_is_kswapd());
-+      sc->last_reclaimed = sc->nr_reclaimed;
-+
-+      /*
-+       * To reduce the chance of going into the aging path, which can be
-+       * costly, optimistically skip it if the flag below was cleared in the
-+       * eviction path. This improves the overall performance when multiple
-+       * memcgs are available.
-+       */
-+      if (!sc->memcgs_need_aging) {
-+              sc->memcgs_need_aging = true;
-+              return;
-+      }
-+
-       set_mm_walk(pgdat);
-       memcg = mem_cgroup_iter(NULL, NULL, NULL);
-@@ -4613,7 +4632,8 @@ static int isolate_pages(struct lruvec *
-       return scanned;
- }
--static int evict_pages(struct lruvec *lruvec, struct scan_control *sc, int swappiness)
-+static int evict_pages(struct lruvec *lruvec, struct scan_control *sc, int swappiness,
-+                     bool *need_swapping)
- {
-       int type;
-       int scanned;
-@@ -4676,6 +4696,9 @@ static int evict_pages(struct lruvec *lr
-       sc->nr_reclaimed += reclaimed;
-+      if (need_swapping && type == LRU_GEN_ANON)
-+              *need_swapping = true;
-+
-       return scanned;
- }
-@@ -4685,9 +4708,8 @@ static int evict_pages(struct lruvec *lr
-  *    reclaim.
-  */
- static unsigned long get_nr_to_scan(struct lruvec *lruvec, struct scan_control *sc,
--                                  bool can_swap)
-+                                  bool can_swap, bool *need_aging)
- {
--      bool need_aging;
-       unsigned long nr_to_scan;
-       struct mem_cgroup *memcg = lruvec_memcg(lruvec);
-       DEFINE_MAX_SEQ(lruvec);
-@@ -4697,8 +4719,8 @@ static unsigned long get_nr_to_scan(stru
-           (mem_cgroup_below_low(memcg) && !sc->memcg_low_reclaim))
-               return 0;
--      need_aging = should_run_aging(lruvec, max_seq, min_seq, sc, can_swap, &nr_to_scan);
--      if (!need_aging)
-+      *need_aging = should_run_aging(lruvec, max_seq, min_seq, sc, can_swap, &nr_to_scan);
-+      if (!*need_aging)
-               return nr_to_scan;
-       /* skip the aging path at the default priority */
-@@ -4715,10 +4737,68 @@ done:
-       return min_seq[!can_swap] + MIN_NR_GENS <= max_seq ? nr_to_scan : 0;
- }
-+static bool should_abort_scan(struct lruvec *lruvec, unsigned long seq,
-+                            struct scan_control *sc, bool need_swapping)
-+{
-+      int i;
-+      DEFINE_MAX_SEQ(lruvec);
-+
-+      if (!current_is_kswapd()) {
-+              /* age each memcg once to ensure fairness */
-+              if (max_seq - seq > 1)
-+                      return true;
-+
-+              /* over-swapping can increase allocation latency */
-+              if (sc->nr_reclaimed >= sc->nr_to_reclaim && need_swapping)
-+                      return true;
-+
-+              /* give this thread a chance to exit and free its memory */
-+              if (fatal_signal_pending(current)) {
-+                      sc->nr_reclaimed += MIN_LRU_BATCH;
-+                      return true;
-+              }
-+
-+              if (cgroup_reclaim(sc))
-+                      return false;
-+      } else if (sc->nr_reclaimed - sc->last_reclaimed < sc->nr_to_reclaim)
-+              return false;
-+
-+      /* keep scanning at low priorities to ensure fairness */
-+      if (sc->priority > DEF_PRIORITY - 2)
-+              return false;
-+
-+      /*
-+       * A minimum amount of work was done under global memory pressure. For
-+       * kswapd, it may be overshooting. For direct reclaim, the target isn't
-+       * met, and yet the allocation may still succeed, since kswapd may have
-+       * caught up. In either case, it's better to stop now, and restart if
-+       * necessary.
-+       */
-+      for (i = 0; i <= sc->reclaim_idx; i++) {
-+              unsigned long wmark;
-+              struct zone *zone = lruvec_pgdat(lruvec)->node_zones + i;
-+
-+              if (!managed_zone(zone))
-+                      continue;
-+
-+              wmark = current_is_kswapd() ? high_wmark_pages(zone) : low_wmark_pages(zone);
-+              if (wmark > zone_page_state(zone, NR_FREE_PAGES))
-+                      return false;
-+      }
-+
-+      sc->nr_reclaimed += MIN_LRU_BATCH;
-+
-+      return true;
-+}
-+
- static void lru_gen_shrink_lruvec(struct lruvec *lruvec, struct scan_control *sc)
- {
-       struct blk_plug plug;
-+      bool need_aging = false;
-+      bool need_swapping = false;
-       unsigned long scanned = 0;
-+      unsigned long reclaimed = sc->nr_reclaimed;
-+      DEFINE_MAX_SEQ(lruvec);
-       lru_add_drain();
-@@ -4738,21 +4818,28 @@ static void lru_gen_shrink_lruvec(struct
-               else
-                       swappiness = 0;
--              nr_to_scan = get_nr_to_scan(lruvec, sc, swappiness);
-+              nr_to_scan = get_nr_to_scan(lruvec, sc, swappiness, &need_aging);
-               if (!nr_to_scan)
--                      break;
-+                      goto done;
--              delta = evict_pages(lruvec, sc, swappiness);
-+              delta = evict_pages(lruvec, sc, swappiness, &need_swapping);
-               if (!delta)
--                      break;
-+                      goto done;
-               scanned += delta;
-               if (scanned >= nr_to_scan)
-                       break;
-+              if (should_abort_scan(lruvec, max_seq, sc, need_swapping))
-+                      break;
-+
-               cond_resched();
-       }
-+      /* see the comment in lru_gen_age_node() */
-+      if (sc->nr_reclaimed - reclaimed >= MIN_LRU_BATCH && !need_aging)
-+              sc->memcgs_need_aging = false;
-+done:
-       clear_mm_walk();
-       blk_finish_plug(&plug);
diff --git a/target/linux/generic/backport-5.15/020-v6.1-10-mm-multi-gen-LRU-kill-switch.patch b/target/linux/generic/backport-5.15/020-v6.1-10-mm-multi-gen-LRU-kill-switch.patch
deleted file mode 100644 (file)
index 8ee032f..0000000
+++ /dev/null
@@ -1,498 +0,0 @@
-From 640db3a029dca909af47157ca18f52b29d34a1b9 Mon Sep 17 00:00:00 2001
-From: Yu Zhao <[email protected]>
-Date: Sun, 18 Sep 2022 02:00:07 -0600
-Subject: [PATCH 10/29] mm: multi-gen LRU: kill switch
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-Add /sys/kernel/mm/lru_gen/enabled as a kill switch. Components that
-can be disabled include:
-  0x0001: the multi-gen LRU core
-  0x0002: walking page table, when arch_has_hw_pte_young() returns
-          true
-  0x0004: clearing the accessed bit in non-leaf PMD entries, when
-          CONFIG_ARCH_HAS_NONLEAF_PMD_YOUNG=y
-  [yYnN]: apply to all the components above
-E.g.,
-  echo y >/sys/kernel/mm/lru_gen/enabled
-  cat /sys/kernel/mm/lru_gen/enabled
-  0x0007
-  echo 5 >/sys/kernel/mm/lru_gen/enabled
-  cat /sys/kernel/mm/lru_gen/enabled
-  0x0005
-
-NB: the page table walks happen on the scale of seconds under heavy memory
-pressure, in which case the mmap_lock contention is a lesser concern,
-compared with the LRU lock contention and the I/O congestion.  So far the
-only well-known case of the mmap_lock contention happens on Android, due
-to Scudo [1] which allocates several thousand VMAs for merely a few
-hundred MBs.  The SPF and the Maple Tree also have provided their own
-assessments [2][3].  However, if walking page tables does worsen the
-mmap_lock contention, the kill switch can be used to disable it.  In this
-case the multi-gen LRU will suffer a minor performance degradation, as
-shown previously.
-
-Clearing the accessed bit in non-leaf PMD entries can also be disabled,
-since this behavior was not tested on x86 varieties other than Intel and
-AMD.
-
-[1] https://source.android.com/devices/tech/debug/scudo
-[2] https://lore.kernel.org/r/[email protected]/
-[3] https://lore.kernel.org/r/[email protected]/
-
-Link: https://lkml.kernel.org/r/[email protected]
-Signed-off-by: Yu Zhao <[email protected]>
-Acked-by: Brian Geffon <[email protected]>
-Acked-by: Jan Alexander Steffens (heftig) <[email protected]>
-Acked-by: Oleksandr Natalenko <[email protected]>
-Acked-by: Steven Barrett <[email protected]>
-Acked-by: Suleiman Souhlal <[email protected]>
-Tested-by: Daniel Byrne <[email protected]>
-Tested-by: Donald Carr <[email protected]>
-Tested-by: Holger Hoffstätte <[email protected]>
-Tested-by: Konstantin Kharlamov <[email protected]>
-Tested-by: Shuang Zhai <[email protected]>
-Tested-by: Sofia Trinh <[email protected]>
-Tested-by: Vaibhav Jain <[email protected]>
-Cc: Andi Kleen <[email protected]>
-Cc: Aneesh Kumar K.V <[email protected]>
-Cc: Barry Song <[email protected]>
-Cc: Catalin Marinas <[email protected]>
-Cc: Dave Hansen <[email protected]>
-Cc: Hillf Danton <[email protected]>
-Cc: Jens Axboe <[email protected]>
-Cc: Johannes Weiner <[email protected]>
-Cc: Jonathan Corbet <[email protected]>
-Cc: Linus Torvalds <[email protected]>
-Cc: Matthew Wilcox <[email protected]>
-Cc: Mel Gorman <[email protected]>
-Cc: Miaohe Lin <[email protected]>
-Cc: Michael Larabel <[email protected]>
-Cc: Michal Hocko <[email protected]>
-Cc: Mike Rapoport <[email protected]>
-Cc: Mike Rapoport <[email protected]>
-Cc: Peter Zijlstra <[email protected]>
-Cc: Qi Zheng <[email protected]>
-Cc: Tejun Heo <[email protected]>
-Cc: Vlastimil Babka <[email protected]>
-Cc: Will Deacon <[email protected]>
-Signed-off-by: Andrew Morton <[email protected]>
----
- include/linux/cgroup.h          |  15 ++-
- include/linux/mm_inline.h       |  15 ++-
- include/linux/mmzone.h          |   9 ++
- kernel/cgroup/cgroup-internal.h |   1 -
- mm/Kconfig                      |   6 +
- mm/vmscan.c                     | 228 +++++++++++++++++++++++++++++++-
- 6 files changed, 265 insertions(+), 9 deletions(-)
-
---- a/include/linux/cgroup.h
-+++ b/include/linux/cgroup.h
-@@ -433,6 +433,18 @@ static inline void cgroup_put(struct cgr
-       css_put(&cgrp->self);
- }
-+extern struct mutex cgroup_mutex;
-+
-+static inline void cgroup_lock(void)
-+{
-+      mutex_lock(&cgroup_mutex);
-+}
-+
-+static inline void cgroup_unlock(void)
-+{
-+      mutex_unlock(&cgroup_mutex);
-+}
-+
- /**
-  * task_css_set_check - obtain a task's css_set with extra access conditions
-  * @task: the task to obtain css_set for
-@@ -447,7 +459,6 @@ static inline void cgroup_put(struct cgr
-  * as locks used during the cgroup_subsys::attach() methods.
-  */
- #ifdef CONFIG_PROVE_RCU
--extern struct mutex cgroup_mutex;
- extern spinlock_t css_set_lock;
- #define task_css_set_check(task, __c)                                 \
-       rcu_dereference_check((task)->cgroups,                          \
-@@ -709,6 +720,8 @@ struct cgroup;
- static inline u64 cgroup_id(const struct cgroup *cgrp) { return 1; }
- static inline void css_get(struct cgroup_subsys_state *css) {}
- static inline void css_put(struct cgroup_subsys_state *css) {}
-+static inline void cgroup_lock(void) {}
-+static inline void cgroup_unlock(void) {}
- static inline int cgroup_attach_task_all(struct task_struct *from,
-                                        struct task_struct *t) { return 0; }
- static inline int cgroupstats_build(struct cgroupstats *stats,
---- a/include/linux/mm_inline.h
-+++ b/include/linux/mm_inline.h
-@@ -91,10 +91,21 @@ static __always_inline enum lru_list pag
- #ifdef CONFIG_LRU_GEN
-+#ifdef CONFIG_LRU_GEN_ENABLED
- static inline bool lru_gen_enabled(void)
- {
--      return true;
-+      DECLARE_STATIC_KEY_TRUE(lru_gen_caps[NR_LRU_GEN_CAPS]);
-+
-+      return static_branch_likely(&lru_gen_caps[LRU_GEN_CORE]);
-+}
-+#else
-+static inline bool lru_gen_enabled(void)
-+{
-+      DECLARE_STATIC_KEY_FALSE(lru_gen_caps[NR_LRU_GEN_CAPS]);
-+
-+      return static_branch_unlikely(&lru_gen_caps[LRU_GEN_CORE]);
- }
-+#endif
- static inline bool lru_gen_in_fault(void)
- {
-@@ -207,7 +218,7 @@ static inline bool lru_gen_add_page(stru
-       VM_WARN_ON_ONCE_PAGE(gen != -1, page);
--      if (PageUnevictable(page))
-+      if (PageUnevictable(page) || !lrugen->enabled)
-               return false;
-       /*
-        * There are three common cases for this page:
---- a/include/linux/mmzone.h
-+++ b/include/linux/mmzone.h
-@@ -364,6 +364,13 @@ enum {
-       LRU_GEN_FILE,
- };
-+enum {
-+      LRU_GEN_CORE,
-+      LRU_GEN_MM_WALK,
-+      LRU_GEN_NONLEAF_YOUNG,
-+      NR_LRU_GEN_CAPS
-+};
-+
- #define MIN_LRU_BATCH         BITS_PER_LONG
- #define MAX_LRU_BATCH         (MIN_LRU_BATCH * 64)
-@@ -405,6 +412,8 @@ struct lru_gen_struct {
-       /* can be modified without holding the LRU lock */
-       atomic_long_t evicted[NR_HIST_GENS][ANON_AND_FILE][MAX_NR_TIERS];
-       atomic_long_t refaulted[NR_HIST_GENS][ANON_AND_FILE][MAX_NR_TIERS];
-+      /* whether the multi-gen LRU is enabled */
-+      bool enabled;
- };
- enum {
---- a/kernel/cgroup/cgroup-internal.h
-+++ b/kernel/cgroup/cgroup-internal.h
-@@ -165,7 +165,6 @@ struct cgroup_mgctx {
- #define DEFINE_CGROUP_MGCTX(name)                                             \
-       struct cgroup_mgctx name = CGROUP_MGCTX_INIT(name)
--extern struct mutex cgroup_mutex;
- extern spinlock_t css_set_lock;
- extern struct cgroup_subsys *cgroup_subsys[];
- extern struct list_head cgroup_roots;
---- a/mm/Kconfig
-+++ b/mm/Kconfig
-@@ -906,6 +906,12 @@ config LRU_GEN
-       help
-         A high performance LRU implementation to overcommit memory.
-+config LRU_GEN_ENABLED
-+      bool "Enable by default"
-+      depends on LRU_GEN
-+      help
-+        This option enables the multi-gen LRU by default.
-+
- config LRU_GEN_STATS
-       bool "Full stats for debugging"
-       depends on LRU_GEN
---- a/mm/vmscan.c
-+++ b/mm/vmscan.c
-@@ -52,6 +52,7 @@
- #include <linux/psi.h>
- #include <linux/pagewalk.h>
- #include <linux/shmem_fs.h>
-+#include <linux/ctype.h>
- #include <asm/tlbflush.h>
- #include <asm/div64.h>
-@@ -2841,6 +2842,14 @@ static bool can_age_anon_pages(struct pg
- #ifdef CONFIG_LRU_GEN
-+#ifdef CONFIG_LRU_GEN_ENABLED
-+DEFINE_STATIC_KEY_ARRAY_TRUE(lru_gen_caps, NR_LRU_GEN_CAPS);
-+#define get_cap(cap)  static_branch_likely(&lru_gen_caps[cap])
-+#else
-+DEFINE_STATIC_KEY_ARRAY_FALSE(lru_gen_caps, NR_LRU_GEN_CAPS);
-+#define get_cap(cap)  static_branch_unlikely(&lru_gen_caps[cap])
-+#endif
-+
- /******************************************************************************
-  *                          shorthand helpers
-  ******************************************************************************/
-@@ -3717,7 +3726,8 @@ static void walk_pmd_range_locked(pud_t
-                       goto next;
-               if (!pmd_trans_huge(pmd[i])) {
--                      if (IS_ENABLED(CONFIG_ARCH_HAS_NONLEAF_PMD_YOUNG))
-+                      if (IS_ENABLED(CONFIG_ARCH_HAS_NONLEAF_PMD_YOUNG) &&
-+                          get_cap(LRU_GEN_NONLEAF_YOUNG))
-                               pmdp_test_and_clear_young(vma, addr, pmd + i);
-                       goto next;
-               }
-@@ -3815,10 +3825,12 @@ restart:
-               walk->mm_stats[MM_NONLEAF_TOTAL]++;
- #ifdef CONFIG_ARCH_HAS_NONLEAF_PMD_YOUNG
--              if (!pmd_young(val))
--                      continue;
-+              if (get_cap(LRU_GEN_NONLEAF_YOUNG)) {
-+                      if (!pmd_young(val))
-+                              continue;
--              walk_pmd_range_locked(pud, addr, vma, args, bitmap, &pos);
-+                      walk_pmd_range_locked(pud, addr, vma, args, bitmap, &pos);
-+              }
- #endif
-               if (!walk->force_scan && !test_bloom_filter(walk->lruvec, walk->max_seq, pmd + i))
-                       continue;
-@@ -4080,7 +4092,7 @@ static bool try_to_inc_max_seq(struct lr
-        * handful of PTEs. Spreading the work out over a period of time usually
-        * is less efficient, but it avoids bursty page faults.
-        */
--      if (!arch_has_hw_pte_young()) {
-+      if (!(arch_has_hw_pte_young() && get_cap(LRU_GEN_MM_WALK))) {
-               success = iterate_mm_list_nowalk(lruvec, max_seq);
-               goto done;
-       }
-@@ -4846,6 +4858,208 @@ done:
- }
- /******************************************************************************
-+ *                          state change
-+ ******************************************************************************/
-+
-+static bool __maybe_unused state_is_valid(struct lruvec *lruvec)
-+{
-+      struct lru_gen_struct *lrugen = &lruvec->lrugen;
-+
-+      if (lrugen->enabled) {
-+              enum lru_list lru;
-+
-+              for_each_evictable_lru(lru) {
-+                      if (!list_empty(&lruvec->lists[lru]))
-+                              return false;
-+              }
-+      } else {
-+              int gen, type, zone;
-+
-+              for_each_gen_type_zone(gen, type, zone) {
-+                      if (!list_empty(&lrugen->lists[gen][type][zone]))
-+                              return false;
-+              }
-+      }
-+
-+      return true;
-+}
-+
-+static bool fill_evictable(struct lruvec *lruvec)
-+{
-+      enum lru_list lru;
-+      int remaining = MAX_LRU_BATCH;
-+
-+      for_each_evictable_lru(lru) {
-+              int type = is_file_lru(lru);
-+              bool active = is_active_lru(lru);
-+              struct list_head *head = &lruvec->lists[lru];
-+
-+              while (!list_empty(head)) {
-+                      bool success;
-+                      struct page *page = lru_to_page(head);
-+
-+                      VM_WARN_ON_ONCE_PAGE(PageUnevictable(page), page);
-+                      VM_WARN_ON_ONCE_PAGE(PageActive(page) != active, page);
-+                      VM_WARN_ON_ONCE_PAGE(page_is_file_lru(page) != type, page);
-+                      VM_WARN_ON_ONCE_PAGE(page_lru_gen(page) != -1, page);
-+
-+                      del_page_from_lru_list(page, lruvec);
-+                      success = lru_gen_add_page(lruvec, page, false);
-+                      VM_WARN_ON_ONCE(!success);
-+
-+                      if (!--remaining)
-+                              return false;
-+              }
-+      }
-+
-+      return true;
-+}
-+
-+static bool drain_evictable(struct lruvec *lruvec)
-+{
-+      int gen, type, zone;
-+      int remaining = MAX_LRU_BATCH;
-+
-+      for_each_gen_type_zone(gen, type, zone) {
-+              struct list_head *head = &lruvec->lrugen.lists[gen][type][zone];
-+
-+              while (!list_empty(head)) {
-+                      bool success;
-+                      struct page *page = lru_to_page(head);
-+
-+                      VM_WARN_ON_ONCE_PAGE(PageUnevictable(page), page);
-+                      VM_WARN_ON_ONCE_PAGE(PageActive(page), page);
-+                      VM_WARN_ON_ONCE_PAGE(page_is_file_lru(page) != type, page);
-+                      VM_WARN_ON_ONCE_PAGE(page_zonenum(page) != zone, page);
-+
-+                      success = lru_gen_del_page(lruvec, page, false);
-+                      VM_WARN_ON_ONCE(!success);
-+                      add_page_to_lru_list(page, lruvec);
-+
-+                      if (!--remaining)
-+                              return false;
-+              }
-+      }
-+
-+      return true;
-+}
-+
-+static void lru_gen_change_state(bool enabled)
-+{
-+      static DEFINE_MUTEX(state_mutex);
-+
-+      struct mem_cgroup *memcg;
-+
-+      cgroup_lock();
-+      cpus_read_lock();
-+      get_online_mems();
-+      mutex_lock(&state_mutex);
-+
-+      if (enabled == lru_gen_enabled())
-+              goto unlock;
-+
-+      if (enabled)
-+              static_branch_enable_cpuslocked(&lru_gen_caps[LRU_GEN_CORE]);
-+      else
-+              static_branch_disable_cpuslocked(&lru_gen_caps[LRU_GEN_CORE]);
-+
-+      memcg = mem_cgroup_iter(NULL, NULL, NULL);
-+      do {
-+              int nid;
-+
-+              for_each_node(nid) {
-+                      struct lruvec *lruvec = get_lruvec(memcg, nid);
-+
-+                      if (!lruvec)
-+                              continue;
-+
-+                      spin_lock_irq(&lruvec->lru_lock);
-+
-+                      VM_WARN_ON_ONCE(!seq_is_valid(lruvec));
-+                      VM_WARN_ON_ONCE(!state_is_valid(lruvec));
-+
-+                      lruvec->lrugen.enabled = enabled;
-+
-+                      while (!(enabled ? fill_evictable(lruvec) : drain_evictable(lruvec))) {
-+                              spin_unlock_irq(&lruvec->lru_lock);
-+                              cond_resched();
-+                              spin_lock_irq(&lruvec->lru_lock);
-+                      }
-+
-+                      spin_unlock_irq(&lruvec->lru_lock);
-+              }
-+
-+              cond_resched();
-+      } while ((memcg = mem_cgroup_iter(NULL, memcg, NULL)));
-+unlock:
-+      mutex_unlock(&state_mutex);
-+      put_online_mems();
-+      cpus_read_unlock();
-+      cgroup_unlock();
-+}
-+
-+/******************************************************************************
-+ *                          sysfs interface
-+ ******************************************************************************/
-+
-+static ssize_t show_enabled(struct kobject *kobj, struct kobj_attribute *attr, char *buf)
-+{
-+      unsigned int caps = 0;
-+
-+      if (get_cap(LRU_GEN_CORE))
-+              caps |= BIT(LRU_GEN_CORE);
-+
-+      if (arch_has_hw_pte_young() && get_cap(LRU_GEN_MM_WALK))
-+              caps |= BIT(LRU_GEN_MM_WALK);
-+
-+      if (IS_ENABLED(CONFIG_ARCH_HAS_NONLEAF_PMD_YOUNG) && get_cap(LRU_GEN_NONLEAF_YOUNG))
-+              caps |= BIT(LRU_GEN_NONLEAF_YOUNG);
-+
-+      return snprintf(buf, PAGE_SIZE, "0x%04x\n", caps);
-+}
-+
-+static ssize_t store_enabled(struct kobject *kobj, struct kobj_attribute *attr,
-+                           const char *buf, size_t len)
-+{
-+      int i;
-+      unsigned int caps;
-+
-+      if (tolower(*buf) == 'n')
-+              caps = 0;
-+      else if (tolower(*buf) == 'y')
-+              caps = -1;
-+      else if (kstrtouint(buf, 0, &caps))
-+              return -EINVAL;
-+
-+      for (i = 0; i < NR_LRU_GEN_CAPS; i++) {
-+              bool enabled = caps & BIT(i);
-+
-+              if (i == LRU_GEN_CORE)
-+                      lru_gen_change_state(enabled);
-+              else if (enabled)
-+                      static_branch_enable(&lru_gen_caps[i]);
-+              else
-+                      static_branch_disable(&lru_gen_caps[i]);
-+      }
-+
-+      return len;
-+}
-+
-+static struct kobj_attribute lru_gen_enabled_attr = __ATTR(
-+      enabled, 0644, show_enabled, store_enabled
-+);
-+
-+static struct attribute *lru_gen_attrs[] = {
-+      &lru_gen_enabled_attr.attr,
-+      NULL
-+};
-+
-+static struct attribute_group lru_gen_attr_group = {
-+      .name = "lru_gen",
-+      .attrs = lru_gen_attrs,
-+};
-+
-+/******************************************************************************
-  *                          initialization
-  ******************************************************************************/
-@@ -4855,6 +5069,7 @@ void lru_gen_init_lruvec(struct lruvec *
-       struct lru_gen_struct *lrugen = &lruvec->lrugen;
-       lrugen->max_seq = MIN_NR_GENS + 1;
-+      lrugen->enabled = lru_gen_enabled();
-       for_each_gen_type_zone(gen, type, zone)
-               INIT_LIST_HEAD(&lrugen->lists[gen][type][zone]);
-@@ -4894,6 +5109,9 @@ static int __init init_lru_gen(void)
-       BUILD_BUG_ON(MIN_NR_GENS + 1 >= MAX_NR_GENS);
-       BUILD_BUG_ON(BIT(LRU_GEN_WIDTH) <= MAX_NR_GENS);
-+      if (sysfs_create_group(mm_kobj, &lru_gen_attr_group))
-+              pr_err("lru_gen: failed to create sysfs group\n");
-+
-       return 0;
- };
- late_initcall(init_lru_gen);
diff --git a/target/linux/generic/backport-5.15/020-v6.1-11-mm-multi-gen-LRU-thrashing-prevention.patch b/target/linux/generic/backport-5.15/020-v6.1-11-mm-multi-gen-LRU-thrashing-prevention.patch
deleted file mode 100644 (file)
index 30e20af..0000000
+++ /dev/null
@@ -1,226 +0,0 @@
-From 73d1ff551760f0c79c47ab70faa4c2ca91413f5c Mon Sep 17 00:00:00 2001
-From: Yu Zhao <[email protected]>
-Date: Sun, 18 Sep 2022 02:00:08 -0600
-Subject: [PATCH 11/29] mm: multi-gen LRU: thrashing prevention
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-Add /sys/kernel/mm/lru_gen/min_ttl_ms for thrashing prevention, as
-requested by many desktop users [1].
-
-When set to value N, it prevents the working set of N milliseconds from
-getting evicted.  The OOM killer is triggered if this working set cannot
-be kept in memory.  Based on the average human detectable lag (~100ms),
-N=1000 usually eliminates intolerable lags due to thrashing.  Larger
-values like N=3000 make lags less noticeable at the risk of premature OOM
-kills.
-
-Compared with the size-based approach [2], this time-based approach
-has the following advantages:
-
-1. It is easier to configure because it is agnostic to applications
-   and memory sizes.
-2. It is more reliable because it is directly wired to the OOM killer.
-
-[1] https://lore.kernel.org/r/Ydza%[email protected]/
-[2] https://lore.kernel.org/r/[email protected]/
-
-Link: https://lkml.kernel.org/r/[email protected]
-Signed-off-by: Yu Zhao <[email protected]>
-Acked-by: Brian Geffon <[email protected]>
-Acked-by: Jan Alexander Steffens (heftig) <[email protected]>
-Acked-by: Oleksandr Natalenko <[email protected]>
-Acked-by: Steven Barrett <[email protected]>
-Acked-by: Suleiman Souhlal <[email protected]>
-Tested-by: Daniel Byrne <[email protected]>
-Tested-by: Donald Carr <[email protected]>
-Tested-by: Holger Hoffstätte <[email protected]>
-Tested-by: Konstantin Kharlamov <[email protected]>
-Tested-by: Shuang Zhai <[email protected]>
-Tested-by: Sofia Trinh <[email protected]>
-Tested-by: Vaibhav Jain <[email protected]>
-Cc: Andi Kleen <[email protected]>
-Cc: Aneesh Kumar K.V <[email protected]>
-Cc: Barry Song <[email protected]>
-Cc: Catalin Marinas <[email protected]>
-Cc: Dave Hansen <[email protected]>
-Cc: Hillf Danton <[email protected]>
-Cc: Jens Axboe <[email protected]>
-Cc: Johannes Weiner <[email protected]>
-Cc: Jonathan Corbet <[email protected]>
-Cc: Linus Torvalds <[email protected]>
-Cc: Matthew Wilcox <[email protected]>
-Cc: Mel Gorman <[email protected]>
-Cc: Miaohe Lin <[email protected]>
-Cc: Michael Larabel <[email protected]>
-Cc: Michal Hocko <[email protected]>
-Cc: Mike Rapoport <[email protected]>
-Cc: Mike Rapoport <[email protected]>
-Cc: Peter Zijlstra <[email protected]>
-Cc: Qi Zheng <[email protected]>
-Cc: Tejun Heo <[email protected]>
-Cc: Vlastimil Babka <[email protected]>
-Cc: Will Deacon <[email protected]>
-Signed-off-by: Andrew Morton <[email protected]>
----
- include/linux/mmzone.h |  2 ++
- mm/vmscan.c            | 74 ++++++++++++++++++++++++++++++++++++++++--
- 2 files changed, 73 insertions(+), 3 deletions(-)
-
---- a/include/linux/mmzone.h
-+++ b/include/linux/mmzone.h
-@@ -399,6 +399,8 @@ struct lru_gen_struct {
-       unsigned long max_seq;
-       /* the eviction increments the oldest generation numbers */
-       unsigned long min_seq[ANON_AND_FILE];
-+      /* the birth time of each generation in jiffies */
-+      unsigned long timestamps[MAX_NR_GENS];
-       /* the multi-gen LRU lists, lazily sorted on eviction */
-       struct list_head lists[MAX_NR_GENS][ANON_AND_FILE][MAX_NR_ZONES];
-       /* the multi-gen LRU sizes, eventually consistent */
---- a/mm/vmscan.c
-+++ b/mm/vmscan.c
-@@ -4064,6 +4064,7 @@ static void inc_max_seq(struct lruvec *l
-       for (type = 0; type < ANON_AND_FILE; type++)
-               reset_ctrl_pos(lruvec, type, false);
-+      WRITE_ONCE(lrugen->timestamps[next], jiffies);
-       /* make sure preceding modifications appear */
-       smp_store_release(&lrugen->max_seq, lrugen->max_seq + 1);
-@@ -4193,7 +4194,7 @@ static bool should_run_aging(struct lruv
-       return false;
- }
--static void age_lruvec(struct lruvec *lruvec, struct scan_control *sc)
-+static bool age_lruvec(struct lruvec *lruvec, struct scan_control *sc, unsigned long min_ttl)
- {
-       bool need_aging;
-       unsigned long nr_to_scan;
-@@ -4207,16 +4208,36 @@ static void age_lruvec(struct lruvec *lr
-       mem_cgroup_calculate_protection(NULL, memcg);
-       if (mem_cgroup_below_min(memcg))
--              return;
-+              return false;
-       need_aging = should_run_aging(lruvec, max_seq, min_seq, sc, swappiness, &nr_to_scan);
-+
-+      if (min_ttl) {
-+              int gen = lru_gen_from_seq(min_seq[LRU_GEN_FILE]);
-+              unsigned long birth = READ_ONCE(lruvec->lrugen.timestamps[gen]);
-+
-+              if (time_is_after_jiffies(birth + min_ttl))
-+                      return false;
-+
-+              /* the size is likely too small to be helpful */
-+              if (!nr_to_scan && sc->priority != DEF_PRIORITY)
-+                      return false;
-+      }
-+
-       if (need_aging)
-               try_to_inc_max_seq(lruvec, max_seq, sc, swappiness);
-+
-+      return true;
- }
-+/* to protect the working set of the last N jiffies */
-+static unsigned long lru_gen_min_ttl __read_mostly;
-+
- static void lru_gen_age_node(struct pglist_data *pgdat, struct scan_control *sc)
- {
-       struct mem_cgroup *memcg;
-+      bool success = false;
-+      unsigned long min_ttl = READ_ONCE(lru_gen_min_ttl);
-       VM_WARN_ON_ONCE(!current_is_kswapd());
-@@ -4239,12 +4260,32 @@ static void lru_gen_age_node(struct pgli
-       do {
-               struct lruvec *lruvec = mem_cgroup_lruvec(memcg, pgdat);
--              age_lruvec(lruvec, sc);
-+              if (age_lruvec(lruvec, sc, min_ttl))
-+                      success = true;
-               cond_resched();
-       } while ((memcg = mem_cgroup_iter(NULL, memcg, NULL)));
-       clear_mm_walk();
-+
-+      /* check the order to exclude compaction-induced reclaim */
-+      if (success || !min_ttl || sc->order)
-+              return;
-+
-+      /*
-+       * The main goal is to OOM kill if every generation from all memcgs is
-+       * younger than min_ttl. However, another possibility is all memcgs are
-+       * either below min or empty.
-+       */
-+      if (mutex_trylock(&oom_lock)) {
-+              struct oom_control oc = {
-+                      .gfp_mask = sc->gfp_mask,
-+              };
-+
-+              out_of_memory(&oc);
-+
-+              mutex_unlock(&oom_lock);
-+      }
- }
- /*
-@@ -5002,6 +5043,28 @@ unlock:
-  *                          sysfs interface
-  ******************************************************************************/
-+static ssize_t show_min_ttl(struct kobject *kobj, struct kobj_attribute *attr, char *buf)
-+{
-+      return sprintf(buf, "%u\n", jiffies_to_msecs(READ_ONCE(lru_gen_min_ttl)));
-+}
-+
-+static ssize_t store_min_ttl(struct kobject *kobj, struct kobj_attribute *attr,
-+                           const char *buf, size_t len)
-+{
-+      unsigned int msecs;
-+
-+      if (kstrtouint(buf, 0, &msecs))
-+              return -EINVAL;
-+
-+      WRITE_ONCE(lru_gen_min_ttl, msecs_to_jiffies(msecs));
-+
-+      return len;
-+}
-+
-+static struct kobj_attribute lru_gen_min_ttl_attr = __ATTR(
-+      min_ttl_ms, 0644, show_min_ttl, store_min_ttl
-+);
-+
- static ssize_t show_enabled(struct kobject *kobj, struct kobj_attribute *attr, char *buf)
- {
-       unsigned int caps = 0;
-@@ -5050,6 +5113,7 @@ static struct kobj_attribute lru_gen_ena
- );
- static struct attribute *lru_gen_attrs[] = {
-+      &lru_gen_min_ttl_attr.attr,
-       &lru_gen_enabled_attr.attr,
-       NULL
- };
-@@ -5065,12 +5129,16 @@ static struct attribute_group lru_gen_at
- void lru_gen_init_lruvec(struct lruvec *lruvec)
- {
-+      int i;
-       int gen, type, zone;
-       struct lru_gen_struct *lrugen = &lruvec->lrugen;
-       lrugen->max_seq = MIN_NR_GENS + 1;
-       lrugen->enabled = lru_gen_enabled();
-+      for (i = 0; i <= MIN_NR_GENS + 1; i++)
-+              lrugen->timestamps[i] = jiffies;
-+
-       for_each_gen_type_zone(gen, type, zone)
-               INIT_LIST_HEAD(&lrugen->lists[gen][type][zone]);
diff --git a/target/linux/generic/backport-5.15/020-v6.1-12-mm-multi-gen-LRU-debugfs-interface.patch b/target/linux/generic/backport-5.15/020-v6.1-12-mm-multi-gen-LRU-debugfs-interface.patch
deleted file mode 100644 (file)
index 482e714..0000000
+++ /dev/null
@@ -1,579 +0,0 @@
-From 530716d008ca26315f246cd70dc1cefc636beaa4 Mon Sep 17 00:00:00 2001
-From: Yu Zhao <[email protected]>
-Date: Sun, 18 Sep 2022 02:00:09 -0600
-Subject: [PATCH 12/29] mm: multi-gen LRU: debugfs interface
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-Add /sys/kernel/debug/lru_gen for working set estimation and proactive
-reclaim.  These techniques are commonly used to optimize job scheduling
-(bin packing) in data centers [1][2].
-
-Compared with the page table-based approach and the PFN-based
-approach, this lruvec-based approach has the following advantages:
-1. It offers better choices because it is aware of memcgs, NUMA nodes,
-   shared mappings and unmapped page cache.
-2. It is more scalable because it is O(nr_hot_pages), whereas the
-   PFN-based approach is O(nr_total_pages).
-
-Add /sys/kernel/debug/lru_gen_full for debugging.
-
-[1] https://dl.acm.org/doi/10.1145/3297858.3304053
-[2] https://dl.acm.org/doi/10.1145/3503222.3507731
-
-Link: https://lkml.kernel.org/r/[email protected]
-Signed-off-by: Yu Zhao <[email protected]>
-Reviewed-by: Qi Zheng <[email protected]>
-Acked-by: Brian Geffon <[email protected]>
-Acked-by: Jan Alexander Steffens (heftig) <[email protected]>
-Acked-by: Oleksandr Natalenko <[email protected]>
-Acked-by: Steven Barrett <[email protected]>
-Acked-by: Suleiman Souhlal <[email protected]>
-Tested-by: Daniel Byrne <[email protected]>
-Tested-by: Donald Carr <[email protected]>
-Tested-by: Holger Hoffstätte <[email protected]>
-Tested-by: Konstantin Kharlamov <[email protected]>
-Tested-by: Shuang Zhai <[email protected]>
-Tested-by: Sofia Trinh <[email protected]>
-Tested-by: Vaibhav Jain <[email protected]>
-Cc: Andi Kleen <[email protected]>
-Cc: Aneesh Kumar K.V <[email protected]>
-Cc: Barry Song <[email protected]>
-Cc: Catalin Marinas <[email protected]>
-Cc: Dave Hansen <[email protected]>
-Cc: Hillf Danton <[email protected]>
-Cc: Jens Axboe <[email protected]>
-Cc: Johannes Weiner <[email protected]>
-Cc: Jonathan Corbet <[email protected]>
-Cc: Linus Torvalds <[email protected]>
-Cc: Matthew Wilcox <[email protected]>
-Cc: Mel Gorman <[email protected]>
-Cc: Miaohe Lin <[email protected]>
-Cc: Michael Larabel <[email protected]>
-Cc: Michal Hocko <[email protected]>
-Cc: Mike Rapoport <[email protected]>
-Cc: Mike Rapoport <[email protected]>
-Cc: Peter Zijlstra <[email protected]>
-Cc: Tejun Heo <[email protected]>
-Cc: Vlastimil Babka <[email protected]>
-Cc: Will Deacon <[email protected]>
-Signed-off-by: Andrew Morton <[email protected]>
----
- include/linux/nodemask.h |   1 +
- mm/vmscan.c              | 411 ++++++++++++++++++++++++++++++++++++++-
- 2 files changed, 402 insertions(+), 10 deletions(-)
-
---- a/include/linux/nodemask.h
-+++ b/include/linux/nodemask.h
-@@ -485,6 +485,7 @@ static inline int num_node_state(enum no
- #define first_online_node     0
- #define first_memory_node     0
- #define next_online_node(nid) (MAX_NUMNODES)
-+#define next_memory_node(nid) (MAX_NUMNODES)
- #define nr_node_ids           1U
- #define nr_online_nodes               1U
---- a/mm/vmscan.c
-+++ b/mm/vmscan.c
-@@ -53,6 +53,7 @@
- #include <linux/pagewalk.h>
- #include <linux/shmem_fs.h>
- #include <linux/ctype.h>
-+#include <linux/debugfs.h>
- #include <asm/tlbflush.h>
- #include <asm/div64.h>
-@@ -3968,12 +3969,40 @@ static void clear_mm_walk(void)
-               kfree(walk);
- }
--static void inc_min_seq(struct lruvec *lruvec, int type)
-+static bool inc_min_seq(struct lruvec *lruvec, int type, bool can_swap)
- {
-+      int zone;
-+      int remaining = MAX_LRU_BATCH;
-       struct lru_gen_struct *lrugen = &lruvec->lrugen;
-+      int new_gen, old_gen = lru_gen_from_seq(lrugen->min_seq[type]);
-+
-+      if (type == LRU_GEN_ANON && !can_swap)
-+              goto done;
-+
-+      /* prevent cold/hot inversion if force_scan is true */
-+      for (zone = 0; zone < MAX_NR_ZONES; zone++) {
-+              struct list_head *head = &lrugen->lists[old_gen][type][zone];
-+
-+              while (!list_empty(head)) {
-+                      struct page *page = lru_to_page(head);
-+
-+                      VM_WARN_ON_ONCE_PAGE(PageUnevictable(page), page);
-+                      VM_WARN_ON_ONCE_PAGE(PageActive(page), page);
-+                      VM_WARN_ON_ONCE_PAGE(page_is_file_lru(page) != type, page);
-+                      VM_WARN_ON_ONCE_PAGE(page_zonenum(page) != zone, page);
-+                      new_gen = page_inc_gen(lruvec, page, false);
-+                      list_move_tail(&page->lru, &lrugen->lists[new_gen][type][zone]);
-+
-+                      if (!--remaining)
-+                              return false;
-+              }
-+      }
-+done:
-       reset_ctrl_pos(lruvec, type, true);
-       WRITE_ONCE(lrugen->min_seq[type], lrugen->min_seq[type] + 1);
-+
-+      return true;
- }
- static bool try_to_inc_min_seq(struct lruvec *lruvec, bool can_swap)
-@@ -4019,7 +4048,7 @@ next:
-       return success;
- }
--static void inc_max_seq(struct lruvec *lruvec, bool can_swap)
-+static void inc_max_seq(struct lruvec *lruvec, bool can_swap, bool force_scan)
- {
-       int prev, next;
-       int type, zone;
-@@ -4033,9 +4062,13 @@ static void inc_max_seq(struct lruvec *l
-               if (get_nr_gens(lruvec, type) != MAX_NR_GENS)
-                       continue;
--              VM_WARN_ON_ONCE(type == LRU_GEN_FILE || can_swap);
-+              VM_WARN_ON_ONCE(!force_scan && (type == LRU_GEN_FILE || can_swap));
--              inc_min_seq(lruvec, type);
-+              while (!inc_min_seq(lruvec, type, can_swap)) {
-+                      spin_unlock_irq(&lruvec->lru_lock);
-+                      cond_resched();
-+                      spin_lock_irq(&lruvec->lru_lock);
-+              }
-       }
-       /*
-@@ -4072,7 +4105,7 @@ static void inc_max_seq(struct lruvec *l
- }
- static bool try_to_inc_max_seq(struct lruvec *lruvec, unsigned long max_seq,
--                             struct scan_control *sc, bool can_swap)
-+                             struct scan_control *sc, bool can_swap, bool force_scan)
- {
-       bool success;
-       struct lru_gen_mm_walk *walk;
-@@ -4093,7 +4126,7 @@ static bool try_to_inc_max_seq(struct lr
-        * handful of PTEs. Spreading the work out over a period of time usually
-        * is less efficient, but it avoids bursty page faults.
-        */
--      if (!(arch_has_hw_pte_young() && get_cap(LRU_GEN_MM_WALK))) {
-+      if (!force_scan && !(arch_has_hw_pte_young() && get_cap(LRU_GEN_MM_WALK))) {
-               success = iterate_mm_list_nowalk(lruvec, max_seq);
-               goto done;
-       }
-@@ -4107,7 +4140,7 @@ static bool try_to_inc_max_seq(struct lr
-       walk->lruvec = lruvec;
-       walk->max_seq = max_seq;
-       walk->can_swap = can_swap;
--      walk->force_scan = false;
-+      walk->force_scan = force_scan;
-       do {
-               success = iterate_mm_list(lruvec, walk, &mm);
-@@ -4127,7 +4160,7 @@ done:
-       VM_WARN_ON_ONCE(max_seq != READ_ONCE(lrugen->max_seq));
--      inc_max_seq(lruvec, can_swap);
-+      inc_max_seq(lruvec, can_swap, force_scan);
-       /* either this sees any waiters or they will see updated max_seq */
-       if (wq_has_sleeper(&lruvec->mm_state.wait))
-               wake_up_all(&lruvec->mm_state.wait);
-@@ -4225,7 +4258,7 @@ static bool age_lruvec(struct lruvec *lr
-       }
-       if (need_aging)
--              try_to_inc_max_seq(lruvec, max_seq, sc, swappiness);
-+              try_to_inc_max_seq(lruvec, max_seq, sc, swappiness, false);
-       return true;
- }
-@@ -4784,7 +4817,7 @@ static unsigned long get_nr_to_scan(stru
-       if (current_is_kswapd())
-               return 0;
--      if (try_to_inc_max_seq(lruvec, max_seq, sc, can_swap))
-+      if (try_to_inc_max_seq(lruvec, max_seq, sc, can_swap, false))
-               return nr_to_scan;
- done:
-       return min_seq[!can_swap] + MIN_NR_GENS <= max_seq ? nr_to_scan : 0;
-@@ -5124,6 +5157,361 @@ static struct attribute_group lru_gen_at
- };
- /******************************************************************************
-+ *                          debugfs interface
-+ ******************************************************************************/
-+
-+static void *lru_gen_seq_start(struct seq_file *m, loff_t *pos)
-+{
-+      struct mem_cgroup *memcg;
-+      loff_t nr_to_skip = *pos;
-+
-+      m->private = kvmalloc(PATH_MAX, GFP_KERNEL);
-+      if (!m->private)
-+              return ERR_PTR(-ENOMEM);
-+
-+      memcg = mem_cgroup_iter(NULL, NULL, NULL);
-+      do {
-+              int nid;
-+
-+              for_each_node_state(nid, N_MEMORY) {
-+                      if (!nr_to_skip--)
-+                              return get_lruvec(memcg, nid);
-+              }
-+      } while ((memcg = mem_cgroup_iter(NULL, memcg, NULL)));
-+
-+      return NULL;
-+}
-+
-+static void lru_gen_seq_stop(struct seq_file *m, void *v)
-+{
-+      if (!IS_ERR_OR_NULL(v))
-+              mem_cgroup_iter_break(NULL, lruvec_memcg(v));
-+
-+      kvfree(m->private);
-+      m->private = NULL;
-+}
-+
-+static void *lru_gen_seq_next(struct seq_file *m, void *v, loff_t *pos)
-+{
-+      int nid = lruvec_pgdat(v)->node_id;
-+      struct mem_cgroup *memcg = lruvec_memcg(v);
-+
-+      ++*pos;
-+
-+      nid = next_memory_node(nid);
-+      if (nid == MAX_NUMNODES) {
-+              memcg = mem_cgroup_iter(NULL, memcg, NULL);
-+              if (!memcg)
-+                      return NULL;
-+
-+              nid = first_memory_node;
-+      }
-+
-+      return get_lruvec(memcg, nid);
-+}
-+
-+static void lru_gen_seq_show_full(struct seq_file *m, struct lruvec *lruvec,
-+                                unsigned long max_seq, unsigned long *min_seq,
-+                                unsigned long seq)
-+{
-+      int i;
-+      int type, tier;
-+      int hist = lru_hist_from_seq(seq);
-+      struct lru_gen_struct *lrugen = &lruvec->lrugen;
-+
-+      for (tier = 0; tier < MAX_NR_TIERS; tier++) {
-+              seq_printf(m, "            %10d", tier);
-+              for (type = 0; type < ANON_AND_FILE; type++) {
-+                      const char *s = "   ";
-+                      unsigned long n[3] = {};
-+
-+                      if (seq == max_seq) {
-+                              s = "RT ";
-+                              n[0] = READ_ONCE(lrugen->avg_refaulted[type][tier]);
-+                              n[1] = READ_ONCE(lrugen->avg_total[type][tier]);
-+                      } else if (seq == min_seq[type] || NR_HIST_GENS > 1) {
-+                              s = "rep";
-+                              n[0] = atomic_long_read(&lrugen->refaulted[hist][type][tier]);
-+                              n[1] = atomic_long_read(&lrugen->evicted[hist][type][tier]);
-+                              if (tier)
-+                                      n[2] = READ_ONCE(lrugen->protected[hist][type][tier - 1]);
-+                      }
-+
-+                      for (i = 0; i < 3; i++)
-+                              seq_printf(m, " %10lu%c", n[i], s[i]);
-+              }
-+              seq_putc(m, '\n');
-+      }
-+
-+      seq_puts(m, "                      ");
-+      for (i = 0; i < NR_MM_STATS; i++) {
-+              const char *s = "      ";
-+              unsigned long n = 0;
-+
-+              if (seq == max_seq && NR_HIST_GENS == 1) {
-+                      s = "LOYNFA";
-+                      n = READ_ONCE(lruvec->mm_state.stats[hist][i]);
-+              } else if (seq != max_seq && NR_HIST_GENS > 1) {
-+                      s = "loynfa";
-+                      n = READ_ONCE(lruvec->mm_state.stats[hist][i]);
-+              }
-+
-+              seq_printf(m, " %10lu%c", n, s[i]);
-+      }
-+      seq_putc(m, '\n');
-+}
-+
-+static int lru_gen_seq_show(struct seq_file *m, void *v)
-+{
-+      unsigned long seq;
-+      bool full = !debugfs_real_fops(m->file)->write;
-+      struct lruvec *lruvec = v;
-+      struct lru_gen_struct *lrugen = &lruvec->lrugen;
-+      int nid = lruvec_pgdat(lruvec)->node_id;
-+      struct mem_cgroup *memcg = lruvec_memcg(lruvec);
-+      DEFINE_MAX_SEQ(lruvec);
-+      DEFINE_MIN_SEQ(lruvec);
-+
-+      if (nid == first_memory_node) {
-+              const char *path = memcg ? m->private : "";
-+
-+#ifdef CONFIG_MEMCG
-+              if (memcg)
-+                      cgroup_path(memcg->css.cgroup, m->private, PATH_MAX);
-+#endif
-+              seq_printf(m, "memcg %5hu %s\n", mem_cgroup_id(memcg), path);
-+      }
-+
-+      seq_printf(m, " node %5d\n", nid);
-+
-+      if (!full)
-+              seq = min_seq[LRU_GEN_ANON];
-+      else if (max_seq >= MAX_NR_GENS)
-+              seq = max_seq - MAX_NR_GENS + 1;
-+      else
-+              seq = 0;
-+
-+      for (; seq <= max_seq; seq++) {
-+              int type, zone;
-+              int gen = lru_gen_from_seq(seq);
-+              unsigned long birth = READ_ONCE(lruvec->lrugen.timestamps[gen]);
-+
-+              seq_printf(m, " %10lu %10u", seq, jiffies_to_msecs(jiffies - birth));
-+
-+              for (type = 0; type < ANON_AND_FILE; type++) {
-+                      unsigned long size = 0;
-+                      char mark = full && seq < min_seq[type] ? 'x' : ' ';
-+
-+                      for (zone = 0; zone < MAX_NR_ZONES; zone++)
-+                              size += max(READ_ONCE(lrugen->nr_pages[gen][type][zone]), 0L);
-+
-+                      seq_printf(m, " %10lu%c", size, mark);
-+              }
-+
-+              seq_putc(m, '\n');
-+
-+              if (full)
-+                      lru_gen_seq_show_full(m, lruvec, max_seq, min_seq, seq);
-+      }
-+
-+      return 0;
-+}
-+
-+static const struct seq_operations lru_gen_seq_ops = {
-+      .start = lru_gen_seq_start,
-+      .stop = lru_gen_seq_stop,
-+      .next = lru_gen_seq_next,
-+      .show = lru_gen_seq_show,
-+};
-+
-+static int run_aging(struct lruvec *lruvec, unsigned long seq, struct scan_control *sc,
-+                   bool can_swap, bool force_scan)
-+{
-+      DEFINE_MAX_SEQ(lruvec);
-+      DEFINE_MIN_SEQ(lruvec);
-+
-+      if (seq < max_seq)
-+              return 0;
-+
-+      if (seq > max_seq)
-+              return -EINVAL;
-+
-+      if (!force_scan && min_seq[!can_swap] + MAX_NR_GENS - 1 <= max_seq)
-+              return -ERANGE;
-+
-+      try_to_inc_max_seq(lruvec, max_seq, sc, can_swap, force_scan);
-+
-+      return 0;
-+}
-+
-+static int run_eviction(struct lruvec *lruvec, unsigned long seq, struct scan_control *sc,
-+                      int swappiness, unsigned long nr_to_reclaim)
-+{
-+      DEFINE_MAX_SEQ(lruvec);
-+
-+      if (seq + MIN_NR_GENS > max_seq)
-+              return -EINVAL;
-+
-+      sc->nr_reclaimed = 0;
-+
-+      while (!signal_pending(current)) {
-+              DEFINE_MIN_SEQ(lruvec);
-+
-+              if (seq < min_seq[!swappiness])
-+                      return 0;
-+
-+              if (sc->nr_reclaimed >= nr_to_reclaim)
-+                      return 0;
-+
-+              if (!evict_pages(lruvec, sc, swappiness, NULL))
-+                      return 0;
-+
-+              cond_resched();
-+      }
-+
-+      return -EINTR;
-+}
-+
-+static int run_cmd(char cmd, int memcg_id, int nid, unsigned long seq,
-+                 struct scan_control *sc, int swappiness, unsigned long opt)
-+{
-+      struct lruvec *lruvec;
-+      int err = -EINVAL;
-+      struct mem_cgroup *memcg = NULL;
-+
-+      if (nid < 0 || nid >= MAX_NUMNODES || !node_state(nid, N_MEMORY))
-+              return -EINVAL;
-+
-+      if (!mem_cgroup_disabled()) {
-+              rcu_read_lock();
-+              memcg = mem_cgroup_from_id(memcg_id);
-+#ifdef CONFIG_MEMCG
-+              if (memcg && !css_tryget(&memcg->css))
-+                      memcg = NULL;
-+#endif
-+              rcu_read_unlock();
-+
-+              if (!memcg)
-+                      return -EINVAL;
-+      }
-+
-+      if (memcg_id != mem_cgroup_id(memcg))
-+              goto done;
-+
-+      lruvec = get_lruvec(memcg, nid);
-+
-+      if (swappiness < 0)
-+              swappiness = get_swappiness(lruvec, sc);
-+      else if (swappiness > 200)
-+              goto done;
-+
-+      switch (cmd) {
-+      case '+':
-+              err = run_aging(lruvec, seq, sc, swappiness, opt);
-+              break;
-+      case '-':
-+              err = run_eviction(lruvec, seq, sc, swappiness, opt);
-+              break;
-+      }
-+done:
-+      mem_cgroup_put(memcg);
-+
-+      return err;
-+}
-+
-+static ssize_t lru_gen_seq_write(struct file *file, const char __user *src,
-+                               size_t len, loff_t *pos)
-+{
-+      void *buf;
-+      char *cur, *next;
-+      unsigned int flags;
-+      struct blk_plug plug;
-+      int err = -EINVAL;
-+      struct scan_control sc = {
-+              .may_writepage = true,
-+              .may_unmap = true,
-+              .may_swap = true,
-+              .reclaim_idx = MAX_NR_ZONES - 1,
-+              .gfp_mask = GFP_KERNEL,
-+      };
-+
-+      buf = kvmalloc(len + 1, GFP_KERNEL);
-+      if (!buf)
-+              return -ENOMEM;
-+
-+      if (copy_from_user(buf, src, len)) {
-+              kvfree(buf);
-+              return -EFAULT;
-+      }
-+
-+      set_task_reclaim_state(current, &sc.reclaim_state);
-+      flags = memalloc_noreclaim_save();
-+      blk_start_plug(&plug);
-+      if (!set_mm_walk(NULL)) {
-+              err = -ENOMEM;
-+              goto done;
-+      }
-+
-+      next = buf;
-+      next[len] = '\0';
-+
-+      while ((cur = strsep(&next, ",;\n"))) {
-+              int n;
-+              int end;
-+              char cmd;
-+              unsigned int memcg_id;
-+              unsigned int nid;
-+              unsigned long seq;
-+              unsigned int swappiness = -1;
-+              unsigned long opt = -1;
-+
-+              cur = skip_spaces(cur);
-+              if (!*cur)
-+                      continue;
-+
-+              n = sscanf(cur, "%c %u %u %lu %n %u %n %lu %n", &cmd, &memcg_id, &nid,
-+                         &seq, &end, &swappiness, &end, &opt, &end);
-+              if (n < 4 || cur[end]) {
-+                      err = -EINVAL;
-+                      break;
-+              }
-+
-+              err = run_cmd(cmd, memcg_id, nid, seq, &sc, swappiness, opt);
-+              if (err)
-+                      break;
-+      }
-+done:
-+      clear_mm_walk();
-+      blk_finish_plug(&plug);
-+      memalloc_noreclaim_restore(flags);
-+      set_task_reclaim_state(current, NULL);
-+
-+      kvfree(buf);
-+
-+      return err ? : len;
-+}
-+
-+static int lru_gen_seq_open(struct inode *inode, struct file *file)
-+{
-+      return seq_open(file, &lru_gen_seq_ops);
-+}
-+
-+static const struct file_operations lru_gen_rw_fops = {
-+      .open = lru_gen_seq_open,
-+      .read = seq_read,
-+      .write = lru_gen_seq_write,
-+      .llseek = seq_lseek,
-+      .release = seq_release,
-+};
-+
-+static const struct file_operations lru_gen_ro_fops = {
-+      .open = lru_gen_seq_open,
-+      .read = seq_read,
-+      .llseek = seq_lseek,
-+      .release = seq_release,
-+};
-+
-+/******************************************************************************
-  *                          initialization
-  ******************************************************************************/
-@@ -5180,6 +5568,9 @@ static int __init init_lru_gen(void)
-       if (sysfs_create_group(mm_kobj, &lru_gen_attr_group))
-               pr_err("lru_gen: failed to create sysfs group\n");
-+      debugfs_create_file("lru_gen", 0644, NULL, NULL, &lru_gen_rw_fops);
-+      debugfs_create_file("lru_gen_full", 0444, NULL, NULL, &lru_gen_ro_fops);
-+
-       return 0;
- };
- late_initcall(init_lru_gen);
diff --git a/target/linux/generic/backport-5.15/020-v6.1-13-mm-mglru-don-t-sync-disk-for-each-aging-cycle.patch b/target/linux/generic/backport-5.15/020-v6.1-13-mm-mglru-don-t-sync-disk-for-each-aging-cycle.patch
deleted file mode 100644 (file)
index fd4aa72..0000000
+++ /dev/null
@@ -1,32 +0,0 @@
-From 92d430e8955c976eacb7cc91d7ff849c0dd009af Mon Sep 17 00:00:00 2001
-From: Yu Zhao <[email protected]>
-Date: Wed, 28 Sep 2022 13:36:58 -0600
-Subject: [PATCH 13/29] mm/mglru: don't sync disk for each aging cycle
-
-wakeup_flusher_threads() was added under the assumption that if a system
-runs out of clean cold pages, it might want to write back dirty pages more
-aggressively so that they can become clean and be dropped.
-
-However, doing so can breach the rate limit a system wants to impose on
-writeback, resulting in early SSD wearout.
-
-Link: https://lkml.kernel.org/r/[email protected]
-Fixes: bd74fdaea146 ("mm: multi-gen LRU: support page table walks")
-Signed-off-by: Yu Zhao <[email protected]>
-Reported-by: Axel Rasmussen <[email protected]>
-Signed-off-by: Andrew Morton <[email protected]>
----
- mm/vmscan.c | 2 --
- 1 file changed, 2 deletions(-)
-
---- a/mm/vmscan.c
-+++ b/mm/vmscan.c
-@@ -4165,8 +4165,6 @@ done:
-       if (wq_has_sleeper(&lruvec->mm_state.wait))
-               wake_up_all(&lruvec->mm_state.wait);
--      wakeup_flusher_threads(WB_REASON_VMSCAN);
--
-       return true;
- }
diff --git a/target/linux/generic/backport-5.15/020-v6.1-14-mm-multi-gen-LRU-retry-pages-written-back-while-isol.patch b/target/linux/generic/backport-5.15/020-v6.1-14-mm-multi-gen-LRU-retry-pages-written-back-while-isol.patch
deleted file mode 100644 (file)
index 31b35cb..0000000
+++ /dev/null
@@ -1,124 +0,0 @@
-From 6f315879ad750391a0b1fab8c9170bc054a5f5d7 Mon Sep 17 00:00:00 2001
-From: Yu Zhao <[email protected]>
-Date: Tue, 15 Nov 2022 18:38:07 -0700
-Subject: [PATCH 14/29] mm: multi-gen LRU: retry pages written back while
- isolated
-
-The page reclaim isolates a batch of pages from the tail of one of the
-LRU lists and works on those pages one by one.  For a suitable
-swap-backed page, if the swap device is async, it queues that page for
-writeback.  After the page reclaim finishes an entire batch, it puts back
-the pages it queued for writeback to the head of the original LRU list.
-
-In the meantime, the page writeback flushes the queued pages also by
-batches.  Its batching logic is independent from that of the page reclaim.
-For each of the pages it writes back, the page writeback calls
-rotate_reclaimable_page() which tries to rotate a page to the tail.
-
-rotate_reclaimable_page() only works for a page after the page reclaim
-has put it back.  If an async swap device is fast enough, the page
-writeback can finish with that page while the page reclaim is still
-working on the rest of the batch containing it.  In this case, that page
-will remain at the head and the page reclaim will not retry it before
-reaching there.
-
-This patch adds a retry to evict_pages().  After evict_pages() has
-finished an entire batch and before it puts back pages it cannot free
-immediately, it retries those that may have missed the rotation.
-
-Before this patch, ~60% of pages swapped to an Intel Optane missed
-rotate_reclaimable_page().  After this patch, ~99% of missed pages were
-reclaimed upon retry.
-
-This problem affects relatively slow async swap devices like Samsung 980
-Pro much less and does not affect sync swap devices like zram or zswap at
-all.
-
-Link: https://lkml.kernel.org/r/[email protected]
-Fixes: ac35a4902374 ("mm: multi-gen LRU: minimal implementation")
-Signed-off-by: Yu Zhao <[email protected]>
-Cc: "Yin, Fengwei" <[email protected]>
-Signed-off-by: Andrew Morton <[email protected]>
----
- mm/vmscan.c | 48 +++++++++++++++++++++++++++++++++++++-----------
- 1 file changed, 37 insertions(+), 11 deletions(-)
-
---- a/mm/vmscan.c
-+++ b/mm/vmscan.c
-@@ -4723,10 +4723,13 @@ static int evict_pages(struct lruvec *lr
-       int scanned;
-       int reclaimed;
-       LIST_HEAD(list);
-+      LIST_HEAD(clean);
-       struct page *page;
-+      struct page *next;
-       enum vm_event_item item;
-       struct reclaim_stat stat;
-       struct lru_gen_mm_walk *walk;
-+      bool skip_retry = false;
-       struct mem_cgroup *memcg = lruvec_memcg(lruvec);
-       struct pglist_data *pgdat = lruvec_pgdat(lruvec);
-@@ -4743,20 +4746,37 @@ static int evict_pages(struct lruvec *lr
-       if (list_empty(&list))
-               return scanned;
--
-+retry:
-       reclaimed = shrink_page_list(&list, pgdat, sc, &stat, false);
-+      sc->nr_reclaimed += reclaimed;
--      list_for_each_entry(page, &list, lru) {
--              /* restore LRU_REFS_FLAGS cleared by isolate_page() */
--              if (PageWorkingset(page))
--                      SetPageReferenced(page);
-+      list_for_each_entry_safe_reverse(page, next, &list, lru) {
-+              if (!page_evictable(page)) {
-+                      list_del(&page->lru);
-+                      putback_lru_page(page);
-+                      continue;
-+              }
--              /* don't add rejected pages to the oldest generation */
-               if (PageReclaim(page) &&
--                  (PageDirty(page) || PageWriteback(page)))
--                      ClearPageActive(page);
--              else
--                      SetPageActive(page);
-+                  (PageDirty(page) || PageWriteback(page))) {
-+                      /* restore LRU_REFS_FLAGS cleared by isolate_page() */
-+                      if (PageWorkingset(page))
-+                              SetPageReferenced(page);
-+                      continue;
-+              }
-+
-+              if (skip_retry || PageActive(page) || PageReferenced(page) ||
-+                  page_mapped(page) || PageLocked(page) ||
-+                  PageDirty(page) || PageWriteback(page)) {
-+                      /* don't add rejected pages to the oldest generation */
-+                      set_mask_bits(&page->flags, LRU_REFS_MASK | LRU_REFS_FLAGS,
-+                                    BIT(PG_active));
-+                      continue;
-+              }
-+
-+              /* retry pages that may have missed rotate_reclaimable_page() */
-+              list_move(&page->lru, &clean);
-+              sc->nr_scanned -= thp_nr_pages(page);
-       }
-       spin_lock_irq(&lruvec->lru_lock);
-@@ -4778,7 +4798,13 @@ static int evict_pages(struct lruvec *lr
-       mem_cgroup_uncharge_list(&list);
-       free_unref_page_list(&list);
--      sc->nr_reclaimed += reclaimed;
-+      INIT_LIST_HEAD(&list);
-+      list_splice_init(&clean, &list);
-+
-+      if (!list_empty(&list)) {
-+              skip_retry = true;
-+              goto retry;
-+      }
-       if (need_swapping && type == LRU_GEN_ANON)
-               *need_swapping = true;
diff --git a/target/linux/generic/backport-5.15/020-v6.1-15-mm-multi-gen-LRU-move-lru_gen_add_mm-out-of-IRQ-off-.patch b/target/linux/generic/backport-5.15/020-v6.1-15-mm-multi-gen-LRU-move-lru_gen_add_mm-out-of-IRQ-off-.patch
deleted file mode 100644 (file)
index b1319d9..0000000
+++ /dev/null
@@ -1,49 +0,0 @@
-From 255bb0ac393f1c2818cd75af45a9226300ab3daf Mon Sep 17 00:00:00 2001
-From: Sebastian Andrzej Siewior <[email protected]>
-Date: Wed, 26 Oct 2022 15:48:30 +0200
-Subject: [PATCH 15/29] mm: multi-gen LRU: move lru_gen_add_mm() out of IRQ-off
- region
-
-lru_gen_add_mm() has been added within an IRQ-off region in the commit
-mentioned below.  The other invocations of lru_gen_add_mm() are not within
-an IRQ-off region.
-
-The invocation within IRQ-off region is problematic on PREEMPT_RT because
-the function is using a spin_lock_t which must not be used within
-IRQ-disabled regions.
-
-The other invocations of lru_gen_add_mm() occur while
-task_struct::alloc_lock is acquired.  Move lru_gen_add_mm() after
-interrupts are enabled and before task_unlock().
-
-Link: https://lkml.kernel.org/r/[email protected]
-Fixes: bd74fdaea1460 ("mm: multi-gen LRU: support page table walks")
-Signed-off-by: Sebastian Andrzej Siewior <[email protected]>
-Acked-by: Yu Zhao <[email protected]>
-Cc: Al Viro <[email protected]>
-Cc: "Eric W . Biederman" <[email protected]>
-Cc: Kees Cook <[email protected]>
-Cc: Thomas Gleixner <[email protected]>
-Signed-off-by: Andrew Morton <[email protected]>
----
- fs/exec.c | 2 +-
- 1 file changed, 1 insertion(+), 1 deletion(-)
-
---- a/fs/exec.c
-+++ b/fs/exec.c
-@@ -1014,7 +1014,6 @@ static int exec_mmap(struct mm_struct *m
-       active_mm = tsk->active_mm;
-       tsk->active_mm = mm;
-       tsk->mm = mm;
--      lru_gen_add_mm(mm);
-       /*
-        * This prevents preemption while active_mm is being loaded and
-        * it and mm are being updated, which could cause problems for
-@@ -1029,6 +1028,7 @@ static int exec_mmap(struct mm_struct *m
-               local_irq_enable();
-       tsk->mm->vmacache_seqnum = 0;
-       vmacache_flush(tsk);
-+      lru_gen_add_mm(mm);
-       task_unlock(tsk);
-       lru_gen_use_mm(mm);
-       if (old_mm) {
diff --git a/target/linux/generic/backport-5.15/020-v6.1-17-mm-add-dummy-pmd_young-for-architectures-not-having-.patch b/target/linux/generic/backport-5.15/020-v6.1-17-mm-add-dummy-pmd_young-for-architectures-not-having-.patch
deleted file mode 100644 (file)
index 1c10c16..0000000
+++ /dev/null
@@ -1,96 +0,0 @@
-From c5ec455ebd2b488d91de9d8915a0c8036a2a04dd Mon Sep 17 00:00:00 2001
-From: Juergen Gross <[email protected]>
-Date: Wed, 30 Nov 2022 14:49:41 -0800
-Subject: [PATCH 17/29] mm: add dummy pmd_young() for architectures not having
- it
-
-In order to avoid #ifdeffery add a dummy pmd_young() implementation as a
-fallback.  This is required for the later patch "mm: introduce
-arch_has_hw_nonleaf_pmd_young()".
-
-Link: https://lkml.kernel.org/r/[email protected]
-Signed-off-by: Juergen Gross <[email protected]>
-Acked-by: Yu Zhao <[email protected]>
-Cc: Borislav Petkov <[email protected]>
-Cc: Dave Hansen <[email protected]>
-Cc: Geert Uytterhoeven <[email protected]>
-Cc: "H. Peter Anvin" <[email protected]>
-Cc: Ingo Molnar <[email protected]>
-Cc: Sander Eikelenboom <[email protected]>
-Cc: Thomas Gleixner <[email protected]>
-Signed-off-by: Andrew Morton <[email protected]>
----
- arch/mips/include/asm/pgtable.h     | 1 +
- arch/riscv/include/asm/pgtable.h    | 1 +
- arch/s390/include/asm/pgtable.h     | 1 +
- arch/sparc/include/asm/pgtable_64.h | 1 +
- arch/x86/include/asm/pgtable.h      | 1 +
- include/linux/pgtable.h             | 7 +++++++
- 6 files changed, 12 insertions(+)
-
---- a/arch/mips/include/asm/pgtable.h
-+++ b/arch/mips/include/asm/pgtable.h
-@@ -632,6 +632,7 @@ static inline pmd_t pmd_mkdirty(pmd_t pm
-       return pmd;
- }
-+#define pmd_young pmd_young
- static inline int pmd_young(pmd_t pmd)
- {
-       return !!(pmd_val(pmd) & _PAGE_ACCESSED);
---- a/arch/riscv/include/asm/pgtable.h
-+++ b/arch/riscv/include/asm/pgtable.h
-@@ -535,6 +535,7 @@ static inline int pmd_dirty(pmd_t pmd)
-       return pte_dirty(pmd_pte(pmd));
- }
-+#define pmd_young pmd_young
- static inline int pmd_young(pmd_t pmd)
- {
-       return pte_young(pmd_pte(pmd));
---- a/arch/s390/include/asm/pgtable.h
-+++ b/arch/s390/include/asm/pgtable.h
-@@ -748,6 +748,7 @@ static inline int pmd_dirty(pmd_t pmd)
-       return (pmd_val(pmd) & _SEGMENT_ENTRY_DIRTY) != 0;
- }
-+#define pmd_young pmd_young
- static inline int pmd_young(pmd_t pmd)
- {
-       return (pmd_val(pmd) & _SEGMENT_ENTRY_YOUNG) != 0;
---- a/arch/sparc/include/asm/pgtable_64.h
-+++ b/arch/sparc/include/asm/pgtable_64.h
-@@ -712,6 +712,7 @@ static inline unsigned long pmd_dirty(pm
-       return pte_dirty(pte);
- }
-+#define pmd_young pmd_young
- static inline unsigned long pmd_young(pmd_t pmd)
- {
-       pte_t pte = __pte(pmd_val(pmd));
---- a/arch/x86/include/asm/pgtable.h
-+++ b/arch/x86/include/asm/pgtable.h
-@@ -136,6 +136,7 @@ static inline int pmd_dirty(pmd_t pmd)
-       return pmd_flags(pmd) & _PAGE_DIRTY;
- }
-+#define pmd_young pmd_young
- static inline int pmd_young(pmd_t pmd)
- {
-       return pmd_flags(pmd) & _PAGE_ACCESSED;
---- a/include/linux/pgtable.h
-+++ b/include/linux/pgtable.h
-@@ -164,6 +164,13 @@ static inline pte_t *virt_to_kpte(unsign
-       return pmd_none(*pmd) ? NULL : pte_offset_kernel(pmd, vaddr);
- }
-+#ifndef pmd_young
-+static inline int pmd_young(pmd_t pmd)
-+{
-+      return 0;
-+}
-+#endif
-+
- #ifndef __HAVE_ARCH_PTEP_SET_ACCESS_FLAGS
- extern int ptep_set_access_flags(struct vm_area_struct *vma,
-                                unsigned long address, pte_t *ptep,
diff --git a/target/linux/generic/backport-5.15/020-v6.1-18-mm-introduce-arch_has_hw_nonleaf_pmd_young.patch b/target/linux/generic/backport-5.15/020-v6.1-18-mm-introduce-arch_has_hw_nonleaf_pmd_young.patch
deleted file mode 100644 (file)
index 9a1f9be..0000000
+++ /dev/null
@@ -1,113 +0,0 @@
-From 46cbda7b65998a5af4493f745d94417af697bd68 Mon Sep 17 00:00:00 2001
-From: Juergen Gross <[email protected]>
-Date: Wed, 23 Nov 2022 07:45:10 +0100
-Subject: [PATCH 18/29] mm: introduce arch_has_hw_nonleaf_pmd_young()
-
-When running as a Xen PV guests commit eed9a328aa1a ("mm: x86: add
-CONFIG_ARCH_HAS_NONLEAF_PMD_YOUNG") can cause a protection violation in
-pmdp_test_and_clear_young():
-
- BUG: unable to handle page fault for address: ffff8880083374d0
- #PF: supervisor write access in kernel mode
- #PF: error_code(0x0003) - permissions violation
- PGD 3026067 P4D 3026067 PUD 3027067 PMD 7fee5067 PTE 8010000008337065
- Oops: 0003 [#1] PREEMPT SMP NOPTI
- CPU: 7 PID: 158 Comm: kswapd0 Not tainted 6.1.0-rc5-20221118-doflr+ #1
- RIP: e030:pmdp_test_and_clear_young+0x25/0x40
-
-This happens because the Xen hypervisor can't emulate direct writes to
-page table entries other than PTEs.
-
-This can easily be fixed by introducing arch_has_hw_nonleaf_pmd_young()
-similar to arch_has_hw_pte_young() and test that instead of
-CONFIG_ARCH_HAS_NONLEAF_PMD_YOUNG.
-
-Link: https://lkml.kernel.org/r/[email protected]
-Fixes: eed9a328aa1a ("mm: x86: add CONFIG_ARCH_HAS_NONLEAF_PMD_YOUNG")
-Signed-off-by: Juergen Gross <[email protected]>
-Reported-by: Sander Eikelenboom <[email protected]>
-Acked-by: Yu Zhao <[email protected]>
-Tested-by: Sander Eikelenboom <[email protected]>
-Acked-by: David Hildenbrand <[email protected]> [core changes]
-Signed-off-by: Andrew Morton <[email protected]>
----
- arch/x86/include/asm/pgtable.h |  8 ++++++++
- include/linux/pgtable.h        | 11 +++++++++++
- mm/vmscan.c                    | 10 +++++-----
- 3 files changed, 24 insertions(+), 5 deletions(-)
-
---- a/arch/x86/include/asm/pgtable.h
-+++ b/arch/x86/include/asm/pgtable.h
-@@ -1405,6 +1405,14 @@ static inline bool arch_has_hw_pte_young
-       return true;
- }
-+#ifdef CONFIG_XEN_PV
-+#define arch_has_hw_nonleaf_pmd_young arch_has_hw_nonleaf_pmd_young
-+static inline bool arch_has_hw_nonleaf_pmd_young(void)
-+{
-+      return !cpu_feature_enabled(X86_FEATURE_XENPV);
-+}
-+#endif
-+
- #endif        /* __ASSEMBLY__ */
- #endif /* _ASM_X86_PGTABLE_H */
---- a/include/linux/pgtable.h
-+++ b/include/linux/pgtable.h
-@@ -266,6 +266,17 @@ static inline int pmdp_clear_flush_young
- #endif /* CONFIG_TRANSPARENT_HUGEPAGE */
- #endif
-+#ifndef arch_has_hw_nonleaf_pmd_young
-+/*
-+ * Return whether the accessed bit in non-leaf PMD entries is supported on the
-+ * local CPU.
-+ */
-+static inline bool arch_has_hw_nonleaf_pmd_young(void)
-+{
-+      return IS_ENABLED(CONFIG_ARCH_HAS_NONLEAF_PMD_YOUNG);
-+}
-+#endif
-+
- #ifndef arch_has_hw_pte_young
- /*
-  * Return whether the accessed bit is supported on the local CPU.
---- a/mm/vmscan.c
-+++ b/mm/vmscan.c
-@@ -3727,7 +3727,7 @@ static void walk_pmd_range_locked(pud_t
-                       goto next;
-               if (!pmd_trans_huge(pmd[i])) {
--                      if (IS_ENABLED(CONFIG_ARCH_HAS_NONLEAF_PMD_YOUNG) &&
-+                      if (arch_has_hw_nonleaf_pmd_young() &&
-                           get_cap(LRU_GEN_NONLEAF_YOUNG))
-                               pmdp_test_and_clear_young(vma, addr, pmd + i);
-                       goto next;
-@@ -3825,14 +3825,14 @@ restart:
- #endif
-               walk->mm_stats[MM_NONLEAF_TOTAL]++;
--#ifdef CONFIG_ARCH_HAS_NONLEAF_PMD_YOUNG
--              if (get_cap(LRU_GEN_NONLEAF_YOUNG)) {
-+              if (arch_has_hw_nonleaf_pmd_young() &&
-+                  get_cap(LRU_GEN_NONLEAF_YOUNG)) {
-                       if (!pmd_young(val))
-                               continue;
-                       walk_pmd_range_locked(pud, addr, vma, args, bitmap, &pos);
-               }
--#endif
-+
-               if (!walk->force_scan && !test_bloom_filter(walk->lruvec, walk->max_seq, pmd + i))
-                       continue;
-@@ -5132,7 +5132,7 @@ static ssize_t show_enabled(struct kobje
-       if (arch_has_hw_pte_young() && get_cap(LRU_GEN_MM_WALK))
-               caps |= BIT(LRU_GEN_MM_WALK);
--      if (IS_ENABLED(CONFIG_ARCH_HAS_NONLEAF_PMD_YOUNG) && get_cap(LRU_GEN_NONLEAF_YOUNG))
-+      if (arch_has_hw_nonleaf_pmd_young() && get_cap(LRU_GEN_NONLEAF_YOUNG))
-               caps |= BIT(LRU_GEN_NONLEAF_YOUNG);
-       return snprintf(buf, PAGE_SIZE, "0x%04x\n", caps);
diff --git a/target/linux/generic/backport-5.15/020-v6.2-16-mm-multi-gen-LRU-fix-crash-during-cgroup-migration.patch b/target/linux/generic/backport-5.15/020-v6.2-16-mm-multi-gen-LRU-fix-crash-during-cgroup-migration.patch
deleted file mode 100644 (file)
index e37386a..0000000
+++ /dev/null
@@ -1,56 +0,0 @@
-From c7dfefd4bdfba3d5171038d1cc2d4160288e6ee4 Mon Sep 17 00:00:00 2001
-From: Yu Zhao <[email protected]>
-Date: Sun, 15 Jan 2023 20:44:05 -0700
-Subject: [PATCH 16/29] mm: multi-gen LRU: fix crash during cgroup migration
-
-lru_gen_migrate_mm() assumes lru_gen_add_mm() runs prior to itself.  This
-isn't true for the following scenario:
-
-    CPU 1                         CPU 2
-
-  clone()
-    cgroup_can_fork()
-                                cgroup_procs_write()
-    cgroup_post_fork()
-                                  task_lock()
-                                  lru_gen_migrate_mm()
-                                  task_unlock()
-    task_lock()
-    lru_gen_add_mm()
-    task_unlock()
-
-And when the above happens, kernel crashes because of linked list
-corruption (mm_struct->lru_gen.list).
-
-Link: https://lore.kernel.org/r/[email protected]/
-Link: https://lkml.kernel.org/r/[email protected]
-Fixes: bd74fdaea146 ("mm: multi-gen LRU: support page table walks")
-Signed-off-by: Yu Zhao <[email protected]>
-Reported-by: msizanoen <[email protected]>
-Tested-by: msizanoen <[email protected]>
-Cc: <[email protected]>   [6.1+]
-Signed-off-by: Andrew Morton <[email protected]>
----
- mm/vmscan.c | 5 ++++-
- 1 file changed, 4 insertions(+), 1 deletion(-)
-
---- a/mm/vmscan.c
-+++ b/mm/vmscan.c
-@@ -3024,13 +3024,16 @@ void lru_gen_migrate_mm(struct mm_struct
-       if (mem_cgroup_disabled())
-               return;
-+      /* migration can happen before addition */
-+      if (!mm->lru_gen.memcg)
-+              return;
-+
-       rcu_read_lock();
-       memcg = mem_cgroup_from_task(task);
-       rcu_read_unlock();
-       if (memcg == mm->lru_gen.memcg)
-               return;
--      VM_WARN_ON_ONCE(!mm->lru_gen.memcg);
-       VM_WARN_ON_ONCE(list_empty(&mm->lru_gen.list));
-       lru_gen_del_mm(mm);
diff --git a/target/linux/generic/backport-5.15/020-v6.3-19-mm-add-vma_has_recency.patch b/target/linux/generic/backport-5.15/020-v6.3-19-mm-add-vma_has_recency.patch
deleted file mode 100644 (file)
index 0e9ed9a..0000000
+++ /dev/null
@@ -1,196 +0,0 @@
-From 6c7f552a48b49a8612786a28a2239fbc24fac289 Mon Sep 17 00:00:00 2001
-From: Yu Zhao <[email protected]>
-Date: Fri, 30 Dec 2022 14:52:51 -0700
-Subject: [PATCH 19/29] mm: add vma_has_recency()
-
-Add vma_has_recency() to indicate whether a VMA may exhibit temporal
-locality that the LRU algorithm relies on.
-
-This function returns false for VMAs marked by VM_SEQ_READ or
-VM_RAND_READ.  While the former flag indicates linear access, i.e., a
-special case of spatial locality, both flags indicate a lack of temporal
-locality, i.e., the reuse of an area within a relatively small duration.
-
-"Recency" is chosen over "locality" to avoid confusion between temporal
-and spatial localities.
-
-Before this patch, the active/inactive LRU only ignored the accessed bit
-from VMAs marked by VM_SEQ_READ.  After this patch, the active/inactive
-LRU and MGLRU share the same logic: they both ignore the accessed bit if
-vma_has_recency() returns false.
-
-For the active/inactive LRU, the following fio test showed a [6, 8]%
-increase in IOPS when randomly accessing mapped files under memory
-pressure.
-
-  kb=$(awk '/MemTotal/ { print $2 }' /proc/meminfo)
-  kb=$((kb - 8*1024*1024))
-
-  modprobe brd rd_nr=1 rd_size=$kb
-  dd if=/dev/zero of=/dev/ram0 bs=1M
-
-  mkfs.ext4 /dev/ram0
-  mount /dev/ram0 /mnt/
-  swapoff -a
-
-  fio --name=test --directory=/mnt/ --ioengine=mmap --numjobs=8 \
-      --size=8G --rw=randrw --time_based --runtime=10m \
-      --group_reporting
-
-The discussion that led to this patch is here [1].  Additional test
-results are available in that thread.
-
-[1] https://lore.kernel.org/r/Y31s%[email protected]/
-
-Link: https://lkml.kernel.org/r/[email protected]
-Signed-off-by: Yu Zhao <[email protected]>
-Cc: Alexander Viro <[email protected]>
-Cc: Andrea Righi <[email protected]>
-Cc: Johannes Weiner <[email protected]>
-Cc: Michael Larabel <[email protected]>
-Signed-off-by: Andrew Morton <[email protected]>
----
- include/linux/mm_inline.h |  9 +++++++++
- mm/memory.c               |  8 ++++----
- mm/rmap.c                 | 42 +++++++++++++++++----------------------
- mm/vmscan.c               |  5 ++++-
- 4 files changed, 35 insertions(+), 29 deletions(-)
-
---- a/include/linux/mm_inline.h
-+++ b/include/linux/mm_inline.h
-@@ -333,4 +333,13 @@ static __always_inline void del_page_fro
-       update_lru_size(lruvec, page_lru(page), page_zonenum(page),
-                       -thp_nr_pages(page));
- }
-+
-+static inline bool vma_has_recency(struct vm_area_struct *vma)
-+{
-+      if (vma->vm_flags & (VM_SEQ_READ | VM_RAND_READ))
-+              return false;
-+
-+      return true;
-+}
-+
- #endif
---- a/mm/memory.c
-+++ b/mm/memory.c
-@@ -41,6 +41,7 @@
- #include <linux/kernel_stat.h>
- #include <linux/mm.h>
-+#include <linux/mm_inline.h>
- #include <linux/sched/mm.h>
- #include <linux/sched/coredump.h>
- #include <linux/sched/numa_balancing.h>
-@@ -1353,8 +1354,7 @@ again:
-                                       force_flush = 1;
-                                       set_page_dirty(page);
-                               }
--                              if (pte_young(ptent) &&
--                                  likely(!(vma->vm_flags & VM_SEQ_READ)))
-+                              if (pte_young(ptent) && likely(vma_has_recency(vma)))
-                                       mark_page_accessed(page);
-                       }
-                       rss[mm_counter(page)]--;
-@@ -4808,8 +4808,8 @@ static inline void mm_account_fault(stru
- #ifdef CONFIG_LRU_GEN
- static void lru_gen_enter_fault(struct vm_area_struct *vma)
- {
--      /* the LRU algorithm doesn't apply to sequential or random reads */
--      current->in_lru_fault = !(vma->vm_flags & (VM_SEQ_READ | VM_RAND_READ));
-+      /* the LRU algorithm only applies to accesses with recency */
-+      current->in_lru_fault = vma_has_recency(vma);
- }
- static void lru_gen_exit_fault(void)
---- a/mm/rmap.c
-+++ b/mm/rmap.c
-@@ -794,25 +794,14 @@ static bool page_referenced_one(struct p
-               }
-               if (pvmw.pte) {
--                      if (lru_gen_enabled() && pte_young(*pvmw.pte) &&
--                          !(vma->vm_flags & (VM_SEQ_READ | VM_RAND_READ))) {
-+                      if (lru_gen_enabled() && pte_young(*pvmw.pte)) {
-                               lru_gen_look_around(&pvmw);
-                               referenced++;
-                       }
-                       if (ptep_clear_flush_young_notify(vma, address,
--                                              pvmw.pte)) {
--                              /*
--                               * Don't treat a reference through
--                               * a sequentially read mapping as such.
--                               * If the page has been used in another mapping,
--                               * we will catch it; if this other mapping is
--                               * already gone, the unmap path will have set
--                               * PG_referenced or activated the page.
--                               */
--                              if (likely(!(vma->vm_flags & VM_SEQ_READ)))
--                                      referenced++;
--                      }
-+                                              pvmw.pte))
-+                              referenced++;
-               } else if (IS_ENABLED(CONFIG_TRANSPARENT_HUGEPAGE)) {
-                       if (pmdp_clear_flush_young_notify(vma, address,
-                                               pvmw.pmd))
-@@ -846,7 +835,20 @@ static bool invalid_page_referenced_vma(
-       struct page_referenced_arg *pra = arg;
-       struct mem_cgroup *memcg = pra->memcg;
--      if (!mm_match_cgroup(vma->vm_mm, memcg))
-+      /*
-+       * Ignore references from this mapping if it has no recency. If the
-+       * page has been used in another mapping, we will catch it; if this
-+       * other mapping is already gone, the unmap path will have set the
-+       * referenced flag or activated the page in zap_pte_range().
-+       */
-+      if (!vma_has_recency(vma))
-+              return true;
-+
-+      /*
-+       * If we are reclaiming on behalf of a cgroup, skip counting on behalf
-+       * of references from different cgroups.
-+       */
-+      if (memcg && !mm_match_cgroup(vma->vm_mm, memcg))
-               return true;
-       return false;
-@@ -876,6 +878,7 @@ int page_referenced(struct page *page,
-               .rmap_one = page_referenced_one,
-               .arg = (void *)&pra,
-               .anon_lock = page_lock_anon_vma_read,
-+              .invalid_vma = invalid_page_referenced_vma,
-       };
-       *vm_flags = 0;
-@@ -891,15 +894,6 @@ int page_referenced(struct page *page,
-                       return 1;
-       }
--      /*
--       * If we are reclaiming on behalf of a cgroup, skip
--       * counting on behalf of references from different
--       * cgroups
--       */
--      if (memcg) {
--              rwc.invalid_vma = invalid_page_referenced_vma;
--      }
--
-       rmap_walk(page, &rwc);
-       *vm_flags = pra.vm_flags;
---- a/mm/vmscan.c
-+++ b/mm/vmscan.c
-@@ -3486,7 +3486,10 @@ static int should_skip_vma(unsigned long
-       if (is_vm_hugetlb_page(vma))
-               return true;
--      if (vma->vm_flags & (VM_LOCKED | VM_SPECIAL | VM_SEQ_READ | VM_RAND_READ))
-+      if (!vma_has_recency(vma))
-+              return true;
-+
-+      if (vma->vm_flags & (VM_LOCKED | VM_SPECIAL))
-               return true;
-       if (vma == get_gate_vma(vma->vm_mm))
diff --git a/target/linux/generic/backport-5.15/020-v6.3-20-mm-support-POSIX_FADV_NOREUSE.patch b/target/linux/generic/backport-5.15/020-v6.3-20-mm-support-POSIX_FADV_NOREUSE.patch
deleted file mode 100644 (file)
index 3bb075b..0000000
+++ /dev/null
@@ -1,125 +0,0 @@
-From 686c3d4f71de9e0e7a27f03a5617a712385f90cd Mon Sep 17 00:00:00 2001
-From: Yu Zhao <[email protected]>
-Date: Fri, 30 Dec 2022 14:52:52 -0700
-Subject: [PATCH 20/29] mm: support POSIX_FADV_NOREUSE
-
-This patch adds POSIX_FADV_NOREUSE to vma_has_recency() so that the LRU
-algorithm can ignore access to mapped files marked by this flag.
-
-The advantages of POSIX_FADV_NOREUSE are:
-1. Unlike MADV_SEQUENTIAL and MADV_RANDOM, it does not alter the
-   default readahead behavior.
-2. Unlike MADV_SEQUENTIAL and MADV_RANDOM, it does not split VMAs and
-   therefore does not take mmap_lock.
-3. Unlike MADV_COLD, setting it has a negligible cost, regardless of
-   how many pages it affects.
-
-Its limitations are:
-1. Like POSIX_FADV_RANDOM and POSIX_FADV_SEQUENTIAL, it currently does
-   not support range. IOW, its scope is the entire file.
-2. It currently does not ignore access through file descriptors.
-   Specifically, for the active/inactive LRU, given a file page shared
-   by two users and one of them having set POSIX_FADV_NOREUSE on the
-   file, this page will be activated upon the second user accessing
-   it. This corner case can be covered by checking POSIX_FADV_NOREUSE
-   before calling mark_page_accessed() on the read path. But it is
-   considered not worth the effort.
-
-There have been a few attempts to support POSIX_FADV_NOREUSE, e.g., [1].
-This time the goal is to fill a niche: a few desktop applications, e.g.,
-large file transferring and video encoding/decoding, want fast file
-streaming with mmap() rather than direct IO.  Among those applications, an
-SVT-AV1 regression was reported when running with MGLRU [2].  The
-following test can reproduce that regression.
-
-  kb=$(awk '/MemTotal/ { print $2 }' /proc/meminfo)
-  kb=$((kb - 8*1024*1024))
-
-  modprobe brd rd_nr=1 rd_size=$kb
-  dd if=/dev/zero of=/dev/ram0 bs=1M
-
-  mkfs.ext4 /dev/ram0
-  mount /dev/ram0 /mnt/
-  swapoff -a
-
-  fallocate -l 8G /mnt/swapfile
-  mkswap /mnt/swapfile
-  swapon /mnt/swapfile
-
-  wget http://ultravideo.cs.tut.fi/video/Bosphorus_3840x2160_120fps_420_8bit_YUV_Y4M.7z
-  7z e -o/mnt/ Bosphorus_3840x2160_120fps_420_8bit_YUV_Y4M.7z
-  SvtAv1EncApp --preset 12 -w 3840 -h 2160 \
-               -i /mnt/Bosphorus_3840x2160.y4m
-
-For MGLRU, the following change showed a [9-11]% increase in FPS,
-which makes it on par with the active/inactive LRU.
-
-  patch Source/App/EncApp/EbAppMain.c <<EOF
-  31a32
-  > #include <fcntl.h>
-  35d35
-  < #include <fcntl.h> /* _O_BINARY */
-  117a118
-  >             posix_fadvise(config->mmap.fd, 0, 0, POSIX_FADV_NOREUSE);
-  EOF
-
-[1] https://lore.kernel.org/r/[email protected]/
-[2] https://openbenchmarking.org/result/2209259-PTS-MGLRU8GB57
-
-Link: https://lkml.kernel.org/r/[email protected]
-Signed-off-by: Yu Zhao <[email protected]>
-Cc: Alexander Viro <[email protected]>
-Cc: Andrea Righi <[email protected]>
-Cc: Johannes Weiner <[email protected]>
-Cc: Michael Larabel <[email protected]>
-Signed-off-by: Andrew Morton <[email protected]>
----
- include/linux/fs.h        | 2 ++
- include/linux/mm_inline.h | 3 +++
- mm/fadvise.c              | 5 ++++-
- 3 files changed, 9 insertions(+), 1 deletion(-)
-
---- a/include/linux/fs.h
-+++ b/include/linux/fs.h
-@@ -167,6 +167,8 @@ typedef int (dio_iodone_t)(struct kiocb
- /* File is stream-like */
- #define FMODE_STREAM          ((__force fmode_t)0x200000)
-+#define       FMODE_NOREUSE           ((__force fmode_t)0x400000)
-+
- /* File was opened by fanotify and shouldn't generate fanotify events */
- #define FMODE_NONOTIFY                ((__force fmode_t)0x4000000)
---- a/include/linux/mm_inline.h
-+++ b/include/linux/mm_inline.h
-@@ -339,6 +339,9 @@ static inline bool vma_has_recency(struc
-       if (vma->vm_flags & (VM_SEQ_READ | VM_RAND_READ))
-               return false;
-+      if (vma->vm_file && (vma->vm_file->f_mode & FMODE_NOREUSE))
-+              return false;
-+
-       return true;
- }
---- a/mm/fadvise.c
-+++ b/mm/fadvise.c
-@@ -80,7 +80,7 @@ int generic_fadvise(struct file *file, l
-       case POSIX_FADV_NORMAL:
-               file->f_ra.ra_pages = bdi->ra_pages;
-               spin_lock(&file->f_lock);
--              file->f_mode &= ~FMODE_RANDOM;
-+              file->f_mode &= ~(FMODE_RANDOM | FMODE_NOREUSE);
-               spin_unlock(&file->f_lock);
-               break;
-       case POSIX_FADV_RANDOM:
-@@ -107,6 +107,9 @@ int generic_fadvise(struct file *file, l
-               force_page_cache_readahead(mapping, file, start_index, nrpages);
-               break;
-       case POSIX_FADV_NOREUSE:
-+              spin_lock(&file->f_lock);
-+              file->f_mode |= FMODE_NOREUSE;
-+              spin_unlock(&file->f_lock);
-               break;
-       case POSIX_FADV_DONTNEED:
-               if (!inode_write_congested(mapping->host))
diff --git a/target/linux/generic/backport-5.15/020-v6.3-21-mm-multi-gen-LRU-rename-lru_gen_struct-to-lru_gen_pa.patch b/target/linux/generic/backport-5.15/020-v6.3-21-mm-multi-gen-LRU-rename-lru_gen_struct-to-lru_gen_pa.patch
deleted file mode 100644 (file)
index 4e09173..0000000
+++ /dev/null
@@ -1,348 +0,0 @@
-From 348fdbada9fb3f0bf1a53651be46319105af187f Mon Sep 17 00:00:00 2001
-From: Yu Zhao <[email protected]>
-Date: Wed, 21 Dec 2022 21:18:59 -0700
-Subject: [PATCH 21/29] mm: multi-gen LRU: rename lru_gen_struct to
- lru_gen_page
-
-Patch series "mm: multi-gen LRU: memcg LRU", v3.
-
-Overview
-========
-
-An memcg LRU is a per-node LRU of memcgs.  It is also an LRU of LRUs,
-since each node and memcg combination has an LRU of pages (see
-mem_cgroup_lruvec()).
-
-Its goal is to improve the scalability of global reclaim, which is
-critical to system-wide memory overcommit in data centers.  Note that
-memcg reclaim is currently out of scope.
-
-Its memory bloat is a pointer to each lruvec and negligible to each
-pglist_data.  In terms of traversing memcgs during global reclaim, it
-improves the best-case complexity from O(n) to O(1) and does not affect
-the worst-case complexity O(n).  Therefore, on average, it has a sublinear
-complexity in contrast to the current linear complexity.
-
-The basic structure of an memcg LRU can be understood by an analogy to
-the active/inactive LRU (of pages):
-1. It has the young and the old (generations), i.e., the counterparts
-   to the active and the inactive;
-2. The increment of max_seq triggers promotion, i.e., the counterpart
-   to activation;
-3. Other events trigger similar operations, e.g., offlining an memcg
-   triggers demotion, i.e., the counterpart to deactivation.
-
-In terms of global reclaim, it has two distinct features:
-1. Sharding, which allows each thread to start at a random memcg (in
-   the old generation) and improves parallelism;
-2. Eventual fairness, which allows direct reclaim to bail out at will
-   and reduces latency without affecting fairness over some time.
-
-The commit message in patch 6 details the workflow:
-https://lore.kernel.org/r/[email protected]/
-
-The following is a simple test to quickly verify its effectiveness.
-
-  Test design:
-  1. Create multiple memcgs.
-  2. Each memcg contains a job (fio).
-  3. All jobs access the same amount of memory randomly.
-  4. The system does not experience global memory pressure.
-  5. Periodically write to the root memory.reclaim.
-
-  Desired outcome:
-  1. All memcgs have similar pgsteal counts, i.e., stddev(pgsteal)
-     over mean(pgsteal) is close to 0%.
-  2. The total pgsteal is close to the total requested through
-     memory.reclaim, i.e., sum(pgsteal) over sum(requested) is close
-     to 100%.
-
-  Actual outcome [1]:
-                                     MGLRU off    MGLRU on
-  stddev(pgsteal) / mean(pgsteal)    75%          20%
-  sum(pgsteal) / sum(requested)      425%         95%
-
-  ####################################################################
-  MEMCGS=128
-
-  for ((memcg = 0; memcg < $MEMCGS; memcg++)); do
-      mkdir /sys/fs/cgroup/memcg$memcg
-  done
-
-  start() {
-      echo $BASHPID > /sys/fs/cgroup/memcg$memcg/cgroup.procs
-
-      fio -name=memcg$memcg --numjobs=1 --ioengine=mmap \
-          --filename=/dev/zero --size=1920M --rw=randrw \
-          --rate=64m,64m --random_distribution=random \
-          --fadvise_hint=0 --time_based --runtime=10h \
-          --group_reporting --minimal
-  }
-
-  for ((memcg = 0; memcg < $MEMCGS; memcg++)); do
-      start &
-  done
-
-  sleep 600
-
-  for ((i = 0; i < 600; i++)); do
-      echo 256m >/sys/fs/cgroup/memory.reclaim
-      sleep 6
-  done
-
-  for ((memcg = 0; memcg < $MEMCGS; memcg++)); do
-      grep "pgsteal " /sys/fs/cgroup/memcg$memcg/memory.stat
-  done
-  ####################################################################
-
-[1]: This was obtained from running the above script (touches less
-     than 256GB memory) on an EPYC 7B13 with 512GB DRAM for over an
-     hour.
-
-This patch (of 8):
-
-The new name lru_gen_page will be more distinct from the coming
-lru_gen_memcg.
-
-Link: https://lkml.kernel.org/r/[email protected]
-Link: https://lkml.kernel.org/r/[email protected]
-Signed-off-by: Yu Zhao <[email protected]>
-Cc: Johannes Weiner <[email protected]>
-Cc: Jonathan Corbet <[email protected]>
-Cc: Michael Larabel <[email protected]>
-Cc: Michal Hocko <[email protected]>
-Cc: Mike Rapoport <[email protected]>
-Cc: Roman Gushchin <[email protected]>
-Cc: Suren Baghdasaryan <[email protected]>
-Signed-off-by: Andrew Morton <[email protected]>
----
- include/linux/mm_inline.h |  4 ++--
- include/linux/mmzone.h    |  6 +++---
- mm/vmscan.c               | 34 +++++++++++++++++-----------------
- mm/workingset.c           |  4 ++--
- 4 files changed, 24 insertions(+), 24 deletions(-)
-
---- a/include/linux/mm_inline.h
-+++ b/include/linux/mm_inline.h
-@@ -168,7 +168,7 @@ static inline void lru_gen_update_size(s
-       int zone = page_zonenum(page);
-       int delta = thp_nr_pages(page);
-       enum lru_list lru = type * LRU_INACTIVE_FILE;
--      struct lru_gen_struct *lrugen = &lruvec->lrugen;
-+      struct lru_gen_page *lrugen = &lruvec->lrugen;
-       VM_WARN_ON_ONCE(old_gen != -1 && old_gen >= MAX_NR_GENS);
-       VM_WARN_ON_ONCE(new_gen != -1 && new_gen >= MAX_NR_GENS);
-@@ -214,7 +214,7 @@ static inline bool lru_gen_add_page(stru
-       int gen = page_lru_gen(page);
-       int type = page_is_file_lru(page);
-       int zone = page_zonenum(page);
--      struct lru_gen_struct *lrugen = &lruvec->lrugen;
-+      struct lru_gen_page *lrugen = &lruvec->lrugen;
-       VM_WARN_ON_ONCE_PAGE(gen != -1, page);
---- a/include/linux/mmzone.h
-+++ b/include/linux/mmzone.h
-@@ -394,7 +394,7 @@ enum {
-  * The number of pages in each generation is eventually consistent and therefore
-  * can be transiently negative when reset_batch_size() is pending.
-  */
--struct lru_gen_struct {
-+struct lru_gen_page {
-       /* the aging increments the youngest generation number */
-       unsigned long max_seq;
-       /* the eviction increments the oldest generation numbers */
-@@ -451,7 +451,7 @@ struct lru_gen_mm_state {
- struct lru_gen_mm_walk {
-       /* the lruvec under reclaim */
-       struct lruvec *lruvec;
--      /* unstable max_seq from lru_gen_struct */
-+      /* unstable max_seq from lru_gen_page */
-       unsigned long max_seq;
-       /* the next address within an mm to scan */
-       unsigned long next_addr;
-@@ -514,7 +514,7 @@ struct lruvec {
-       unsigned long                   flags;
- #ifdef CONFIG_LRU_GEN
-       /* evictable pages divided into generations */
--      struct lru_gen_struct           lrugen;
-+      struct lru_gen_page             lrugen;
-       /* to concurrently iterate lru_gen_mm_list */
-       struct lru_gen_mm_state         mm_state;
- #endif
---- a/mm/vmscan.c
-+++ b/mm/vmscan.c
-@@ -2910,7 +2910,7 @@ static int get_nr_gens(struct lruvec *lr
- static bool __maybe_unused seq_is_valid(struct lruvec *lruvec)
- {
--      /* see the comment on lru_gen_struct */
-+      /* see the comment on lru_gen_page */
-       return get_nr_gens(lruvec, LRU_GEN_FILE) >= MIN_NR_GENS &&
-              get_nr_gens(lruvec, LRU_GEN_FILE) <= get_nr_gens(lruvec, LRU_GEN_ANON) &&
-              get_nr_gens(lruvec, LRU_GEN_ANON) <= MAX_NR_GENS;
-@@ -3316,7 +3316,7 @@ struct ctrl_pos {
- static void read_ctrl_pos(struct lruvec *lruvec, int type, int tier, int gain,
-                         struct ctrl_pos *pos)
- {
--      struct lru_gen_struct *lrugen = &lruvec->lrugen;
-+      struct lru_gen_page *lrugen = &lruvec->lrugen;
-       int hist = lru_hist_from_seq(lrugen->min_seq[type]);
-       pos->refaulted = lrugen->avg_refaulted[type][tier] +
-@@ -3331,7 +3331,7 @@ static void read_ctrl_pos(struct lruvec
- static void reset_ctrl_pos(struct lruvec *lruvec, int type, bool carryover)
- {
-       int hist, tier;
--      struct lru_gen_struct *lrugen = &lruvec->lrugen;
-+      struct lru_gen_page *lrugen = &lruvec->lrugen;
-       bool clear = carryover ? NR_HIST_GENS == 1 : NR_HIST_GENS > 1;
-       unsigned long seq = carryover ? lrugen->min_seq[type] : lrugen->max_seq + 1;
-@@ -3408,7 +3408,7 @@ static int page_update_gen(struct page *
- static int page_inc_gen(struct lruvec *lruvec, struct page *page, bool reclaiming)
- {
-       int type = page_is_file_lru(page);
--      struct lru_gen_struct *lrugen = &lruvec->lrugen;
-+      struct lru_gen_page *lrugen = &lruvec->lrugen;
-       int new_gen, old_gen = lru_gen_from_seq(lrugen->min_seq[type]);
-       unsigned long new_flags, old_flags = READ_ONCE(page->flags);
-@@ -3453,7 +3453,7 @@ static void update_batch_size(struct lru
- static void reset_batch_size(struct lruvec *lruvec, struct lru_gen_mm_walk *walk)
- {
-       int gen, type, zone;
--      struct lru_gen_struct *lrugen = &lruvec->lrugen;
-+      struct lru_gen_page *lrugen = &lruvec->lrugen;
-       walk->batched = 0;
-@@ -3979,7 +3979,7 @@ static bool inc_min_seq(struct lruvec *l
- {
-       int zone;
-       int remaining = MAX_LRU_BATCH;
--      struct lru_gen_struct *lrugen = &lruvec->lrugen;
-+      struct lru_gen_page *lrugen = &lruvec->lrugen;
-       int new_gen, old_gen = lru_gen_from_seq(lrugen->min_seq[type]);
-       if (type == LRU_GEN_ANON && !can_swap)
-@@ -4015,7 +4015,7 @@ static bool try_to_inc_min_seq(struct lr
- {
-       int gen, type, zone;
-       bool success = false;
--      struct lru_gen_struct *lrugen = &lruvec->lrugen;
-+      struct lru_gen_page *lrugen = &lruvec->lrugen;
-       DEFINE_MIN_SEQ(lruvec);
-       VM_WARN_ON_ONCE(!seq_is_valid(lruvec));
-@@ -4036,7 +4036,7 @@ next:
-               ;
-       }
--      /* see the comment on lru_gen_struct */
-+      /* see the comment on lru_gen_page */
-       if (can_swap) {
-               min_seq[LRU_GEN_ANON] = min(min_seq[LRU_GEN_ANON], min_seq[LRU_GEN_FILE]);
-               min_seq[LRU_GEN_FILE] = max(min_seq[LRU_GEN_ANON], lrugen->min_seq[LRU_GEN_FILE]);
-@@ -4058,7 +4058,7 @@ static void inc_max_seq(struct lruvec *l
- {
-       int prev, next;
-       int type, zone;
--      struct lru_gen_struct *lrugen = &lruvec->lrugen;
-+      struct lru_gen_page *lrugen = &lruvec->lrugen;
-       spin_lock_irq(&lruvec->lru_lock);
-@@ -4116,7 +4116,7 @@ static bool try_to_inc_max_seq(struct lr
-       bool success;
-       struct lru_gen_mm_walk *walk;
-       struct mm_struct *mm = NULL;
--      struct lru_gen_struct *lrugen = &lruvec->lrugen;
-+      struct lru_gen_page *lrugen = &lruvec->lrugen;
-       VM_WARN_ON_ONCE(max_seq > READ_ONCE(lrugen->max_seq));
-@@ -4181,7 +4181,7 @@ static bool should_run_aging(struct lruv
-       unsigned long old = 0;
-       unsigned long young = 0;
-       unsigned long total = 0;
--      struct lru_gen_struct *lrugen = &lruvec->lrugen;
-+      struct lru_gen_page *lrugen = &lruvec->lrugen;
-       struct mem_cgroup *memcg = lruvec_memcg(lruvec);
-       for (type = !can_swap; type < ANON_AND_FILE; type++) {
-@@ -4466,7 +4466,7 @@ static bool sort_page(struct lruvec *lru
-       int delta = thp_nr_pages(page);
-       int refs = page_lru_refs(page);
-       int tier = lru_tier_from_refs(refs);
--      struct lru_gen_struct *lrugen = &lruvec->lrugen;
-+      struct lru_gen_page *lrugen = &lruvec->lrugen;
-       VM_WARN_ON_ONCE_PAGE(gen >= MAX_NR_GENS, page);
-@@ -4566,7 +4566,7 @@ static int scan_pages(struct lruvec *lru
-       int scanned = 0;
-       int isolated = 0;
-       int remaining = MAX_LRU_BATCH;
--      struct lru_gen_struct *lrugen = &lruvec->lrugen;
-+      struct lru_gen_page *lrugen = &lruvec->lrugen;
-       struct mem_cgroup *memcg = lruvec_memcg(lruvec);
-       VM_WARN_ON_ONCE(!list_empty(list));
-@@ -4967,7 +4967,7 @@ done:
- static bool __maybe_unused state_is_valid(struct lruvec *lruvec)
- {
--      struct lru_gen_struct *lrugen = &lruvec->lrugen;
-+      struct lru_gen_page *lrugen = &lruvec->lrugen;
-       if (lrugen->enabled) {
-               enum lru_list lru;
-@@ -5247,7 +5247,7 @@ static void lru_gen_seq_show_full(struct
-       int i;
-       int type, tier;
-       int hist = lru_hist_from_seq(seq);
--      struct lru_gen_struct *lrugen = &lruvec->lrugen;
-+      struct lru_gen_page *lrugen = &lruvec->lrugen;
-       for (tier = 0; tier < MAX_NR_TIERS; tier++) {
-               seq_printf(m, "            %10d", tier);
-@@ -5296,7 +5296,7 @@ static int lru_gen_seq_show(struct seq_f
-       unsigned long seq;
-       bool full = !debugfs_real_fops(m->file)->write;
-       struct lruvec *lruvec = v;
--      struct lru_gen_struct *lrugen = &lruvec->lrugen;
-+      struct lru_gen_page *lrugen = &lruvec->lrugen;
-       int nid = lruvec_pgdat(lruvec)->node_id;
-       struct mem_cgroup *memcg = lruvec_memcg(lruvec);
-       DEFINE_MAX_SEQ(lruvec);
-@@ -5549,7 +5549,7 @@ void lru_gen_init_lruvec(struct lruvec *
- {
-       int i;
-       int gen, type, zone;
--      struct lru_gen_struct *lrugen = &lruvec->lrugen;
-+      struct lru_gen_page *lrugen = &lruvec->lrugen;
-       lrugen->max_seq = MIN_NR_GENS + 1;
-       lrugen->enabled = lru_gen_enabled();
---- a/mm/workingset.c
-+++ b/mm/workingset.c
-@@ -223,7 +223,7 @@ static void *lru_gen_eviction(struct pag
-       unsigned long token;
-       unsigned long min_seq;
-       struct lruvec *lruvec;
--      struct lru_gen_struct *lrugen;
-+      struct lru_gen_page *lrugen;
-       int type = page_is_file_lru(page);
-       int delta = thp_nr_pages(page);
-       int refs = page_lru_refs(page);
-@@ -252,7 +252,7 @@ static void lru_gen_refault(struct page
-       unsigned long token;
-       unsigned long min_seq;
-       struct lruvec *lruvec;
--      struct lru_gen_struct *lrugen;
-+      struct lru_gen_page *lrugen;
-       struct mem_cgroup *memcg;
-       struct pglist_data *pgdat;
-       int type = page_is_file_lru(page);
diff --git a/target/linux/generic/backport-5.15/020-v6.3-22-mm-multi-gen-LRU-rename-lrugen-lists-to-lrugen-pages.patch b/target/linux/generic/backport-5.15/020-v6.3-22-mm-multi-gen-LRU-rename-lrugen-lists-to-lrugen-pages.patch
deleted file mode 100644 (file)
index b548c1c..0000000
+++ /dev/null
@@ -1,162 +0,0 @@
-From afd37e73db04c7e6b47411120ac5f6a7eca51fec Mon Sep 17 00:00:00 2001
-From: Yu Zhao <[email protected]>
-Date: Wed, 21 Dec 2022 21:19:00 -0700
-Subject: [PATCH 22/29] mm: multi-gen LRU: rename lrugen->lists[] to
- lrugen->pages[]
-
-lru_gen_page will be chained into per-node lists by the coming
-lrugen->list.
-
-Link: https://lkml.kernel.org/r/[email protected]
-Signed-off-by: Yu Zhao <[email protected]>
-Cc: Johannes Weiner <[email protected]>
-Cc: Jonathan Corbet <[email protected]>
-Cc: Michael Larabel <[email protected]>
-Cc: Michal Hocko <[email protected]>
-Cc: Mike Rapoport <[email protected]>
-Cc: Roman Gushchin <[email protected]>
-Cc: Suren Baghdasaryan <[email protected]>
-Signed-off-by: Andrew Morton <[email protected]>
----
- include/linux/mm_inline.h |  4 ++--
- include/linux/mmzone.h    |  8 ++++----
- mm/vmscan.c               | 20 ++++++++++----------
- 3 files changed, 16 insertions(+), 16 deletions(-)
-
---- a/include/linux/mm_inline.h
-+++ b/include/linux/mm_inline.h
-@@ -246,9 +246,9 @@ static inline bool lru_gen_add_page(stru
-       lru_gen_update_size(lruvec, page, -1, gen);
-       /* for rotate_reclaimable_page() */
-       if (reclaiming)
--              list_add_tail(&page->lru, &lrugen->lists[gen][type][zone]);
-+              list_add_tail(&page->lru, &lrugen->pages[gen][type][zone]);
-       else
--              list_add(&page->lru, &lrugen->lists[gen][type][zone]);
-+              list_add(&page->lru, &lrugen->pages[gen][type][zone]);
-       return true;
- }
---- a/include/linux/mmzone.h
-+++ b/include/linux/mmzone.h
-@@ -302,7 +302,7 @@ enum lruvec_flags {
-  * They form a sliding window of a variable size [MIN_NR_GENS, MAX_NR_GENS]. An
-  * offset within MAX_NR_GENS, i.e., gen, indexes the LRU list of the
-  * corresponding generation. The gen counter in page->flags stores gen+1 while
-- * a page is on one of lrugen->lists[]. Otherwise it stores 0.
-+ * a page is on one of lrugen->pages[]. Otherwise it stores 0.
-  *
-  * A page is added to the youngest generation on faulting. The aging needs to
-  * check the accessed bit at least twice before handing this page over to the
-@@ -314,8 +314,8 @@ enum lruvec_flags {
-  * rest of generations, if they exist, are considered inactive. See
-  * lru_gen_is_active().
-  *
-- * PG_active is always cleared while a page is on one of lrugen->lists[] so that
-- * the aging needs not to worry about it. And it's set again when a page
-+ * PG_active is always cleared while a page is on one of lrugen->pages[] so
-+ * that the aging needs not to worry about it. And it's set again when a page
-  * considered active is isolated for non-reclaiming purposes, e.g., migration.
-  * See lru_gen_add_page() and lru_gen_del_page().
-  *
-@@ -402,7 +402,7 @@ struct lru_gen_page {
-       /* the birth time of each generation in jiffies */
-       unsigned long timestamps[MAX_NR_GENS];
-       /* the multi-gen LRU lists, lazily sorted on eviction */
--      struct list_head lists[MAX_NR_GENS][ANON_AND_FILE][MAX_NR_ZONES];
-+      struct list_head pages[MAX_NR_GENS][ANON_AND_FILE][MAX_NR_ZONES];
-       /* the multi-gen LRU sizes, eventually consistent */
-       long nr_pages[MAX_NR_GENS][ANON_AND_FILE][MAX_NR_ZONES];
-       /* the exponential moving average of refaulted */
---- a/mm/vmscan.c
-+++ b/mm/vmscan.c
-@@ -3987,7 +3987,7 @@ static bool inc_min_seq(struct lruvec *l
-       /* prevent cold/hot inversion if force_scan is true */
-       for (zone = 0; zone < MAX_NR_ZONES; zone++) {
--              struct list_head *head = &lrugen->lists[old_gen][type][zone];
-+              struct list_head *head = &lrugen->pages[old_gen][type][zone];
-               while (!list_empty(head)) {
-                       struct page *page = lru_to_page(head);
-@@ -3998,7 +3998,7 @@ static bool inc_min_seq(struct lruvec *l
-                       VM_WARN_ON_ONCE_PAGE(page_zonenum(page) != zone, page);
-                       new_gen = page_inc_gen(lruvec, page, false);
--                      list_move_tail(&page->lru, &lrugen->lists[new_gen][type][zone]);
-+                      list_move_tail(&page->lru, &lrugen->pages[new_gen][type][zone]);
-                       if (!--remaining)
-                               return false;
-@@ -4026,7 +4026,7 @@ static bool try_to_inc_min_seq(struct lr
-                       gen = lru_gen_from_seq(min_seq[type]);
-                       for (zone = 0; zone < MAX_NR_ZONES; zone++) {
--                              if (!list_empty(&lrugen->lists[gen][type][zone]))
-+                              if (!list_empty(&lrugen->pages[gen][type][zone]))
-                                       goto next;
-                       }
-@@ -4491,7 +4491,7 @@ static bool sort_page(struct lruvec *lru
-       /* promoted */
-       if (gen != lru_gen_from_seq(lrugen->min_seq[type])) {
--              list_move(&page->lru, &lrugen->lists[gen][type][zone]);
-+              list_move(&page->lru, &lrugen->pages[gen][type][zone]);
-               return true;
-       }
-@@ -4500,7 +4500,7 @@ static bool sort_page(struct lruvec *lru
-               int hist = lru_hist_from_seq(lrugen->min_seq[type]);
-               gen = page_inc_gen(lruvec, page, false);
--              list_move_tail(&page->lru, &lrugen->lists[gen][type][zone]);
-+              list_move_tail(&page->lru, &lrugen->pages[gen][type][zone]);
-               WRITE_ONCE(lrugen->protected[hist][type][tier - 1],
-                          lrugen->protected[hist][type][tier - 1] + delta);
-@@ -4512,7 +4512,7 @@ static bool sort_page(struct lruvec *lru
-       if (PageLocked(page) || PageWriteback(page) ||
-           (type == LRU_GEN_FILE && PageDirty(page))) {
-               gen = page_inc_gen(lruvec, page, true);
--              list_move(&page->lru, &lrugen->lists[gen][type][zone]);
-+              list_move(&page->lru, &lrugen->pages[gen][type][zone]);
-               return true;
-       }
-@@ -4579,7 +4579,7 @@ static int scan_pages(struct lruvec *lru
-       for (zone = sc->reclaim_idx; zone >= 0; zone--) {
-               LIST_HEAD(moved);
-               int skipped = 0;
--              struct list_head *head = &lrugen->lists[gen][type][zone];
-+              struct list_head *head = &lrugen->pages[gen][type][zone];
-               while (!list_empty(head)) {
-                       struct page *page = lru_to_page(head);
-@@ -4980,7 +4980,7 @@ static bool __maybe_unused state_is_vali
-               int gen, type, zone;
-               for_each_gen_type_zone(gen, type, zone) {
--                      if (!list_empty(&lrugen->lists[gen][type][zone]))
-+                      if (!list_empty(&lrugen->pages[gen][type][zone]))
-                               return false;
-               }
-       }
-@@ -5025,7 +5025,7 @@ static bool drain_evictable(struct lruve
-       int remaining = MAX_LRU_BATCH;
-       for_each_gen_type_zone(gen, type, zone) {
--              struct list_head *head = &lruvec->lrugen.lists[gen][type][zone];
-+              struct list_head *head = &lruvec->lrugen.pages[gen][type][zone];
-               while (!list_empty(head)) {
-                       bool success;
-@@ -5558,7 +5558,7 @@ void lru_gen_init_lruvec(struct lruvec *
-               lrugen->timestamps[i] = jiffies;
-       for_each_gen_type_zone(gen, type, zone)
--              INIT_LIST_HEAD(&lrugen->lists[gen][type][zone]);
-+              INIT_LIST_HEAD(&lrugen->pages[gen][type][zone]);
-       lruvec->mm_state.seq = MIN_NR_GENS;
-       init_waitqueue_head(&lruvec->mm_state.wait);
diff --git a/target/linux/generic/backport-5.15/020-v6.3-23-mm-multi-gen-LRU-remove-eviction-fairness-safeguard.patch b/target/linux/generic/backport-5.15/020-v6.3-23-mm-multi-gen-LRU-remove-eviction-fairness-safeguard.patch
deleted file mode 100644 (file)
index 2bb6e12..0000000
+++ /dev/null
@@ -1,188 +0,0 @@
-From ce45f1c4b32cf69b166f56ef5bc6c761e06ed4e5 Mon Sep 17 00:00:00 2001
-From: Yu Zhao <[email protected]>
-Date: Wed, 21 Dec 2022 21:19:01 -0700
-Subject: [PATCH 23/29] mm: multi-gen LRU: remove eviction fairness safeguard
-
-Recall that the eviction consumes the oldest generation: first it
-bucket-sorts pages whose gen counters were updated by the aging and
-reclaims the rest; then it increments lrugen->min_seq.
-
-The current eviction fairness safeguard for global reclaim has a
-dilemma: when there are multiple eligible memcgs, should it continue
-or stop upon meeting the reclaim goal? If it continues, it overshoots
-and increases direct reclaim latency; if it stops, it loses fairness
-between memcgs it has taken memory away from and those it has yet to.
-
-With memcg LRU, the eviction, while ensuring eventual fairness, will
-stop upon meeting its goal. Therefore the current eviction fairness
-safeguard for global reclaim will not be needed.
-
-Note that memcg LRU only applies to global reclaim. For memcg reclaim,
-the eviction will continue, even if it is overshooting. This becomes
-unconditional due to code simplification.
-
-Link: https://lkml.kernel.org/r/[email protected]
-Signed-off-by: Yu Zhao <[email protected]>
-Cc: Johannes Weiner <[email protected]>
-Cc: Jonathan Corbet <[email protected]>
-Cc: Michael Larabel <[email protected]>
-Cc: Michal Hocko <[email protected]>
-Cc: Mike Rapoport <[email protected]>
-Cc: Roman Gushchin <[email protected]>
-Cc: Suren Baghdasaryan <[email protected]>
-Signed-off-by: Andrew Morton <[email protected]>
----
- mm/vmscan.c | 82 +++++++++++++++--------------------------------------
- 1 file changed, 23 insertions(+), 59 deletions(-)
-
---- a/mm/vmscan.c
-+++ b/mm/vmscan.c
-@@ -443,6 +443,11 @@ static bool cgroup_reclaim(struct scan_c
-       return sc->target_mem_cgroup;
- }
-+static bool global_reclaim(struct scan_control *sc)
-+{
-+      return !sc->target_mem_cgroup || mem_cgroup_is_root(sc->target_mem_cgroup);
-+}
-+
- /**
-  * writeback_throttling_sane - is the usual dirty throttling mechanism available?
-  * @sc: scan_control in question
-@@ -493,6 +498,11 @@ static bool cgroup_reclaim(struct scan_c
-       return false;
- }
-+static bool global_reclaim(struct scan_control *sc)
-+{
-+      return true;
-+}
-+
- static bool writeback_throttling_sane(struct scan_control *sc)
- {
-       return true;
-@@ -4722,8 +4732,7 @@ static int isolate_pages(struct lruvec *
-       return scanned;
- }
--static int evict_pages(struct lruvec *lruvec, struct scan_control *sc, int swappiness,
--                     bool *need_swapping)
-+static int evict_pages(struct lruvec *lruvec, struct scan_control *sc, int swappiness)
- {
-       int type;
-       int scanned;
-@@ -4812,9 +4821,6 @@ retry:
-               goto retry;
-       }
--      if (need_swapping && type == LRU_GEN_ANON)
--              *need_swapping = true;
--
-       return scanned;
- }
-@@ -4853,68 +4859,26 @@ done:
-       return min_seq[!can_swap] + MIN_NR_GENS <= max_seq ? nr_to_scan : 0;
- }
--static bool should_abort_scan(struct lruvec *lruvec, unsigned long seq,
--                            struct scan_control *sc, bool need_swapping)
-+static unsigned long get_nr_to_reclaim(struct scan_control *sc)
- {
--      int i;
--      DEFINE_MAX_SEQ(lruvec);
--
--      if (!current_is_kswapd()) {
--              /* age each memcg once to ensure fairness */
--              if (max_seq - seq > 1)
--                      return true;
--
--              /* over-swapping can increase allocation latency */
--              if (sc->nr_reclaimed >= sc->nr_to_reclaim && need_swapping)
--                      return true;
--
--              /* give this thread a chance to exit and free its memory */
--              if (fatal_signal_pending(current)) {
--                      sc->nr_reclaimed += MIN_LRU_BATCH;
--                      return true;
--              }
--
--              if (cgroup_reclaim(sc))
--                      return false;
--      } else if (sc->nr_reclaimed - sc->last_reclaimed < sc->nr_to_reclaim)
--              return false;
--
--      /* keep scanning at low priorities to ensure fairness */
--      if (sc->priority > DEF_PRIORITY - 2)
--              return false;
--
--      /*
--       * A minimum amount of work was done under global memory pressure. For
--       * kswapd, it may be overshooting. For direct reclaim, the target isn't
--       * met, and yet the allocation may still succeed, since kswapd may have
--       * caught up. In either case, it's better to stop now, and restart if
--       * necessary.
--       */
--      for (i = 0; i <= sc->reclaim_idx; i++) {
--              unsigned long wmark;
--              struct zone *zone = lruvec_pgdat(lruvec)->node_zones + i;
--
--              if (!managed_zone(zone))
--                      continue;
--
--              wmark = current_is_kswapd() ? high_wmark_pages(zone) : low_wmark_pages(zone);
--              if (wmark > zone_page_state(zone, NR_FREE_PAGES))
--                      return false;
--      }
-+      /* don't abort memcg reclaim to ensure fairness */
-+      if (!global_reclaim(sc))
-+              return -1;
--      sc->nr_reclaimed += MIN_LRU_BATCH;
-+      /* discount the previous progress for kswapd */
-+      if (current_is_kswapd())
-+              return sc->nr_to_reclaim + sc->last_reclaimed;
--      return true;
-+      return max(sc->nr_to_reclaim, compact_gap(sc->order));
- }
- static void lru_gen_shrink_lruvec(struct lruvec *lruvec, struct scan_control *sc)
- {
-       struct blk_plug plug;
-       bool need_aging = false;
--      bool need_swapping = false;
-       unsigned long scanned = 0;
-       unsigned long reclaimed = sc->nr_reclaimed;
--      DEFINE_MAX_SEQ(lruvec);
-+      unsigned long nr_to_reclaim = get_nr_to_reclaim(sc);
-       lru_add_drain();
-@@ -4938,7 +4902,7 @@ static void lru_gen_shrink_lruvec(struct
-               if (!nr_to_scan)
-                       goto done;
--              delta = evict_pages(lruvec, sc, swappiness, &need_swapping);
-+              delta = evict_pages(lruvec, sc, swappiness);
-               if (!delta)
-                       goto done;
-@@ -4946,7 +4910,7 @@ static void lru_gen_shrink_lruvec(struct
-               if (scanned >= nr_to_scan)
-                       break;
--              if (should_abort_scan(lruvec, max_seq, sc, need_swapping))
-+              if (sc->nr_reclaimed >= nr_to_reclaim)
-                       break;
-               cond_resched();
-@@ -5393,7 +5357,7 @@ static int run_eviction(struct lruvec *l
-               if (sc->nr_reclaimed >= nr_to_reclaim)
-                       return 0;
--              if (!evict_pages(lruvec, sc, swappiness, NULL))
-+              if (!evict_pages(lruvec, sc, swappiness))
-                       return 0;
-               cond_resched();
diff --git a/target/linux/generic/backport-5.15/020-v6.3-24-mm-multi-gen-LRU-remove-aging-fairness-safeguard.patch b/target/linux/generic/backport-5.15/020-v6.3-24-mm-multi-gen-LRU-remove-aging-fairness-safeguard.patch
deleted file mode 100644 (file)
index 316217e..0000000
+++ /dev/null
@@ -1,287 +0,0 @@
-From e20b7386fccc18c791796eb1dc1a91eee3ccf801 Mon Sep 17 00:00:00 2001
-From: Yu Zhao <[email protected]>
-Date: Wed, 21 Dec 2022 21:19:02 -0700
-Subject: [PATCH 24/29] mm: multi-gen LRU: remove aging fairness safeguard
-
-Recall that the aging produces the youngest generation: first it scans
-for accessed pages and updates their gen counters; then it increments
-lrugen->max_seq.
-
-The current aging fairness safeguard for kswapd uses two passes to
-ensure the fairness to multiple eligible memcgs. On the first pass,
-which is shared with the eviction, it checks whether all eligible
-memcgs are low on cold pages. If so, it requires a second pass, on
-which it ages all those memcgs at the same time.
-
-With memcg LRU, the aging, while ensuring eventual fairness, will run
-when necessary. Therefore the current aging fairness safeguard for
-kswapd will not be needed.
-
-Note that memcg LRU only applies to global reclaim. For memcg reclaim,
-the aging can be unfair to different memcgs, i.e., their
-lrugen->max_seq can be incremented at different paces.
-
-Link: https://lkml.kernel.org/r/[email protected]
-Signed-off-by: Yu Zhao <[email protected]>
-Cc: Johannes Weiner <[email protected]>
-Cc: Jonathan Corbet <[email protected]>
-Cc: Michael Larabel <[email protected]>
-Cc: Michal Hocko <[email protected]>
-Cc: Mike Rapoport <[email protected]>
-Cc: Roman Gushchin <[email protected]>
-Cc: Suren Baghdasaryan <[email protected]>
-Signed-off-by: Andrew Morton <[email protected]>
----
- mm/vmscan.c | 126 ++++++++++++++++++++++++----------------------------
- 1 file changed, 59 insertions(+), 67 deletions(-)
-
---- a/mm/vmscan.c
-+++ b/mm/vmscan.c
-@@ -131,7 +131,6 @@ struct scan_control {
- #ifdef CONFIG_LRU_GEN
-       /* help kswapd make better choices among multiple memcgs */
--      unsigned int memcgs_need_aging:1;
-       unsigned long last_reclaimed;
- #endif
-@@ -4184,7 +4183,7 @@ done:
-       return true;
- }
--static bool should_run_aging(struct lruvec *lruvec, unsigned long max_seq, unsigned long *min_seq,
-+static bool should_run_aging(struct lruvec *lruvec, unsigned long max_seq,
-                            struct scan_control *sc, bool can_swap, unsigned long *nr_to_scan)
- {
-       int gen, type, zone;
-@@ -4193,6 +4192,13 @@ static bool should_run_aging(struct lruv
-       unsigned long total = 0;
-       struct lru_gen_page *lrugen = &lruvec->lrugen;
-       struct mem_cgroup *memcg = lruvec_memcg(lruvec);
-+      DEFINE_MIN_SEQ(lruvec);
-+
-+      /* whether this lruvec is completely out of cold pages */
-+      if (min_seq[!can_swap] + MIN_NR_GENS > max_seq) {
-+              *nr_to_scan = 0;
-+              return true;
-+      }
-       for (type = !can_swap; type < ANON_AND_FILE; type++) {
-               unsigned long seq;
-@@ -4221,8 +4227,6 @@ static bool should_run_aging(struct lruv
-        * stalls when the number of generations reaches MIN_NR_GENS. Hence, the
-        * ideal number of generations is MIN_NR_GENS+1.
-        */
--      if (min_seq[!can_swap] + MIN_NR_GENS > max_seq)
--              return true;
-       if (min_seq[!can_swap] + MIN_NR_GENS < max_seq)
-               return false;
-@@ -4241,40 +4245,54 @@ static bool should_run_aging(struct lruv
-       return false;
- }
--static bool age_lruvec(struct lruvec *lruvec, struct scan_control *sc, unsigned long min_ttl)
-+static bool lruvec_is_sizable(struct lruvec *lruvec, struct scan_control *sc)
- {
--      bool need_aging;
--      unsigned long nr_to_scan;
--      int swappiness = get_swappiness(lruvec, sc);
-+      int gen, type, zone;
-+      unsigned long total = 0;
-+      bool can_swap = get_swappiness(lruvec, sc);
-+      struct lru_gen_page *lrugen = &lruvec->lrugen;
-       struct mem_cgroup *memcg = lruvec_memcg(lruvec);
-       DEFINE_MAX_SEQ(lruvec);
-       DEFINE_MIN_SEQ(lruvec);
--      VM_WARN_ON_ONCE(sc->memcg_low_reclaim);
-+      for (type = !can_swap; type < ANON_AND_FILE; type++) {
-+              unsigned long seq;
--      mem_cgroup_calculate_protection(NULL, memcg);
-+              for (seq = min_seq[type]; seq <= max_seq; seq++) {
-+                      gen = lru_gen_from_seq(seq);
--      if (mem_cgroup_below_min(memcg))
--              return false;
-+                      for (zone = 0; zone < MAX_NR_ZONES; zone++)
-+                              total += max(READ_ONCE(lrugen->nr_pages[gen][type][zone]), 0L);
-+              }
-+      }
--      need_aging = should_run_aging(lruvec, max_seq, min_seq, sc, swappiness, &nr_to_scan);
-+      /* whether the size is big enough to be helpful */
-+      return mem_cgroup_online(memcg) ? (total >> sc->priority) : total;
-+}
--      if (min_ttl) {
--              int gen = lru_gen_from_seq(min_seq[LRU_GEN_FILE]);
--              unsigned long birth = READ_ONCE(lruvec->lrugen.timestamps[gen]);
-+static bool lruvec_is_reclaimable(struct lruvec *lruvec, struct scan_control *sc,
-+                                unsigned long min_ttl)
-+{
-+      int gen;
-+      unsigned long birth;
-+      struct mem_cgroup *memcg = lruvec_memcg(lruvec);
-+      DEFINE_MIN_SEQ(lruvec);
--              if (time_is_after_jiffies(birth + min_ttl))
--                      return false;
-+      VM_WARN_ON_ONCE(sc->memcg_low_reclaim);
--              /* the size is likely too small to be helpful */
--              if (!nr_to_scan && sc->priority != DEF_PRIORITY)
--                      return false;
--      }
-+      /* see the comment on lru_gen_page */
-+      gen = lru_gen_from_seq(min_seq[LRU_GEN_FILE]);
-+      birth = READ_ONCE(lruvec->lrugen.timestamps[gen]);
--      if (need_aging)
--              try_to_inc_max_seq(lruvec, max_seq, sc, swappiness, false);
-+      if (time_is_after_jiffies(birth + min_ttl))
-+              return false;
--      return true;
-+      if (!lruvec_is_sizable(lruvec, sc))
-+              return false;
-+
-+      mem_cgroup_calculate_protection(NULL, memcg);
-+
-+      return !mem_cgroup_below_min(memcg);
- }
- /* to protect the working set of the last N jiffies */
-@@ -4283,46 +4301,32 @@ static unsigned long lru_gen_min_ttl __r
- static void lru_gen_age_node(struct pglist_data *pgdat, struct scan_control *sc)
- {
-       struct mem_cgroup *memcg;
--      bool success = false;
-       unsigned long min_ttl = READ_ONCE(lru_gen_min_ttl);
-       VM_WARN_ON_ONCE(!current_is_kswapd());
-       sc->last_reclaimed = sc->nr_reclaimed;
--      /*
--       * To reduce the chance of going into the aging path, which can be
--       * costly, optimistically skip it if the flag below was cleared in the
--       * eviction path. This improves the overall performance when multiple
--       * memcgs are available.
--       */
--      if (!sc->memcgs_need_aging) {
--              sc->memcgs_need_aging = true;
-+      /* check the order to exclude compaction-induced reclaim */
-+      if (!min_ttl || sc->order || sc->priority == DEF_PRIORITY)
-               return;
--      }
--
--      set_mm_walk(pgdat);
-       memcg = mem_cgroup_iter(NULL, NULL, NULL);
-       do {
-               struct lruvec *lruvec = mem_cgroup_lruvec(memcg, pgdat);
--              if (age_lruvec(lruvec, sc, min_ttl))
--                      success = true;
-+              if (lruvec_is_reclaimable(lruvec, sc, min_ttl)) {
-+                      mem_cgroup_iter_break(NULL, memcg);
-+                      return;
-+              }
-               cond_resched();
-       } while ((memcg = mem_cgroup_iter(NULL, memcg, NULL)));
--      clear_mm_walk();
--
--      /* check the order to exclude compaction-induced reclaim */
--      if (success || !min_ttl || sc->order)
--              return;
--
-       /*
-        * The main goal is to OOM kill if every generation from all memcgs is
-        * younger than min_ttl. However, another possibility is all memcgs are
--       * either below min or empty.
-+       * either too small or below min.
-        */
-       if (mutex_trylock(&oom_lock)) {
-               struct oom_control oc = {
-@@ -4830,33 +4834,27 @@ retry:
-  *    reclaim.
-  */
- static unsigned long get_nr_to_scan(struct lruvec *lruvec, struct scan_control *sc,
--                                  bool can_swap, bool *need_aging)
-+                                  bool can_swap)
- {
-       unsigned long nr_to_scan;
-       struct mem_cgroup *memcg = lruvec_memcg(lruvec);
-       DEFINE_MAX_SEQ(lruvec);
--      DEFINE_MIN_SEQ(lruvec);
-       if (mem_cgroup_below_min(memcg) ||
-           (mem_cgroup_below_low(memcg) && !sc->memcg_low_reclaim))
-               return 0;
--      *need_aging = should_run_aging(lruvec, max_seq, min_seq, sc, can_swap, &nr_to_scan);
--      if (!*need_aging)
-+      if (!should_run_aging(lruvec, max_seq, sc, can_swap, &nr_to_scan))
-               return nr_to_scan;
-       /* skip the aging path at the default priority */
-       if (sc->priority == DEF_PRIORITY)
--              goto done;
-+              return nr_to_scan;
--      /* leave the work to lru_gen_age_node() */
--      if (current_is_kswapd())
--              return 0;
-+      try_to_inc_max_seq(lruvec, max_seq, sc, can_swap, false);
--      if (try_to_inc_max_seq(lruvec, max_seq, sc, can_swap, false))
--              return nr_to_scan;
--done:
--      return min_seq[!can_swap] + MIN_NR_GENS <= max_seq ? nr_to_scan : 0;
-+      /* skip this lruvec as it's low on cold pages */
-+      return 0;
- }
- static unsigned long get_nr_to_reclaim(struct scan_control *sc)
-@@ -4875,9 +4873,7 @@ static unsigned long get_nr_to_reclaim(s
- static void lru_gen_shrink_lruvec(struct lruvec *lruvec, struct scan_control *sc)
- {
-       struct blk_plug plug;
--      bool need_aging = false;
-       unsigned long scanned = 0;
--      unsigned long reclaimed = sc->nr_reclaimed;
-       unsigned long nr_to_reclaim = get_nr_to_reclaim(sc);
-       lru_add_drain();
-@@ -4898,13 +4894,13 @@ static void lru_gen_shrink_lruvec(struct
-               else
-                       swappiness = 0;
--              nr_to_scan = get_nr_to_scan(lruvec, sc, swappiness, &need_aging);
-+              nr_to_scan = get_nr_to_scan(lruvec, sc, swappiness);
-               if (!nr_to_scan)
--                      goto done;
-+                      break;
-               delta = evict_pages(lruvec, sc, swappiness);
-               if (!delta)
--                      goto done;
-+                      break;
-               scanned += delta;
-               if (scanned >= nr_to_scan)
-@@ -4916,10 +4912,6 @@ static void lru_gen_shrink_lruvec(struct
-               cond_resched();
-       }
--      /* see the comment in lru_gen_age_node() */
--      if (sc->nr_reclaimed - reclaimed >= MIN_LRU_BATCH && !need_aging)
--              sc->memcgs_need_aging = false;
--done:
-       clear_mm_walk();
-       blk_finish_plug(&plug);
diff --git a/target/linux/generic/backport-5.15/020-v6.3-25-mm-multi-gen-LRU-shuffle-should_run_aging.patch b/target/linux/generic/backport-5.15/020-v6.3-25-mm-multi-gen-LRU-shuffle-should_run_aging.patch
deleted file mode 100644 (file)
index 391ee6e..0000000
+++ /dev/null
@@ -1,161 +0,0 @@
-From 107d54931df3c28d81648122e219bf0034ef4e99 Mon Sep 17 00:00:00 2001
-From: Yu Zhao <[email protected]>
-Date: Wed, 21 Dec 2022 21:19:03 -0700
-Subject: [PATCH 25/29] mm: multi-gen LRU: shuffle should_run_aging()
-
-Move should_run_aging() next to its only caller left.
-
-Link: https://lkml.kernel.org/r/[email protected]
-Signed-off-by: Yu Zhao <[email protected]>
-Cc: Johannes Weiner <[email protected]>
-Cc: Jonathan Corbet <[email protected]>
-Cc: Michael Larabel <[email protected]>
-Cc: Michal Hocko <[email protected]>
-Cc: Mike Rapoport <[email protected]>
-Cc: Roman Gushchin <[email protected]>
-Cc: Suren Baghdasaryan <[email protected]>
-Signed-off-by: Andrew Morton <[email protected]>
----
- mm/vmscan.c | 124 ++++++++++++++++++++++++++--------------------------
- 1 file changed, 62 insertions(+), 62 deletions(-)
-
---- a/mm/vmscan.c
-+++ b/mm/vmscan.c
-@@ -4183,68 +4183,6 @@ done:
-       return true;
- }
--static bool should_run_aging(struct lruvec *lruvec, unsigned long max_seq,
--                           struct scan_control *sc, bool can_swap, unsigned long *nr_to_scan)
--{
--      int gen, type, zone;
--      unsigned long old = 0;
--      unsigned long young = 0;
--      unsigned long total = 0;
--      struct lru_gen_page *lrugen = &lruvec->lrugen;
--      struct mem_cgroup *memcg = lruvec_memcg(lruvec);
--      DEFINE_MIN_SEQ(lruvec);
--
--      /* whether this lruvec is completely out of cold pages */
--      if (min_seq[!can_swap] + MIN_NR_GENS > max_seq) {
--              *nr_to_scan = 0;
--              return true;
--      }
--
--      for (type = !can_swap; type < ANON_AND_FILE; type++) {
--              unsigned long seq;
--
--              for (seq = min_seq[type]; seq <= max_seq; seq++) {
--                      unsigned long size = 0;
--
--                      gen = lru_gen_from_seq(seq);
--
--                      for (zone = 0; zone < MAX_NR_ZONES; zone++)
--                              size += max(READ_ONCE(lrugen->nr_pages[gen][type][zone]), 0L);
--
--                      total += size;
--                      if (seq == max_seq)
--                              young += size;
--                      else if (seq + MIN_NR_GENS == max_seq)
--                              old += size;
--              }
--      }
--
--      /* try to scrape all its memory if this memcg was deleted */
--      *nr_to_scan = mem_cgroup_online(memcg) ? (total >> sc->priority) : total;
--
--      /*
--       * The aging tries to be lazy to reduce the overhead, while the eviction
--       * stalls when the number of generations reaches MIN_NR_GENS. Hence, the
--       * ideal number of generations is MIN_NR_GENS+1.
--       */
--      if (min_seq[!can_swap] + MIN_NR_GENS < max_seq)
--              return false;
--
--      /*
--       * It's also ideal to spread pages out evenly, i.e., 1/(MIN_NR_GENS+1)
--       * of the total number of pages for each generation. A reasonable range
--       * for this average portion is [1/MIN_NR_GENS, 1/(MIN_NR_GENS+2)]. The
--       * aging cares about the upper bound of hot pages, while the eviction
--       * cares about the lower bound of cold pages.
--       */
--      if (young * MIN_NR_GENS > total)
--              return true;
--      if (old * (MIN_NR_GENS + 2) < total)
--              return true;
--
--      return false;
--}
--
- static bool lruvec_is_sizable(struct lruvec *lruvec, struct scan_control *sc)
- {
-       int gen, type, zone;
-@@ -4828,6 +4766,68 @@ retry:
-       return scanned;
- }
-+static bool should_run_aging(struct lruvec *lruvec, unsigned long max_seq,
-+                           struct scan_control *sc, bool can_swap, unsigned long *nr_to_scan)
-+{
-+      int gen, type, zone;
-+      unsigned long old = 0;
-+      unsigned long young = 0;
-+      unsigned long total = 0;
-+      struct lru_gen_page *lrugen = &lruvec->lrugen;
-+      struct mem_cgroup *memcg = lruvec_memcg(lruvec);
-+      DEFINE_MIN_SEQ(lruvec);
-+
-+      /* whether this lruvec is completely out of cold pages */
-+      if (min_seq[!can_swap] + MIN_NR_GENS > max_seq) {
-+              *nr_to_scan = 0;
-+              return true;
-+      }
-+
-+      for (type = !can_swap; type < ANON_AND_FILE; type++) {
-+              unsigned long seq;
-+
-+              for (seq = min_seq[type]; seq <= max_seq; seq++) {
-+                      unsigned long size = 0;
-+
-+                      gen = lru_gen_from_seq(seq);
-+
-+                      for (zone = 0; zone < MAX_NR_ZONES; zone++)
-+                              size += max(READ_ONCE(lrugen->nr_pages[gen][type][zone]), 0L);
-+
-+                      total += size;
-+                      if (seq == max_seq)
-+                              young += size;
-+                      else if (seq + MIN_NR_GENS == max_seq)
-+                              old += size;
-+              }
-+      }
-+
-+      /* try to scrape all its memory if this memcg was deleted */
-+      *nr_to_scan = mem_cgroup_online(memcg) ? (total >> sc->priority) : total;
-+
-+      /*
-+       * The aging tries to be lazy to reduce the overhead, while the eviction
-+       * stalls when the number of generations reaches MIN_NR_GENS. Hence, the
-+       * ideal number of generations is MIN_NR_GENS+1.
-+       */
-+      if (min_seq[!can_swap] + MIN_NR_GENS < max_seq)
-+              return false;
-+
-+      /*
-+       * It's also ideal to spread pages out evenly, i.e., 1/(MIN_NR_GENS+1)
-+       * of the total number of pages for each generation. A reasonable range
-+       * for this average portion is [1/MIN_NR_GENS, 1/(MIN_NR_GENS+2)]. The
-+       * aging cares about the upper bound of hot pages, while the eviction
-+       * cares about the lower bound of cold pages.
-+       */
-+      if (young * MIN_NR_GENS > total)
-+              return true;
-+      if (old * (MIN_NR_GENS + 2) < total)
-+              return true;
-+
-+      return false;
-+}
-+
- /*
-  * For future optimizations:
-  * 1. Defer try_to_inc_max_seq() to workqueues to reduce latency for memcg
diff --git a/target/linux/generic/backport-5.15/020-v6.3-26-mm-multi-gen-LRU-per-node-lru_gen_page-lists.patch b/target/linux/generic/backport-5.15/020-v6.3-26-mm-multi-gen-LRU-per-node-lru_gen_page-lists.patch
deleted file mode 100644 (file)
index cfeeaa6..0000000
+++ /dev/null
@@ -1,868 +0,0 @@
-From fa6363828d314e837c5f79e97ea5e8c0d2f7f062 Mon Sep 17 00:00:00 2001
-From: Yu Zhao <[email protected]>
-Date: Wed, 21 Dec 2022 21:19:04 -0700
-Subject: [PATCH 26/29] mm: multi-gen LRU: per-node lru_gen_page lists
-
-For each node, memcgs are divided into two generations: the old and
-the young. For each generation, memcgs are randomly sharded into
-multiple bins to improve scalability. For each bin, an RCU hlist_nulls
-is virtually divided into three segments: the head, the tail and the
-default.
-
-An onlining memcg is added to the tail of a random bin in the old
-generation. The eviction starts at the head of a random bin in the old
-generation. The per-node memcg generation counter, whose reminder (mod
-2) indexes the old generation, is incremented when all its bins become
-empty.
-
-There are four operations:
-1. MEMCG_LRU_HEAD, which moves an memcg to the head of a random bin in
-   its current generation (old or young) and updates its "seg" to
-   "head";
-2. MEMCG_LRU_TAIL, which moves an memcg to the tail of a random bin in
-   its current generation (old or young) and updates its "seg" to
-   "tail";
-3. MEMCG_LRU_OLD, which moves an memcg to the head of a random bin in
-   the old generation, updates its "gen" to "old" and resets its "seg"
-   to "default";
-4. MEMCG_LRU_YOUNG, which moves an memcg to the tail of a random bin
-   in the young generation, updates its "gen" to "young" and resets
-   its "seg" to "default".
-
-The events that trigger the above operations are:
-1. Exceeding the soft limit, which triggers MEMCG_LRU_HEAD;
-2. The first attempt to reclaim an memcg below low, which triggers
-   MEMCG_LRU_TAIL;
-3. The first attempt to reclaim an memcg below reclaimable size
-   threshold, which triggers MEMCG_LRU_TAIL;
-4. The second attempt to reclaim an memcg below reclaimable size
-   threshold, which triggers MEMCG_LRU_YOUNG;
-5. Attempting to reclaim an memcg below min, which triggers
-   MEMCG_LRU_YOUNG;
-6. Finishing the aging on the eviction path, which triggers
-   MEMCG_LRU_YOUNG;
-7. Offlining an memcg, which triggers MEMCG_LRU_OLD.
-
-Note that memcg LRU only applies to global reclaim, and the
-round-robin incrementing of their max_seq counters ensures the
-eventual fairness to all eligible memcgs. For memcg reclaim, it still
-relies on mem_cgroup_iter().
-
-Link: https://lkml.kernel.org/r/[email protected]
-Signed-off-by: Yu Zhao <[email protected]>
-Cc: Johannes Weiner <[email protected]>
-Cc: Jonathan Corbet <[email protected]>
-Cc: Michael Larabel <[email protected]>
-Cc: Michal Hocko <[email protected]>
-Cc: Mike Rapoport <[email protected]>
-Cc: Roman Gushchin <[email protected]>
-Cc: Suren Baghdasaryan <[email protected]>
-Signed-off-by: Andrew Morton <[email protected]>
----
- include/linux/memcontrol.h |  10 +
- include/linux/mm_inline.h  |  17 ++
- include/linux/mmzone.h     | 117 +++++++++++-
- mm/memcontrol.c            |  16 ++
- mm/page_alloc.c            |   1 +
- mm/vmscan.c                | 373 +++++++++++++++++++++++++++++++++----
- 6 files changed, 499 insertions(+), 35 deletions(-)
-
---- a/include/linux/memcontrol.h
-+++ b/include/linux/memcontrol.h
-@@ -823,6 +823,11 @@ static inline void obj_cgroup_put(struct
-       percpu_ref_put(&objcg->refcnt);
- }
-+static inline bool mem_cgroup_tryget(struct mem_cgroup *memcg)
-+{
-+      return !memcg || css_tryget(&memcg->css);
-+}
-+
- static inline void mem_cgroup_put(struct mem_cgroup *memcg)
- {
-       if (memcg)
-@@ -1288,6 +1293,11 @@ struct mem_cgroup *mem_cgroup_from_css(s
-       return NULL;
- }
-+static inline bool mem_cgroup_tryget(struct mem_cgroup *memcg)
-+{
-+      return true;
-+}
-+
- static inline void mem_cgroup_put(struct mem_cgroup *memcg)
- {
- }
---- a/include/linux/mm_inline.h
-+++ b/include/linux/mm_inline.h
-@@ -112,6 +112,18 @@ static inline bool lru_gen_in_fault(void
-       return current->in_lru_fault;
- }
-+#ifdef CONFIG_MEMCG
-+static inline int lru_gen_memcg_seg(struct lruvec *lruvec)
-+{
-+      return READ_ONCE(lruvec->lrugen.seg);
-+}
-+#else
-+static inline int lru_gen_memcg_seg(struct lruvec *lruvec)
-+{
-+      return 0;
-+}
-+#endif
-+
- static inline int lru_gen_from_seq(unsigned long seq)
- {
-       return seq % MAX_NR_GENS;
-@@ -287,6 +299,11 @@ static inline bool lru_gen_in_fault(void
-       return false;
- }
-+static inline int lru_gen_memcg_seg(struct lruvec *lruvec)
-+{
-+      return 0;
-+}
-+
- static inline bool lru_gen_add_page(struct lruvec *lruvec, struct page *page, bool reclaiming)
- {
-       return false;
---- a/include/linux/mmzone.h
-+++ b/include/linux/mmzone.h
-@@ -7,6 +7,7 @@
- #include <linux/spinlock.h>
- #include <linux/list.h>
-+#include <linux/list_nulls.h>
- #include <linux/wait.h>
- #include <linux/bitops.h>
- #include <linux/cache.h>
-@@ -357,6 +358,15 @@ struct page_vma_mapped_walk;
- #define LRU_GEN_MASK          ((BIT(LRU_GEN_WIDTH) - 1) << LRU_GEN_PGOFF)
- #define LRU_REFS_MASK         ((BIT(LRU_REFS_WIDTH) - 1) << LRU_REFS_PGOFF)
-+/* see the comment on MEMCG_NR_GENS */
-+enum {
-+      MEMCG_LRU_NOP,
-+      MEMCG_LRU_HEAD,
-+      MEMCG_LRU_TAIL,
-+      MEMCG_LRU_OLD,
-+      MEMCG_LRU_YOUNG,
-+};
-+
- #ifdef CONFIG_LRU_GEN
- enum {
-@@ -416,6 +426,14 @@ struct lru_gen_page {
-       atomic_long_t refaulted[NR_HIST_GENS][ANON_AND_FILE][MAX_NR_TIERS];
-       /* whether the multi-gen LRU is enabled */
-       bool enabled;
-+#ifdef CONFIG_MEMCG
-+      /* the memcg generation this lru_gen_page belongs to */
-+      u8 gen;
-+      /* the list segment this lru_gen_page belongs to */
-+      u8 seg;
-+      /* per-node lru_gen_page list for global reclaim */
-+      struct hlist_nulls_node list;
-+#endif
- };
- enum {
-@@ -469,12 +487,87 @@ void lru_gen_init_lruvec(struct lruvec *
- void lru_gen_look_around(struct page_vma_mapped_walk *pvmw);
- #ifdef CONFIG_MEMCG
-+
-+/*
-+ * For each node, memcgs are divided into two generations: the old and the
-+ * young. For each generation, memcgs are randomly sharded into multiple bins
-+ * to improve scalability. For each bin, the hlist_nulls is virtually divided
-+ * into three segments: the head, the tail and the default.
-+ *
-+ * An onlining memcg is added to the tail of a random bin in the old generation.
-+ * The eviction starts at the head of a random bin in the old generation. The
-+ * per-node memcg generation counter, whose reminder (mod MEMCG_NR_GENS) indexes
-+ * the old generation, is incremented when all its bins become empty.
-+ *
-+ * There are four operations:
-+ * 1. MEMCG_LRU_HEAD, which moves an memcg to the head of a random bin in its
-+ *    current generation (old or young) and updates its "seg" to "head";
-+ * 2. MEMCG_LRU_TAIL, which moves an memcg to the tail of a random bin in its
-+ *    current generation (old or young) and updates its "seg" to "tail";
-+ * 3. MEMCG_LRU_OLD, which moves an memcg to the head of a random bin in the old
-+ *    generation, updates its "gen" to "old" and resets its "seg" to "default";
-+ * 4. MEMCG_LRU_YOUNG, which moves an memcg to the tail of a random bin in the
-+ *    young generation, updates its "gen" to "young" and resets its "seg" to
-+ *    "default".
-+ *
-+ * The events that trigger the above operations are:
-+ * 1. Exceeding the soft limit, which triggers MEMCG_LRU_HEAD;
-+ * 2. The first attempt to reclaim an memcg below low, which triggers
-+ *    MEMCG_LRU_TAIL;
-+ * 3. The first attempt to reclaim an memcg below reclaimable size threshold,
-+ *    which triggers MEMCG_LRU_TAIL;
-+ * 4. The second attempt to reclaim an memcg below reclaimable size threshold,
-+ *    which triggers MEMCG_LRU_YOUNG;
-+ * 5. Attempting to reclaim an memcg below min, which triggers MEMCG_LRU_YOUNG;
-+ * 6. Finishing the aging on the eviction path, which triggers MEMCG_LRU_YOUNG;
-+ * 7. Offlining an memcg, which triggers MEMCG_LRU_OLD.
-+ *
-+ * Note that memcg LRU only applies to global reclaim, and the round-robin
-+ * incrementing of their max_seq counters ensures the eventual fairness to all
-+ * eligible memcgs. For memcg reclaim, it still relies on mem_cgroup_iter().
-+ */
-+#define MEMCG_NR_GENS 2
-+#define MEMCG_NR_BINS 8
-+
-+struct lru_gen_memcg {
-+      /* the per-node memcg generation counter */
-+      unsigned long seq;
-+      /* each memcg has one lru_gen_page per node */
-+      unsigned long nr_memcgs[MEMCG_NR_GENS];
-+      /* per-node lru_gen_page list for global reclaim */
-+      struct hlist_nulls_head fifo[MEMCG_NR_GENS][MEMCG_NR_BINS];
-+      /* protects the above */
-+      spinlock_t lock;
-+};
-+
-+void lru_gen_init_pgdat(struct pglist_data *pgdat);
-+
- void lru_gen_init_memcg(struct mem_cgroup *memcg);
- void lru_gen_exit_memcg(struct mem_cgroup *memcg);
--#endif
-+void lru_gen_online_memcg(struct mem_cgroup *memcg);
-+void lru_gen_offline_memcg(struct mem_cgroup *memcg);
-+void lru_gen_release_memcg(struct mem_cgroup *memcg);
-+void lru_gen_rotate_memcg(struct lruvec *lruvec, int op);
-+
-+#else /* !CONFIG_MEMCG */
-+
-+#define MEMCG_NR_GENS 1
-+
-+struct lru_gen_memcg {
-+};
-+
-+static inline void lru_gen_init_pgdat(struct pglist_data *pgdat)
-+{
-+}
-+
-+#endif /* CONFIG_MEMCG */
- #else /* !CONFIG_LRU_GEN */
-+static inline void lru_gen_init_pgdat(struct pglist_data *pgdat)
-+{
-+}
-+
- static inline void lru_gen_init_lruvec(struct lruvec *lruvec)
- {
- }
-@@ -484,6 +577,7 @@ static inline void lru_gen_look_around(s
- }
- #ifdef CONFIG_MEMCG
-+
- static inline void lru_gen_init_memcg(struct mem_cgroup *memcg)
- {
- }
-@@ -491,7 +585,24 @@ static inline void lru_gen_init_memcg(st
- static inline void lru_gen_exit_memcg(struct mem_cgroup *memcg)
- {
- }
--#endif
-+
-+static inline void lru_gen_online_memcg(struct mem_cgroup *memcg)
-+{
-+}
-+
-+static inline void lru_gen_offline_memcg(struct mem_cgroup *memcg)
-+{
-+}
-+
-+static inline void lru_gen_release_memcg(struct mem_cgroup *memcg)
-+{
-+}
-+
-+static inline void lru_gen_rotate_memcg(struct lruvec *lruvec, int op)
-+{
-+}
-+
-+#endif /* CONFIG_MEMCG */
- #endif /* CONFIG_LRU_GEN */
-@@ -1105,6 +1216,8 @@ typedef struct pglist_data {
- #ifdef CONFIG_LRU_GEN
-       /* kswap mm walk data */
-       struct lru_gen_mm_walk  mm_walk;
-+      /* lru_gen_page list */
-+      struct lru_gen_memcg memcg_lru;
- #endif
-       ZONE_PADDING(_pad2_)
---- a/mm/memcontrol.c
-+++ b/mm/memcontrol.c
-@@ -549,6 +549,16 @@ static void mem_cgroup_update_tree(struc
-       struct mem_cgroup_per_node *mz;
-       struct mem_cgroup_tree_per_node *mctz;
-+      if (lru_gen_enabled()) {
-+              struct lruvec *lruvec = &mem_cgroup_page_nodeinfo(memcg, page)->lruvec;
-+
-+              /* see the comment on MEMCG_NR_GENS */
-+              if (soft_limit_excess(memcg) && lru_gen_memcg_seg(lruvec) != MEMCG_LRU_HEAD)
-+                      lru_gen_rotate_memcg(lruvec, MEMCG_LRU_HEAD);
-+
-+              return;
-+      }
-+
-       mctz = soft_limit_tree_from_page(page);
-       if (!mctz)
-               return;
-@@ -3434,6 +3444,9 @@ unsigned long mem_cgroup_soft_limit_recl
-       unsigned long excess;
-       unsigned long nr_scanned;
-+      if (lru_gen_enabled())
-+              return 0;
-+
-       if (order > 0)
-               return 0;
-@@ -5322,6 +5335,7 @@ static int mem_cgroup_css_online(struct
-       if (unlikely(mem_cgroup_is_root(memcg)))
-               queue_delayed_work(system_unbound_wq, &stats_flush_dwork,
-                                  2UL*HZ);
-+      lru_gen_online_memcg(memcg);
-       return 0;
- }
-@@ -5348,6 +5362,7 @@ static void mem_cgroup_css_offline(struc
-       memcg_offline_kmem(memcg);
-       reparent_shrinker_deferred(memcg);
-       wb_memcg_offline(memcg);
-+      lru_gen_offline_memcg(memcg);
-       drain_all_stock(memcg);
-@@ -5359,6 +5374,7 @@ static void mem_cgroup_css_released(stru
-       struct mem_cgroup *memcg = mem_cgroup_from_css(css);
-       invalidate_reclaim_iterators(memcg);
-+      lru_gen_release_memcg(memcg);
- }
- static void mem_cgroup_css_free(struct cgroup_subsys_state *css)
---- a/mm/page_alloc.c
-+++ b/mm/page_alloc.c
-@@ -7663,6 +7663,7 @@ static void __init free_area_init_node(i
-       pgdat_set_deferred_range(pgdat);
-       free_area_init_core(pgdat);
-+      lru_gen_init_pgdat(pgdat);
- }
- void __init free_area_init_memoryless_node(int nid)
---- a/mm/vmscan.c
-+++ b/mm/vmscan.c
-@@ -54,6 +54,8 @@
- #include <linux/shmem_fs.h>
- #include <linux/ctype.h>
- #include <linux/debugfs.h>
-+#include <linux/rculist_nulls.h>
-+#include <linux/random.h>
- #include <asm/tlbflush.h>
- #include <asm/div64.h>
-@@ -129,11 +131,6 @@ struct scan_control {
-       /* Always discard instead of demoting to lower tier memory */
-       unsigned int no_demotion:1;
--#ifdef CONFIG_LRU_GEN
--      /* help kswapd make better choices among multiple memcgs */
--      unsigned long last_reclaimed;
--#endif
--
-       /* Allocation order */
-       s8 order;
-@@ -2880,6 +2877,9 @@ DEFINE_STATIC_KEY_ARRAY_FALSE(lru_gen_ca
-               for ((type) = 0; (type) < ANON_AND_FILE; (type)++)      \
-                       for ((zone) = 0; (zone) < MAX_NR_ZONES; (zone)++)
-+#define get_memcg_gen(seq)    ((seq) % MEMCG_NR_GENS)
-+#define get_memcg_bin(bin)    ((bin) % MEMCG_NR_BINS)
-+
- static struct lruvec *get_lruvec(struct mem_cgroup *memcg, int nid)
- {
-       struct pglist_data *pgdat = NODE_DATA(nid);
-@@ -4169,8 +4169,7 @@ done:
-               if (sc->priority <= DEF_PRIORITY - 2)
-                       wait_event_killable(lruvec->mm_state.wait,
-                                           max_seq < READ_ONCE(lrugen->max_seq));
--
--              return max_seq < READ_ONCE(lrugen->max_seq);
-+              return false;
-       }
-       VM_WARN_ON_ONCE(max_seq != READ_ONCE(lrugen->max_seq));
-@@ -4243,8 +4242,6 @@ static void lru_gen_age_node(struct pgli
-       VM_WARN_ON_ONCE(!current_is_kswapd());
--      sc->last_reclaimed = sc->nr_reclaimed;
--
-       /* check the order to exclude compaction-induced reclaim */
-       if (!min_ttl || sc->order || sc->priority == DEF_PRIORITY)
-               return;
-@@ -4833,8 +4830,7 @@ static bool should_run_aging(struct lruv
-  * 1. Defer try_to_inc_max_seq() to workqueues to reduce latency for memcg
-  *    reclaim.
-  */
--static unsigned long get_nr_to_scan(struct lruvec *lruvec, struct scan_control *sc,
--                                  bool can_swap)
-+static long get_nr_to_scan(struct lruvec *lruvec, struct scan_control *sc, bool can_swap)
- {
-       unsigned long nr_to_scan;
-       struct mem_cgroup *memcg = lruvec_memcg(lruvec);
-@@ -4851,10 +4847,8 @@ static unsigned long get_nr_to_scan(stru
-       if (sc->priority == DEF_PRIORITY)
-               return nr_to_scan;
--      try_to_inc_max_seq(lruvec, max_seq, sc, can_swap, false);
--
-       /* skip this lruvec as it's low on cold pages */
--      return 0;
-+      return try_to_inc_max_seq(lruvec, max_seq, sc, can_swap, false) ? -1 : 0;
- }
- static unsigned long get_nr_to_reclaim(struct scan_control *sc)
-@@ -4863,29 +4857,18 @@ static unsigned long get_nr_to_reclaim(s
-       if (!global_reclaim(sc))
-               return -1;
--      /* discount the previous progress for kswapd */
--      if (current_is_kswapd())
--              return sc->nr_to_reclaim + sc->last_reclaimed;
--
-       return max(sc->nr_to_reclaim, compact_gap(sc->order));
- }
--static void lru_gen_shrink_lruvec(struct lruvec *lruvec, struct scan_control *sc)
-+static bool try_to_shrink_lruvec(struct lruvec *lruvec, struct scan_control *sc)
- {
--      struct blk_plug plug;
-+      long nr_to_scan;
-       unsigned long scanned = 0;
-       unsigned long nr_to_reclaim = get_nr_to_reclaim(sc);
--      lru_add_drain();
--
--      blk_start_plug(&plug);
--
--      set_mm_walk(lruvec_pgdat(lruvec));
--
-       while (true) {
-               int delta;
-               int swappiness;
--              unsigned long nr_to_scan;
-               if (sc->may_swap)
-                       swappiness = get_swappiness(lruvec, sc);
-@@ -4895,7 +4878,7 @@ static void lru_gen_shrink_lruvec(struct
-                       swappiness = 0;
-               nr_to_scan = get_nr_to_scan(lruvec, sc, swappiness);
--              if (!nr_to_scan)
-+              if (nr_to_scan <= 0)
-                       break;
-               delta = evict_pages(lruvec, sc, swappiness);
-@@ -4912,10 +4895,250 @@ static void lru_gen_shrink_lruvec(struct
-               cond_resched();
-       }
-+      /* whether try_to_inc_max_seq() was successful */
-+      return nr_to_scan < 0;
-+}
-+
-+static int shrink_one(struct lruvec *lruvec, struct scan_control *sc)
-+{
-+      bool success;
-+      unsigned long scanned = sc->nr_scanned;
-+      unsigned long reclaimed = sc->nr_reclaimed;
-+      int seg = lru_gen_memcg_seg(lruvec);
-+      struct mem_cgroup *memcg = lruvec_memcg(lruvec);
-+      struct pglist_data *pgdat = lruvec_pgdat(lruvec);
-+
-+      /* see the comment on MEMCG_NR_GENS */
-+      if (!lruvec_is_sizable(lruvec, sc))
-+              return seg != MEMCG_LRU_TAIL ? MEMCG_LRU_TAIL : MEMCG_LRU_YOUNG;
-+
-+      mem_cgroup_calculate_protection(NULL, memcg);
-+
-+      if (mem_cgroup_below_min(memcg))
-+              return MEMCG_LRU_YOUNG;
-+
-+      if (mem_cgroup_below_low(memcg)) {
-+              /* see the comment on MEMCG_NR_GENS */
-+              if (seg != MEMCG_LRU_TAIL)
-+                      return MEMCG_LRU_TAIL;
-+
-+              memcg_memory_event(memcg, MEMCG_LOW);
-+      }
-+
-+      success = try_to_shrink_lruvec(lruvec, sc);
-+
-+      shrink_slab(sc->gfp_mask, pgdat->node_id, memcg, sc->priority);
-+
-+      vmpressure(sc->gfp_mask, memcg, false, sc->nr_scanned - scanned,
-+                 sc->nr_reclaimed - reclaimed);
-+
-+      sc->nr_reclaimed += current->reclaim_state->reclaimed_slab;
-+      current->reclaim_state->reclaimed_slab = 0;
-+
-+      return success ? MEMCG_LRU_YOUNG : 0;
-+}
-+
-+#ifdef CONFIG_MEMCG
-+
-+static void shrink_many(struct pglist_data *pgdat, struct scan_control *sc)
-+{
-+      int gen;
-+      int bin;
-+      int first_bin;
-+      struct lruvec *lruvec;
-+      struct lru_gen_page *lrugen;
-+      const struct hlist_nulls_node *pos;
-+      int op = 0;
-+      struct mem_cgroup *memcg = NULL;
-+      unsigned long nr_to_reclaim = get_nr_to_reclaim(sc);
-+
-+      bin = first_bin = prandom_u32_max(MEMCG_NR_BINS);
-+restart:
-+      gen = get_memcg_gen(READ_ONCE(pgdat->memcg_lru.seq));
-+
-+      rcu_read_lock();
-+
-+      hlist_nulls_for_each_entry_rcu(lrugen, pos, &pgdat->memcg_lru.fifo[gen][bin], list) {
-+              if (op)
-+                      lru_gen_rotate_memcg(lruvec, op);
-+
-+              mem_cgroup_put(memcg);
-+
-+              lruvec = container_of(lrugen, struct lruvec, lrugen);
-+              memcg = lruvec_memcg(lruvec);
-+
-+              if (!mem_cgroup_tryget(memcg)) {
-+                      op = 0;
-+                      memcg = NULL;
-+                      continue;
-+              }
-+
-+              rcu_read_unlock();
-+
-+              op = shrink_one(lruvec, sc);
-+
-+              if (sc->nr_reclaimed >= nr_to_reclaim)
-+                      goto success;
-+
-+              rcu_read_lock();
-+      }
-+
-+      rcu_read_unlock();
-+
-+      /* restart if raced with lru_gen_rotate_memcg() */
-+      if (gen != get_nulls_value(pos))
-+              goto restart;
-+
-+      /* try the rest of the bins of the current generation */
-+      bin = get_memcg_bin(bin + 1);
-+      if (bin != first_bin)
-+              goto restart;
-+success:
-+      if (op)
-+              lru_gen_rotate_memcg(lruvec, op);
-+
-+      mem_cgroup_put(memcg);
-+}
-+
-+static void lru_gen_shrink_lruvec(struct lruvec *lruvec, struct scan_control *sc)
-+{
-+      struct blk_plug plug;
-+
-+      VM_WARN_ON_ONCE(global_reclaim(sc));
-+
-+      lru_add_drain();
-+
-+      blk_start_plug(&plug);
-+
-+      set_mm_walk(lruvec_pgdat(lruvec));
-+
-+      if (try_to_shrink_lruvec(lruvec, sc))
-+              lru_gen_rotate_memcg(lruvec, MEMCG_LRU_YOUNG);
-+
-+      clear_mm_walk();
-+
-+      blk_finish_plug(&plug);
-+}
-+
-+#else /* !CONFIG_MEMCG */
-+
-+static void shrink_many(struct pglist_data *pgdat, struct scan_control *sc)
-+{
-+      BUILD_BUG();
-+}
-+
-+static void lru_gen_shrink_lruvec(struct lruvec *lruvec, struct scan_control *sc)
-+{
-+      BUILD_BUG();
-+}
-+
-+#endif
-+
-+static void set_initial_priority(struct pglist_data *pgdat, struct scan_control *sc)
-+{
-+      int priority;
-+      unsigned long reclaimable;
-+      struct lruvec *lruvec = mem_cgroup_lruvec(NULL, pgdat);
-+
-+      if (sc->priority != DEF_PRIORITY || sc->nr_to_reclaim < MIN_LRU_BATCH)
-+              return;
-+      /*
-+       * Determine the initial priority based on ((total / MEMCG_NR_GENS) >>
-+       * priority) * reclaimed_to_scanned_ratio = nr_to_reclaim, where the
-+       * estimated reclaimed_to_scanned_ratio = inactive / total.
-+       */
-+      reclaimable = node_page_state(pgdat, NR_INACTIVE_FILE);
-+      if (get_swappiness(lruvec, sc))
-+              reclaimable += node_page_state(pgdat, NR_INACTIVE_ANON);
-+
-+      reclaimable /= MEMCG_NR_GENS;
-+
-+      /* round down reclaimable and round up sc->nr_to_reclaim */
-+      priority = fls_long(reclaimable) - 1 - fls_long(sc->nr_to_reclaim - 1);
-+
-+      sc->priority = clamp(priority, 0, DEF_PRIORITY);
-+}
-+
-+static void lru_gen_shrink_node(struct pglist_data *pgdat, struct scan_control *sc)
-+{
-+      struct blk_plug plug;
-+      unsigned long reclaimed = sc->nr_reclaimed;
-+
-+      VM_WARN_ON_ONCE(!global_reclaim(sc));
-+
-+      lru_add_drain();
-+
-+      blk_start_plug(&plug);
-+
-+      set_mm_walk(pgdat);
-+
-+      set_initial_priority(pgdat, sc);
-+
-+      if (current_is_kswapd())
-+              sc->nr_reclaimed = 0;
-+
-+      if (mem_cgroup_disabled())
-+              shrink_one(&pgdat->__lruvec, sc);
-+      else
-+              shrink_many(pgdat, sc);
-+
-+      if (current_is_kswapd())
-+              sc->nr_reclaimed += reclaimed;
-+
-       clear_mm_walk();
-       blk_finish_plug(&plug);
-+
-+      /* kswapd should never fail */
-+      pgdat->kswapd_failures = 0;
-+}
-+
-+#ifdef CONFIG_MEMCG
-+void lru_gen_rotate_memcg(struct lruvec *lruvec, int op)
-+{
-+      int seg;
-+      int old, new;
-+      int bin = prandom_u32_max(MEMCG_NR_BINS);
-+      struct pglist_data *pgdat = lruvec_pgdat(lruvec);
-+
-+      spin_lock(&pgdat->memcg_lru.lock);
-+
-+      VM_WARN_ON_ONCE(hlist_nulls_unhashed(&lruvec->lrugen.list));
-+
-+      seg = 0;
-+      new = old = lruvec->lrugen.gen;
-+
-+      /* see the comment on MEMCG_NR_GENS */
-+      if (op == MEMCG_LRU_HEAD)
-+              seg = MEMCG_LRU_HEAD;
-+      else if (op == MEMCG_LRU_TAIL)
-+              seg = MEMCG_LRU_TAIL;
-+      else if (op == MEMCG_LRU_OLD)
-+              new = get_memcg_gen(pgdat->memcg_lru.seq);
-+      else if (op == MEMCG_LRU_YOUNG)
-+              new = get_memcg_gen(pgdat->memcg_lru.seq + 1);
-+      else
-+              VM_WARN_ON_ONCE(true);
-+
-+      hlist_nulls_del_rcu(&lruvec->lrugen.list);
-+
-+      if (op == MEMCG_LRU_HEAD || op == MEMCG_LRU_OLD)
-+              hlist_nulls_add_head_rcu(&lruvec->lrugen.list, &pgdat->memcg_lru.fifo[new][bin]);
-+      else
-+              hlist_nulls_add_tail_rcu(&lruvec->lrugen.list, &pgdat->memcg_lru.fifo[new][bin]);
-+
-+      pgdat->memcg_lru.nr_memcgs[old]--;
-+      pgdat->memcg_lru.nr_memcgs[new]++;
-+
-+      lruvec->lrugen.gen = new;
-+      WRITE_ONCE(lruvec->lrugen.seg, seg);
-+
-+      if (!pgdat->memcg_lru.nr_memcgs[old] && old == get_memcg_gen(pgdat->memcg_lru.seq))
-+              WRITE_ONCE(pgdat->memcg_lru.seq, pgdat->memcg_lru.seq + 1);
-+
-+      spin_unlock(&pgdat->memcg_lru.lock);
- }
-+#endif
- /******************************************************************************
-  *                          state change
-@@ -5370,11 +5593,11 @@ static int run_cmd(char cmd, int memcg_i
-       if (!mem_cgroup_disabled()) {
-               rcu_read_lock();
-+
-               memcg = mem_cgroup_from_id(memcg_id);
--#ifdef CONFIG_MEMCG
--              if (memcg && !css_tryget(&memcg->css))
-+              if (!mem_cgroup_tryget(memcg))
-                       memcg = NULL;
--#endif
-+
-               rcu_read_unlock();
-               if (!memcg)
-@@ -5521,6 +5744,19 @@ void lru_gen_init_lruvec(struct lruvec *
- }
- #ifdef CONFIG_MEMCG
-+
-+void lru_gen_init_pgdat(struct pglist_data *pgdat)
-+{
-+      int i, j;
-+
-+      spin_lock_init(&pgdat->memcg_lru.lock);
-+
-+      for (i = 0; i < MEMCG_NR_GENS; i++) {
-+              for (j = 0; j < MEMCG_NR_BINS; j++)
-+                      INIT_HLIST_NULLS_HEAD(&pgdat->memcg_lru.fifo[i][j], i);
-+      }
-+}
-+
- void lru_gen_init_memcg(struct mem_cgroup *memcg)
- {
-       INIT_LIST_HEAD(&memcg->mm_list.fifo);
-@@ -5544,7 +5780,69 @@ void lru_gen_exit_memcg(struct mem_cgrou
-               }
-       }
- }
--#endif
-+
-+void lru_gen_online_memcg(struct mem_cgroup *memcg)
-+{
-+      int gen;
-+      int nid;
-+      int bin = prandom_u32_max(MEMCG_NR_BINS);
-+
-+      for_each_node(nid) {
-+              struct pglist_data *pgdat = NODE_DATA(nid);
-+              struct lruvec *lruvec = get_lruvec(memcg, nid);
-+
-+              spin_lock(&pgdat->memcg_lru.lock);
-+
-+              VM_WARN_ON_ONCE(!hlist_nulls_unhashed(&lruvec->lrugen.list));
-+
-+              gen = get_memcg_gen(pgdat->memcg_lru.seq);
-+
-+              hlist_nulls_add_tail_rcu(&lruvec->lrugen.list, &pgdat->memcg_lru.fifo[gen][bin]);
-+              pgdat->memcg_lru.nr_memcgs[gen]++;
-+
-+              lruvec->lrugen.gen = gen;
-+
-+              spin_unlock(&pgdat->memcg_lru.lock);
-+      }
-+}
-+
-+void lru_gen_offline_memcg(struct mem_cgroup *memcg)
-+{
-+      int nid;
-+
-+      for_each_node(nid) {
-+              struct lruvec *lruvec = get_lruvec(memcg, nid);
-+
-+              lru_gen_rotate_memcg(lruvec, MEMCG_LRU_OLD);
-+      }
-+}
-+
-+void lru_gen_release_memcg(struct mem_cgroup *memcg)
-+{
-+      int gen;
-+      int nid;
-+
-+      for_each_node(nid) {
-+              struct pglist_data *pgdat = NODE_DATA(nid);
-+              struct lruvec *lruvec = get_lruvec(memcg, nid);
-+
-+              spin_lock(&pgdat->memcg_lru.lock);
-+
-+              VM_WARN_ON_ONCE(hlist_nulls_unhashed(&lruvec->lrugen.list));
-+
-+              gen = lruvec->lrugen.gen;
-+
-+              hlist_nulls_del_rcu(&lruvec->lrugen.list);
-+              pgdat->memcg_lru.nr_memcgs[gen]--;
-+
-+              if (!pgdat->memcg_lru.nr_memcgs[gen] && gen == get_memcg_gen(pgdat->memcg_lru.seq))
-+                      WRITE_ONCE(pgdat->memcg_lru.seq, pgdat->memcg_lru.seq + 1);
-+
-+              spin_unlock(&pgdat->memcg_lru.lock);
-+      }
-+}
-+
-+#endif /* CONFIG_MEMCG */
- static int __init init_lru_gen(void)
- {
-@@ -5571,6 +5869,10 @@ static void lru_gen_shrink_lruvec(struct
- {
- }
-+static void lru_gen_shrink_node(struct pglist_data *pgdat, struct scan_control *sc)
-+{
-+}
-+
- #endif /* CONFIG_LRU_GEN */
- static void shrink_lruvec(struct lruvec *lruvec, struct scan_control *sc)
-@@ -5584,7 +5886,7 @@ static void shrink_lruvec(struct lruvec
-       bool proportional_reclaim;
-       struct blk_plug plug;
--      if (lru_gen_enabled()) {
-+      if (lru_gen_enabled() && !global_reclaim(sc)) {
-               lru_gen_shrink_lruvec(lruvec, sc);
-               return;
-       }
-@@ -5826,6 +6128,11 @@ static void shrink_node(pg_data_t *pgdat
-       struct lruvec *target_lruvec;
-       bool reclaimable = false;
-+      if (lru_gen_enabled() && global_reclaim(sc)) {
-+              lru_gen_shrink_node(pgdat, sc);
-+              return;
-+      }
-+
-       target_lruvec = mem_cgroup_lruvec(sc->target_mem_cgroup, pgdat);
- again:
diff --git a/target/linux/generic/backport-5.15/020-v6.3-27-mm-multi-gen-LRU-clarify-scan_control-flags.patch b/target/linux/generic/backport-5.15/020-v6.3-27-mm-multi-gen-LRU-clarify-scan_control-flags.patch
deleted file mode 100644 (file)
index 882f29e..0000000
+++ /dev/null
@@ -1,196 +0,0 @@
-From 93147736b5b3a21bea24313bfc7a696829932009 Mon Sep 17 00:00:00 2001
-From: Yu Zhao <[email protected]>
-Date: Wed, 21 Dec 2022 21:19:05 -0700
-Subject: [PATCH 27/29] mm: multi-gen LRU: clarify scan_control flags
-
-Among the flags in scan_control:
-1. sc->may_swap, which indicates swap constraint due to memsw.max, is
-   supported as usual.
-2. sc->proactive, which indicates reclaim by memory.reclaim, may not
-   opportunistically skip the aging path, since it is considered less
-   latency sensitive.
-3. !(sc->gfp_mask & __GFP_IO), which indicates IO constraint, lowers
-   swappiness to prioritize file LRU, since clean file pages are more
-   likely to exist.
-4. sc->may_writepage and sc->may_unmap, which indicates opportunistic
-   reclaim, are rejected, since unmapped clean pages are already
-   prioritized. Scanning for more of them is likely futile and can
-   cause high reclaim latency when there is a large number of memcgs.
-
-The rest are handled by the existing code.
-
-Link: https://lkml.kernel.org/r/[email protected]
-Signed-off-by: Yu Zhao <[email protected]>
-Cc: Johannes Weiner <[email protected]>
-Cc: Jonathan Corbet <[email protected]>
-Cc: Michael Larabel <[email protected]>
-Cc: Michal Hocko <[email protected]>
-Cc: Mike Rapoport <[email protected]>
-Cc: Roman Gushchin <[email protected]>
-Cc: Suren Baghdasaryan <[email protected]>
-Signed-off-by: Andrew Morton <[email protected]>
----
- mm/vmscan.c | 55 +++++++++++++++++++++++++++--------------------------
- 1 file changed, 28 insertions(+), 27 deletions(-)
-
---- a/mm/vmscan.c
-+++ b/mm/vmscan.c
-@@ -2905,6 +2905,9 @@ static int get_swappiness(struct lruvec
-       struct mem_cgroup *memcg = lruvec_memcg(lruvec);
-       struct pglist_data *pgdat = lruvec_pgdat(lruvec);
-+      if (!sc->may_swap)
-+              return 0;
-+
-       if (!can_demote(pgdat->node_id, sc) &&
-           mem_cgroup_get_nr_swap_pages(memcg) < MIN_LRU_BATCH)
-               return 0;
-@@ -3952,7 +3955,7 @@ static void walk_mm(struct lruvec *lruve
-       } while (err == -EAGAIN);
- }
--static struct lru_gen_mm_walk *set_mm_walk(struct pglist_data *pgdat)
-+static struct lru_gen_mm_walk *set_mm_walk(struct pglist_data *pgdat, bool force_alloc)
- {
-       struct lru_gen_mm_walk *walk = current->reclaim_state->mm_walk;
-@@ -3960,7 +3963,7 @@ static struct lru_gen_mm_walk *set_mm_wa
-               VM_WARN_ON_ONCE(walk);
-               walk = &pgdat->mm_walk;
--      } else if (!pgdat && !walk) {
-+      } else if (!walk && force_alloc) {
-               VM_WARN_ON_ONCE(current_is_kswapd());
-               walk = kzalloc(sizeof(*walk), __GFP_HIGH | __GFP_NOMEMALLOC | __GFP_NOWARN);
-@@ -4146,7 +4149,7 @@ static bool try_to_inc_max_seq(struct lr
-               goto done;
-       }
--      walk = set_mm_walk(NULL);
-+      walk = set_mm_walk(NULL, true);
-       if (!walk) {
-               success = iterate_mm_list_nowalk(lruvec, max_seq);
-               goto done;
-@@ -4215,8 +4218,6 @@ static bool lruvec_is_reclaimable(struct
-       struct mem_cgroup *memcg = lruvec_memcg(lruvec);
-       DEFINE_MIN_SEQ(lruvec);
--      VM_WARN_ON_ONCE(sc->memcg_low_reclaim);
--
-       /* see the comment on lru_gen_page */
-       gen = lru_gen_from_seq(min_seq[LRU_GEN_FILE]);
-       birth = READ_ONCE(lruvec->lrugen.timestamps[gen]);
-@@ -4472,12 +4473,8 @@ static bool isolate_page(struct lruvec *
- {
-       bool success;
--      /* unmapping inhibited */
--      if (!sc->may_unmap && page_mapped(page))
--              return false;
--
-       /* swapping inhibited */
--      if (!(sc->may_writepage && (sc->gfp_mask & __GFP_IO)) &&
-+      if (!(sc->gfp_mask & __GFP_IO) &&
-           (PageDirty(page) ||
-            (PageAnon(page) && !PageSwapCache(page))))
-               return false;
-@@ -4574,9 +4571,8 @@ static int scan_pages(struct lruvec *lru
-       __count_vm_events(PGSCAN_ANON + type, isolated);
-       /*
--       * There might not be eligible pages due to reclaim_idx, may_unmap and
--       * may_writepage. Check the remaining to prevent livelock if it's not
--       * making progress.
-+       * There might not be eligible pages due to reclaim_idx. Check the
-+       * remaining to prevent livelock if it's not making progress.
-        */
-       return isolated || !remaining ? scanned : 0;
- }
-@@ -4836,8 +4832,7 @@ static long get_nr_to_scan(struct lruvec
-       struct mem_cgroup *memcg = lruvec_memcg(lruvec);
-       DEFINE_MAX_SEQ(lruvec);
--      if (mem_cgroup_below_min(memcg) ||
--          (mem_cgroup_below_low(memcg) && !sc->memcg_low_reclaim))
-+      if (mem_cgroup_below_min(memcg))
-               return 0;
-       if (!should_run_aging(lruvec, max_seq, sc, can_swap, &nr_to_scan))
-@@ -4865,17 +4860,14 @@ static bool try_to_shrink_lruvec(struct
-       long nr_to_scan;
-       unsigned long scanned = 0;
-       unsigned long nr_to_reclaim = get_nr_to_reclaim(sc);
-+      int swappiness = get_swappiness(lruvec, sc);
-+
-+      /* clean file pages are more likely to exist */
-+      if (swappiness && !(sc->gfp_mask & __GFP_IO))
-+              swappiness = 1;
-       while (true) {
-               int delta;
--              int swappiness;
--
--              if (sc->may_swap)
--                      swappiness = get_swappiness(lruvec, sc);
--              else if (!cgroup_reclaim(sc) && get_swappiness(lruvec, sc))
--                      swappiness = 1;
--              else
--                      swappiness = 0;
-               nr_to_scan = get_nr_to_scan(lruvec, sc, swappiness);
-               if (nr_to_scan <= 0)
-@@ -5005,12 +4997,13 @@ static void lru_gen_shrink_lruvec(struct
-       struct blk_plug plug;
-       VM_WARN_ON_ONCE(global_reclaim(sc));
-+      VM_WARN_ON_ONCE(!sc->may_writepage || !sc->may_unmap);
-       lru_add_drain();
-       blk_start_plug(&plug);
--      set_mm_walk(lruvec_pgdat(lruvec));
-+      set_mm_walk(NULL, false);
-       if (try_to_shrink_lruvec(lruvec, sc))
-               lru_gen_rotate_memcg(lruvec, MEMCG_LRU_YOUNG);
-@@ -5066,11 +5059,19 @@ static void lru_gen_shrink_node(struct p
-       VM_WARN_ON_ONCE(!global_reclaim(sc));
-+      /*
-+       * Unmapped clean pages are already prioritized. Scanning for more of
-+       * them is likely futile and can cause high reclaim latency when there
-+       * is a large number of memcgs.
-+       */
-+      if (!sc->may_writepage || !sc->may_unmap)
-+              goto done;
-+
-       lru_add_drain();
-       blk_start_plug(&plug);
--      set_mm_walk(pgdat);
-+      set_mm_walk(pgdat, false);
-       set_initial_priority(pgdat, sc);
-@@ -5088,7 +5089,7 @@ static void lru_gen_shrink_node(struct p
-       clear_mm_walk();
-       blk_finish_plug(&plug);
--
-+done:
-       /* kswapd should never fail */
-       pgdat->kswapd_failures = 0;
- }
-@@ -5656,7 +5657,7 @@ static ssize_t lru_gen_seq_write(struct
-       set_task_reclaim_state(current, &sc.reclaim_state);
-       flags = memalloc_noreclaim_save();
-       blk_start_plug(&plug);
--      if (!set_mm_walk(NULL)) {
-+      if (!set_mm_walk(NULL, true)) {
-               err = -ENOMEM;
-               goto done;
-       }
diff --git a/target/linux/generic/backport-5.15/020-v6.3-28-mm-multi-gen-LRU-simplify-arch_has_hw_pte_young-chec.patch b/target/linux/generic/backport-5.15/020-v6.3-28-mm-multi-gen-LRU-simplify-arch_has_hw_pte_young-chec.patch
deleted file mode 100644 (file)
index 38d0e54..0000000
+++ /dev/null
@@ -1,34 +0,0 @@
-From cf3297e4c7a928da8b2b2f0baff2f9c69ea57952 Mon Sep 17 00:00:00 2001
-From: Yu Zhao <[email protected]>
-Date: Wed, 21 Dec 2022 21:19:06 -0700
-Subject: [PATCH 28/29] mm: multi-gen LRU: simplify arch_has_hw_pte_young()
- check
-
-Scanning page tables when hardware does not set the accessed bit has
-no real use cases.
-
-Link: https://lkml.kernel.org/r/[email protected]
-Signed-off-by: Yu Zhao <[email protected]>
-Cc: Johannes Weiner <[email protected]>
-Cc: Jonathan Corbet <[email protected]>
-Cc: Michael Larabel <[email protected]>
-Cc: Michal Hocko <[email protected]>
-Cc: Mike Rapoport <[email protected]>
-Cc: Roman Gushchin <[email protected]>
-Cc: Suren Baghdasaryan <[email protected]>
-Signed-off-by: Andrew Morton <[email protected]>
----
- mm/vmscan.c | 2 +-
- 1 file changed, 1 insertion(+), 1 deletion(-)
-
---- a/mm/vmscan.c
-+++ b/mm/vmscan.c
-@@ -4144,7 +4144,7 @@ static bool try_to_inc_max_seq(struct lr
-        * handful of PTEs. Spreading the work out over a period of time usually
-        * is less efficient, but it avoids bursty page faults.
-        */
--      if (!force_scan && !(arch_has_hw_pte_young() && get_cap(LRU_GEN_MM_WALK))) {
-+      if (!arch_has_hw_pte_young() || !get_cap(LRU_GEN_MM_WALK)) {
-               success = iterate_mm_list_nowalk(lruvec, max_seq);
-               goto done;
-       }
diff --git a/target/linux/generic/backport-5.15/020-v6.3-29-mm-multi-gen-LRU-avoid-futile-retries.patch b/target/linux/generic/backport-5.15/020-v6.3-29-mm-multi-gen-LRU-avoid-futile-retries.patch
deleted file mode 100644 (file)
index 2d19d0d..0000000
+++ /dev/null
@@ -1,88 +0,0 @@
-From cc67f962cc53f6e1dfa92eb85b7b26fe83a3c66f Mon Sep 17 00:00:00 2001
-From: Yu Zhao <[email protected]>
-Date: Mon, 13 Feb 2023 00:53:22 -0700
-Subject: [PATCH 29/29] mm: multi-gen LRU: avoid futile retries
-
-Recall that the per-node memcg LRU has two generations and they alternate
-when the last memcg (of a given node) is moved from one to the other.
-Each generation is also sharded into multiple bins to improve scalability.
-A reclaimer starts with a random bin (in the old generation) and, if it
-fails, it will retry, i.e., to try the rest of the bins.
-
-If a reclaimer fails with the last memcg, it should move this memcg to the
-young generation first, which causes the generations to alternate, and
-then retry.  Otherwise, the retries will be futile because all other bins
-are empty.
-
-Link: https://lkml.kernel.org/r/[email protected]
-Fixes: e4dde56cd208 ("mm: multi-gen LRU: per-node lru_gen_folio lists")
-Signed-off-by: Yu Zhao <[email protected]>
-Reported-by: T.J. Mercier <[email protected]>
-Signed-off-by: Andrew Morton <[email protected]>
----
- mm/vmscan.c | 25 +++++++++++++++----------
- 1 file changed, 15 insertions(+), 10 deletions(-)
-
---- a/mm/vmscan.c
-+++ b/mm/vmscan.c
-@@ -4934,18 +4934,20 @@ static int shrink_one(struct lruvec *lru
- static void shrink_many(struct pglist_data *pgdat, struct scan_control *sc)
- {
-+      int op;
-       int gen;
-       int bin;
-       int first_bin;
-       struct lruvec *lruvec;
-       struct lru_gen_page *lrugen;
-+      struct mem_cgroup *memcg;
-       const struct hlist_nulls_node *pos;
--      int op = 0;
--      struct mem_cgroup *memcg = NULL;
-       unsigned long nr_to_reclaim = get_nr_to_reclaim(sc);
-       bin = first_bin = prandom_u32_max(MEMCG_NR_BINS);
- restart:
-+      op = 0;
-+      memcg = NULL;
-       gen = get_memcg_gen(READ_ONCE(pgdat->memcg_lru.seq));
-       rcu_read_lock();
-@@ -4969,14 +4971,22 @@ restart:
-               op = shrink_one(lruvec, sc);
--              if (sc->nr_reclaimed >= nr_to_reclaim)
--                      goto success;
--
-               rcu_read_lock();
-+
-+              if (sc->nr_reclaimed >= nr_to_reclaim)
-+                      break;
-       }
-       rcu_read_unlock();
-+      if (op)
-+              lru_gen_rotate_memcg(lruvec, op);
-+
-+      mem_cgroup_put(memcg);
-+
-+      if (sc->nr_reclaimed >= nr_to_reclaim)
-+              return;
-+
-       /* restart if raced with lru_gen_rotate_memcg() */
-       if (gen != get_nulls_value(pos))
-               goto restart;
-@@ -4985,11 +4995,6 @@ restart:
-       bin = get_memcg_bin(bin + 1);
-       if (bin != first_bin)
-               goto restart;
--success:
--      if (op)
--              lru_gen_rotate_memcg(lruvec, op);
--
--      mem_cgroup_put(memcg);
- }
- static void lru_gen_shrink_lruvec(struct lruvec *lruvec, struct scan_control *sc)
diff --git a/target/linux/generic/backport-5.15/021-v6.4-mm-Multi-gen-LRU-remove-wait_event_killable.patch b/target/linux/generic/backport-5.15/021-v6.4-mm-Multi-gen-LRU-remove-wait_event_killable.patch
deleted file mode 100644 (file)
index e154494..0000000
+++ /dev/null
@@ -1,266 +0,0 @@
-From 087ed25eaf5a78a678508e893f80addab9b1c103 Mon Sep 17 00:00:00 2001
-From: Kalesh Singh <[email protected]>
-Date: Thu, 13 Apr 2023 14:43:26 -0700
-Subject: [PATCH] mm: Multi-gen LRU: remove wait_event_killable()
-
-Android 14 and later default to MGLRU [1] and field telemetry showed
-occasional long tail latency (>100ms) in the reclaim path.
-
-Tracing revealed priority inversion in the reclaim path.  In
-try_to_inc_max_seq(), when high priority tasks were blocked on
-wait_event_killable(), the preemption of the low priority task to call
-wake_up_all() caused those high priority tasks to wait longer than
-necessary.  In general, this problem is not different from others of its
-kind, e.g., one caused by mutex_lock().  However, it is specific to MGLRU
-because it introduced the new wait queue lruvec->mm_state.wait.
-
-The purpose of this new wait queue is to avoid the thundering herd
-problem.  If many direct reclaimers rush into try_to_inc_max_seq(), only
-one can succeed, i.e., the one to wake up the rest, and the rest who
-failed might cause premature OOM kills if they do not wait.  So far there
-is no evidence supporting this scenario, based on how often the wait has
-been hit.  And this begs the question how useful the wait queue is in
-practice.
-
-Based on Minchan's recommendation, which is in line with his commit
-6d4675e60135 ("mm: don't be stuck to rmap lock on reclaim path") and the
-rest of the MGLRU code which also uses trylock when possible, remove the
-wait queue.
-
-[1] https://android-review.googlesource.com/q/I7ed7fbfd6ef9ce10053347528125dd98c39e50bf
-
-Link: https://lkml.kernel.org/r/[email protected]
-Fixes: bd74fdaea146 ("mm: multi-gen LRU: support page table walks")
-Change-Id: I911f3968fd1adb25171279cc5b6f48ccb7efc8de
-Signed-off-by: Kalesh Singh <[email protected]>
-Suggested-by: Minchan Kim <[email protected]>
-Reported-by: Wei Wang <[email protected]>
-Acked-by: Yu Zhao <[email protected]>
-Cc: Minchan Kim <[email protected]>
-Cc: Jan Alexander Steffens (heftig) <[email protected]>
-Cc: Oleksandr Natalenko <[email protected]>
-Cc: Suleiman Souhlal <[email protected]>
-Cc: Suren Baghdasaryan <[email protected]>
-Signed-off-by: Andrew Morton <[email protected]>
----
- include/linux/mmzone.h |   8 +--
- mm/vmscan.c            | 111 +++++++++++++++--------------------------
- 2 files changed, 42 insertions(+), 77 deletions(-)
-
---- a/include/linux/mmzone.h
-+++ b/include/linux/mmzone.h
-@@ -452,18 +452,14 @@ enum {
- struct lru_gen_mm_state {
-       /* set to max_seq after each iteration */
-       unsigned long seq;
--      /* where the current iteration continues (inclusive) */
-+      /* where the current iteration continues after */
-       struct list_head *head;
--      /* where the last iteration ended (exclusive) */
-+      /* where the last iteration ended before */
-       struct list_head *tail;
--      /* to wait for the last page table walker to finish */
--      struct wait_queue_head wait;
-       /* Bloom filters flip after each iteration */
-       unsigned long *filters[NR_BLOOM_FILTERS];
-       /* the mm stats for debugging */
-       unsigned long stats[NR_HIST_GENS][NR_MM_STATS];
--      /* the number of concurrent page table walkers */
--      int nr_walkers;
- };
- struct lru_gen_mm_walk {
---- a/mm/vmscan.c
-+++ b/mm/vmscan.c
-@@ -2999,18 +2999,13 @@ void lru_gen_del_mm(struct mm_struct *mm
-               if (!lruvec)
-                       continue;
--              /* where the last iteration ended (exclusive) */
-+              /* where the current iteration continues after */
-+              if (lruvec->mm_state.head == &mm->lru_gen.list)
-+                      lruvec->mm_state.head = lruvec->mm_state.head->prev;
-+
-+              /* where the last iteration ended before */
-               if (lruvec->mm_state.tail == &mm->lru_gen.list)
-                       lruvec->mm_state.tail = lruvec->mm_state.tail->next;
--
--              /* where the current iteration continues (inclusive) */
--              if (lruvec->mm_state.head != &mm->lru_gen.list)
--                      continue;
--
--              lruvec->mm_state.head = lruvec->mm_state.head->next;
--              /* the deletion ends the current iteration */
--              if (lruvec->mm_state.head == &mm_list->fifo)
--                      WRITE_ONCE(lruvec->mm_state.seq, lruvec->mm_state.seq + 1);
-       }
-       list_del_init(&mm->lru_gen.list);
-@@ -3194,68 +3189,54 @@ static bool iterate_mm_list(struct lruve
-                           struct mm_struct **iter)
- {
-       bool first = false;
--      bool last = true;
-+      bool last = false;
-       struct mm_struct *mm = NULL;
-       struct mem_cgroup *memcg = lruvec_memcg(lruvec);
-       struct lru_gen_mm_list *mm_list = get_mm_list(memcg);
-       struct lru_gen_mm_state *mm_state = &lruvec->mm_state;
-       /*
--       * There are four interesting cases for this page table walker:
--       * 1. It tries to start a new iteration of mm_list with a stale max_seq;
--       *    there is nothing left to do.
--       * 2. It's the first of the current generation, and it needs to reset
--       *    the Bloom filter for the next generation.
--       * 3. It reaches the end of mm_list, and it needs to increment
--       *    mm_state->seq; the iteration is done.
--       * 4. It's the last of the current generation, and it needs to reset the
--       *    mm stats counters for the next generation.
-+       * mm_state->seq is incremented after each iteration of mm_list. There
-+       * are three interesting cases for this page table walker:
-+       * 1. It tries to start a new iteration with a stale max_seq: there is
-+       *    nothing left to do.
-+       * 2. It started the next iteration: it needs to reset the Bloom filter
-+       *    so that a fresh set of PTE tables can be recorded.
-+       * 3. It ended the current iteration: it needs to reset the mm stats
-+       *    counters and tell its caller to increment max_seq.
-        */
-       spin_lock(&mm_list->lock);
-       VM_WARN_ON_ONCE(mm_state->seq + 1 < walk->max_seq);
--      VM_WARN_ON_ONCE(*iter && mm_state->seq > walk->max_seq);
--      VM_WARN_ON_ONCE(*iter && !mm_state->nr_walkers);
--      if (walk->max_seq <= mm_state->seq) {
--              if (!*iter)
--                      last = false;
-+      if (walk->max_seq <= mm_state->seq)
-               goto done;
--      }
--      if (!mm_state->nr_walkers) {
--              VM_WARN_ON_ONCE(mm_state->head && mm_state->head != &mm_list->fifo);
-+      if (!mm_state->head)
-+              mm_state->head = &mm_list->fifo;
--              mm_state->head = mm_list->fifo.next;
-+      if (mm_state->head == &mm_list->fifo)
-               first = true;
--      }
--
--      while (!mm && mm_state->head != &mm_list->fifo) {
--              mm = list_entry(mm_state->head, struct mm_struct, lru_gen.list);
-+      do {
-               mm_state->head = mm_state->head->next;
-+              if (mm_state->head == &mm_list->fifo) {
-+                      WRITE_ONCE(mm_state->seq, mm_state->seq + 1);
-+                      last = true;
-+                      break;
-+              }
-               /* force scan for those added after the last iteration */
--              if (!mm_state->tail || mm_state->tail == &mm->lru_gen.list) {
--                      mm_state->tail = mm_state->head;
-+              if (!mm_state->tail || mm_state->tail == mm_state->head) {
-+                      mm_state->tail = mm_state->head->next;
-                       walk->force_scan = true;
-               }
-+              mm = list_entry(mm_state->head, struct mm_struct, lru_gen.list);
-               if (should_skip_mm(mm, walk))
-                       mm = NULL;
--      }
--
--      if (mm_state->head == &mm_list->fifo)
--              WRITE_ONCE(mm_state->seq, mm_state->seq + 1);
-+      } while (!mm);
- done:
--      if (*iter && !mm)
--              mm_state->nr_walkers--;
--      if (!*iter && mm)
--              mm_state->nr_walkers++;
--
--      if (mm_state->nr_walkers)
--              last = false;
--
-       if (*iter || last)
-               reset_mm_stats(lruvec, walk, last);
-@@ -3283,9 +3264,9 @@ static bool iterate_mm_list_nowalk(struc
-       VM_WARN_ON_ONCE(mm_state->seq + 1 < max_seq);
--      if (max_seq > mm_state->seq && !mm_state->nr_walkers) {
--              VM_WARN_ON_ONCE(mm_state->head && mm_state->head != &mm_list->fifo);
--
-+      if (max_seq > mm_state->seq) {
-+              mm_state->head = NULL;
-+              mm_state->tail = NULL;
-               WRITE_ONCE(mm_state->seq, mm_state->seq + 1);
-               reset_mm_stats(lruvec, NULL, true);
-               success = true;
-@@ -3894,10 +3875,6 @@ restart:
-               walk_pmd_range(&val, addr, next, args);
--              /* a racy check to curtail the waiting time */
--              if (wq_has_sleeper(&walk->lruvec->mm_state.wait))
--                      return 1;
--
-               if (need_resched() || walk->batched >= MAX_LRU_BATCH) {
-                       end = (addr | ~PUD_MASK) + 1;
-                       goto done;
-@@ -3930,8 +3907,14 @@ static void walk_mm(struct lruvec *lruve
-       walk->next_addr = FIRST_USER_ADDRESS;
-       do {
-+              DEFINE_MAX_SEQ(lruvec);
-+
-               err = -EBUSY;
-+              /* another thread might have called inc_max_seq() */
-+              if (walk->max_seq != max_seq)
-+                      break;
-+
-               /* page_update_gen() requires stable page_memcg() */
-               if (!mem_cgroup_trylock_pages(memcg))
-                       break;
-@@ -4164,25 +4147,12 @@ static bool try_to_inc_max_seq(struct lr
-               success = iterate_mm_list(lruvec, walk, &mm);
-               if (mm)
-                       walk_mm(lruvec, mm, walk);
--
--              cond_resched();
-       } while (mm);
- done:
--      if (!success) {
--              if (sc->priority <= DEF_PRIORITY - 2)
--                      wait_event_killable(lruvec->mm_state.wait,
--                                          max_seq < READ_ONCE(lrugen->max_seq));
--              return false;
--      }
-+      if (success)
-+              inc_max_seq(lruvec, can_swap, force_scan);
--      VM_WARN_ON_ONCE(max_seq != READ_ONCE(lrugen->max_seq));
--
--      inc_max_seq(lruvec, can_swap, force_scan);
--      /* either this sees any waiters or they will see updated max_seq */
--      if (wq_has_sleeper(&lruvec->mm_state.wait))
--              wake_up_all(&lruvec->mm_state.wait);
--
--      return true;
-+      return success;
- }
- static bool lruvec_is_sizable(struct lruvec *lruvec, struct scan_control *sc)
-@@ -5746,7 +5716,6 @@ void lru_gen_init_lruvec(struct lruvec *
-               INIT_LIST_HEAD(&lrugen->pages[gen][type][zone]);
-       lruvec->mm_state.seq = MIN_NR_GENS;
--      init_waitqueue_head(&lruvec->mm_state.wait);
- }
- #ifdef CONFIG_MEMCG
diff --git a/target/linux/generic/backport-5.15/050-v5.16-00-MIPS-uasm-Enable-muhu-opcode-for-MIPS-R6.patch b/target/linux/generic/backport-5.15/050-v5.16-00-MIPS-uasm-Enable-muhu-opcode-for-MIPS-R6.patch
deleted file mode 100644 (file)
index 82feb74..0000000
+++ /dev/null
@@ -1,65 +0,0 @@
-From: Johan Almbladh <[email protected]>
-Date: Tue, 5 Oct 2021 18:54:02 +0200
-Subject: [PATCH] MIPS: uasm: Enable muhu opcode for MIPS R6
-
-Enable the 'muhu' instruction, complementing the existing 'mulu', needed
-to implement a MIPS32 BPF JIT.
-
-Also fix a typo in the existing definition of 'dmulu'.
-
-Signed-off-by: Tony Ambardar <[email protected]>
-
-This patch is a dependency for my 32-bit MIPS eBPF JIT.
-
-Signed-off-by: Johan Almbladh <[email protected]>
----
-
---- a/arch/mips/include/asm/uasm.h
-+++ b/arch/mips/include/asm/uasm.h
-@@ -145,6 +145,7 @@ Ip_u1(_mtlo);
- Ip_u3u1u2(_mul);
- Ip_u1u2(_multu);
- Ip_u3u1u2(_mulu);
-+Ip_u3u1u2(_muhu);
- Ip_u3u1u2(_nor);
- Ip_u3u1u2(_or);
- Ip_u2u1u3(_ori);
---- a/arch/mips/mm/uasm-mips.c
-+++ b/arch/mips/mm/uasm-mips.c
-@@ -90,7 +90,7 @@ static const struct insn insn_table[insn
-                               RS | RT | RD},
-       [insn_dmtc0]    = {M(cop0_op, dmtc_op, 0, 0, 0, 0), RT | RD | SET},
-       [insn_dmultu]   = {M(spec_op, 0, 0, 0, 0, dmultu_op), RS | RT},
--      [insn_dmulu]    = {M(spec_op, 0, 0, 0, dmult_dmul_op, dmultu_op),
-+      [insn_dmulu]    = {M(spec_op, 0, 0, 0, dmultu_dmulu_op, dmultu_op),
-                               RS | RT | RD},
-       [insn_drotr]    = {M(spec_op, 1, 0, 0, 0, dsrl_op), RT | RD | RE},
-       [insn_drotr32]  = {M(spec_op, 1, 0, 0, 0, dsrl32_op), RT | RD | RE},
-@@ -150,6 +150,8 @@ static const struct insn insn_table[insn
-       [insn_mtlo]     = {M(spec_op, 0, 0, 0, 0, mtlo_op), RS},
-       [insn_mulu]     = {M(spec_op, 0, 0, 0, multu_mulu_op, multu_op),
-                               RS | RT | RD},
-+      [insn_muhu]     = {M(spec_op, 0, 0, 0, multu_muhu_op, multu_op),
-+                              RS | RT | RD},
- #ifndef CONFIG_CPU_MIPSR6
-       [insn_mul]      = {M(spec2_op, 0, 0, 0, 0, mul_op), RS | RT | RD},
- #else
---- a/arch/mips/mm/uasm.c
-+++ b/arch/mips/mm/uasm.c
-@@ -59,7 +59,7 @@ enum opcode {
-       insn_lddir, insn_ldpte, insn_ldx, insn_lh, insn_lhu, insn_ll, insn_lld,
-       insn_lui, insn_lw, insn_lwu, insn_lwx, insn_mfc0, insn_mfhc0, insn_mfhi,
-       insn_mflo, insn_modu, insn_movn, insn_movz, insn_mtc0, insn_mthc0,
--      insn_mthi, insn_mtlo, insn_mul, insn_multu, insn_mulu, insn_nor,
-+      insn_mthi, insn_mtlo, insn_mul, insn_multu, insn_mulu, insn_muhu, insn_nor,
-       insn_or, insn_ori, insn_pref, insn_rfe, insn_rotr, insn_sb, insn_sc,
-       insn_scd, insn_seleqz, insn_selnez, insn_sd, insn_sh, insn_sll,
-       insn_sllv, insn_slt, insn_slti, insn_sltiu, insn_sltu, insn_sra,
-@@ -344,6 +344,7 @@ I_u1(_mtlo)
- I_u3u1u2(_mul)
- I_u1u2(_multu)
- I_u3u1u2(_mulu)
-+I_u3u1u2(_muhu)
- I_u3u1u2(_nor)
- I_u3u1u2(_or)
- I_u2u1u3(_ori)
diff --git a/target/linux/generic/backport-5.15/050-v5.16-01-mips-uasm-Add-workaround-for-Loongson-2F-nop-CPU-err.patch b/target/linux/generic/backport-5.15/050-v5.16-01-mips-uasm-Add-workaround-for-Loongson-2F-nop-CPU-err.patch
deleted file mode 100644 (file)
index 3a4d573..0000000
+++ /dev/null
@@ -1,31 +0,0 @@
-From: Johan Almbladh <[email protected]>
-Date: Tue, 5 Oct 2021 18:54:03 +0200
-Subject: [PATCH] mips: uasm: Add workaround for Loongson-2F nop CPU errata
-
-This patch implements a workaround for the Loongson-2F nop in generated,
-code, if the existing option CONFIG_CPU_NOP_WORKAROUND is set. Before,
-the binutils option -mfix-loongson2f-nop was enabled, but no workaround
-was done when emitting MIPS code. Now, the nop pseudo instruction is
-emitted as "or ax,ax,zero" instead of the default "sll zero,zero,0". This
-is consistent with the workaround implemented by binutils.
-
-Link: https://sourceware.org/legacy-ml/binutils/2009-11/msg00387.html
-
-Signed-off-by: Johan Almbladh <[email protected]>
-Reviewed-by: Jiaxun Yang <[email protected]>
----
-
---- a/arch/mips/include/asm/uasm.h
-+++ b/arch/mips/include/asm/uasm.h
-@@ -249,7 +249,11 @@ static inline void uasm_l##lb(struct uas
- #define uasm_i_bnezl(buf, rs, off) uasm_i_bnel(buf, rs, 0, off)
- #define uasm_i_ehb(buf) uasm_i_sll(buf, 0, 0, 3)
- #define uasm_i_move(buf, a, b) UASM_i_ADDU(buf, a, 0, b)
-+#ifdef CONFIG_CPU_NOP_WORKAROUNDS
-+#define uasm_i_nop(buf) uasm_i_or(buf, 1, 1, 0)
-+#else
- #define uasm_i_nop(buf) uasm_i_sll(buf, 0, 0, 0)
-+#endif
- #define uasm_i_ssnop(buf) uasm_i_sll(buf, 0, 0, 1)
- static inline void uasm_i_drotr_safe(u32 **p, unsigned int a1,
diff --git a/target/linux/generic/backport-5.15/050-v5.16-02-mips-bpf-Add-eBPF-JIT-for-32-bit-MIPS.patch b/target/linux/generic/backport-5.15/050-v5.16-02-mips-bpf-Add-eBPF-JIT-for-32-bit-MIPS.patch
deleted file mode 100644 (file)
index 7980659..0000000
+++ /dev/null
@@ -1,3078 +0,0 @@
-From: Johan Almbladh <[email protected]>
-Date: Tue, 5 Oct 2021 18:54:04 +0200
-Subject: [PATCH] mips: bpf: Add eBPF JIT for 32-bit MIPS
-
-This is an implementation of an eBPF JIT for 32-bit MIPS I-V and MIPS32.
-The implementation supports all 32-bit and 64-bit ALU and JMP operations,
-including the recently-added atomics. 64-bit div/mod and 64-bit atomics
-are implemented using function calls to math64 and atomic64 functions,
-respectively. All 32-bit operations are implemented natively by the JIT,
-except if the CPU lacks ll/sc instructions.
-
-Register mapping
-================
-All 64-bit eBPF registers are mapped to native 32-bit MIPS register pairs,
-and does not use any stack scratch space for register swapping. This means
-that all eBPF register data is kept in CPU registers all the time, and
-this simplifies the register management a lot. It also reduces the JIT's
-pressure on temporary registers since we do not have to move data around.
-
-Native register pairs are ordered according to CPU endiannes, following
-the O32 calling convention for passing 64-bit arguments and return values.
-The eBPF return value, arguments and callee-saved registers are mapped to
-their native MIPS equivalents.
-
-Since the 32 highest bits in the eBPF FP (frame pointer) register are
-always zero, only one general-purpose register is actually needed for the
-mapping. The MIPS fp register is used for this purpose. The high bits are
-mapped to MIPS register r0. This saves us one CPU register, which is much
-needed for temporaries, while still allowing us to treat the R10 (FP)
-register just like any other eBPF register in the JIT.
-
-The MIPS gp (global pointer) and at (assembler temporary) registers are
-used as internal temporary registers for constant blinding. CPU registers
-t6-t9 are used internally by the JIT when constructing more complex 64-bit
-operations. This is precisely what is needed - two registers to store an
-operand value, and two more as scratch registers when performing the
-operation.
-
-The register mapping is shown below.
-
-    R0 - $v1, $v0   return value
-    R1 - $a1, $a0   argument 1, passed in registers
-    R2 - $a3, $a2   argument 2, passed in registers
-    R3 - $t1, $t0   argument 3, passed on stack
-    R4 - $t3, $t2   argument 4, passed on stack
-    R5 - $t4, $t3   argument 5, passed on stack
-    R6 - $s1, $s0   callee-saved
-    R7 - $s3, $s2   callee-saved
-    R8 - $s5, $s4   callee-saved
-    R9 - $s7, $s6   callee-saved
-    FP - $r0, $fp   32-bit frame pointer
-    AX - $gp, $at   constant-blinding
-         $t6 - $t9  unallocated, JIT temporaries
-
-Jump offsets
-============
-The JIT tries to map all conditional JMP operations to MIPS conditional
-PC-relative branches. The MIPS branch offset field is 18 bits, in bytes,
-which is equivalent to the eBPF 16-bit instruction offset. However, since
-the JIT may emit more than one CPU instruction per eBPF instruction, the
-field width may overflow. If that happens, the JIT converts the long
-conditional jump to a short PC-relative branch with the condition
-inverted, jumping over a long unconditional absolute jmp (j).
-
-This conversion will change the instruction offset mapping used for jumps,
-and may in turn result in more branch offset overflows. The JIT therefore
-dry-runs the translation until no more branches are converted and the
-offsets do not change anymore. There is an upper bound on this of course,
-and if the JIT hits that limit, the last two iterations are run with all
-branches being converted.
-
-Tail call count
-===============
-The current tail call count is stored in the 16-byte area of the caller's
-stack frame that is reserved for the callee in the o32 ABI. The value is
-initialized in the prologue, and propagated to the tail-callee by skipping
-the initialization instructions when emitting the tail call.
-
-Signed-off-by: Johan Almbladh <[email protected]>
----
- create mode 100644 arch/mips/net/bpf_jit_comp.c
- create mode 100644 arch/mips/net/bpf_jit_comp.h
- create mode 100644 arch/mips/net/bpf_jit_comp32.c
-
---- a/arch/mips/net/Makefile
-+++ b/arch/mips/net/Makefile
-@@ -2,4 +2,9 @@
- # MIPS networking code
- obj-$(CONFIG_MIPS_CBPF_JIT) += bpf_jit.o bpf_jit_asm.o
--obj-$(CONFIG_MIPS_EBPF_JIT) += ebpf_jit.o
-+
-+ifeq ($(CONFIG_32BIT),y)
-+        obj-$(CONFIG_MIPS_EBPF_JIT) += bpf_jit_comp.o bpf_jit_comp32.o
-+else
-+        obj-$(CONFIG_MIPS_EBPF_JIT) += ebpf_jit.o
-+endif
---- /dev/null
-+++ b/arch/mips/net/bpf_jit_comp.c
-@@ -0,0 +1,1020 @@
-+// SPDX-License-Identifier: GPL-2.0-only
-+/*
-+ * Just-In-Time compiler for eBPF bytecode on MIPS.
-+ * Implementation of JIT functions common to 32-bit and 64-bit CPUs.
-+ *
-+ * Copyright (c) 2021 Anyfi Networks AB.
-+ * Author: Johan Almbladh <[email protected]>
-+ *
-+ * Based on code and ideas from
-+ * Copyright (c) 2017 Cavium, Inc.
-+ * Copyright (c) 2017 Shubham Bansal <[email protected]>
-+ * Copyright (c) 2011 Mircea Gherzan <[email protected]>
-+ */
-+
-+/*
-+ * Code overview
-+ * =============
-+ *
-+ * - bpf_jit_comp.h
-+ *   Common definitions and utilities.
-+ *
-+ * - bpf_jit_comp.c
-+ *   Implementation of JIT top-level logic and exported JIT API functions.
-+ *   Implementation of internal operations shared by 32-bit and 64-bit code.
-+ *   JMP and ALU JIT control code, register control code, shared ALU and
-+ *   JMP/JMP32 JIT operations.
-+ *
-+ * - bpf_jit_comp32.c
-+ *   Implementation of functions to JIT prologue, epilogue and a single eBPF
-+ *   instruction for 32-bit MIPS CPUs. The functions use shared operations
-+ *   where possible, and implement the rest for 32-bit MIPS such as ALU64
-+ *   operations.
-+ *
-+ * - bpf_jit_comp64.c
-+ *   Ditto, for 64-bit MIPS CPUs.
-+ *
-+ * Zero and sign extension
-+ * ========================
-+ * 32-bit MIPS instructions on 64-bit MIPS registers use sign extension,
-+ * but the eBPF instruction set mandates zero extension. We let the verifier
-+ * insert explicit zero-extensions after 32-bit ALU operations, both for
-+ * 32-bit and 64-bit MIPS JITs. Conditional JMP32 operations on 64-bit MIPs
-+ * are JITed with sign extensions inserted when so expected.
-+ *
-+ * ALU operations
-+ * ==============
-+ * ALU operations on 32/64-bit MIPS and ALU64 operations on 64-bit MIPS are
-+ * JITed in the following steps. ALU64 operations on 32-bit MIPS are more
-+ * complicated and therefore only processed by special implementations in
-+ * step (3).
-+ *
-+ * 1) valid_alu_i:
-+ *    Determine if an immediate operation can be emitted as such, or if
-+ *    we must fall back to the register version.
-+ *
-+ * 2) rewrite_alu_i:
-+ *    Convert BPF operation and immediate value to a canonical form for
-+ *    JITing. In some degenerate cases this form may be a no-op.
-+ *
-+ * 3) emit_alu_{i,i64,r,64}:
-+ *    Emit instructions for an ALU or ALU64 immediate or register operation.
-+ *
-+ * JMP operations
-+ * ==============
-+ * JMP and JMP32 operations require an JIT instruction offset table for
-+ * translating the jump offset. This table is computed by dry-running the
-+ * JIT without actually emitting anything. However, the computed PC-relative
-+ * offset may overflow the 18-bit offset field width of the native MIPS
-+ * branch instruction. In such cases, the long jump is converted into the
-+ * following sequence.
-+ *
-+ *    <branch> !<cond> +2    Inverted PC-relative branch
-+ *    nop                    Delay slot
-+ *    j <offset>             Unconditional absolute long jump
-+ *    nop                    Delay slot
-+ *
-+ * Since this converted sequence alters the offset table, all offsets must
-+ * be re-calculated. This may in turn trigger new branch conversions, so
-+ * the process is repeated until no further changes are made. Normally it
-+ * completes in 1-2 iterations. If JIT_MAX_ITERATIONS should reached, we
-+ * fall back to converting every remaining jump operation. The branch
-+ * conversion is independent of how the JMP or JMP32 condition is JITed.
-+ *
-+ * JMP32 and JMP operations are JITed as follows.
-+ *
-+ * 1) setup_jmp_{i,r}:
-+ *    Convert jump conditional and offset into a form that can be JITed.
-+ *    This form may be a no-op, a canonical form, or an inverted PC-relative
-+ *    jump if branch conversion is necessary.
-+ *
-+ * 2) valid_jmp_i:
-+ *    Determine if an immediate operations can be emitted as such, or if
-+ *    we must fall back to the register version. Applies to JMP32 for 32-bit
-+ *    MIPS, and both JMP and JMP32 for 64-bit MIPS.
-+ *
-+ * 3) emit_jmp_{i,i64,r,r64}:
-+ *    Emit instructions for an JMP or JMP32 immediate or register operation.
-+ *
-+ * 4) finish_jmp_{i,r}:
-+ *    Emit any instructions needed to finish the jump. This includes a nop
-+ *    for the delay slot if a branch was emitted, and a long absolute jump
-+ *    if the branch was converted.
-+ */
-+
-+#include <linux/limits.h>
-+#include <linux/bitops.h>
-+#include <linux/errno.h>
-+#include <linux/filter.h>
-+#include <linux/bpf.h>
-+#include <linux/slab.h>
-+#include <asm/bitops.h>
-+#include <asm/cacheflush.h>
-+#include <asm/cpu-features.h>
-+#include <asm/isa-rev.h>
-+#include <asm/uasm.h>
-+
-+#include "bpf_jit_comp.h"
-+
-+/* Convenience macros for descriptor access */
-+#define CONVERTED(desc)       ((desc) & JIT_DESC_CONVERT)
-+#define INDEX(desc)   ((desc) & ~JIT_DESC_CONVERT)
-+
-+/*
-+ * Push registers on the stack, starting at a given depth from the stack
-+ * pointer and increasing. The next depth to be written is returned.
-+ */
-+int push_regs(struct jit_context *ctx, u32 mask, u32 excl, int depth)
-+{
-+      int reg;
-+
-+      for (reg = 0; reg < BITS_PER_BYTE * sizeof(mask); reg++)
-+              if (mask & BIT(reg)) {
-+                      if ((excl & BIT(reg)) == 0) {
-+                              if (sizeof(long) == 4)
-+                                      emit(ctx, sw, reg, depth, MIPS_R_SP);
-+                              else /* sizeof(long) == 8 */
-+                                      emit(ctx, sd, reg, depth, MIPS_R_SP);
-+                      }
-+                      depth += sizeof(long);
-+              }
-+
-+      ctx->stack_used = max((int)ctx->stack_used, depth);
-+      return depth;
-+}
-+
-+/*
-+ * Pop registers from the stack, starting at a given depth from the stack
-+ * pointer and increasing. The next depth to be read is returned.
-+ */
-+int pop_regs(struct jit_context *ctx, u32 mask, u32 excl, int depth)
-+{
-+      int reg;
-+
-+      for (reg = 0; reg < BITS_PER_BYTE * sizeof(mask); reg++)
-+              if (mask & BIT(reg)) {
-+                      if ((excl & BIT(reg)) == 0) {
-+                              if (sizeof(long) == 4)
-+                                      emit(ctx, lw, reg, depth, MIPS_R_SP);
-+                              else /* sizeof(long) == 8 */
-+                                      emit(ctx, ld, reg, depth, MIPS_R_SP);
-+                      }
-+                      depth += sizeof(long);
-+              }
-+
-+      return depth;
-+}
-+
-+/* Compute the 28-bit jump target address from a BPF program location */
-+int get_target(struct jit_context *ctx, u32 loc)
-+{
-+      u32 index = INDEX(ctx->descriptors[loc]);
-+      unsigned long pc = (unsigned long)&ctx->target[ctx->jit_index];
-+      unsigned long addr = (unsigned long)&ctx->target[index];
-+
-+      if (!ctx->target)
-+              return 0;
-+
-+      if ((addr ^ pc) & ~MIPS_JMP_MASK)
-+              return -1;
-+
-+      return addr & MIPS_JMP_MASK;
-+}
-+
-+/* Compute the PC-relative offset to relative BPF program offset */
-+int get_offset(const struct jit_context *ctx, int off)
-+{
-+      return (INDEX(ctx->descriptors[ctx->bpf_index + off]) -
-+              ctx->jit_index - 1) * sizeof(u32);
-+}
-+
-+/* dst = imm (register width) */
-+void emit_mov_i(struct jit_context *ctx, u8 dst, s32 imm)
-+{
-+      if (imm >= -0x8000 && imm <= 0x7fff) {
-+              emit(ctx, addiu, dst, MIPS_R_ZERO, imm);
-+      } else {
-+              emit(ctx, lui, dst, (s16)((u32)imm >> 16));
-+              emit(ctx, ori, dst, dst, (u16)(imm & 0xffff));
-+      }
-+      clobber_reg(ctx, dst);
-+}
-+
-+/* dst = src (register width) */
-+void emit_mov_r(struct jit_context *ctx, u8 dst, u8 src)
-+{
-+      emit(ctx, ori, dst, src, 0);
-+      clobber_reg(ctx, dst);
-+}
-+
-+/* Validate ALU immediate range */
-+bool valid_alu_i(u8 op, s32 imm)
-+{
-+      switch (BPF_OP(op)) {
-+      case BPF_NEG:
-+      case BPF_LSH:
-+      case BPF_RSH:
-+      case BPF_ARSH:
-+              /* All legal eBPF values are valid */
-+              return true;
-+      case BPF_ADD:
-+              /* imm must be 16 bits */
-+              return imm >= -0x8000 && imm <= 0x7fff;
-+      case BPF_SUB:
-+              /* -imm must be 16 bits */
-+              return imm >= -0x7fff && imm <= 0x8000;
-+      case BPF_AND:
-+      case BPF_OR:
-+      case BPF_XOR:
-+              /* imm must be 16 bits unsigned */
-+              return imm >= 0 && imm <= 0xffff;
-+      case BPF_MUL:
-+              /* imm must be zero or a positive power of two */
-+              return imm == 0 || (imm > 0 && is_power_of_2(imm));
-+      case BPF_DIV:
-+      case BPF_MOD:
-+              /* imm must be an 17-bit power of two */
-+              return (u32)imm <= 0x10000 && is_power_of_2((u32)imm);
-+      }
-+      return false;
-+}
-+
-+/* Rewrite ALU immediate operation */
-+bool rewrite_alu_i(u8 op, s32 imm, u8 *alu, s32 *val)
-+{
-+      bool act = true;
-+
-+      switch (BPF_OP(op)) {
-+      case BPF_LSH:
-+      case BPF_RSH:
-+      case BPF_ARSH:
-+      case BPF_ADD:
-+      case BPF_SUB:
-+      case BPF_OR:
-+      case BPF_XOR:
-+              /* imm == 0 is a no-op */
-+              act = imm != 0;
-+              break;
-+      case BPF_MUL:
-+              if (imm == 1) {
-+                      /* dst * 1 is a no-op */
-+                      act = false;
-+              } else if (imm == 0) {
-+                      /* dst * 0 is dst & 0 */
-+                      op = BPF_AND;
-+              } else {
-+                      /* dst * (1 << n) is dst << n */
-+                      op = BPF_LSH;
-+                      imm = ilog2(abs(imm));
-+              }
-+              break;
-+      case BPF_DIV:
-+              if (imm == 1) {
-+                      /* dst / 1 is a no-op */
-+                      act = false;
-+              } else {
-+                      /* dst / (1 << n) is dst >> n */
-+                      op = BPF_RSH;
-+                      imm = ilog2(imm);
-+              }
-+              break;
-+      case BPF_MOD:
-+              /* dst % (1 << n) is dst & ((1 << n) - 1) */
-+              op = BPF_AND;
-+              imm--;
-+              break;
-+      }
-+
-+      *alu = op;
-+      *val = imm;
-+      return act;
-+}
-+
-+/* ALU immediate operation (32-bit) */
-+void emit_alu_i(struct jit_context *ctx, u8 dst, s32 imm, u8 op)
-+{
-+      switch (BPF_OP(op)) {
-+      /* dst = -dst */
-+      case BPF_NEG:
-+              emit(ctx, subu, dst, MIPS_R_ZERO, dst);
-+              break;
-+      /* dst = dst & imm */
-+      case BPF_AND:
-+              emit(ctx, andi, dst, dst, (u16)imm);
-+              break;
-+      /* dst = dst | imm */
-+      case BPF_OR:
-+              emit(ctx, ori, dst, dst, (u16)imm);
-+              break;
-+      /* dst = dst ^ imm */
-+      case BPF_XOR:
-+              emit(ctx, xori, dst, dst, (u16)imm);
-+              break;
-+      /* dst = dst << imm */
-+      case BPF_LSH:
-+              emit(ctx, sll, dst, dst, imm);
-+              break;
-+      /* dst = dst >> imm */
-+      case BPF_RSH:
-+              emit(ctx, srl, dst, dst, imm);
-+              break;
-+      /* dst = dst >> imm (arithmetic) */
-+      case BPF_ARSH:
-+              emit(ctx, sra, dst, dst, imm);
-+              break;
-+      /* dst = dst + imm */
-+      case BPF_ADD:
-+              emit(ctx, addiu, dst, dst, imm);
-+              break;
-+      /* dst = dst - imm */
-+      case BPF_SUB:
-+              emit(ctx, addiu, dst, dst, -imm);
-+              break;
-+      }
-+      clobber_reg(ctx, dst);
-+}
-+
-+/* ALU register operation (32-bit) */
-+void emit_alu_r(struct jit_context *ctx, u8 dst, u8 src, u8 op)
-+{
-+      switch (BPF_OP(op)) {
-+      /* dst = dst & src */
-+      case BPF_AND:
-+              emit(ctx, and, dst, dst, src);
-+              break;
-+      /* dst = dst | src */
-+      case BPF_OR:
-+              emit(ctx, or, dst, dst, src);
-+              break;
-+      /* dst = dst ^ src */
-+      case BPF_XOR:
-+              emit(ctx, xor, dst, dst, src);
-+              break;
-+      /* dst = dst << src */
-+      case BPF_LSH:
-+              emit(ctx, sllv, dst, dst, src);
-+              break;
-+      /* dst = dst >> src */
-+      case BPF_RSH:
-+              emit(ctx, srlv, dst, dst, src);
-+              break;
-+      /* dst = dst >> src (arithmetic) */
-+      case BPF_ARSH:
-+              emit(ctx, srav, dst, dst, src);
-+              break;
-+      /* dst = dst + src */
-+      case BPF_ADD:
-+              emit(ctx, addu, dst, dst, src);
-+              break;
-+      /* dst = dst - src */
-+      case BPF_SUB:
-+              emit(ctx, subu, dst, dst, src);
-+              break;
-+      /* dst = dst * src */
-+      case BPF_MUL:
-+              if (cpu_has_mips32r1 || cpu_has_mips32r6) {
-+                      emit(ctx, mul, dst, dst, src);
-+              } else {
-+                      emit(ctx, multu, dst, src);
-+                      emit(ctx, mflo, dst);
-+              }
-+              break;
-+      /* dst = dst / src */
-+      case BPF_DIV:
-+              if (cpu_has_mips32r6) {
-+                      emit(ctx, divu_r6, dst, dst, src);
-+              } else {
-+                      emit(ctx, divu, dst, src);
-+                      emit(ctx, mflo, dst);
-+              }
-+              break;
-+      /* dst = dst % src */
-+      case BPF_MOD:
-+              if (cpu_has_mips32r6) {
-+                      emit(ctx, modu, dst, dst, src);
-+              } else {
-+                      emit(ctx, divu, dst, src);
-+                      emit(ctx, mfhi, dst);
-+              }
-+              break;
-+      }
-+      clobber_reg(ctx, dst);
-+}
-+
-+/* Atomic read-modify-write (32-bit) */
-+void emit_atomic_r(struct jit_context *ctx, u8 dst, u8 src, s16 off, u8 code)
-+{
-+      emit(ctx, ll, MIPS_R_T9, off, dst);
-+      switch (code) {
-+      case BPF_ADD:
-+              emit(ctx, addu, MIPS_R_T8, MIPS_R_T9, src);
-+              break;
-+      case BPF_AND:
-+              emit(ctx, and, MIPS_R_T8, MIPS_R_T9, src);
-+              break;
-+      case BPF_OR:
-+              emit(ctx, or, MIPS_R_T8, MIPS_R_T9, src);
-+              break;
-+      case BPF_XOR:
-+              emit(ctx, xor, MIPS_R_T8, MIPS_R_T9, src);
-+              break;
-+      }
-+      emit(ctx, sc, MIPS_R_T8, off, dst);
-+      emit(ctx, beqz, MIPS_R_T8, -16);
-+      emit(ctx, nop); /* Delay slot */
-+}
-+
-+/* Atomic compare-and-exchange (32-bit) */
-+void emit_cmpxchg_r(struct jit_context *ctx, u8 dst, u8 src, u8 res, s16 off)
-+{
-+      emit(ctx, ll, MIPS_R_T9, off, dst);
-+      emit(ctx, bne, MIPS_R_T9, res, 12);
-+      emit(ctx, move, MIPS_R_T8, src);     /* Delay slot */
-+      emit(ctx, sc, MIPS_R_T8, off, dst);
-+      emit(ctx, beqz, MIPS_R_T8, -20);
-+      emit(ctx, move, res, MIPS_R_T9);     /* Delay slot */
-+      clobber_reg(ctx, res);
-+}
-+
-+/* Swap bytes and truncate a register word or half word */
-+void emit_bswap_r(struct jit_context *ctx, u8 dst, u32 width)
-+{
-+      u8 tmp = MIPS_R_T8;
-+      u8 msk = MIPS_R_T9;
-+
-+      switch (width) {
-+      /* Swap bytes in a word */
-+      case 32:
-+              if (cpu_has_mips32r2 || cpu_has_mips32r6) {
-+                      emit(ctx, wsbh, dst, dst);
-+                      emit(ctx, rotr, dst, dst, 16);
-+              } else {
-+                      emit(ctx, sll, tmp, dst, 16);    /* tmp  = dst << 16 */
-+                      emit(ctx, srl, dst, dst, 16);    /* dst = dst >> 16  */
-+                      emit(ctx, or, dst, dst, tmp);    /* dst = dst | tmp  */
-+
-+                      emit(ctx, lui, msk, 0xff);       /* msk = 0x00ff0000 */
-+                      emit(ctx, ori, msk, msk, 0xff);  /* msk = msk | 0xff */
-+
-+                      emit(ctx, and, tmp, dst, msk);   /* tmp = dst & msk  */
-+                      emit(ctx, sll, tmp, tmp, 8);     /* tmp = tmp << 8   */
-+                      emit(ctx, srl, dst, dst, 8);     /* dst = dst >> 8   */
-+                      emit(ctx, and, dst, dst, msk);   /* dst = dst & msk  */
-+                      emit(ctx, or, dst, dst, tmp);    /* reg = dst | tmp  */
-+              }
-+              break;
-+      /* Swap bytes in a half word */
-+      case 16:
-+              if (cpu_has_mips32r2 || cpu_has_mips32r6) {
-+                      emit(ctx, wsbh, dst, dst);
-+                      emit(ctx, andi, dst, dst, 0xffff);
-+              } else {
-+                      emit(ctx, andi, tmp, dst, 0xff00); /* t = d & 0xff00 */
-+                      emit(ctx, srl, tmp, tmp, 8);       /* t = t >> 8     */
-+                      emit(ctx, andi, dst, dst, 0x00ff); /* d = d & 0x00ff */
-+                      emit(ctx, sll, dst, dst, 8);       /* d = d << 8     */
-+                      emit(ctx, or,  dst, dst, tmp);     /* d = d | t      */
-+              }
-+              break;
-+      }
-+      clobber_reg(ctx, dst);
-+}
-+
-+/* Validate jump immediate range */
-+bool valid_jmp_i(u8 op, s32 imm)
-+{
-+      switch (op) {
-+      case JIT_JNOP:
-+              /* Immediate value not used */
-+              return true;
-+      case BPF_JEQ:
-+      case BPF_JNE:
-+              /* No immediate operation */
-+              return false;
-+      case BPF_JSET:
-+      case JIT_JNSET:
-+              /* imm must be 16 bits unsigned */
-+              return imm >= 0 && imm <= 0xffff;
-+      case BPF_JGE:
-+      case BPF_JLT:
-+      case BPF_JSGE:
-+      case BPF_JSLT:
-+              /* imm must be 16 bits */
-+              return imm >= -0x8000 && imm <= 0x7fff;
-+      case BPF_JGT:
-+      case BPF_JLE:
-+      case BPF_JSGT:
-+      case BPF_JSLE:
-+              /* imm + 1 must be 16 bits */
-+              return imm >= -0x8001 && imm <= 0x7ffe;
-+      }
-+      return false;
-+}
-+
-+/* Invert a conditional jump operation */
-+static u8 invert_jmp(u8 op)
-+{
-+      switch (op) {
-+      case BPF_JA: return JIT_JNOP;
-+      case BPF_JEQ: return BPF_JNE;
-+      case BPF_JNE: return BPF_JEQ;
-+      case BPF_JSET: return JIT_JNSET;
-+      case BPF_JGT: return BPF_JLE;
-+      case BPF_JGE: return BPF_JLT;
-+      case BPF_JLT: return BPF_JGE;
-+      case BPF_JLE: return BPF_JGT;
-+      case BPF_JSGT: return BPF_JSLE;
-+      case BPF_JSGE: return BPF_JSLT;
-+      case BPF_JSLT: return BPF_JSGE;
-+      case BPF_JSLE: return BPF_JSGT;
-+      }
-+      return 0;
-+}
-+
-+/* Prepare a PC-relative jump operation */
-+static void setup_jmp(struct jit_context *ctx, u8 bpf_op,
-+                    s16 bpf_off, u8 *jit_op, s32 *jit_off)
-+{
-+      u32 *descp = &ctx->descriptors[ctx->bpf_index];
-+      int op = bpf_op;
-+      int offset = 0;
-+
-+      /* Do not compute offsets on the first pass */
-+      if (INDEX(*descp) == 0)
-+              goto done;
-+
-+      /* Skip jumps never taken */
-+      if (bpf_op == JIT_JNOP)
-+              goto done;
-+
-+      /* Convert jumps always taken */
-+      if (bpf_op == BPF_JA)
-+              *descp |= JIT_DESC_CONVERT;
-+
-+      /*
-+       * Current ctx->jit_index points to the start of the branch preamble.
-+       * Since the preamble differs among different branch conditionals,
-+       * the current index cannot be used to compute the branch offset.
-+       * Instead, we use the offset table value for the next instruction,
-+       * which gives the index immediately after the branch delay slot.
-+       */
-+      if (!CONVERTED(*descp)) {
-+              int target = ctx->bpf_index + bpf_off + 1;
-+              int origin = ctx->bpf_index + 1;
-+
-+              offset = (INDEX(ctx->descriptors[target]) -
-+                        INDEX(ctx->descriptors[origin]) + 1) * sizeof(u32);
-+      }
-+
-+      /*
-+       * The PC-relative branch offset field on MIPS is 18 bits signed,
-+       * so if the computed offset is larger than this we generate a an
-+       * absolute jump that we skip with an inverted conditional branch.
-+       */
-+      if (CONVERTED(*descp) || offset < -0x20000 || offset > 0x1ffff) {
-+              offset = 3 * sizeof(u32);
-+              op = invert_jmp(bpf_op);
-+              ctx->changes += !CONVERTED(*descp);
-+              *descp |= JIT_DESC_CONVERT;
-+      }
-+
-+done:
-+      *jit_off = offset;
-+      *jit_op = op;
-+}
-+
-+/* Prepare a PC-relative jump operation with immediate conditional */
-+void setup_jmp_i(struct jit_context *ctx, s32 imm, u8 width,
-+               u8 bpf_op, s16 bpf_off, u8 *jit_op, s32 *jit_off)
-+{
-+      bool always = false;
-+      bool never = false;
-+
-+      switch (bpf_op) {
-+      case BPF_JEQ:
-+      case BPF_JNE:
-+              break;
-+      case BPF_JSET:
-+      case BPF_JLT:
-+              never = imm == 0;
-+              break;
-+      case BPF_JGE:
-+              always = imm == 0;
-+              break;
-+      case BPF_JGT:
-+              never = (u32)imm == U32_MAX;
-+              break;
-+      case BPF_JLE:
-+              always = (u32)imm == U32_MAX;
-+              break;
-+      case BPF_JSGT:
-+              never = imm == S32_MAX && width == 32;
-+              break;
-+      case BPF_JSGE:
-+              always = imm == S32_MIN && width == 32;
-+              break;
-+      case BPF_JSLT:
-+              never = imm == S32_MIN && width == 32;
-+              break;
-+      case BPF_JSLE:
-+              always = imm == S32_MAX && width == 32;
-+              break;
-+      }
-+
-+      if (never)
-+              bpf_op = JIT_JNOP;
-+      if (always)
-+              bpf_op = BPF_JA;
-+      setup_jmp(ctx, bpf_op, bpf_off, jit_op, jit_off);
-+}
-+
-+/* Prepare a PC-relative jump operation with register conditional */
-+void setup_jmp_r(struct jit_context *ctx, bool same_reg,
-+               u8 bpf_op, s16 bpf_off, u8 *jit_op, s32 *jit_off)
-+{
-+      switch (bpf_op) {
-+      case BPF_JSET:
-+              break;
-+      case BPF_JEQ:
-+      case BPF_JGE:
-+      case BPF_JLE:
-+      case BPF_JSGE:
-+      case BPF_JSLE:
-+              if (same_reg)
-+                      bpf_op = BPF_JA;
-+              break;
-+      case BPF_JNE:
-+      case BPF_JLT:
-+      case BPF_JGT:
-+      case BPF_JSGT:
-+      case BPF_JSLT:
-+              if (same_reg)
-+                      bpf_op = JIT_JNOP;
-+              break;
-+      }
-+      setup_jmp(ctx, bpf_op, bpf_off, jit_op, jit_off);
-+}
-+
-+/* Finish a PC-relative jump operation */
-+int finish_jmp(struct jit_context *ctx, u8 jit_op, s16 bpf_off)
-+{
-+      /* Emit conditional branch delay slot */
-+      if (jit_op != JIT_JNOP)
-+              emit(ctx, nop);
-+      /*
-+       * Emit an absolute long jump with delay slot,
-+       * if the PC-relative branch was converted.
-+       */
-+      if (CONVERTED(ctx->descriptors[ctx->bpf_index])) {
-+              int target = get_target(ctx, ctx->bpf_index + bpf_off + 1);
-+
-+              if (target < 0)
-+                      return -1;
-+              emit(ctx, j, target);
-+              emit(ctx, nop);
-+      }
-+      return 0;
-+}
-+
-+/* Jump immediate (32-bit) */
-+void emit_jmp_i(struct jit_context *ctx, u8 dst, s32 imm, s32 off, u8 op)
-+{
-+      switch (op) {
-+      /* No-op, used internally for branch optimization */
-+      case JIT_JNOP:
-+              break;
-+      /* PC += off if dst & imm */
-+      case BPF_JSET:
-+              emit(ctx, andi, MIPS_R_T9, dst, (u16)imm);
-+              emit(ctx, bnez, MIPS_R_T9, off);
-+              break;
-+      /* PC += off if (dst & imm) == 0 (not in BPF, used for long jumps) */
-+      case JIT_JNSET:
-+              emit(ctx, andi, MIPS_R_T9, dst, (u16)imm);
-+              emit(ctx, beqz, MIPS_R_T9, off);
-+              break;
-+      /* PC += off if dst > imm */
-+      case BPF_JGT:
-+              emit(ctx, sltiu, MIPS_R_T9, dst, imm + 1);
-+              emit(ctx, beqz, MIPS_R_T9, off);
-+              break;
-+      /* PC += off if dst >= imm */
-+      case BPF_JGE:
-+              emit(ctx, sltiu, MIPS_R_T9, dst, imm);
-+              emit(ctx, beqz, MIPS_R_T9, off);
-+              break;
-+      /* PC += off if dst < imm */
-+      case BPF_JLT:
-+              emit(ctx, sltiu, MIPS_R_T9, dst, imm);
-+              emit(ctx, bnez, MIPS_R_T9, off);
-+              break;
-+      /* PC += off if dst <= imm */
-+      case BPF_JLE:
-+              emit(ctx, sltiu, MIPS_R_T9, dst, imm + 1);
-+              emit(ctx, bnez, MIPS_R_T9, off);
-+              break;
-+      /* PC += off if dst > imm (signed) */
-+      case BPF_JSGT:
-+              emit(ctx, slti, MIPS_R_T9, dst, imm + 1);
-+              emit(ctx, beqz, MIPS_R_T9, off);
-+              break;
-+      /* PC += off if dst >= imm (signed) */
-+      case BPF_JSGE:
-+              emit(ctx, slti, MIPS_R_T9, dst, imm);
-+              emit(ctx, beqz, MIPS_R_T9, off);
-+              break;
-+      /* PC += off if dst < imm (signed) */
-+      case BPF_JSLT:
-+              emit(ctx, slti, MIPS_R_T9, dst, imm);
-+              emit(ctx, bnez, MIPS_R_T9, off);
-+              break;
-+      /* PC += off if dst <= imm (signed) */
-+      case BPF_JSLE:
-+              emit(ctx, slti, MIPS_R_T9, dst, imm + 1);
-+              emit(ctx, bnez, MIPS_R_T9, off);
-+              break;
-+      }
-+}
-+
-+/* Jump register (32-bit) */
-+void emit_jmp_r(struct jit_context *ctx, u8 dst, u8 src, s32 off, u8 op)
-+{
-+      switch (op) {
-+      /* No-op, used internally for branch optimization */
-+      case JIT_JNOP:
-+              break;
-+      /* PC += off if dst == src */
-+      case BPF_JEQ:
-+              emit(ctx, beq, dst, src, off);
-+              break;
-+      /* PC += off if dst != src */
-+      case BPF_JNE:
-+              emit(ctx, bne, dst, src, off);
-+              break;
-+      /* PC += off if dst & src */
-+      case BPF_JSET:
-+              emit(ctx, and, MIPS_R_T9, dst, src);
-+              emit(ctx, bnez, MIPS_R_T9, off);
-+              break;
-+      /* PC += off if (dst & imm) == 0 (not in BPF, used for long jumps) */
-+      case JIT_JNSET:
-+              emit(ctx, and, MIPS_R_T9, dst, src);
-+              emit(ctx, beqz, MIPS_R_T9, off);
-+              break;
-+      /* PC += off if dst > src */
-+      case BPF_JGT:
-+              emit(ctx, sltu, MIPS_R_T9, src, dst);
-+              emit(ctx, bnez, MIPS_R_T9, off);
-+              break;
-+      /* PC += off if dst >= src */
-+      case BPF_JGE:
-+              emit(ctx, sltu, MIPS_R_T9, dst, src);
-+              emit(ctx, beqz, MIPS_R_T9, off);
-+              break;
-+      /* PC += off if dst < src */
-+      case BPF_JLT:
-+              emit(ctx, sltu, MIPS_R_T9, dst, src);
-+              emit(ctx, bnez, MIPS_R_T9, off);
-+              break;
-+      /* PC += off if dst <= src */
-+      case BPF_JLE:
-+              emit(ctx, sltu, MIPS_R_T9, src, dst);
-+              emit(ctx, beqz, MIPS_R_T9, off);
-+              break;
-+      /* PC += off if dst > src (signed) */
-+      case BPF_JSGT:
-+              emit(ctx, slt, MIPS_R_T9, src, dst);
-+              emit(ctx, bnez, MIPS_R_T9, off);
-+              break;
-+      /* PC += off if dst >= src (signed) */
-+      case BPF_JSGE:
-+              emit(ctx, slt, MIPS_R_T9, dst, src);
-+              emit(ctx, beqz, MIPS_R_T9, off);
-+              break;
-+      /* PC += off if dst < src (signed) */
-+      case BPF_JSLT:
-+              emit(ctx, slt, MIPS_R_T9, dst, src);
-+              emit(ctx, bnez, MIPS_R_T9, off);
-+              break;
-+      /* PC += off if dst <= src (signed) */
-+      case BPF_JSLE:
-+              emit(ctx, slt, MIPS_R_T9, src, dst);
-+              emit(ctx, beqz, MIPS_R_T9, off);
-+              break;
-+      }
-+}
-+
-+/* Jump always */
-+int emit_ja(struct jit_context *ctx, s16 off)
-+{
-+      int target = get_target(ctx, ctx->bpf_index + off + 1);
-+
-+      if (target < 0)
-+              return -1;
-+      emit(ctx, j, target);
-+      emit(ctx, nop);
-+      return 0;
-+}
-+
-+/* Jump to epilogue */
-+int emit_exit(struct jit_context *ctx)
-+{
-+      int target = get_target(ctx, ctx->program->len);
-+
-+      if (target < 0)
-+              return -1;
-+      emit(ctx, j, target);
-+      emit(ctx, nop);
-+      return 0;
-+}
-+
-+/* Build the program body from eBPF bytecode */
-+static int build_body(struct jit_context *ctx)
-+{
-+      const struct bpf_prog *prog = ctx->program;
-+      unsigned int i;
-+
-+      ctx->stack_used = 0;
-+      for (i = 0; i < prog->len; i++) {
-+              const struct bpf_insn *insn = &prog->insnsi[i];
-+              u32 *descp = &ctx->descriptors[i];
-+              int ret;
-+
-+              access_reg(ctx, insn->src_reg);
-+              access_reg(ctx, insn->dst_reg);
-+
-+              ctx->bpf_index = i;
-+              if (ctx->target == NULL) {
-+                      ctx->changes += INDEX(*descp) != ctx->jit_index;
-+                      *descp &= JIT_DESC_CONVERT;
-+                      *descp |= ctx->jit_index;
-+              }
-+
-+              ret = build_insn(insn, ctx);
-+              if (ret < 0)
-+                      return ret;
-+
-+              if (ret > 0) {
-+                      i++;
-+                      if (ctx->target == NULL)
-+                              descp[1] = ctx->jit_index;
-+              }
-+      }
-+
-+      /* Store the end offset, where the epilogue begins */
-+      ctx->descriptors[prog->len] = ctx->jit_index;
-+      return 0;
-+}
-+
-+/* Set the branch conversion flag on all instructions */
-+static void set_convert_flag(struct jit_context *ctx, bool enable)
-+{
-+      const struct bpf_prog *prog = ctx->program;
-+      u32 flag = enable ? JIT_DESC_CONVERT : 0;
-+      unsigned int i;
-+
-+      for (i = 0; i <= prog->len; i++)
-+              ctx->descriptors[i] = INDEX(ctx->descriptors[i]) | flag;
-+}
-+
-+static void jit_fill_hole(void *area, unsigned int size)
-+{
-+      u32 *p;
-+
-+      /* We are guaranteed to have aligned memory. */
-+      for (p = area; size >= sizeof(u32); size -= sizeof(u32))
-+              uasm_i_break(&p, BRK_BUG); /* Increments p */
-+}
-+
-+bool bpf_jit_needs_zext(void)
-+{
-+      return true;
-+}
-+
-+struct bpf_prog *bpf_int_jit_compile(struct bpf_prog *prog)
-+{
-+      struct bpf_prog *tmp, *orig_prog = prog;
-+      struct bpf_binary_header *header = NULL;
-+      struct jit_context ctx;
-+      bool tmp_blinded = false;
-+      unsigned int tmp_idx;
-+      unsigned int image_size;
-+      u8 *image_ptr;
-+      int tries;
-+
-+      /*
-+       * If BPF JIT was not enabled then we must fall back to
-+       * the interpreter.
-+       */
-+      if (!prog->jit_requested)
-+              return orig_prog;
-+      /*
-+       * If constant blinding was enabled and we failed during blinding
-+       * then we must fall back to the interpreter. Otherwise, we save
-+       * the new JITed code.
-+       */
-+      tmp = bpf_jit_blind_constants(prog);
-+      if (IS_ERR(tmp))
-+              return orig_prog;
-+      if (tmp != prog) {
-+              tmp_blinded = true;
-+              prog = tmp;
-+      }
-+
-+      memset(&ctx, 0, sizeof(ctx));
-+      ctx.program = prog;
-+
-+      /*
-+       * Not able to allocate memory for descriptors[], then
-+       * we must fall back to the interpreter
-+       */
-+      ctx.descriptors = kcalloc(prog->len + 1, sizeof(*ctx.descriptors),
-+                                GFP_KERNEL);
-+      if (ctx.descriptors == NULL)
-+              goto out_err;
-+
-+      /* First pass discovers used resources */
-+      if (build_body(&ctx) < 0)
-+              goto out_err;
-+      /*
-+       * Second pass computes instruction offsets.
-+       * If any PC-relative branches are out of range, a sequence of
-+       * a PC-relative branch + a jump is generated, and we have to
-+       * try again from the beginning to generate the new offsets.
-+       * This is done until no additional conversions are necessary.
-+       * The last two iterations are done with all branches being
-+       * converted, to guarantee offset table convergence within a
-+       * fixed number of iterations.
-+       */
-+      ctx.jit_index = 0;
-+      build_prologue(&ctx);
-+      tmp_idx = ctx.jit_index;
-+
-+      tries = JIT_MAX_ITERATIONS;
-+      do {
-+              ctx.jit_index = tmp_idx;
-+              ctx.changes = 0;
-+              if (tries == 2)
-+                      set_convert_flag(&ctx, true);
-+              if (build_body(&ctx) < 0)
-+                      goto out_err;
-+      } while (ctx.changes > 0 && --tries > 0);
-+
-+      if (WARN_ONCE(ctx.changes > 0, "JIT offsets failed to converge"))
-+              goto out_err;
-+
-+      build_epilogue(&ctx, MIPS_R_RA);
-+
-+      /* Now we know the size of the structure to make */
-+      image_size = sizeof(u32) * ctx.jit_index;
-+      header = bpf_jit_binary_alloc(image_size, &image_ptr,
-+                                    sizeof(u32), jit_fill_hole);
-+      /*
-+       * Not able to allocate memory for the structure then
-+       * we must fall back to the interpretation
-+       */
-+      if (header == NULL)
-+              goto out_err;
-+
-+      /* Actual pass to generate final JIT code */
-+      ctx.target = (u32 *)image_ptr;
-+      ctx.jit_index = 0;
-+
-+      /*
-+       * If building the JITed code fails somehow,
-+       * we fall back to the interpretation.
-+       */
-+      build_prologue(&ctx);
-+      if (build_body(&ctx) < 0)
-+              goto out_err;
-+      build_epilogue(&ctx, MIPS_R_RA);
-+
-+      /* Populate line info meta data */
-+      set_convert_flag(&ctx, false);
-+      bpf_prog_fill_jited_linfo(prog, &ctx.descriptors[1]);
-+
-+      /* Set as read-only exec and flush instruction cache */
-+      bpf_jit_binary_lock_ro(header);
-+      flush_icache_range((unsigned long)header,
-+                         (unsigned long)&ctx.target[ctx.jit_index]);
-+
-+      if (bpf_jit_enable > 1)
-+              bpf_jit_dump(prog->len, image_size, 2, ctx.target);
-+
-+      prog->bpf_func = (void *)ctx.target;
-+      prog->jited = 1;
-+      prog->jited_len = image_size;
-+
-+out:
-+      if (tmp_blinded)
-+              bpf_jit_prog_release_other(prog, prog == orig_prog ?
-+                                         tmp : orig_prog);
-+      kfree(ctx.descriptors);
-+      return prog;
-+
-+out_err:
-+      prog = orig_prog;
-+      if (header)
-+              bpf_jit_binary_free(header);
-+      goto out;
-+}
---- /dev/null
-+++ b/arch/mips/net/bpf_jit_comp.h
-@@ -0,0 +1,211 @@
-+/* SPDX-License-Identifier: GPL-2.0-only */
-+/*
-+ * Just-In-Time compiler for eBPF bytecode on 32-bit and 64-bit MIPS.
-+ *
-+ * Copyright (c) 2021 Anyfi Networks AB.
-+ * Author: Johan Almbladh <[email protected]>
-+ *
-+ * Based on code and ideas from
-+ * Copyright (c) 2017 Cavium, Inc.
-+ * Copyright (c) 2017 Shubham Bansal <[email protected]>
-+ * Copyright (c) 2011 Mircea Gherzan <[email protected]>
-+ */
-+
-+#ifndef _BPF_JIT_COMP_H
-+#define _BPF_JIT_COMP_H
-+
-+/* MIPS registers */
-+#define MIPS_R_ZERO   0   /* Const zero */
-+#define MIPS_R_AT     1   /* Asm temp   */
-+#define MIPS_R_V0     2   /* Result     */
-+#define MIPS_R_V1     3   /* Result     */
-+#define MIPS_R_A0     4   /* Argument   */
-+#define MIPS_R_A1     5   /* Argument   */
-+#define MIPS_R_A2     6   /* Argument   */
-+#define MIPS_R_A3     7   /* Argument   */
-+#define MIPS_R_A4     8   /* Arg (n64)  */
-+#define MIPS_R_A5     9   /* Arg (n64)  */
-+#define MIPS_R_A6     10  /* Arg (n64)  */
-+#define MIPS_R_A7     11  /* Arg (n64)  */
-+#define MIPS_R_T0     8   /* Temp (o32) */
-+#define MIPS_R_T1     9   /* Temp (o32) */
-+#define MIPS_R_T2     10  /* Temp (o32) */
-+#define MIPS_R_T3     11  /* Temp (o32) */
-+#define MIPS_R_T4     12  /* Temporary  */
-+#define MIPS_R_T5     13  /* Temporary  */
-+#define MIPS_R_T6     14  /* Temporary  */
-+#define MIPS_R_T7     15  /* Temporary  */
-+#define MIPS_R_S0     16  /* Saved      */
-+#define MIPS_R_S1     17  /* Saved      */
-+#define MIPS_R_S2     18  /* Saved      */
-+#define MIPS_R_S3     19  /* Saved      */
-+#define MIPS_R_S4     20  /* Saved      */
-+#define MIPS_R_S5     21  /* Saved      */
-+#define MIPS_R_S6     22  /* Saved      */
-+#define MIPS_R_S7     23  /* Saved      */
-+#define MIPS_R_T8     24  /* Temporary  */
-+#define MIPS_R_T9     25  /* Temporary  */
-+/*      MIPS_R_K0     26     Reserved   */
-+/*      MIPS_R_K1     27     Reserved   */
-+#define MIPS_R_GP     28  /* Global ptr */
-+#define MIPS_R_SP     29  /* Stack ptr  */
-+#define MIPS_R_FP     30  /* Frame ptr  */
-+#define MIPS_R_RA     31  /* Return     */
-+
-+/*
-+ * Jump address mask for immediate jumps. The four most significant bits
-+ * must be equal to PC.
-+ */
-+#define MIPS_JMP_MASK 0x0fffffffUL
-+
-+/* Maximum number of iterations in offset table computation */
-+#define JIT_MAX_ITERATIONS    8
-+
-+/*
-+ * Jump pseudo-instructions used internally
-+ * for branch conversion and branch optimization.
-+ */
-+#define JIT_JNSET     0xe0
-+#define JIT_JNOP      0xf0
-+
-+/* Descriptor flag for PC-relative branch conversion */
-+#define JIT_DESC_CONVERT      BIT(31)
-+
-+/* JIT context for an eBPF program */
-+struct jit_context {
-+      struct bpf_prog *program;     /* The eBPF program being JITed        */
-+      u32 *descriptors;             /* eBPF to JITed CPU insn descriptors  */
-+      u32 *target;                  /* JITed code buffer                   */
-+      u32 bpf_index;                /* Index of current BPF program insn   */
-+      u32 jit_index;                /* Index of current JIT target insn    */
-+      u32 changes;                  /* Number of PC-relative branch conv   */
-+      u32 accessed;                 /* Bit mask of read eBPF registers     */
-+      u32 clobbered;                /* Bit mask of modified CPU registers  */
-+      u32 stack_size;               /* Total allocated stack size in bytes */
-+      u32 saved_size;               /* Size of callee-saved registers      */
-+      u32 stack_used;               /* Stack size used for function calls  */
-+};
-+
-+/* Emit the instruction if the JIT memory space has been allocated */
-+#define emit(ctx, func, ...)                                  \
-+do {                                                          \
-+      if ((ctx)->target != NULL) {                            \
-+              u32 *p = &(ctx)->target[ctx->jit_index];        \
-+              uasm_i_##func(&p, ##__VA_ARGS__);               \
-+      }                                                       \
-+      (ctx)->jit_index++;                                     \
-+} while (0)
-+
-+/*
-+ * Mark a BPF register as accessed, it needs to be
-+ * initialized by the program if expected, e.g. FP.
-+ */
-+static inline void access_reg(struct jit_context *ctx, u8 reg)
-+{
-+      ctx->accessed |= BIT(reg);
-+}
-+
-+/*
-+ * Mark a CPU register as clobbered, it needs to be
-+ * saved/restored by the program if callee-saved.
-+ */
-+static inline void clobber_reg(struct jit_context *ctx, u8 reg)
-+{
-+      ctx->clobbered |= BIT(reg);
-+}
-+
-+/*
-+ * Push registers on the stack, starting at a given depth from the stack
-+ * pointer and increasing. The next depth to be written is returned.
-+ */
-+int push_regs(struct jit_context *ctx, u32 mask, u32 excl, int depth);
-+
-+/*
-+ * Pop registers from the stack, starting at a given depth from the stack
-+ * pointer and increasing. The next depth to be read is returned.
-+ */
-+int pop_regs(struct jit_context *ctx, u32 mask, u32 excl, int depth);
-+
-+/* Compute the 28-bit jump target address from a BPF program location */
-+int get_target(struct jit_context *ctx, u32 loc);
-+
-+/* Compute the PC-relative offset to relative BPF program offset */
-+int get_offset(const struct jit_context *ctx, int off);
-+
-+/* dst = imm (32-bit) */
-+void emit_mov_i(struct jit_context *ctx, u8 dst, s32 imm);
-+
-+/* dst = src (32-bit) */
-+void emit_mov_r(struct jit_context *ctx, u8 dst, u8 src);
-+
-+/* Validate ALU/ALU64 immediate range */
-+bool valid_alu_i(u8 op, s32 imm);
-+
-+/* Rewrite ALU/ALU64 immediate operation */
-+bool rewrite_alu_i(u8 op, s32 imm, u8 *alu, s32 *val);
-+
-+/* ALU immediate operation (32-bit) */
-+void emit_alu_i(struct jit_context *ctx, u8 dst, s32 imm, u8 op);
-+
-+/* ALU register operation (32-bit) */
-+void emit_alu_r(struct jit_context *ctx, u8 dst, u8 src, u8 op);
-+
-+/* Atomic read-modify-write (32-bit) */
-+void emit_atomic_r(struct jit_context *ctx, u8 dst, u8 src, s16 off, u8 code);
-+
-+/* Atomic compare-and-exchange (32-bit) */
-+void emit_cmpxchg_r(struct jit_context *ctx, u8 dst, u8 src, u8 res, s16 off);
-+
-+/* Swap bytes and truncate a register word or half word */
-+void emit_bswap_r(struct jit_context *ctx, u8 dst, u32 width);
-+
-+/* Validate JMP/JMP32 immediate range */
-+bool valid_jmp_i(u8 op, s32 imm);
-+
-+/* Prepare a PC-relative jump operation with immediate conditional */
-+void setup_jmp_i(struct jit_context *ctx, s32 imm, u8 width,
-+               u8 bpf_op, s16 bpf_off, u8 *jit_op, s32 *jit_off);
-+
-+/* Prepare a PC-relative jump operation with register conditional */
-+void setup_jmp_r(struct jit_context *ctx, bool same_reg,
-+               u8 bpf_op, s16 bpf_off, u8 *jit_op, s32 *jit_off);
-+
-+/* Finish a PC-relative jump operation */
-+int finish_jmp(struct jit_context *ctx, u8 jit_op, s16 bpf_off);
-+
-+/* Conditional JMP/JMP32 immediate */
-+void emit_jmp_i(struct jit_context *ctx, u8 dst, s32 imm, s32 off, u8 op);
-+
-+/* Conditional JMP/JMP32 register */
-+void emit_jmp_r(struct jit_context *ctx, u8 dst, u8 src, s32 off, u8 op);
-+
-+/* Jump always */
-+int emit_ja(struct jit_context *ctx, s16 off);
-+
-+/* Jump to epilogue */
-+int emit_exit(struct jit_context *ctx);
-+
-+/*
-+ * Build program prologue to set up the stack and registers.
-+ * This function is implemented separately for 32-bit and 64-bit JITs.
-+ */
-+void build_prologue(struct jit_context *ctx);
-+
-+/*
-+ * Build the program epilogue to restore the stack and registers.
-+ * This function is implemented separately for 32-bit and 64-bit JITs.
-+ */
-+void build_epilogue(struct jit_context *ctx, int dest_reg);
-+
-+/*
-+ * Convert an eBPF instruction to native instruction, i.e
-+ * JITs an eBPF instruction.
-+ * Returns :
-+ *    0  - Successfully JITed an 8-byte eBPF instruction
-+ *    >0 - Successfully JITed a 16-byte eBPF instruction
-+ *    <0 - Failed to JIT.
-+ * This function is implemented separately for 32-bit and 64-bit JITs.
-+ */
-+int build_insn(const struct bpf_insn *insn, struct jit_context *ctx);
-+
-+#endif /* _BPF_JIT_COMP_H */
---- /dev/null
-+++ b/arch/mips/net/bpf_jit_comp32.c
-@@ -0,0 +1,1741 @@
-+// SPDX-License-Identifier: GPL-2.0-only
-+/*
-+ * Just-In-Time compiler for eBPF bytecode on MIPS.
-+ * Implementation of JIT functions for 32-bit CPUs.
-+ *
-+ * Copyright (c) 2021 Anyfi Networks AB.
-+ * Author: Johan Almbladh <[email protected]>
-+ *
-+ * Based on code and ideas from
-+ * Copyright (c) 2017 Cavium, Inc.
-+ * Copyright (c) 2017 Shubham Bansal <[email protected]>
-+ * Copyright (c) 2011 Mircea Gherzan <[email protected]>
-+ */
-+
-+#include <linux/math64.h>
-+#include <linux/errno.h>
-+#include <linux/filter.h>
-+#include <linux/bpf.h>
-+#include <asm/cpu-features.h>
-+#include <asm/isa-rev.h>
-+#include <asm/uasm.h>
-+
-+#include "bpf_jit_comp.h"
-+
-+/* MIPS a4-a7 are not available in the o32 ABI */
-+#undef MIPS_R_A4
-+#undef MIPS_R_A5
-+#undef MIPS_R_A6
-+#undef MIPS_R_A7
-+
-+/* Stack is 8-byte aligned in o32 ABI */
-+#define MIPS_STACK_ALIGNMENT 8
-+
-+/*
-+ * The top 16 bytes of a stack frame is reserved for the callee in O32 ABI.
-+ * This corresponds to stack space for register arguments a0-a3.
-+ */
-+#define JIT_RESERVED_STACK 16
-+
-+/* Temporary 64-bit register used by JIT */
-+#define JIT_REG_TMP MAX_BPF_JIT_REG
-+
-+/*
-+ * Number of prologue bytes to skip when doing a tail call.
-+ * Tail call count (TCC) initialization (8 bytes) always, plus
-+ * R0-to-v0 assignment (4 bytes) if big endian.
-+ */
-+#ifdef __BIG_ENDIAN
-+#define JIT_TCALL_SKIP 12
-+#else
-+#define JIT_TCALL_SKIP 8
-+#endif
-+
-+/* CPU registers holding the callee return value */
-+#define JIT_RETURN_REGS         \
-+      (BIT(MIPS_R_V0) | \
-+       BIT(MIPS_R_V1))
-+
-+/* CPU registers arguments passed to callee directly */
-+#define JIT_ARG_REGS      \
-+      (BIT(MIPS_R_A0) | \
-+       BIT(MIPS_R_A1) | \
-+       BIT(MIPS_R_A2) | \
-+       BIT(MIPS_R_A3))
-+
-+/* CPU register arguments passed to callee on stack */
-+#define JIT_STACK_REGS    \
-+      (BIT(MIPS_R_T0) | \
-+       BIT(MIPS_R_T1) | \
-+       BIT(MIPS_R_T2) | \
-+       BIT(MIPS_R_T3) | \
-+       BIT(MIPS_R_T4) | \
-+       BIT(MIPS_R_T5))
-+
-+/* Caller-saved CPU registers */
-+#define JIT_CALLER_REGS    \
-+      (JIT_RETURN_REGS | \
-+       JIT_ARG_REGS    | \
-+       JIT_STACK_REGS)
-+
-+/* Callee-saved CPU registers */
-+#define JIT_CALLEE_REGS   \
-+      (BIT(MIPS_R_S0) | \
-+       BIT(MIPS_R_S1) | \
-+       BIT(MIPS_R_S2) | \
-+       BIT(MIPS_R_S3) | \
-+       BIT(MIPS_R_S4) | \
-+       BIT(MIPS_R_S5) | \
-+       BIT(MIPS_R_S6) | \
-+       BIT(MIPS_R_S7) | \
-+       BIT(MIPS_R_GP) | \
-+       BIT(MIPS_R_FP) | \
-+       BIT(MIPS_R_RA))
-+
-+/*
-+ * Mapping of 64-bit eBPF registers to 32-bit native MIPS registers.
-+ *
-+ * 1) Native register pairs are ordered according to CPU endiannes, following
-+ *    the MIPS convention for passing 64-bit arguments and return values.
-+ * 2) The eBPF return value, arguments and callee-saved registers are mapped
-+ *    to their native MIPS equivalents.
-+ * 3) Since the 32 highest bits in the eBPF FP register are always zero,
-+ *    only one general-purpose register is actually needed for the mapping.
-+ *    We use the fp register for this purpose, and map the highest bits to
-+ *    the MIPS register r0 (zero).
-+ * 4) We use the MIPS gp and at registers as internal temporary registers
-+ *    for constant blinding. The gp register is callee-saved.
-+ * 5) One 64-bit temporary register is mapped for use when sign-extending
-+ *    immediate operands. MIPS registers t6-t9 are available to the JIT
-+ *    for as temporaries when implementing complex 64-bit operations.
-+ *
-+ * With this scheme all eBPF registers are being mapped to native MIPS
-+ * registers without having to use any stack scratch space. The direct
-+ * register mapping (2) simplifies the handling of function calls.
-+ */
-+static const u8 bpf2mips32[][2] = {
-+      /* Return value from in-kernel function, and exit value from eBPF */
-+      [BPF_REG_0] = {MIPS_R_V1, MIPS_R_V0},
-+      /* Arguments from eBPF program to in-kernel function */
-+      [BPF_REG_1] = {MIPS_R_A1, MIPS_R_A0},
-+      [BPF_REG_2] = {MIPS_R_A3, MIPS_R_A2},
-+      /* Remaining arguments, to be passed on the stack per O32 ABI */
-+      [BPF_REG_3] = {MIPS_R_T1, MIPS_R_T0},
-+      [BPF_REG_4] = {MIPS_R_T3, MIPS_R_T2},
-+      [BPF_REG_5] = {MIPS_R_T5, MIPS_R_T4},
-+      /* Callee-saved registers that in-kernel function will preserve */
-+      [BPF_REG_6] = {MIPS_R_S1, MIPS_R_S0},
-+      [BPF_REG_7] = {MIPS_R_S3, MIPS_R_S2},
-+      [BPF_REG_8] = {MIPS_R_S5, MIPS_R_S4},
-+      [BPF_REG_9] = {MIPS_R_S7, MIPS_R_S6},
-+      /* Read-only frame pointer to access the eBPF stack */
-+#ifdef __BIG_ENDIAN
-+      [BPF_REG_FP] = {MIPS_R_FP, MIPS_R_ZERO},
-+#else
-+      [BPF_REG_FP] = {MIPS_R_ZERO, MIPS_R_FP},
-+#endif
-+      /* Temporary register for blinding constants */
-+      [BPF_REG_AX] = {MIPS_R_GP, MIPS_R_AT},
-+      /* Temporary register for internal JIT use */
-+      [JIT_REG_TMP] = {MIPS_R_T7, MIPS_R_T6},
-+};
-+
-+/* Get low CPU register for a 64-bit eBPF register mapping */
-+static inline u8 lo(const u8 reg[])
-+{
-+#ifdef __BIG_ENDIAN
-+      return reg[0];
-+#else
-+      return reg[1];
-+#endif
-+}
-+
-+/* Get high CPU register for a 64-bit eBPF register mapping */
-+static inline u8 hi(const u8 reg[])
-+{
-+#ifdef __BIG_ENDIAN
-+      return reg[1];
-+#else
-+      return reg[0];
-+#endif
-+}
-+
-+/*
-+ * Mark a 64-bit CPU register pair as clobbered, it needs to be
-+ * saved/restored by the program if callee-saved.
-+ */
-+static void clobber_reg64(struct jit_context *ctx, const u8 reg[])
-+{
-+      clobber_reg(ctx, reg[0]);
-+      clobber_reg(ctx, reg[1]);
-+}
-+
-+/* dst = imm (sign-extended) */
-+static void emit_mov_se_i64(struct jit_context *ctx, const u8 dst[], s32 imm)
-+{
-+      emit_mov_i(ctx, lo(dst), imm);
-+      if (imm < 0)
-+              emit(ctx, addiu, hi(dst), MIPS_R_ZERO, -1);
-+      else
-+              emit(ctx, move, hi(dst), MIPS_R_ZERO);
-+      clobber_reg64(ctx, dst);
-+}
-+
-+/* Zero extension, if verifier does not do it for us  */
-+static void emit_zext_ver(struct jit_context *ctx, const u8 dst[])
-+{
-+      if (!ctx->program->aux->verifier_zext) {
-+              emit(ctx, move, hi(dst), MIPS_R_ZERO);
-+              clobber_reg(ctx, hi(dst));
-+      }
-+}
-+
-+/* Load delay slot, if ISA mandates it */
-+static void emit_load_delay(struct jit_context *ctx)
-+{
-+      if (!cpu_has_mips_2_3_4_5_r)
-+              emit(ctx, nop);
-+}
-+
-+/* ALU immediate operation (64-bit) */
-+static void emit_alu_i64(struct jit_context *ctx,
-+                       const u8 dst[], s32 imm, u8 op)
-+{
-+      u8 src = MIPS_R_T6;
-+
-+      /*
-+       * ADD/SUB with all but the max negative imm can be handled by
-+       * inverting the operation and the imm value, saving one insn.
-+       */
-+      if (imm > S32_MIN && imm < 0)
-+              switch (op) {
-+              case BPF_ADD:
-+                      op = BPF_SUB;
-+                      imm = -imm;
-+                      break;
-+              case BPF_SUB:
-+                      op = BPF_ADD;
-+                      imm = -imm;
-+                      break;
-+              }
-+
-+      /* Move immediate to temporary register */
-+      emit_mov_i(ctx, src, imm);
-+
-+      switch (op) {
-+      /* dst = dst + imm */
-+      case BPF_ADD:
-+              emit(ctx, addu, lo(dst), lo(dst), src);
-+              emit(ctx, sltu, MIPS_R_T9, lo(dst), src);
-+              emit(ctx, addu, hi(dst), hi(dst), MIPS_R_T9);
-+              if (imm < 0)
-+                      emit(ctx, addiu, hi(dst), hi(dst), -1);
-+              break;
-+      /* dst = dst - imm */
-+      case BPF_SUB:
-+              emit(ctx, sltu, MIPS_R_T9, lo(dst), src);
-+              emit(ctx, subu, lo(dst), lo(dst), src);
-+              emit(ctx, subu, hi(dst), hi(dst), MIPS_R_T9);
-+              if (imm < 0)
-+                      emit(ctx, addiu, hi(dst), hi(dst), 1);
-+              break;
-+      /* dst = dst | imm */
-+      case BPF_OR:
-+              emit(ctx, or, lo(dst), lo(dst), src);
-+              if (imm < 0)
-+                      emit(ctx, addiu, hi(dst), MIPS_R_ZERO, -1);
-+              break;
-+      /* dst = dst & imm */
-+      case BPF_AND:
-+              emit(ctx, and, lo(dst), lo(dst), src);
-+              if (imm >= 0)
-+                      emit(ctx, move, hi(dst), MIPS_R_ZERO);
-+              break;
-+      /* dst = dst ^ imm */
-+      case BPF_XOR:
-+              emit(ctx, xor, lo(dst), lo(dst), src);
-+              if (imm < 0) {
-+                      emit(ctx, subu, hi(dst), MIPS_R_ZERO, hi(dst));
-+                      emit(ctx, addiu, hi(dst), hi(dst), -1);
-+              }
-+              break;
-+      }
-+      clobber_reg64(ctx, dst);
-+}
-+
-+/* ALU register operation (64-bit) */
-+static void emit_alu_r64(struct jit_context *ctx,
-+                       const u8 dst[], const u8 src[], u8 op)
-+{
-+      switch (BPF_OP(op)) {
-+      /* dst = dst + src */
-+      case BPF_ADD:
-+              if (src == dst) {
-+                      emit(ctx, srl, MIPS_R_T9, lo(dst), 31);
-+                      emit(ctx, addu, lo(dst), lo(dst), lo(dst));
-+              } else {
-+                      emit(ctx, addu, lo(dst), lo(dst), lo(src));
-+                      emit(ctx, sltu, MIPS_R_T9, lo(dst), lo(src));
-+              }
-+              emit(ctx, addu, hi(dst), hi(dst), hi(src));
-+              emit(ctx, addu, hi(dst), hi(dst), MIPS_R_T9);
-+              break;
-+      /* dst = dst - src */
-+      case BPF_SUB:
-+              emit(ctx, sltu, MIPS_R_T9, lo(dst), lo(src));
-+              emit(ctx, subu, lo(dst), lo(dst), lo(src));
-+              emit(ctx, subu, hi(dst), hi(dst), hi(src));
-+              emit(ctx, subu, hi(dst), hi(dst), MIPS_R_T9);
-+              break;
-+      /* dst = dst | src */
-+      case BPF_OR:
-+              emit(ctx, or, lo(dst), lo(dst), lo(src));
-+              emit(ctx, or, hi(dst), hi(dst), hi(src));
-+              break;
-+      /* dst = dst & src */
-+      case BPF_AND:
-+              emit(ctx, and, lo(dst), lo(dst), lo(src));
-+              emit(ctx, and, hi(dst), hi(dst), hi(src));
-+              break;
-+      /* dst = dst ^ src */
-+      case BPF_XOR:
-+              emit(ctx, xor, lo(dst), lo(dst), lo(src));
-+              emit(ctx, xor, hi(dst), hi(dst), hi(src));
-+              break;
-+      }
-+      clobber_reg64(ctx, dst);
-+}
-+
-+/* ALU invert (64-bit) */
-+static void emit_neg_i64(struct jit_context *ctx, const u8 dst[])
-+{
-+      emit(ctx, sltu, MIPS_R_T9, MIPS_R_ZERO, lo(dst));
-+      emit(ctx, subu, lo(dst), MIPS_R_ZERO, lo(dst));
-+      emit(ctx, subu, hi(dst), MIPS_R_ZERO, hi(dst));
-+      emit(ctx, subu, hi(dst), hi(dst), MIPS_R_T9);
-+
-+      clobber_reg64(ctx, dst);
-+}
-+
-+/* ALU shift immediate (64-bit) */
-+static void emit_shift_i64(struct jit_context *ctx,
-+                         const u8 dst[], u32 imm, u8 op)
-+{
-+      switch (BPF_OP(op)) {
-+      /* dst = dst << imm */
-+      case BPF_LSH:
-+              if (imm < 32) {
-+                      emit(ctx, srl, MIPS_R_T9, lo(dst), 32 - imm);
-+                      emit(ctx, sll, lo(dst), lo(dst), imm);
-+                      emit(ctx, sll, hi(dst), hi(dst), imm);
-+                      emit(ctx, or, hi(dst), hi(dst), MIPS_R_T9);
-+              } else {
-+                      emit(ctx, sll, hi(dst), lo(dst), imm - 32);
-+                      emit(ctx, move, lo(dst), MIPS_R_ZERO);
-+              }
-+              break;
-+      /* dst = dst >> imm */
-+      case BPF_RSH:
-+              if (imm < 32) {
-+                      emit(ctx, sll, MIPS_R_T9, hi(dst), 32 - imm);
-+                      emit(ctx, srl, lo(dst), lo(dst), imm);
-+                      emit(ctx, srl, hi(dst), hi(dst), imm);
-+                      emit(ctx, or, lo(dst), lo(dst), MIPS_R_T9);
-+              } else {
-+                      emit(ctx, srl, lo(dst), hi(dst), imm - 32);
-+                      emit(ctx, move, hi(dst), MIPS_R_ZERO);
-+              }
-+              break;
-+      /* dst = dst >> imm (arithmetic) */
-+      case BPF_ARSH:
-+              if (imm < 32) {
-+                      emit(ctx, sll, MIPS_R_T9, hi(dst), 32 - imm);
-+                      emit(ctx, srl, lo(dst), lo(dst), imm);
-+                      emit(ctx, sra, hi(dst), hi(dst), imm);
-+                      emit(ctx, or, lo(dst), lo(dst), MIPS_R_T9);
-+              } else {
-+                      emit(ctx, sra, lo(dst), hi(dst), imm - 32);
-+                      emit(ctx, sra, hi(dst), hi(dst), 31);
-+              }
-+              break;
-+      }
-+      clobber_reg64(ctx, dst);
-+}
-+
-+/* ALU shift register (64-bit) */
-+static void emit_shift_r64(struct jit_context *ctx,
-+                         const u8 dst[], u8 src, u8 op)
-+{
-+      u8 t1 = MIPS_R_T8;
-+      u8 t2 = MIPS_R_T9;
-+
-+      emit(ctx, andi, t1, src, 32);              /* t1 = src & 32          */
-+      emit(ctx, beqz, t1, 16);                   /* PC += 16 if t1 == 0    */
-+      emit(ctx, nor, t2, src, MIPS_R_ZERO);      /* t2 = ~src (delay slot) */
-+
-+      switch (BPF_OP(op)) {
-+      /* dst = dst << src */
-+      case BPF_LSH:
-+              /* Next: shift >= 32 */
-+              emit(ctx, sllv, hi(dst), lo(dst), src);    /* dh = dl << src */
-+              emit(ctx, move, lo(dst), MIPS_R_ZERO);     /* dl = 0         */
-+              emit(ctx, b, 20);                          /* PC += 20       */
-+              /* +16: shift < 32 */
-+              emit(ctx, srl, t1, lo(dst), 1);            /* t1 = dl >> 1   */
-+              emit(ctx, srlv, t1, t1, t2);               /* t1 = t1 >> t2  */
-+              emit(ctx, sllv, lo(dst), lo(dst), src);    /* dl = dl << src */
-+              emit(ctx, sllv, hi(dst), hi(dst), src);    /* dh = dh << src */
-+              emit(ctx, or, hi(dst), hi(dst), t1);       /* dh = dh | t1   */
-+              break;
-+      /* dst = dst >> src */
-+      case BPF_RSH:
-+              /* Next: shift >= 32 */
-+              emit(ctx, srlv, lo(dst), hi(dst), src);    /* dl = dh >> src */
-+              emit(ctx, move, hi(dst), MIPS_R_ZERO);     /* dh = 0         */
-+              emit(ctx, b, 20);                          /* PC += 20       */
-+              /* +16: shift < 32 */
-+              emit(ctx, sll, t1, hi(dst), 1);            /* t1 = dl << 1   */
-+              emit(ctx, sllv, t1, t1, t2);               /* t1 = t1 << t2  */
-+              emit(ctx, srlv, lo(dst), lo(dst), src);    /* dl = dl >> src */
-+              emit(ctx, srlv, hi(dst), hi(dst), src);    /* dh = dh >> src */
-+              emit(ctx, or, lo(dst), lo(dst), t1);       /* dl = dl | t1   */
-+              break;
-+      /* dst = dst >> src (arithmetic) */
-+      case BPF_ARSH:
-+              /* Next: shift >= 32 */
-+              emit(ctx, srav, lo(dst), hi(dst), src);   /* dl = dh >>a src */
-+              emit(ctx, sra, hi(dst), hi(dst), 31);     /* dh = dh >>a 31  */
-+              emit(ctx, b, 20);                         /* PC += 20        */
-+              /* +16: shift < 32 */
-+              emit(ctx, sll, t1, hi(dst), 1);           /* t1 = dl << 1    */
-+              emit(ctx, sllv, t1, t1, t2);              /* t1 = t1 << t2   */
-+              emit(ctx, srlv, lo(dst), lo(dst), src);   /* dl = dl >>a src */
-+              emit(ctx, srav, hi(dst), hi(dst), src);   /* dh = dh >> src  */
-+              emit(ctx, or, lo(dst), lo(dst), t1);      /* dl = dl | t1    */
-+              break;
-+      }
-+
-+      /* +20: Done */
-+      clobber_reg64(ctx, dst);
-+}
-+
-+/* ALU mul immediate (64x32-bit) */
-+static void emit_mul_i64(struct jit_context *ctx, const u8 dst[], s32 imm)
-+{
-+      u8 src = MIPS_R_T6;
-+      u8 tmp = MIPS_R_T9;
-+
-+      switch (imm) {
-+      /* dst = dst * 1 is a no-op */
-+      case 1:
-+              break;
-+      /* dst = dst * -1 */
-+      case -1:
-+              emit_neg_i64(ctx, dst);
-+              break;
-+      case 0:
-+              emit_mov_r(ctx, lo(dst), MIPS_R_ZERO);
-+              emit_mov_r(ctx, hi(dst), MIPS_R_ZERO);
-+              break;
-+      /* Full 64x32 multiply */
-+      default:
-+              /* hi(dst) = hi(dst) * src(imm) */
-+              emit_mov_i(ctx, src, imm);
-+              if (cpu_has_mips32r1 || cpu_has_mips32r6) {
-+                      emit(ctx, mul, hi(dst), hi(dst), src);
-+              } else {
-+                      emit(ctx, multu, hi(dst), src);
-+                      emit(ctx, mflo, hi(dst));
-+              }
-+
-+              /* hi(dst) = hi(dst) - lo(dst) */
-+              if (imm < 0)
-+                      emit(ctx, subu, hi(dst), hi(dst), lo(dst));
-+
-+              /* tmp = lo(dst) * src(imm) >> 32 */
-+              /* lo(dst) = lo(dst) * src(imm) */
-+              if (cpu_has_mips32r6) {
-+                      emit(ctx, muhu, tmp, lo(dst), src);
-+                      emit(ctx, mulu, lo(dst), lo(dst), src);
-+              } else {
-+                      emit(ctx, multu, lo(dst), src);
-+                      emit(ctx, mflo, lo(dst));
-+                      emit(ctx, mfhi, tmp);
-+              }
-+
-+              /* hi(dst) += tmp */
-+              emit(ctx, addu, hi(dst), hi(dst), tmp);
-+              clobber_reg64(ctx, dst);
-+              break;
-+      }
-+}
-+
-+/* ALU mul register (64x64-bit) */
-+static void emit_mul_r64(struct jit_context *ctx,
-+                       const u8 dst[], const u8 src[])
-+{
-+      u8 acc = MIPS_R_T8;
-+      u8 tmp = MIPS_R_T9;
-+
-+      /* acc = hi(dst) * lo(src) */
-+      if (cpu_has_mips32r1 || cpu_has_mips32r6) {
-+              emit(ctx, mul, acc, hi(dst), lo(src));
-+      } else {
-+              emit(ctx, multu, hi(dst), lo(src));
-+              emit(ctx, mflo, acc);
-+      }
-+
-+      /* tmp = lo(dst) * hi(src) */
-+      if (cpu_has_mips32r1 || cpu_has_mips32r6) {
-+              emit(ctx, mul, tmp, lo(dst), hi(src));
-+      } else {
-+              emit(ctx, multu, lo(dst), hi(src));
-+              emit(ctx, mflo, tmp);
-+      }
-+
-+      /* acc += tmp */
-+      emit(ctx, addu, acc, acc, tmp);
-+
-+      /* tmp = lo(dst) * lo(src) >> 32 */
-+      /* lo(dst) = lo(dst) * lo(src) */
-+      if (cpu_has_mips32r6) {
-+              emit(ctx, muhu, tmp, lo(dst), lo(src));
-+              emit(ctx, mulu, lo(dst), lo(dst), lo(src));
-+      } else {
-+              emit(ctx, multu, lo(dst), lo(src));
-+              emit(ctx, mflo, lo(dst));
-+              emit(ctx, mfhi, tmp);
-+      }
-+
-+      /* hi(dst) = acc + tmp */
-+      emit(ctx, addu, hi(dst), acc, tmp);
-+      clobber_reg64(ctx, dst);
-+}
-+
-+/* Helper function for 64-bit modulo */
-+static u64 jit_mod64(u64 a, u64 b)
-+{
-+      u64 rem;
-+
-+      div64_u64_rem(a, b, &rem);
-+      return rem;
-+}
-+
-+/* ALU div/mod register (64-bit) */
-+static void emit_divmod_r64(struct jit_context *ctx,
-+                          const u8 dst[], const u8 src[], u8 op)
-+{
-+      const u8 *r0 = bpf2mips32[BPF_REG_0]; /* Mapped to v0-v1 */
-+      const u8 *r1 = bpf2mips32[BPF_REG_1]; /* Mapped to a0-a1 */
-+      const u8 *r2 = bpf2mips32[BPF_REG_2]; /* Mapped to a2-a3 */
-+      int exclude, k;
-+      u32 addr = 0;
-+
-+      /* Push caller-saved registers on stack */
-+      push_regs(ctx, ctx->clobbered & JIT_CALLER_REGS,
-+                0, JIT_RESERVED_STACK);
-+
-+      /* Put 64-bit arguments 1 and 2 in registers a0-a3 */
-+      for (k = 0; k < 2; k++) {
-+              emit(ctx, move, MIPS_R_T9, src[k]);
-+              emit(ctx, move, r1[k], dst[k]);
-+              emit(ctx, move, r2[k], MIPS_R_T9);
-+      }
-+
-+      /* Emit function call */
-+      switch (BPF_OP(op)) {
-+      /* dst = dst / src */
-+      case BPF_DIV:
-+              addr = (u32)&div64_u64;
-+              break;
-+      /* dst = dst % src */
-+      case BPF_MOD:
-+              addr = (u32)&jit_mod64;
-+              break;
-+      }
-+      emit_mov_i(ctx, MIPS_R_T9, addr);
-+      emit(ctx, jalr, MIPS_R_RA, MIPS_R_T9);
-+      emit(ctx, nop); /* Delay slot */
-+
-+      /* Store the 64-bit result in dst */
-+      emit(ctx, move, dst[0], r0[0]);
-+      emit(ctx, move, dst[1], r0[1]);
-+
-+      /* Restore caller-saved registers, excluding the computed result */
-+      exclude = BIT(lo(dst)) | BIT(hi(dst));
-+      pop_regs(ctx, ctx->clobbered & JIT_CALLER_REGS,
-+               exclude, JIT_RESERVED_STACK);
-+      emit_load_delay(ctx);
-+
-+      clobber_reg64(ctx, dst);
-+      clobber_reg(ctx, MIPS_R_V0);
-+      clobber_reg(ctx, MIPS_R_V1);
-+      clobber_reg(ctx, MIPS_R_RA);
-+}
-+
-+/* Swap bytes in a register word */
-+static void emit_swap8_r(struct jit_context *ctx, u8 dst, u8 src, u8 mask)
-+{
-+      u8 tmp = MIPS_R_T9;
-+
-+      emit(ctx, and, tmp, src, mask); /* tmp = src & 0x00ff00ff */
-+      emit(ctx, sll, tmp, tmp, 8);    /* tmp = tmp << 8         */
-+      emit(ctx, srl, dst, src, 8);    /* dst = src >> 8         */
-+      emit(ctx, and, dst, dst, mask); /* dst = dst & 0x00ff00ff */
-+      emit(ctx, or,  dst, dst, tmp);  /* dst = dst | tmp        */
-+}
-+
-+/* Swap half words in a register word */
-+static void emit_swap16_r(struct jit_context *ctx, u8 dst, u8 src)
-+{
-+      u8 tmp = MIPS_R_T9;
-+
-+      emit(ctx, sll, tmp, src, 16);  /* tmp = src << 16 */
-+      emit(ctx, srl, dst, src, 16);  /* dst = src >> 16 */
-+      emit(ctx, or,  dst, dst, tmp); /* dst = dst | tmp */
-+}
-+
-+/* Swap bytes and truncate a register double word, word or half word */
-+static void emit_bswap_r64(struct jit_context *ctx, const u8 dst[], u32 width)
-+{
-+      u8 tmp = MIPS_R_T8;
-+
-+      switch (width) {
-+      /* Swap bytes in a double word */
-+      case 64:
-+              if (cpu_has_mips32r2 || cpu_has_mips32r6) {
-+                      emit(ctx, rotr, tmp, hi(dst), 16);
-+                      emit(ctx, rotr, hi(dst), lo(dst), 16);
-+                      emit(ctx, wsbh, lo(dst), tmp);
-+                      emit(ctx, wsbh, hi(dst), hi(dst));
-+              } else {
-+                      emit_swap16_r(ctx, tmp, lo(dst));
-+                      emit_swap16_r(ctx, lo(dst), hi(dst));
-+                      emit(ctx, move, hi(dst), tmp);
-+
-+                      emit(ctx, lui, tmp, 0xff);      /* tmp = 0x00ff0000 */
-+                      emit(ctx, ori, tmp, tmp, 0xff); /* tmp = 0x00ff00ff */
-+                      emit_swap8_r(ctx, lo(dst), lo(dst), tmp);
-+                      emit_swap8_r(ctx, hi(dst), hi(dst), tmp);
-+              }
-+              break;
-+      /* Swap bytes in a word */
-+      /* Swap bytes in a half word */
-+      case 32:
-+      case 16:
-+              emit_bswap_r(ctx, lo(dst), width);
-+              emit(ctx, move, hi(dst), MIPS_R_ZERO);
-+              break;
-+      }
-+      clobber_reg64(ctx, dst);
-+}
-+
-+/* Truncate a register double word, word or half word */
-+static void emit_trunc_r64(struct jit_context *ctx, const u8 dst[], u32 width)
-+{
-+      switch (width) {
-+      case 64:
-+              break;
-+      /* Zero-extend a word */
-+      case 32:
-+              emit(ctx, move, hi(dst), MIPS_R_ZERO);
-+              clobber_reg(ctx, hi(dst));
-+              break;
-+      /* Zero-extend a half word */
-+      case 16:
-+              emit(ctx, move, hi(dst), MIPS_R_ZERO);
-+              emit(ctx, andi, lo(dst), lo(dst), 0xffff);
-+              clobber_reg64(ctx, dst);
-+              break;
-+      }
-+}
-+
-+/* Load operation: dst = *(size*)(src + off) */
-+static void emit_ldx(struct jit_context *ctx,
-+                   const u8 dst[], u8 src, s16 off, u8 size)
-+{
-+      switch (size) {
-+      /* Load a byte */
-+      case BPF_B:
-+              emit(ctx, lbu, lo(dst), off, src);
-+              emit(ctx, move, hi(dst), MIPS_R_ZERO);
-+              break;
-+      /* Load a half word */
-+      case BPF_H:
-+              emit(ctx, lhu, lo(dst), off, src);
-+              emit(ctx, move, hi(dst), MIPS_R_ZERO);
-+              break;
-+      /* Load a word */
-+      case BPF_W:
-+              emit(ctx, lw, lo(dst), off, src);
-+              emit(ctx, move, hi(dst), MIPS_R_ZERO);
-+              break;
-+      /* Load a double word */
-+      case BPF_DW:
-+              if (dst[1] == src) {
-+                      emit(ctx, lw, dst[0], off + 4, src);
-+                      emit(ctx, lw, dst[1], off, src);
-+              } else {
-+                      emit(ctx, lw, dst[1], off, src);
-+                      emit(ctx, lw, dst[0], off + 4, src);
-+              }
-+              emit_load_delay(ctx);
-+              break;
-+      }
-+      clobber_reg64(ctx, dst);
-+}
-+
-+/* Store operation: *(size *)(dst + off) = src */
-+static void emit_stx(struct jit_context *ctx,
-+                   const u8 dst, const u8 src[], s16 off, u8 size)
-+{
-+      switch (size) {
-+      /* Store a byte */
-+      case BPF_B:
-+              emit(ctx, sb, lo(src), off, dst);
-+              break;
-+      /* Store a half word */
-+      case BPF_H:
-+              emit(ctx, sh, lo(src), off, dst);
-+              break;
-+      /* Store a word */
-+      case BPF_W:
-+              emit(ctx, sw, lo(src), off, dst);
-+              break;
-+      /* Store a double word */
-+      case BPF_DW:
-+              emit(ctx, sw, src[1], off, dst);
-+              emit(ctx, sw, src[0], off + 4, dst);
-+              break;
-+      }
-+}
-+
-+/* Atomic read-modify-write (32-bit, non-ll/sc fallback) */
-+static void emit_atomic_r32(struct jit_context *ctx,
-+                          u8 dst, u8 src, s16 off, u8 code)
-+{
-+      u32 exclude = 0;
-+      u32 addr = 0;
-+
-+      /* Push caller-saved registers on stack */
-+      push_regs(ctx, ctx->clobbered & JIT_CALLER_REGS,
-+                0, JIT_RESERVED_STACK);
-+      /*
-+       * Argument 1: dst+off if xchg, otherwise src, passed in register a0
-+       * Argument 2: src if xchg, othersize dst+off, passed in register a1
-+       */
-+      emit(ctx, move, MIPS_R_T9, dst);
-+      emit(ctx, move, MIPS_R_A0, src);
-+      emit(ctx, addiu, MIPS_R_A1, MIPS_R_T9, off);
-+
-+      /* Emit function call */
-+      switch (code) {
-+      case BPF_ADD:
-+              addr = (u32)&atomic_add;
-+              break;
-+      case BPF_SUB:
-+              addr = (u32)&atomic_sub;
-+              break;
-+      case BPF_OR:
-+              addr = (u32)&atomic_or;
-+              break;
-+      case BPF_AND:
-+              addr = (u32)&atomic_and;
-+              break;
-+      case BPF_XOR:
-+              addr = (u32)&atomic_xor;
-+              break;
-+      }
-+      emit_mov_i(ctx, MIPS_R_T9, addr);
-+      emit(ctx, jalr, MIPS_R_RA, MIPS_R_T9);
-+      emit(ctx, nop); /* Delay slot */
-+
-+      /* Restore caller-saved registers, except any fetched value */
-+      pop_regs(ctx, ctx->clobbered & JIT_CALLER_REGS,
-+               exclude, JIT_RESERVED_STACK);
-+      emit_load_delay(ctx);
-+      clobber_reg(ctx, MIPS_R_RA);
-+}
-+
-+/* Atomic read-modify-write (64-bit) */
-+static void emit_atomic_r64(struct jit_context *ctx,
-+                          u8 dst, const u8 src[], s16 off, u8 code)
-+{
-+      const u8 *r1 = bpf2mips32[BPF_REG_1]; /* Mapped to a0-a1 */
-+      u32 exclude = 0;
-+      u32 addr = 0;
-+
-+      /* Push caller-saved registers on stack */
-+      push_regs(ctx, ctx->clobbered & JIT_CALLER_REGS,
-+                0, JIT_RESERVED_STACK);
-+      /*
-+       * Argument 1: 64-bit src, passed in registers a0-a1
-+       * Argument 2: 32-bit dst+off, passed in register a2
-+       */
-+      emit(ctx, move, MIPS_R_T9, dst);
-+      emit(ctx, move, r1[0], src[0]);
-+      emit(ctx, move, r1[1], src[1]);
-+      emit(ctx, addiu, MIPS_R_A2, MIPS_R_T9, off);
-+
-+      /* Emit function call */
-+      switch (code) {
-+      case BPF_ADD:
-+              addr = (u32)&atomic64_add;
-+              break;
-+      case BPF_SUB:
-+              addr = (u32)&atomic64_sub;
-+              break;
-+      case BPF_OR:
-+              addr = (u32)&atomic64_or;
-+              break;
-+      case BPF_AND:
-+              addr = (u32)&atomic64_and;
-+              break;
-+      case BPF_XOR:
-+              addr = (u32)&atomic64_xor;
-+              break;
-+      }
-+      emit_mov_i(ctx, MIPS_R_T9, addr);
-+      emit(ctx, jalr, MIPS_R_RA, MIPS_R_T9);
-+      emit(ctx, nop); /* Delay slot */
-+
-+      /* Restore caller-saved registers, except any fetched value */
-+      pop_regs(ctx, ctx->clobbered & JIT_CALLER_REGS,
-+               exclude, JIT_RESERVED_STACK);
-+      emit_load_delay(ctx);
-+      clobber_reg(ctx, MIPS_R_RA);
-+}
-+
-+/*
-+ * Conditional movz or an emulated equivalent.
-+ * Note that the rs register may be modified.
-+ */
-+static void emit_movz_r(struct jit_context *ctx, u8 rd, u8 rs, u8 rt)
-+{
-+      if (cpu_has_mips_2) {
-+              emit(ctx, movz, rd, rs, rt);           /* rd = rt ? rd : rs  */
-+      } else if (cpu_has_mips32r6) {
-+              if (rs != MIPS_R_ZERO)
-+                      emit(ctx, seleqz, rs, rs, rt); /* rs = 0 if rt == 0  */
-+              emit(ctx, selnez, rd, rd, rt);         /* rd = 0 if rt != 0  */
-+              if (rs != MIPS_R_ZERO)
-+                      emit(ctx, or, rd, rd, rs);     /* rd = rd | rs       */
-+      } else {
-+              emit(ctx, bnez, rt, 8);                /* PC += 8 if rd != 0 */
-+              emit(ctx, nop);                        /* +0: delay slot     */
-+              emit(ctx, or, rd, rs, MIPS_R_ZERO);    /* +4: rd = rs        */
-+      }
-+      clobber_reg(ctx, rd);
-+      clobber_reg(ctx, rs);
-+}
-+
-+/*
-+ * Conditional movn or an emulated equivalent.
-+ * Note that the rs register may be modified.
-+ */
-+static void emit_movn_r(struct jit_context *ctx, u8 rd, u8 rs, u8 rt)
-+{
-+      if (cpu_has_mips_2) {
-+              emit(ctx, movn, rd, rs, rt);           /* rd = rt ? rs : rd  */
-+      } else if (cpu_has_mips32r6) {
-+              if (rs != MIPS_R_ZERO)
-+                      emit(ctx, selnez, rs, rs, rt); /* rs = 0 if rt == 0  */
-+              emit(ctx, seleqz, rd, rd, rt);         /* rd = 0 if rt != 0  */
-+              if (rs != MIPS_R_ZERO)
-+                      emit(ctx, or, rd, rd, rs);     /* rd = rd | rs       */
-+      } else {
-+              emit(ctx, beqz, rt, 8);                /* PC += 8 if rd == 0 */
-+              emit(ctx, nop);                        /* +0: delay slot     */
-+              emit(ctx, or, rd, rs, MIPS_R_ZERO);    /* +4: rd = rs        */
-+      }
-+      clobber_reg(ctx, rd);
-+      clobber_reg(ctx, rs);
-+}
-+
-+/* Emulation of 64-bit sltiu rd, rs, imm, where imm may be S32_MAX + 1 */
-+static void emit_sltiu_r64(struct jit_context *ctx, u8 rd,
-+                         const u8 rs[], s64 imm)
-+{
-+      u8 tmp = MIPS_R_T9;
-+
-+      if (imm < 0) {
-+              emit_mov_i(ctx, rd, imm);                 /* rd = imm        */
-+              emit(ctx, sltu, rd, lo(rs), rd);          /* rd = rsl < rd   */
-+              emit(ctx, sltiu, tmp, hi(rs), -1);        /* tmp = rsh < ~0U */
-+              emit(ctx, or, rd, rd, tmp);               /* rd = rd | tmp   */
-+      } else { /* imm >= 0 */
-+              if (imm > 0x7fff) {
-+                      emit_mov_i(ctx, rd, (s32)imm);     /* rd = imm       */
-+                      emit(ctx, sltu, rd, lo(rs), rd);   /* rd = rsl < rd  */
-+              } else {
-+                      emit(ctx, sltiu, rd, lo(rs), imm); /* rd = rsl < imm */
-+              }
-+              emit_movn_r(ctx, rd, MIPS_R_ZERO, hi(rs)); /* rd = 0 if rsh  */
-+      }
-+}
-+
-+/* Emulation of 64-bit sltu rd, rs, rt */
-+static void emit_sltu_r64(struct jit_context *ctx, u8 rd,
-+                        const u8 rs[], const u8 rt[])
-+{
-+      u8 tmp = MIPS_R_T9;
-+
-+      emit(ctx, sltu, rd, lo(rs), lo(rt));           /* rd = rsl < rtl     */
-+      emit(ctx, subu, tmp, hi(rs), hi(rt));          /* tmp = rsh - rth    */
-+      emit_movn_r(ctx, rd, MIPS_R_ZERO, tmp);        /* rd = 0 if tmp != 0 */
-+      emit(ctx, sltu, tmp, hi(rs), hi(rt));          /* tmp = rsh < rth    */
-+      emit(ctx, or, rd, rd, tmp);                    /* rd = rd | tmp      */
-+}
-+
-+/* Emulation of 64-bit slti rd, rs, imm, where imm may be S32_MAX + 1 */
-+static void emit_slti_r64(struct jit_context *ctx, u8 rd,
-+                        const u8 rs[], s64 imm)
-+{
-+      u8 t1 = MIPS_R_T8;
-+      u8 t2 = MIPS_R_T9;
-+      u8 cmp;
-+
-+      /*
-+       * if ((rs < 0) ^ (imm < 0)) t1 = imm >u rsl
-+       * else                      t1 = rsl <u imm
-+       */
-+      emit_mov_i(ctx, rd, (s32)imm);
-+      emit(ctx, sltu, t1, lo(rs), rd);               /* t1 = rsl <u imm   */
-+      emit(ctx, sltu, t2, rd, lo(rs));               /* t2 = imm <u rsl   */
-+      emit(ctx, srl, rd, hi(rs), 31);                /* rd = rsh >> 31    */
-+      if (imm < 0)
-+              emit_movz_r(ctx, t1, t2, rd);          /* t1 = rd ? t1 : t2 */
-+      else
-+              emit_movn_r(ctx, t1, t2, rd);          /* t1 = rd ? t2 : t1 */
-+      /*
-+       * if ((imm < 0 && rsh != 0xffffffff) ||
-+       *     (imm >= 0 && rsh != 0))
-+       *      t1 = 0
-+       */
-+      if (imm < 0) {
-+              emit(ctx, addiu, rd, hi(rs), 1);       /* rd = rsh + 1 */
-+              cmp = rd;
-+      } else { /* imm >= 0 */
-+              cmp = hi(rs);
-+      }
-+      emit_movn_r(ctx, t1, MIPS_R_ZERO, cmp);        /* t1 = 0 if cmp != 0 */
-+
-+      /*
-+       * if (imm < 0) rd = rsh < -1
-+       * else         rd = rsh != 0
-+       * rd = rd | t1
-+       */
-+      emit(ctx, slti, rd, hi(rs), imm < 0 ? -1 : 0); /* rd = rsh < hi(imm) */
-+      emit(ctx, or, rd, rd, t1);                     /* rd = rd | t1       */
-+}
-+
-+/* Emulation of 64-bit(slt rd, rs, rt) */
-+static void emit_slt_r64(struct jit_context *ctx, u8 rd,
-+                       const u8 rs[], const u8 rt[])
-+{
-+      u8 t1 = MIPS_R_T7;
-+      u8 t2 = MIPS_R_T8;
-+      u8 t3 = MIPS_R_T9;
-+
-+      /*
-+       * if ((rs < 0) ^ (rt < 0)) t1 = rtl <u rsl
-+       * else                     t1 = rsl <u rtl
-+       * if (rsh == rth)          t1 = 0
-+       */
-+      emit(ctx, sltu, t1, lo(rs), lo(rt));           /* t1 = rsl <u rtl   */
-+      emit(ctx, sltu, t2, lo(rt), lo(rs));           /* t2 = rtl <u rsl   */
-+      emit(ctx, xor, t3, hi(rs), hi(rt));            /* t3 = rlh ^ rth    */
-+      emit(ctx, srl, rd, t3, 31);                    /* rd = t3 >> 31     */
-+      emit_movn_r(ctx, t1, t2, rd);                  /* t1 = rd ? t2 : t1 */
-+      emit_movn_r(ctx, t1, MIPS_R_ZERO, t3);         /* t1 = 0 if t3 != 0 */
-+
-+      /* rd = (rsh < rth) | t1 */
-+      emit(ctx, slt, rd, hi(rs), hi(rt));            /* rd = rsh <s rth   */
-+      emit(ctx, or, rd, rd, t1);                     /* rd = rd | t1      */
-+}
-+
-+/* Jump immediate (64-bit) */
-+static void emit_jmp_i64(struct jit_context *ctx,
-+                       const u8 dst[], s32 imm, s32 off, u8 op)
-+{
-+      u8 tmp = MIPS_R_T6;
-+
-+      switch (op) {
-+      /* No-op, used internally for branch optimization */
-+      case JIT_JNOP:
-+              break;
-+      /* PC += off if dst == imm */
-+      /* PC += off if dst != imm */
-+      case BPF_JEQ:
-+      case BPF_JNE:
-+              if (imm >= -0x7fff && imm <= 0x8000) {
-+                      emit(ctx, addiu, tmp, lo(dst), -imm);
-+              } else if ((u32)imm <= 0xffff) {
-+                      emit(ctx, xori, tmp, lo(dst), imm);
-+              } else {       /* Register fallback */
-+                      emit_mov_i(ctx, tmp, imm);
-+                      emit(ctx, xor, tmp, lo(dst), tmp);
-+              }
-+              if (imm < 0) { /* Compare sign extension */
-+                      emit(ctx, addu, MIPS_R_T9, hi(dst), 1);
-+                      emit(ctx, or, tmp, tmp, MIPS_R_T9);
-+              } else {       /* Compare zero extension */
-+                      emit(ctx, or, tmp, tmp, hi(dst));
-+              }
-+              if (op == BPF_JEQ)
-+                      emit(ctx, beqz, tmp, off);
-+              else   /* BPF_JNE */
-+                      emit(ctx, bnez, tmp, off);
-+              break;
-+      /* PC += off if dst & imm */
-+      /* PC += off if (dst & imm) == 0 (not in BPF, used for long jumps) */
-+      case BPF_JSET:
-+      case JIT_JNSET:
-+              if ((u32)imm <= 0xffff) {
-+                      emit(ctx, andi, tmp, lo(dst), imm);
-+              } else {     /* Register fallback */
-+                      emit_mov_i(ctx, tmp, imm);
-+                      emit(ctx, and, tmp, lo(dst), tmp);
-+              }
-+              if (imm < 0) /* Sign-extension pulls in high word */
-+                      emit(ctx, or, tmp, tmp, hi(dst));
-+              if (op == BPF_JSET)
-+                      emit(ctx, bnez, tmp, off);
-+              else   /* JIT_JNSET */
-+                      emit(ctx, beqz, tmp, off);
-+              break;
-+      /* PC += off if dst > imm */
-+      case BPF_JGT:
-+              emit_sltiu_r64(ctx, tmp, dst, (s64)imm + 1);
-+              emit(ctx, beqz, tmp, off);
-+              break;
-+      /* PC += off if dst >= imm */
-+      case BPF_JGE:
-+              emit_sltiu_r64(ctx, tmp, dst, imm);
-+              emit(ctx, beqz, tmp, off);
-+              break;
-+      /* PC += off if dst < imm */
-+      case BPF_JLT:
-+              emit_sltiu_r64(ctx, tmp, dst, imm);
-+              emit(ctx, bnez, tmp, off);
-+              break;
-+      /* PC += off if dst <= imm */
-+      case BPF_JLE:
-+              emit_sltiu_r64(ctx, tmp, dst, (s64)imm + 1);
-+              emit(ctx, bnez, tmp, off);
-+              break;
-+      /* PC += off if dst > imm (signed) */
-+      case BPF_JSGT:
-+              emit_slti_r64(ctx, tmp, dst, (s64)imm + 1);
-+              emit(ctx, beqz, tmp, off);
-+              break;
-+      /* PC += off if dst >= imm (signed) */
-+      case BPF_JSGE:
-+              emit_slti_r64(ctx, tmp, dst, imm);
-+              emit(ctx, beqz, tmp, off);
-+              break;
-+      /* PC += off if dst < imm (signed) */
-+      case BPF_JSLT:
-+              emit_slti_r64(ctx, tmp, dst, imm);
-+              emit(ctx, bnez, tmp, off);
-+              break;
-+      /* PC += off if dst <= imm (signed) */
-+      case BPF_JSLE:
-+              emit_slti_r64(ctx, tmp, dst, (s64)imm + 1);
-+              emit(ctx, bnez, tmp, off);
-+              break;
-+      }
-+}
-+
-+/* Jump register (64-bit) */
-+static void emit_jmp_r64(struct jit_context *ctx,
-+                       const u8 dst[], const u8 src[], s32 off, u8 op)
-+{
-+      u8 t1 = MIPS_R_T6;
-+      u8 t2 = MIPS_R_T7;
-+
-+      switch (op) {
-+      /* No-op, used internally for branch optimization */
-+      case JIT_JNOP:
-+              break;
-+      /* PC += off if dst == src */
-+      /* PC += off if dst != src */
-+      case BPF_JEQ:
-+      case BPF_JNE:
-+              emit(ctx, subu, t1, lo(dst), lo(src));
-+              emit(ctx, subu, t2, hi(dst), hi(src));
-+              emit(ctx, or, t1, t1, t2);
-+              if (op == BPF_JEQ)
-+                      emit(ctx, beqz, t1, off);
-+              else   /* BPF_JNE */
-+                      emit(ctx, bnez, t1, off);
-+              break;
-+      /* PC += off if dst & src */
-+      /* PC += off if (dst & imm) == 0 (not in BPF, used for long jumps) */
-+      case BPF_JSET:
-+      case JIT_JNSET:
-+              emit(ctx, and, t1, lo(dst), lo(src));
-+              emit(ctx, and, t2, hi(dst), hi(src));
-+              emit(ctx, or, t1, t1, t2);
-+              if (op == BPF_JSET)
-+                      emit(ctx, bnez, t1, off);
-+              else   /* JIT_JNSET */
-+                      emit(ctx, beqz, t1, off);
-+              break;
-+      /* PC += off if dst > src */
-+      case BPF_JGT:
-+              emit_sltu_r64(ctx, t1, src, dst);
-+              emit(ctx, bnez, t1, off);
-+              break;
-+      /* PC += off if dst >= src */
-+      case BPF_JGE:
-+              emit_sltu_r64(ctx, t1, dst, src);
-+              emit(ctx, beqz, t1, off);
-+              break;
-+      /* PC += off if dst < src */
-+      case BPF_JLT:
-+              emit_sltu_r64(ctx, t1, dst, src);
-+              emit(ctx, bnez, t1, off);
-+              break;
-+      /* PC += off if dst <= src */
-+      case BPF_JLE:
-+              emit_sltu_r64(ctx, t1, src, dst);
-+              emit(ctx, beqz, t1, off);
-+              break;
-+      /* PC += off if dst > src (signed) */
-+      case BPF_JSGT:
-+              emit_slt_r64(ctx, t1, src, dst);
-+              emit(ctx, bnez, t1, off);
-+              break;
-+      /* PC += off if dst >= src (signed) */
-+      case BPF_JSGE:
-+              emit_slt_r64(ctx, t1, dst, src);
-+              emit(ctx, beqz, t1, off);
-+              break;
-+      /* PC += off if dst < src (signed) */
-+      case BPF_JSLT:
-+              emit_slt_r64(ctx, t1, dst, src);
-+              emit(ctx, bnez, t1, off);
-+              break;
-+      /* PC += off if dst <= src (signed) */
-+      case BPF_JSLE:
-+              emit_slt_r64(ctx, t1, src, dst);
-+              emit(ctx, beqz, t1, off);
-+              break;
-+      }
-+}
-+
-+/* Function call */
-+static int emit_call(struct jit_context *ctx, const struct bpf_insn *insn)
-+{
-+      bool fixed;
-+      u64 addr;
-+
-+      /* Decode the call address */
-+      if (bpf_jit_get_func_addr(ctx->program, insn, false,
-+                                &addr, &fixed) < 0)
-+              return -1;
-+      if (!fixed)
-+              return -1;
-+
-+      /* Push stack arguments */
-+      push_regs(ctx, JIT_STACK_REGS, 0, JIT_RESERVED_STACK);
-+
-+      /* Emit function call */
-+      emit_mov_i(ctx, MIPS_R_T9, addr);
-+      emit(ctx, jalr, MIPS_R_RA, MIPS_R_T9);
-+      emit(ctx, nop); /* Delay slot */
-+
-+      clobber_reg(ctx, MIPS_R_RA);
-+      clobber_reg(ctx, MIPS_R_V0);
-+      clobber_reg(ctx, MIPS_R_V1);
-+      return 0;
-+}
-+
-+/* Function tail call */
-+static int emit_tail_call(struct jit_context *ctx)
-+{
-+      u8 ary = lo(bpf2mips32[BPF_REG_2]);
-+      u8 ind = lo(bpf2mips32[BPF_REG_3]);
-+      u8 t1 = MIPS_R_T8;
-+      u8 t2 = MIPS_R_T9;
-+      int off;
-+
-+      /*
-+       * Tail call:
-+       * eBPF R1   - function argument (context ptr), passed in a0-a1
-+       * eBPF R2   - ptr to object with array of function entry points
-+       * eBPF R3   - array index of function to be called
-+       * stack[sz] - remaining tail call count, initialized in prologue
-+       */
-+
-+      /* if (ind >= ary->map.max_entries) goto out */
-+      off = offsetof(struct bpf_array, map.max_entries);
-+      if (off > 0x7fff)
-+              return -1;
-+      emit(ctx, lw, t1, off, ary);             /* t1 = ary->map.max_entries*/
-+      emit_load_delay(ctx);                    /* Load delay slot          */
-+      emit(ctx, sltu, t1, ind, t1);            /* t1 = ind < t1            */
-+      emit(ctx, beqz, t1, get_offset(ctx, 1)); /* PC += off(1) if t1 == 0  */
-+                                               /* (next insn delay slot)   */
-+      /* if (TCC-- <= 0) goto out */
-+      emit(ctx, lw, t2, ctx->stack_size, MIPS_R_SP);  /* t2 = *(SP + size) */
-+      emit_load_delay(ctx);                     /* Load delay slot         */
-+      emit(ctx, blez, t2, get_offset(ctx, 1));  /* PC += off(1) if t2 < 0  */
-+      emit(ctx, addiu, t2, t2, -1);             /* t2-- (delay slot)       */
-+      emit(ctx, sw, t2, ctx->stack_size, MIPS_R_SP);  /* *(SP + size) = t2 */
-+
-+      /* prog = ary->ptrs[ind] */
-+      off = offsetof(struct bpf_array, ptrs);
-+      if (off > 0x7fff)
-+              return -1;
-+      emit(ctx, sll, t1, ind, 2);               /* t1 = ind << 2           */
-+      emit(ctx, addu, t1, t1, ary);             /* t1 += ary               */
-+      emit(ctx, lw, t2, off, t1);               /* t2 = *(t1 + off)        */
-+      emit_load_delay(ctx);                     /* Load delay slot         */
-+
-+      /* if (prog == 0) goto out */
-+      emit(ctx, beqz, t2, get_offset(ctx, 1));  /* PC += off(1) if t2 == 0 */
-+      emit(ctx, nop);                           /* Delay slot              */
-+
-+      /* func = prog->bpf_func + 8 (prologue skip offset) */
-+      off = offsetof(struct bpf_prog, bpf_func);
-+      if (off > 0x7fff)
-+              return -1;
-+      emit(ctx, lw, t1, off, t2);                /* t1 = *(t2 + off)       */
-+      emit_load_delay(ctx);                      /* Load delay slot        */
-+      emit(ctx, addiu, t1, t1, JIT_TCALL_SKIP);  /* t1 += skip (8 or 12)   */
-+
-+      /* goto func */
-+      build_epilogue(ctx, t1);
-+      return 0;
-+}
-+
-+/*
-+ * Stack frame layout for a JITed program (stack grows down).
-+ *
-+ * Higher address  : Caller's stack frame       :
-+ *                 :----------------------------:
-+ *                 : 64-bit eBPF args r3-r5     :
-+ *                 :----------------------------:
-+ *                 : Reserved / tail call count :
-+ *                 +============================+  <--- MIPS sp before call
-+ *                 | Callee-saved registers,    |
-+ *                 | including RA and FP        |
-+ *                 +----------------------------+  <--- eBPF FP (MIPS zero,fp)
-+ *                 | Local eBPF variables       |
-+ *                 | allocated by program       |
-+ *                 +----------------------------+
-+ *                 | Reserved for caller-saved  |
-+ *                 | registers                  |
-+ *                 +----------------------------+
-+ *                 | Reserved for 64-bit eBPF   |
-+ *                 | args r3-r5 & args passed   |
-+ *                 | on stack in kernel calls   |
-+ * Lower address   +============================+  <--- MIPS sp
-+ */
-+
-+/* Build program prologue to set up the stack and registers */
-+void build_prologue(struct jit_context *ctx)
-+{
-+      const u8 *r1 = bpf2mips32[BPF_REG_1];
-+      const u8 *fp = bpf2mips32[BPF_REG_FP];
-+      int stack, saved, locals, reserved;
-+
-+      /*
-+       * The first two instructions initialize TCC in the reserved (for us)
-+       * 16-byte area in the parent's stack frame. On a tail call, the
-+       * calling function jumps into the prologue after these instructions.
-+       */
-+      emit(ctx, ori, MIPS_R_T9, MIPS_R_ZERO,
-+           min(MAX_TAIL_CALL_CNT + 1, 0xffff));
-+      emit(ctx, sw, MIPS_R_T9, 0, MIPS_R_SP);
-+
-+      /*
-+       * Register eBPF R1 contains the 32-bit context pointer argument.
-+       * A 32-bit argument is always passed in MIPS register a0, regardless
-+       * of CPU endianness. Initialize R1 accordingly and zero-extend.
-+       */
-+#ifdef __BIG_ENDIAN
-+      emit(ctx, move, lo(r1), MIPS_R_A0);
-+#endif
-+
-+      /* === Entry-point for tail calls === */
-+
-+      /* Zero-extend the 32-bit argument */
-+      emit(ctx, move, hi(r1), MIPS_R_ZERO);
-+
-+      /* If the eBPF frame pointer was accessed it must be saved */
-+      if (ctx->accessed & BIT(BPF_REG_FP))
-+              clobber_reg64(ctx, fp);
-+
-+      /* Compute the stack space needed for callee-saved registers */
-+      saved = hweight32(ctx->clobbered & JIT_CALLEE_REGS) * sizeof(u32);
-+      saved = ALIGN(saved, MIPS_STACK_ALIGNMENT);
-+
-+      /* Stack space used by eBPF program local data */
-+      locals = ALIGN(ctx->program->aux->stack_depth, MIPS_STACK_ALIGNMENT);
-+
-+      /*
-+       * If we are emitting function calls, reserve extra stack space for
-+       * caller-saved registers and function arguments passed on the stack.
-+       * The required space is computed automatically during resource
-+       * usage discovery (pass 1).
-+       */
-+      reserved = ctx->stack_used;
-+
-+      /* Allocate the stack frame */
-+      stack = ALIGN(saved + locals + reserved, MIPS_STACK_ALIGNMENT);
-+      emit(ctx, addiu, MIPS_R_SP, MIPS_R_SP, -stack);
-+
-+      /* Store callee-saved registers on stack */
-+      push_regs(ctx, ctx->clobbered & JIT_CALLEE_REGS, 0, stack - saved);
-+
-+      /* Initialize the eBPF frame pointer if accessed */
-+      if (ctx->accessed & BIT(BPF_REG_FP))
-+              emit(ctx, addiu, lo(fp), MIPS_R_SP, stack - saved);
-+
-+      ctx->saved_size = saved;
-+      ctx->stack_size = stack;
-+}
-+
-+/* Build the program epilogue to restore the stack and registers */
-+void build_epilogue(struct jit_context *ctx, int dest_reg)
-+{
-+      /* Restore callee-saved registers from stack */
-+      pop_regs(ctx, ctx->clobbered & JIT_CALLEE_REGS, 0,
-+               ctx->stack_size - ctx->saved_size);
-+      /*
-+       * A 32-bit return value is always passed in MIPS register v0,
-+       * but on big-endian targets the low part of R0 is mapped to v1.
-+       */
-+#ifdef __BIG_ENDIAN
-+      emit(ctx, move, MIPS_R_V0, MIPS_R_V1);
-+#endif
-+
-+      /* Jump to the return address and adjust the stack pointer */
-+      emit(ctx, jr, dest_reg);
-+      emit(ctx, addiu, MIPS_R_SP, MIPS_R_SP, ctx->stack_size);
-+}
-+
-+/* Build one eBPF instruction */
-+int build_insn(const struct bpf_insn *insn, struct jit_context *ctx)
-+{
-+      const u8 *dst = bpf2mips32[insn->dst_reg];
-+      const u8 *src = bpf2mips32[insn->src_reg];
-+      const u8 *tmp = bpf2mips32[JIT_REG_TMP];
-+      u8 code = insn->code;
-+      s16 off = insn->off;
-+      s32 imm = insn->imm;
-+      s32 val, rel;
-+      u8 alu, jmp;
-+
-+      switch (code) {
-+      /* ALU operations */
-+      /* dst = imm */
-+      case BPF_ALU | BPF_MOV | BPF_K:
-+              emit_mov_i(ctx, lo(dst), imm);
-+              emit_zext_ver(ctx, dst);
-+              break;
-+      /* dst = src */
-+      case BPF_ALU | BPF_MOV | BPF_X:
-+              if (imm == 1) {
-+                      /* Special mov32 for zext */
-+                      emit_mov_i(ctx, hi(dst), 0);
-+              } else {
-+                      emit_mov_r(ctx, lo(dst), lo(src));
-+                      emit_zext_ver(ctx, dst);
-+              }
-+              break;
-+      /* dst = -dst */
-+      case BPF_ALU | BPF_NEG:
-+              emit_alu_i(ctx, lo(dst), 0, BPF_NEG);
-+              emit_zext_ver(ctx, dst);
-+              break;
-+      /* dst = dst & imm */
-+      /* dst = dst | imm */
-+      /* dst = dst ^ imm */
-+      /* dst = dst << imm */
-+      /* dst = dst >> imm */
-+      /* dst = dst >> imm (arithmetic) */
-+      /* dst = dst + imm */
-+      /* dst = dst - imm */
-+      /* dst = dst * imm */
-+      /* dst = dst / imm */
-+      /* dst = dst % imm */
-+      case BPF_ALU | BPF_OR | BPF_K:
-+      case BPF_ALU | BPF_AND | BPF_K:
-+      case BPF_ALU | BPF_XOR | BPF_K:
-+      case BPF_ALU | BPF_LSH | BPF_K:
-+      case BPF_ALU | BPF_RSH | BPF_K:
-+      case BPF_ALU | BPF_ARSH | BPF_K:
-+      case BPF_ALU | BPF_ADD | BPF_K:
-+      case BPF_ALU | BPF_SUB | BPF_K:
-+      case BPF_ALU | BPF_MUL | BPF_K:
-+      case BPF_ALU | BPF_DIV | BPF_K:
-+      case BPF_ALU | BPF_MOD | BPF_K:
-+              if (!valid_alu_i(BPF_OP(code), imm)) {
-+                      emit_mov_i(ctx, MIPS_R_T6, imm);
-+                      emit_alu_r(ctx, lo(dst), MIPS_R_T6, BPF_OP(code));
-+              } else if (rewrite_alu_i(BPF_OP(code), imm, &alu, &val)) {
-+                      emit_alu_i(ctx, lo(dst), val, alu);
-+              }
-+              emit_zext_ver(ctx, dst);
-+              break;
-+      /* dst = dst & src */
-+      /* dst = dst | src */
-+      /* dst = dst ^ src */
-+      /* dst = dst << src */
-+      /* dst = dst >> src */
-+      /* dst = dst >> src (arithmetic) */
-+      /* dst = dst + src */
-+      /* dst = dst - src */
-+      /* dst = dst * src */
-+      /* dst = dst / src */
-+      /* dst = dst % src */
-+      case BPF_ALU | BPF_AND | BPF_X:
-+      case BPF_ALU | BPF_OR | BPF_X:
-+      case BPF_ALU | BPF_XOR | BPF_X:
-+      case BPF_ALU | BPF_LSH | BPF_X:
-+      case BPF_ALU | BPF_RSH | BPF_X:
-+      case BPF_ALU | BPF_ARSH | BPF_X:
-+      case BPF_ALU | BPF_ADD | BPF_X:
-+      case BPF_ALU | BPF_SUB | BPF_X:
-+      case BPF_ALU | BPF_MUL | BPF_X:
-+      case BPF_ALU | BPF_DIV | BPF_X:
-+      case BPF_ALU | BPF_MOD | BPF_X:
-+              emit_alu_r(ctx, lo(dst), lo(src), BPF_OP(code));
-+              emit_zext_ver(ctx, dst);
-+              break;
-+      /* dst = imm (64-bit) */
-+      case BPF_ALU64 | BPF_MOV | BPF_K:
-+              emit_mov_se_i64(ctx, dst, imm);
-+              break;
-+      /* dst = src (64-bit) */
-+      case BPF_ALU64 | BPF_MOV | BPF_X:
-+              emit_mov_r(ctx, lo(dst), lo(src));
-+              emit_mov_r(ctx, hi(dst), hi(src));
-+              break;
-+      /* dst = -dst (64-bit) */
-+      case BPF_ALU64 | BPF_NEG:
-+              emit_neg_i64(ctx, dst);
-+              break;
-+      /* dst = dst & imm (64-bit) */
-+      case BPF_ALU64 | BPF_AND | BPF_K:
-+              emit_alu_i64(ctx, dst, imm, BPF_OP(code));
-+              break;
-+      /* dst = dst | imm (64-bit) */
-+      /* dst = dst ^ imm (64-bit) */
-+      /* dst = dst + imm (64-bit) */
-+      /* dst = dst - imm (64-bit) */
-+      case BPF_ALU64 | BPF_OR | BPF_K:
-+      case BPF_ALU64 | BPF_XOR | BPF_K:
-+      case BPF_ALU64 | BPF_ADD | BPF_K:
-+      case BPF_ALU64 | BPF_SUB | BPF_K:
-+              if (imm)
-+                      emit_alu_i64(ctx, dst, imm, BPF_OP(code));
-+              break;
-+      /* dst = dst << imm (64-bit) */
-+      /* dst = dst >> imm (64-bit) */
-+      /* dst = dst >> imm (64-bit, arithmetic) */
-+      case BPF_ALU64 | BPF_LSH | BPF_K:
-+      case BPF_ALU64 | BPF_RSH | BPF_K:
-+      case BPF_ALU64 | BPF_ARSH | BPF_K:
-+              if (imm)
-+                      emit_shift_i64(ctx, dst, imm, BPF_OP(code));
-+              break;
-+      /* dst = dst * imm (64-bit) */
-+      case BPF_ALU64 | BPF_MUL | BPF_K:
-+              emit_mul_i64(ctx, dst, imm);
-+              break;
-+      /* dst = dst / imm (64-bit) */
-+      /* dst = dst % imm (64-bit) */
-+      case BPF_ALU64 | BPF_DIV | BPF_K:
-+      case BPF_ALU64 | BPF_MOD | BPF_K:
-+              /*
-+               * Sign-extend the immediate value into a temporary register,
-+               * and then do the operation on this register.
-+               */
-+              emit_mov_se_i64(ctx, tmp, imm);
-+              emit_divmod_r64(ctx, dst, tmp, BPF_OP(code));
-+              break;
-+      /* dst = dst & src (64-bit) */
-+      /* dst = dst | src (64-bit) */
-+      /* dst = dst ^ src (64-bit) */
-+      /* dst = dst + src (64-bit) */
-+      /* dst = dst - src (64-bit) */
-+      case BPF_ALU64 | BPF_AND | BPF_X:
-+      case BPF_ALU64 | BPF_OR | BPF_X:
-+      case BPF_ALU64 | BPF_XOR | BPF_X:
-+      case BPF_ALU64 | BPF_ADD | BPF_X:
-+      case BPF_ALU64 | BPF_SUB | BPF_X:
-+              emit_alu_r64(ctx, dst, src, BPF_OP(code));
-+              break;
-+      /* dst = dst << src (64-bit) */
-+      /* dst = dst >> src (64-bit) */
-+      /* dst = dst >> src (64-bit, arithmetic) */
-+      case BPF_ALU64 | BPF_LSH | BPF_X:
-+      case BPF_ALU64 | BPF_RSH | BPF_X:
-+      case BPF_ALU64 | BPF_ARSH | BPF_X:
-+              emit_shift_r64(ctx, dst, lo(src), BPF_OP(code));
-+              break;
-+      /* dst = dst * src (64-bit) */
-+      case BPF_ALU64 | BPF_MUL | BPF_X:
-+              emit_mul_r64(ctx, dst, src);
-+              break;
-+      /* dst = dst / src (64-bit) */
-+      /* dst = dst % src (64-bit) */
-+      case BPF_ALU64 | BPF_DIV | BPF_X:
-+      case BPF_ALU64 | BPF_MOD | BPF_X:
-+              emit_divmod_r64(ctx, dst, src, BPF_OP(code));
-+              break;
-+      /* dst = htole(dst) */
-+      /* dst = htobe(dst) */
-+      case BPF_ALU | BPF_END | BPF_FROM_LE:
-+      case BPF_ALU | BPF_END | BPF_FROM_BE:
-+              if (BPF_SRC(code) ==
-+#ifdef __BIG_ENDIAN
-+                  BPF_FROM_LE
-+#else
-+                  BPF_FROM_BE
-+#endif
-+                  )
-+                      emit_bswap_r64(ctx, dst, imm);
-+              else
-+                      emit_trunc_r64(ctx, dst, imm);
-+              break;
-+      /* dst = imm64 */
-+      case BPF_LD | BPF_IMM | BPF_DW:
-+              emit_mov_i(ctx, lo(dst), imm);
-+              emit_mov_i(ctx, hi(dst), insn[1].imm);
-+              return 1;
-+      /* LDX: dst = *(size *)(src + off) */
-+      case BPF_LDX | BPF_MEM | BPF_W:
-+      case BPF_LDX | BPF_MEM | BPF_H:
-+      case BPF_LDX | BPF_MEM | BPF_B:
-+      case BPF_LDX | BPF_MEM | BPF_DW:
-+              emit_ldx(ctx, dst, lo(src), off, BPF_SIZE(code));
-+              break;
-+      /* ST: *(size *)(dst + off) = imm */
-+      case BPF_ST | BPF_MEM | BPF_W:
-+      case BPF_ST | BPF_MEM | BPF_H:
-+      case BPF_ST | BPF_MEM | BPF_B:
-+      case BPF_ST | BPF_MEM | BPF_DW:
-+              switch (BPF_SIZE(code)) {
-+              case BPF_DW:
-+                      /* Sign-extend immediate value into temporary reg */
-+                      emit_mov_se_i64(ctx, tmp, imm);
-+                      break;
-+              case BPF_W:
-+              case BPF_H:
-+              case BPF_B:
-+                      emit_mov_i(ctx, lo(tmp), imm);
-+                      break;
-+              }
-+              emit_stx(ctx, lo(dst), tmp, off, BPF_SIZE(code));
-+              break;
-+      /* STX: *(size *)(dst + off) = src */
-+      case BPF_STX | BPF_MEM | BPF_W:
-+      case BPF_STX | BPF_MEM | BPF_H:
-+      case BPF_STX | BPF_MEM | BPF_B:
-+      case BPF_STX | BPF_MEM | BPF_DW:
-+              emit_stx(ctx, lo(dst), src, off, BPF_SIZE(code));
-+              break;
-+      /* Speculation barrier */
-+      case BPF_ST | BPF_NOSPEC:
-+              break;
-+      /* Atomics */
-+      case BPF_STX | BPF_XADD | BPF_W:
-+              switch (imm) {
-+              case BPF_ADD:
-+              case BPF_AND:
-+              case BPF_OR:
-+              case BPF_XOR:
-+                      if (cpu_has_llsc)
-+                              emit_atomic_r(ctx, lo(dst), lo(src), off, imm);
-+                      else /* Non-ll/sc fallback */
-+                              emit_atomic_r32(ctx, lo(dst), lo(src),
-+                                              off, imm);
-+                      break;
-+              default:
-+                      goto notyet;
-+              }
-+              break;
-+      /* Atomics (64-bit) */
-+      case BPF_STX | BPF_XADD | BPF_DW:
-+              switch (imm) {
-+              case BPF_ADD:
-+              case BPF_AND:
-+              case BPF_OR:
-+              case BPF_XOR:
-+                      emit_atomic_r64(ctx, lo(dst), src, off, imm);
-+                      break;
-+              default:
-+                      goto notyet;
-+              }
-+              break;
-+      /* PC += off if dst == src */
-+      /* PC += off if dst != src */
-+      /* PC += off if dst & src */
-+      /* PC += off if dst > src */
-+      /* PC += off if dst >= src */
-+      /* PC += off if dst < src */
-+      /* PC += off if dst <= src */
-+      /* PC += off if dst > src (signed) */
-+      /* PC += off if dst >= src (signed) */
-+      /* PC += off if dst < src (signed) */
-+      /* PC += off if dst <= src (signed) */
-+      case BPF_JMP32 | BPF_JEQ | BPF_X:
-+      case BPF_JMP32 | BPF_JNE | BPF_X:
-+      case BPF_JMP32 | BPF_JSET | BPF_X:
-+      case BPF_JMP32 | BPF_JGT | BPF_X:
-+      case BPF_JMP32 | BPF_JGE | BPF_X:
-+      case BPF_JMP32 | BPF_JLT | BPF_X:
-+      case BPF_JMP32 | BPF_JLE | BPF_X:
-+      case BPF_JMP32 | BPF_JSGT | BPF_X:
-+      case BPF_JMP32 | BPF_JSGE | BPF_X:
-+      case BPF_JMP32 | BPF_JSLT | BPF_X:
-+      case BPF_JMP32 | BPF_JSLE | BPF_X:
-+              if (off == 0)
-+                      break;
-+              setup_jmp_r(ctx, dst == src, BPF_OP(code), off, &jmp, &rel);
-+              emit_jmp_r(ctx, lo(dst), lo(src), rel, jmp);
-+              if (finish_jmp(ctx, jmp, off) < 0)
-+                      goto toofar;
-+              break;
-+      /* PC += off if dst == imm */
-+      /* PC += off if dst != imm */
-+      /* PC += off if dst & imm */
-+      /* PC += off if dst > imm */
-+      /* PC += off if dst >= imm */
-+      /* PC += off if dst < imm */
-+      /* PC += off if dst <= imm */
-+      /* PC += off if dst > imm (signed) */
-+      /* PC += off if dst >= imm (signed) */
-+      /* PC += off if dst < imm (signed) */
-+      /* PC += off if dst <= imm (signed) */
-+      case BPF_JMP32 | BPF_JEQ | BPF_K:
-+      case BPF_JMP32 | BPF_JNE | BPF_K:
-+      case BPF_JMP32 | BPF_JSET | BPF_K:
-+      case BPF_JMP32 | BPF_JGT | BPF_K:
-+      case BPF_JMP32 | BPF_JGE | BPF_K:
-+      case BPF_JMP32 | BPF_JLT | BPF_K:
-+      case BPF_JMP32 | BPF_JLE | BPF_K:
-+      case BPF_JMP32 | BPF_JSGT | BPF_K:
-+      case BPF_JMP32 | BPF_JSGE | BPF_K:
-+      case BPF_JMP32 | BPF_JSLT | BPF_K:
-+      case BPF_JMP32 | BPF_JSLE | BPF_K:
-+              if (off == 0)
-+                      break;
-+              setup_jmp_i(ctx, imm, 32, BPF_OP(code), off, &jmp, &rel);
-+              if (valid_jmp_i(jmp, imm)) {
-+                      emit_jmp_i(ctx, lo(dst), imm, rel, jmp);
-+              } else {
-+                      /* Move large immediate to register */
-+                      emit_mov_i(ctx, MIPS_R_T6, imm);
-+                      emit_jmp_r(ctx, lo(dst), MIPS_R_T6, rel, jmp);
-+              }
-+              if (finish_jmp(ctx, jmp, off) < 0)
-+                      goto toofar;
-+              break;
-+      /* PC += off if dst == src */
-+      /* PC += off if dst != src */
-+      /* PC += off if dst & src */
-+      /* PC += off if dst > src */
-+      /* PC += off if dst >= src */
-+      /* PC += off if dst < src */
-+      /* PC += off if dst <= src */
-+      /* PC += off if dst > src (signed) */
-+      /* PC += off if dst >= src (signed) */
-+      /* PC += off if dst < src (signed) */
-+      /* PC += off if dst <= src (signed) */
-+      case BPF_JMP | BPF_JEQ | BPF_X:
-+      case BPF_JMP | BPF_JNE | BPF_X:
-+      case BPF_JMP | BPF_JSET | BPF_X:
-+      case BPF_JMP | BPF_JGT | BPF_X:
-+      case BPF_JMP | BPF_JGE | BPF_X:
-+      case BPF_JMP | BPF_JLT | BPF_X:
-+      case BPF_JMP | BPF_JLE | BPF_X:
-+      case BPF_JMP | BPF_JSGT | BPF_X:
-+      case BPF_JMP | BPF_JSGE | BPF_X:
-+      case BPF_JMP | BPF_JSLT | BPF_X:
-+      case BPF_JMP | BPF_JSLE | BPF_X:
-+              if (off == 0)
-+                      break;
-+              setup_jmp_r(ctx, dst == src, BPF_OP(code), off, &jmp, &rel);
-+              emit_jmp_r64(ctx, dst, src, rel, jmp);
-+              if (finish_jmp(ctx, jmp, off) < 0)
-+                      goto toofar;
-+              break;
-+      /* PC += off if dst == imm */
-+      /* PC += off if dst != imm */
-+      /* PC += off if dst & imm */
-+      /* PC += off if dst > imm */
-+      /* PC += off if dst >= imm */
-+      /* PC += off if dst < imm */
-+      /* PC += off if dst <= imm */
-+      /* PC += off if dst > imm (signed) */
-+      /* PC += off if dst >= imm (signed) */
-+      /* PC += off if dst < imm (signed) */
-+      /* PC += off if dst <= imm (signed) */
-+      case BPF_JMP | BPF_JEQ | BPF_K:
-+      case BPF_JMP | BPF_JNE | BPF_K:
-+      case BPF_JMP | BPF_JSET | BPF_K:
-+      case BPF_JMP | BPF_JGT | BPF_K:
-+      case BPF_JMP | BPF_JGE | BPF_K:
-+      case BPF_JMP | BPF_JLT | BPF_K:
-+      case BPF_JMP | BPF_JLE | BPF_K:
-+      case BPF_JMP | BPF_JSGT | BPF_K:
-+      case BPF_JMP | BPF_JSGE | BPF_K:
-+      case BPF_JMP | BPF_JSLT | BPF_K:
-+      case BPF_JMP | BPF_JSLE | BPF_K:
-+              if (off == 0)
-+                      break;
-+              setup_jmp_i(ctx, imm, 64, BPF_OP(code), off, &jmp, &rel);
-+              emit_jmp_i64(ctx, dst, imm, rel, jmp);
-+              if (finish_jmp(ctx, jmp, off) < 0)
-+                      goto toofar;
-+              break;
-+      /* PC += off */
-+      case BPF_JMP | BPF_JA:
-+              if (off == 0)
-+                      break;
-+              if (emit_ja(ctx, off) < 0)
-+                      goto toofar;
-+              break;
-+      /* Tail call */
-+      case BPF_JMP | BPF_TAIL_CALL:
-+              if (emit_tail_call(ctx) < 0)
-+                      goto invalid;
-+              break;
-+      /* Function call */
-+      case BPF_JMP | BPF_CALL:
-+              if (emit_call(ctx, insn) < 0)
-+                      goto invalid;
-+              break;
-+      /* Function return */
-+      case BPF_JMP | BPF_EXIT:
-+              /*
-+               * Optimization: when last instruction is EXIT
-+               * simply continue to epilogue.
-+               */
-+              if (ctx->bpf_index == ctx->program->len - 1)
-+                      break;
-+              if (emit_exit(ctx) < 0)
-+                      goto toofar;
-+              break;
-+
-+      default:
-+invalid:
-+              pr_err_once("unknown opcode %02x\n", code);
-+              return -EINVAL;
-+notyet:
-+              pr_info_once("*** NOT YET: opcode %02x ***\n", code);
-+              return -EFAULT;
-+toofar:
-+              pr_info_once("*** TOO FAR: jump at %u opcode %02x ***\n",
-+                           ctx->bpf_index, code);
-+              return -E2BIG;
-+      }
-+      return 0;
-+}
diff --git a/target/linux/generic/backport-5.15/050-v5.16-03-mips-bpf-Add-new-eBPF-JIT-for-64-bit-MIPS.patch b/target/linux/generic/backport-5.15/050-v5.16-03-mips-bpf-Add-new-eBPF-JIT-for-64-bit-MIPS.patch
deleted file mode 100644 (file)
index 38b46c0..0000000
+++ /dev/null
@@ -1,1005 +0,0 @@
-From: Johan Almbladh <[email protected]>
-Date: Tue, 5 Oct 2021 18:54:05 +0200
-Subject: [PATCH] mips: bpf: Add new eBPF JIT for 64-bit MIPS
-
-This is an implementation on of an eBPF JIT for 64-bit MIPS III-V and
-MIPS64r1-r6. It uses the same framework introduced by the 32-bit JIT.
-
-Signed-off-by: Johan Almbladh <[email protected]>
----
- create mode 100644 arch/mips/net/bpf_jit_comp64.c
-
---- /dev/null
-+++ b/arch/mips/net/bpf_jit_comp64.c
-@@ -0,0 +1,991 @@
-+// SPDX-License-Identifier: GPL-2.0-only
-+/*
-+ * Just-In-Time compiler for eBPF bytecode on MIPS.
-+ * Implementation of JIT functions for 64-bit CPUs.
-+ *
-+ * Copyright (c) 2021 Anyfi Networks AB.
-+ * Author: Johan Almbladh <[email protected]>
-+ *
-+ * Based on code and ideas from
-+ * Copyright (c) 2017 Cavium, Inc.
-+ * Copyright (c) 2017 Shubham Bansal <[email protected]>
-+ * Copyright (c) 2011 Mircea Gherzan <[email protected]>
-+ */
-+
-+#include <linux/errno.h>
-+#include <linux/filter.h>
-+#include <linux/bpf.h>
-+#include <asm/cpu-features.h>
-+#include <asm/isa-rev.h>
-+#include <asm/uasm.h>
-+
-+#include "bpf_jit_comp.h"
-+
-+/* MIPS t0-t3 are not available in the n64 ABI */
-+#undef MIPS_R_T0
-+#undef MIPS_R_T1
-+#undef MIPS_R_T2
-+#undef MIPS_R_T3
-+
-+/* Stack is 16-byte aligned in n64 ABI */
-+#define MIPS_STACK_ALIGNMENT 16
-+
-+/* Extra 64-bit eBPF registers used by JIT */
-+#define JIT_REG_TC (MAX_BPF_JIT_REG + 0)
-+#define JIT_REG_ZX (MAX_BPF_JIT_REG + 1)
-+
-+/* Number of prologue bytes to skip when doing a tail call */
-+#define JIT_TCALL_SKIP 4
-+
-+/* Callee-saved CPU registers that the JIT must preserve */
-+#define JIT_CALLEE_REGS   \
-+      (BIT(MIPS_R_S0) | \
-+       BIT(MIPS_R_S1) | \
-+       BIT(MIPS_R_S2) | \
-+       BIT(MIPS_R_S3) | \
-+       BIT(MIPS_R_S4) | \
-+       BIT(MIPS_R_S5) | \
-+       BIT(MIPS_R_S6) | \
-+       BIT(MIPS_R_S7) | \
-+       BIT(MIPS_R_GP) | \
-+       BIT(MIPS_R_FP) | \
-+       BIT(MIPS_R_RA))
-+
-+/* Caller-saved CPU registers available for JIT use */
-+#define JIT_CALLER_REGS         \
-+      (BIT(MIPS_R_A5) | \
-+       BIT(MIPS_R_A6) | \
-+       BIT(MIPS_R_A7))
-+/*
-+ * Mapping of 64-bit eBPF registers to 64-bit native MIPS registers.
-+ * MIPS registers t4 - t7 may be used by the JIT as temporary registers.
-+ * MIPS registers t8 - t9 are reserved for single-register common functions.
-+ */
-+static const u8 bpf2mips64[] = {
-+      /* Return value from in-kernel function, and exit value from eBPF */
-+      [BPF_REG_0] = MIPS_R_V0,
-+      /* Arguments from eBPF program to in-kernel function */
-+      [BPF_REG_1] = MIPS_R_A0,
-+      [BPF_REG_2] = MIPS_R_A1,
-+      [BPF_REG_3] = MIPS_R_A2,
-+      [BPF_REG_4] = MIPS_R_A3,
-+      [BPF_REG_5] = MIPS_R_A4,
-+      /* Callee-saved registers that in-kernel function will preserve */
-+      [BPF_REG_6] = MIPS_R_S0,
-+      [BPF_REG_7] = MIPS_R_S1,
-+      [BPF_REG_8] = MIPS_R_S2,
-+      [BPF_REG_9] = MIPS_R_S3,
-+      /* Read-only frame pointer to access the eBPF stack */
-+      [BPF_REG_FP] = MIPS_R_FP,
-+      /* Temporary register for blinding constants */
-+      [BPF_REG_AX] = MIPS_R_AT,
-+      /* Tail call count register, caller-saved */
-+      [JIT_REG_TC] = MIPS_R_A5,
-+      /* Constant for register zero-extension */
-+      [JIT_REG_ZX] = MIPS_R_V1,
-+};
-+
-+/*
-+ * MIPS 32-bit operations on 64-bit registers generate a sign-extended
-+ * result. However, the eBPF ISA mandates zero-extension, so we rely on the
-+ * verifier to add that for us (emit_zext_ver). In addition, ALU arithmetic
-+ * operations, right shift and byte swap require properly sign-extended
-+ * operands or the result is unpredictable. We emit explicit sign-extensions
-+ * in those cases.
-+ */
-+
-+/* Sign extension */
-+static void emit_sext(struct jit_context *ctx, u8 dst, u8 src)
-+{
-+      emit(ctx, sll, dst, src, 0);
-+      clobber_reg(ctx, dst);
-+}
-+
-+/* Zero extension */
-+static void emit_zext(struct jit_context *ctx, u8 dst)
-+{
-+      if (cpu_has_mips64r2 || cpu_has_mips64r6) {
-+              emit(ctx, dinsu, dst, MIPS_R_ZERO, 32, 32);
-+      } else {
-+              emit(ctx, and, dst, dst, bpf2mips64[JIT_REG_ZX]);
-+              access_reg(ctx, JIT_REG_ZX); /* We need the ZX register */
-+      }
-+      clobber_reg(ctx, dst);
-+}
-+
-+/* Zero extension, if verifier does not do it for us  */
-+static void emit_zext_ver(struct jit_context *ctx, u8 dst)
-+{
-+      if (!ctx->program->aux->verifier_zext)
-+              emit_zext(ctx, dst);
-+}
-+
-+/* dst = imm (64-bit) */
-+static void emit_mov_i64(struct jit_context *ctx, u8 dst, u64 imm64)
-+{
-+      if (imm64 >= 0xffffffffffff8000ULL || imm64 < 0x8000ULL) {
-+              emit(ctx, daddiu, dst, MIPS_R_ZERO, (s16)imm64);
-+      } else if (imm64 >= 0xffffffff80000000ULL ||
-+                 (imm64 < 0x80000000 && imm64 > 0xffff)) {
-+              emit(ctx, lui, dst, (s16)(imm64 >> 16));
-+              emit(ctx, ori, dst, dst, (u16)imm64 & 0xffff);
-+      } else {
-+              u8 acc = MIPS_R_ZERO;
-+              int k;
-+
-+              for (k = 0; k < 4; k++) {
-+                      u16 half = imm64 >> (48 - 16 * k);
-+
-+                      if (acc == dst)
-+                              emit(ctx, dsll, dst, dst, 16);
-+
-+                      if (half) {
-+                              emit(ctx, ori, dst, acc, half);
-+                              acc = dst;
-+                      }
-+              }
-+      }
-+      clobber_reg(ctx, dst);
-+}
-+
-+/* ALU immediate operation (64-bit) */
-+static void emit_alu_i64(struct jit_context *ctx, u8 dst, s32 imm, u8 op)
-+{
-+      switch (BPF_OP(op)) {
-+      /* dst = dst | imm */
-+      case BPF_OR:
-+              emit(ctx, ori, dst, dst, (u16)imm);
-+              break;
-+      /* dst = dst ^ imm */
-+      case BPF_XOR:
-+              emit(ctx, xori, dst, dst, (u16)imm);
-+              break;
-+      /* dst = -dst */
-+      case BPF_NEG:
-+              emit(ctx, dsubu, dst, MIPS_R_ZERO, dst);
-+              break;
-+      /* dst = dst << imm */
-+      case BPF_LSH:
-+              emit(ctx, dsll_safe, dst, dst, imm);
-+              break;
-+      /* dst = dst >> imm */
-+      case BPF_RSH:
-+              emit(ctx, dsrl_safe, dst, dst, imm);
-+              break;
-+      /* dst = dst >> imm (arithmetic) */
-+      case BPF_ARSH:
-+              emit(ctx, dsra_safe, dst, dst, imm);
-+              break;
-+      /* dst = dst + imm */
-+      case BPF_ADD:
-+              emit(ctx, daddiu, dst, dst, imm);
-+              break;
-+      /* dst = dst - imm */
-+      case BPF_SUB:
-+              emit(ctx, daddiu, dst, dst, -imm);
-+              break;
-+      default:
-+              /* Width-generic operations */
-+              emit_alu_i(ctx, dst, imm, op);
-+      }
-+      clobber_reg(ctx, dst);
-+}
-+
-+/* ALU register operation (64-bit) */
-+static void emit_alu_r64(struct jit_context *ctx, u8 dst, u8 src, u8 op)
-+{
-+      switch (BPF_OP(op)) {
-+      /* dst = dst << src */
-+      case BPF_LSH:
-+              emit(ctx, dsllv, dst, dst, src);
-+              break;
-+      /* dst = dst >> src */
-+      case BPF_RSH:
-+              emit(ctx, dsrlv, dst, dst, src);
-+              break;
-+      /* dst = dst >> src (arithmetic) */
-+      case BPF_ARSH:
-+              emit(ctx, dsrav, dst, dst, src);
-+              break;
-+      /* dst = dst + src */
-+      case BPF_ADD:
-+              emit(ctx, daddu, dst, dst, src);
-+              break;
-+      /* dst = dst - src */
-+      case BPF_SUB:
-+              emit(ctx, dsubu, dst, dst, src);
-+              break;
-+      /* dst = dst * src */
-+      case BPF_MUL:
-+              if (cpu_has_mips64r6) {
-+                      emit(ctx, dmulu, dst, dst, src);
-+              } else {
-+                      emit(ctx, dmultu, dst, src);
-+                      emit(ctx, mflo, dst);
-+              }
-+              break;
-+      /* dst = dst / src */
-+      case BPF_DIV:
-+              if (cpu_has_mips64r6) {
-+                      emit(ctx, ddivu_r6, dst, dst, src);
-+              } else {
-+                      emit(ctx, ddivu, dst, src);
-+                      emit(ctx, mflo, dst);
-+              }
-+              break;
-+      /* dst = dst % src */
-+      case BPF_MOD:
-+              if (cpu_has_mips64r6) {
-+                      emit(ctx, dmodu, dst, dst, src);
-+              } else {
-+                      emit(ctx, ddivu, dst, src);
-+                      emit(ctx, mfhi, dst);
-+              }
-+              break;
-+      default:
-+              /* Width-generic operations */
-+              emit_alu_r(ctx, dst, src, op);
-+      }
-+      clobber_reg(ctx, dst);
-+}
-+
-+/* Swap sub words in a register double word */
-+static void emit_swap_r64(struct jit_context *ctx, u8 dst, u8 mask, u32 bits)
-+{
-+      u8 tmp = MIPS_R_T9;
-+
-+      emit(ctx, and, tmp, dst, mask);  /* tmp = dst & mask  */
-+      emit(ctx, dsll, tmp, tmp, bits); /* tmp = tmp << bits */
-+      emit(ctx, dsrl, dst, dst, bits); /* dst = dst >> bits */
-+      emit(ctx, and, dst, dst, mask);  /* dst = dst & mask  */
-+      emit(ctx, or, dst, dst, tmp);    /* dst = dst | tmp   */
-+}
-+
-+/* Swap bytes and truncate a register double word, word or half word */
-+static void emit_bswap_r64(struct jit_context *ctx, u8 dst, u32 width)
-+{
-+      switch (width) {
-+      /* Swap bytes in a double word */
-+      case 64:
-+              if (cpu_has_mips64r2 || cpu_has_mips64r6) {
-+                      emit(ctx, dsbh, dst, dst);
-+                      emit(ctx, dshd, dst, dst);
-+              } else {
-+                      u8 t1 = MIPS_R_T6;
-+                      u8 t2 = MIPS_R_T7;
-+
-+                      emit(ctx, dsll32, t2, dst, 0);  /* t2 = dst << 32    */
-+                      emit(ctx, dsrl32, dst, dst, 0); /* dst = dst >> 32   */
-+                      emit(ctx, or, dst, dst, t2);    /* dst = dst | t2    */
-+
-+                      emit(ctx, ori, t2, MIPS_R_ZERO, 0xffff);
-+                      emit(ctx, dsll32, t1, t2, 0);   /* t1 = t2 << 32     */
-+                      emit(ctx, or, t1, t1, t2);      /* t1 = t1 | t2      */
-+                      emit_swap_r64(ctx, dst, t1, 16);/* dst = swap16(dst) */
-+
-+                      emit(ctx, lui, t2, 0xff);       /* t2 = 0x00ff0000   */
-+                      emit(ctx, ori, t2, t2, 0xff);   /* t2 = t2 | 0x00ff  */
-+                      emit(ctx, dsll32, t1, t2, 0);   /* t1 = t2 << 32     */
-+                      emit(ctx, or, t1, t1, t2);      /* t1 = t1 | t2      */
-+                      emit_swap_r64(ctx, dst, t1, 8); /* dst = swap8(dst)  */
-+              }
-+              break;
-+      /* Swap bytes in a half word */
-+      /* Swap bytes in a word */
-+      case 32:
-+      case 16:
-+              emit_sext(ctx, dst, dst);
-+              emit_bswap_r(ctx, dst, width);
-+              if (cpu_has_mips64r2 || cpu_has_mips64r6)
-+                      emit_zext(ctx, dst);
-+              break;
-+      }
-+      clobber_reg(ctx, dst);
-+}
-+
-+/* Truncate a register double word, word or half word */
-+static void emit_trunc_r64(struct jit_context *ctx, u8 dst, u32 width)
-+{
-+      switch (width) {
-+      case 64:
-+              break;
-+      /* Zero-extend a word */
-+      case 32:
-+              emit_zext(ctx, dst);
-+              break;
-+      /* Zero-extend a half word */
-+      case 16:
-+              emit(ctx, andi, dst, dst, 0xffff);
-+              break;
-+      }
-+      clobber_reg(ctx, dst);
-+}
-+
-+/* Load operation: dst = *(size*)(src + off) */
-+static void emit_ldx(struct jit_context *ctx, u8 dst, u8 src, s16 off, u8 size)
-+{
-+      switch (size) {
-+      /* Load a byte */
-+      case BPF_B:
-+              emit(ctx, lbu, dst, off, src);
-+              break;
-+      /* Load a half word */
-+      case BPF_H:
-+              emit(ctx, lhu, dst, off, src);
-+              break;
-+      /* Load a word */
-+      case BPF_W:
-+              emit(ctx, lwu, dst, off, src);
-+              break;
-+      /* Load a double word */
-+      case BPF_DW:
-+              emit(ctx, ld, dst, off, src);
-+              break;
-+      }
-+      clobber_reg(ctx, dst);
-+}
-+
-+/* Store operation: *(size *)(dst + off) = src */
-+static void emit_stx(struct jit_context *ctx, u8 dst, u8 src, s16 off, u8 size)
-+{
-+      switch (size) {
-+      /* Store a byte */
-+      case BPF_B:
-+              emit(ctx, sb, src, off, dst);
-+              break;
-+      /* Store a half word */
-+      case BPF_H:
-+              emit(ctx, sh, src, off, dst);
-+              break;
-+      /* Store a word */
-+      case BPF_W:
-+              emit(ctx, sw, src, off, dst);
-+              break;
-+      /* Store a double word */
-+      case BPF_DW:
-+              emit(ctx, sd, src, off, dst);
-+              break;
-+      }
-+}
-+
-+/* Atomic read-modify-write */
-+static void emit_atomic_r64(struct jit_context *ctx,
-+                          u8 dst, u8 src, s16 off, u8 code)
-+{
-+      u8 t1 = MIPS_R_T6;
-+      u8 t2 = MIPS_R_T7;
-+
-+      emit(ctx, lld, t1, off, dst);
-+      switch (code) {
-+      case BPF_ADD:
-+              emit(ctx, daddu, t2, t1, src);
-+              break;
-+      case BPF_AND:
-+              emit(ctx, and, t2, t1, src);
-+              break;
-+      case BPF_OR:
-+              emit(ctx, or, t2, t1, src);
-+              break;
-+      case BPF_XOR:
-+              emit(ctx, xor, t2, t1, src);
-+              break;
-+      }
-+      emit(ctx, scd, t2, off, dst);
-+      emit(ctx, beqz, t2, -16);
-+      emit(ctx, nop); /* Delay slot */
-+}
-+
-+/* Function call */
-+static int emit_call(struct jit_context *ctx, const struct bpf_insn *insn)
-+{
-+      u8 zx = bpf2mips64[JIT_REG_ZX];
-+      u8 tmp = MIPS_R_T6;
-+      bool fixed;
-+      u64 addr;
-+
-+      /* Decode the call address */
-+      if (bpf_jit_get_func_addr(ctx->program, insn, false,
-+                                &addr, &fixed) < 0)
-+              return -1;
-+      if (!fixed)
-+              return -1;
-+
-+      /* Push caller-saved registers on stack */
-+      push_regs(ctx, ctx->clobbered & JIT_CALLER_REGS, 0, 0);
-+
-+      /* Emit function call */
-+      emit_mov_i64(ctx, tmp, addr);
-+      emit(ctx, jalr, MIPS_R_RA, tmp);
-+      emit(ctx, nop); /* Delay slot */
-+
-+      /* Restore caller-saved registers */
-+      pop_regs(ctx, ctx->clobbered & JIT_CALLER_REGS, 0, 0);
-+
-+      /* Re-initialize the JIT zero-extension register if accessed */
-+      if (ctx->accessed & BIT(JIT_REG_ZX)) {
-+              emit(ctx, daddiu, zx, MIPS_R_ZERO, -1);
-+              emit(ctx, dsrl32, zx, zx, 0);
-+      }
-+
-+      clobber_reg(ctx, MIPS_R_RA);
-+      clobber_reg(ctx, MIPS_R_V0);
-+      clobber_reg(ctx, MIPS_R_V1);
-+      return 0;
-+}
-+
-+/* Function tail call */
-+static int emit_tail_call(struct jit_context *ctx)
-+{
-+      u8 ary = bpf2mips64[BPF_REG_2];
-+      u8 ind = bpf2mips64[BPF_REG_3];
-+      u8 tcc = bpf2mips64[JIT_REG_TC];
-+      u8 tmp = MIPS_R_T6;
-+      int off;
-+
-+      /*
-+       * Tail call:
-+       * eBPF R1 - function argument (context ptr), passed in a0-a1
-+       * eBPF R2 - ptr to object with array of function entry points
-+       * eBPF R3 - array index of function to be called
-+       */
-+
-+      /* if (ind >= ary->map.max_entries) goto out */
-+      off = offsetof(struct bpf_array, map.max_entries);
-+      if (off > 0x7fff)
-+              return -1;
-+      emit(ctx, lwu, tmp, off, ary);            /* tmp = ary->map.max_entrs*/
-+      emit(ctx, sltu, tmp, ind, tmp);           /* tmp = ind < t1          */
-+      emit(ctx, beqz, tmp, get_offset(ctx, 1)); /* PC += off(1) if tmp == 0*/
-+
-+      /* if (--TCC < 0) goto out */
-+      emit(ctx, daddiu, tcc, tcc, -1);          /* tcc-- (delay slot)      */
-+      emit(ctx, bltz, tcc, get_offset(ctx, 1)); /* PC += off(1) if tcc < 0 */
-+                                                /* (next insn delay slot)  */
-+      /* prog = ary->ptrs[ind] */
-+      off = offsetof(struct bpf_array, ptrs);
-+      if (off > 0x7fff)
-+              return -1;
-+      emit(ctx, dsll, tmp, ind, 3);             /* tmp = ind << 3          */
-+      emit(ctx, daddu, tmp, tmp, ary);          /* tmp += ary              */
-+      emit(ctx, ld, tmp, off, tmp);             /* tmp = *(tmp + off)      */
-+
-+      /* if (prog == 0) goto out */
-+      emit(ctx, beqz, tmp, get_offset(ctx, 1)); /* PC += off(1) if tmp == 0*/
-+      emit(ctx, nop);                           /* Delay slot              */
-+
-+      /* func = prog->bpf_func + 8 (prologue skip offset) */
-+      off = offsetof(struct bpf_prog, bpf_func);
-+      if (off > 0x7fff)
-+              return -1;
-+      emit(ctx, ld, tmp, off, tmp);                /* tmp = *(tmp + off)   */
-+      emit(ctx, daddiu, tmp, tmp, JIT_TCALL_SKIP); /* tmp += skip (4)      */
-+
-+      /* goto func */
-+      build_epilogue(ctx, tmp);
-+      access_reg(ctx, JIT_REG_TC);
-+      return 0;
-+}
-+
-+/*
-+ * Stack frame layout for a JITed program (stack grows down).
-+ *
-+ * Higher address  : Previous stack frame      :
-+ *                 +===========================+  <--- MIPS sp before call
-+ *                 | Callee-saved registers,   |
-+ *                 | including RA and FP       |
-+ *                 +---------------------------+  <--- eBPF FP (MIPS fp)
-+ *                 | Local eBPF variables      |
-+ *                 | allocated by program      |
-+ *                 +---------------------------+
-+ *                 | Reserved for caller-saved |
-+ *                 | registers                 |
-+ * Lower address   +===========================+  <--- MIPS sp
-+ */
-+
-+/* Build program prologue to set up the stack and registers */
-+void build_prologue(struct jit_context *ctx)
-+{
-+      u8 fp = bpf2mips64[BPF_REG_FP];
-+      u8 tc = bpf2mips64[JIT_REG_TC];
-+      u8 zx = bpf2mips64[JIT_REG_ZX];
-+      int stack, saved, locals, reserved;
-+
-+      /*
-+       * The first instruction initializes the tail call count register.
-+       * On a tail call, the calling function jumps into the prologue
-+       * after this instruction.
-+       */
-+      emit(ctx, addiu, tc, MIPS_R_ZERO, min(MAX_TAIL_CALL_CNT + 1, 0xffff));
-+
-+      /* === Entry-point for tail calls === */
-+
-+      /*
-+       * If the eBPF frame pointer and tail call count registers were
-+       * accessed they must be preserved. Mark them as clobbered here
-+       * to save and restore them on the stack as needed.
-+       */
-+      if (ctx->accessed & BIT(BPF_REG_FP))
-+              clobber_reg(ctx, fp);
-+      if (ctx->accessed & BIT(JIT_REG_TC))
-+              clobber_reg(ctx, tc);
-+      if (ctx->accessed & BIT(JIT_REG_ZX))
-+              clobber_reg(ctx, zx);
-+
-+      /* Compute the stack space needed for callee-saved registers */
-+      saved = hweight32(ctx->clobbered & JIT_CALLEE_REGS) * sizeof(u64);
-+      saved = ALIGN(saved, MIPS_STACK_ALIGNMENT);
-+
-+      /* Stack space used by eBPF program local data */
-+      locals = ALIGN(ctx->program->aux->stack_depth, MIPS_STACK_ALIGNMENT);
-+
-+      /*
-+       * If we are emitting function calls, reserve extra stack space for
-+       * caller-saved registers needed by the JIT. The required space is
-+       * computed automatically during resource usage discovery (pass 1).
-+       */
-+      reserved = ctx->stack_used;
-+
-+      /* Allocate the stack frame */
-+      stack = ALIGN(saved + locals + reserved, MIPS_STACK_ALIGNMENT);
-+      if (stack)
-+              emit(ctx, daddiu, MIPS_R_SP, MIPS_R_SP, -stack);
-+
-+      /* Store callee-saved registers on stack */
-+      push_regs(ctx, ctx->clobbered & JIT_CALLEE_REGS, 0, stack - saved);
-+
-+      /* Initialize the eBPF frame pointer if accessed */
-+      if (ctx->accessed & BIT(BPF_REG_FP))
-+              emit(ctx, daddiu, fp, MIPS_R_SP, stack - saved);
-+
-+      /* Initialize the ePF JIT zero-extension register if accessed */
-+      if (ctx->accessed & BIT(JIT_REG_ZX)) {
-+              emit(ctx, daddiu, zx, MIPS_R_ZERO, -1);
-+              emit(ctx, dsrl32, zx, zx, 0);
-+      }
-+
-+      ctx->saved_size = saved;
-+      ctx->stack_size = stack;
-+}
-+
-+/* Build the program epilogue to restore the stack and registers */
-+void build_epilogue(struct jit_context *ctx, int dest_reg)
-+{
-+      /* Restore callee-saved registers from stack */
-+      pop_regs(ctx, ctx->clobbered & JIT_CALLEE_REGS, 0,
-+               ctx->stack_size - ctx->saved_size);
-+
-+      /* Release the stack frame */
-+      if (ctx->stack_size)
-+              emit(ctx, daddiu, MIPS_R_SP, MIPS_R_SP, ctx->stack_size);
-+
-+      /* Jump to return address and sign-extend the 32-bit return value */
-+      emit(ctx, jr, dest_reg);
-+      emit(ctx, sll, MIPS_R_V0, MIPS_R_V0, 0); /* Delay slot */
-+}
-+
-+/* Build one eBPF instruction */
-+int build_insn(const struct bpf_insn *insn, struct jit_context *ctx)
-+{
-+      u8 dst = bpf2mips64[insn->dst_reg];
-+      u8 src = bpf2mips64[insn->src_reg];
-+      u8 code = insn->code;
-+      s16 off = insn->off;
-+      s32 imm = insn->imm;
-+      s32 val, rel;
-+      u8 alu, jmp;
-+
-+      switch (code) {
-+      /* ALU operations */
-+      /* dst = imm */
-+      case BPF_ALU | BPF_MOV | BPF_K:
-+              emit_mov_i(ctx, dst, imm);
-+              emit_zext_ver(ctx, dst);
-+              break;
-+      /* dst = src */
-+      case BPF_ALU | BPF_MOV | BPF_X:
-+              if (imm == 1) {
-+                      /* Special mov32 for zext */
-+                      emit_zext(ctx, dst);
-+              } else {
-+                      emit_mov_r(ctx, dst, src);
-+                      emit_zext_ver(ctx, dst);
-+              }
-+              break;
-+      /* dst = -dst */
-+      case BPF_ALU | BPF_NEG:
-+              emit_sext(ctx, dst, dst);
-+              emit_alu_i(ctx, dst, 0, BPF_NEG);
-+              emit_zext_ver(ctx, dst);
-+              break;
-+      /* dst = dst & imm */
-+      /* dst = dst | imm */
-+      /* dst = dst ^ imm */
-+      /* dst = dst << imm */
-+      case BPF_ALU | BPF_OR | BPF_K:
-+      case BPF_ALU | BPF_AND | BPF_K:
-+      case BPF_ALU | BPF_XOR | BPF_K:
-+      case BPF_ALU | BPF_LSH | BPF_K:
-+              if (!valid_alu_i(BPF_OP(code), imm)) {
-+                      emit_mov_i(ctx, MIPS_R_T4, imm);
-+                      emit_alu_r(ctx, dst, MIPS_R_T4, BPF_OP(code));
-+              } else if (rewrite_alu_i(BPF_OP(code), imm, &alu, &val)) {
-+                      emit_alu_i(ctx, dst, val, alu);
-+              }
-+              emit_zext_ver(ctx, dst);
-+              break;
-+      /* dst = dst >> imm */
-+      /* dst = dst >> imm (arithmetic) */
-+      /* dst = dst + imm */
-+      /* dst = dst - imm */
-+      /* dst = dst * imm */
-+      /* dst = dst / imm */
-+      /* dst = dst % imm */
-+      case BPF_ALU | BPF_RSH | BPF_K:
-+      case BPF_ALU | BPF_ARSH | BPF_K:
-+      case BPF_ALU | BPF_ADD | BPF_K:
-+      case BPF_ALU | BPF_SUB | BPF_K:
-+      case BPF_ALU | BPF_MUL | BPF_K:
-+      case BPF_ALU | BPF_DIV | BPF_K:
-+      case BPF_ALU | BPF_MOD | BPF_K:
-+              if (!valid_alu_i(BPF_OP(code), imm)) {
-+                      emit_sext(ctx, dst, dst);
-+                      emit_mov_i(ctx, MIPS_R_T4, imm);
-+                      emit_alu_r(ctx, dst, MIPS_R_T4, BPF_OP(code));
-+              } else if (rewrite_alu_i(BPF_OP(code), imm, &alu, &val)) {
-+                      emit_sext(ctx, dst, dst);
-+                      emit_alu_i(ctx, dst, val, alu);
-+              }
-+              emit_zext_ver(ctx, dst);
-+              break;
-+      /* dst = dst & src */
-+      /* dst = dst | src */
-+      /* dst = dst ^ src */
-+      /* dst = dst << src */
-+      case BPF_ALU | BPF_AND | BPF_X:
-+      case BPF_ALU | BPF_OR | BPF_X:
-+      case BPF_ALU | BPF_XOR | BPF_X:
-+      case BPF_ALU | BPF_LSH | BPF_X:
-+              emit_alu_r(ctx, dst, src, BPF_OP(code));
-+              emit_zext_ver(ctx, dst);
-+              break;
-+      /* dst = dst >> src */
-+      /* dst = dst >> src (arithmetic) */
-+      /* dst = dst + src */
-+      /* dst = dst - src */
-+      /* dst = dst * src */
-+      /* dst = dst / src */
-+      /* dst = dst % src */
-+      case BPF_ALU | BPF_RSH | BPF_X:
-+      case BPF_ALU | BPF_ARSH | BPF_X:
-+      case BPF_ALU | BPF_ADD | BPF_X:
-+      case BPF_ALU | BPF_SUB | BPF_X:
-+      case BPF_ALU | BPF_MUL | BPF_X:
-+      case BPF_ALU | BPF_DIV | BPF_X:
-+      case BPF_ALU | BPF_MOD | BPF_X:
-+              emit_sext(ctx, dst, dst);
-+              emit_sext(ctx, MIPS_R_T4, src);
-+              emit_alu_r(ctx, dst, MIPS_R_T4, BPF_OP(code));
-+              emit_zext_ver(ctx, dst);
-+              break;
-+      /* dst = imm (64-bit) */
-+      case BPF_ALU64 | BPF_MOV | BPF_K:
-+              emit_mov_i(ctx, dst, imm);
-+              break;
-+      /* dst = src (64-bit) */
-+      case BPF_ALU64 | BPF_MOV | BPF_X:
-+              emit_mov_r(ctx, dst, src);
-+              break;
-+      /* dst = -dst (64-bit) */
-+      case BPF_ALU64 | BPF_NEG:
-+              emit_alu_i64(ctx, dst, 0, BPF_NEG);
-+              break;
-+      /* dst = dst & imm (64-bit) */
-+      /* dst = dst | imm (64-bit) */
-+      /* dst = dst ^ imm (64-bit) */
-+      /* dst = dst << imm (64-bit) */
-+      /* dst = dst >> imm (64-bit) */
-+      /* dst = dst >> imm ((64-bit, arithmetic) */
-+      /* dst = dst + imm (64-bit) */
-+      /* dst = dst - imm (64-bit) */
-+      /* dst = dst * imm (64-bit) */
-+      /* dst = dst / imm (64-bit) */
-+      /* dst = dst % imm (64-bit) */
-+      case BPF_ALU64 | BPF_AND | BPF_K:
-+      case BPF_ALU64 | BPF_OR | BPF_K:
-+      case BPF_ALU64 | BPF_XOR | BPF_K:
-+      case BPF_ALU64 | BPF_LSH | BPF_K:
-+      case BPF_ALU64 | BPF_RSH | BPF_K:
-+      case BPF_ALU64 | BPF_ARSH | BPF_K:
-+      case BPF_ALU64 | BPF_ADD | BPF_K:
-+      case BPF_ALU64 | BPF_SUB | BPF_K:
-+      case BPF_ALU64 | BPF_MUL | BPF_K:
-+      case BPF_ALU64 | BPF_DIV | BPF_K:
-+      case BPF_ALU64 | BPF_MOD | BPF_K:
-+              if (!valid_alu_i(BPF_OP(code), imm)) {
-+                      emit_mov_i(ctx, MIPS_R_T4, imm);
-+                      emit_alu_r64(ctx, dst, MIPS_R_T4, BPF_OP(code));
-+              } else if (rewrite_alu_i(BPF_OP(code), imm, &alu, &val)) {
-+                      emit_alu_i64(ctx, dst, val, alu);
-+              }
-+              break;
-+      /* dst = dst & src (64-bit) */
-+      /* dst = dst | src (64-bit) */
-+      /* dst = dst ^ src (64-bit) */
-+      /* dst = dst << src (64-bit) */
-+      /* dst = dst >> src (64-bit) */
-+      /* dst = dst >> src (64-bit, arithmetic) */
-+      /* dst = dst + src (64-bit) */
-+      /* dst = dst - src (64-bit) */
-+      /* dst = dst * src (64-bit) */
-+      /* dst = dst / src (64-bit) */
-+      /* dst = dst % src (64-bit) */
-+      case BPF_ALU64 | BPF_AND | BPF_X:
-+      case BPF_ALU64 | BPF_OR | BPF_X:
-+      case BPF_ALU64 | BPF_XOR | BPF_X:
-+      case BPF_ALU64 | BPF_LSH | BPF_X:
-+      case BPF_ALU64 | BPF_RSH | BPF_X:
-+      case BPF_ALU64 | BPF_ARSH | BPF_X:
-+      case BPF_ALU64 | BPF_ADD | BPF_X:
-+      case BPF_ALU64 | BPF_SUB | BPF_X:
-+      case BPF_ALU64 | BPF_MUL | BPF_X:
-+      case BPF_ALU64 | BPF_DIV | BPF_X:
-+      case BPF_ALU64 | BPF_MOD | BPF_X:
-+              emit_alu_r64(ctx, dst, src, BPF_OP(code));
-+              break;
-+      /* dst = htole(dst) */
-+      /* dst = htobe(dst) */
-+      case BPF_ALU | BPF_END | BPF_FROM_LE:
-+      case BPF_ALU | BPF_END | BPF_FROM_BE:
-+              if (BPF_SRC(code) ==
-+#ifdef __BIG_ENDIAN
-+                  BPF_FROM_LE
-+#else
-+                  BPF_FROM_BE
-+#endif
-+                  )
-+                      emit_bswap_r64(ctx, dst, imm);
-+              else
-+                      emit_trunc_r64(ctx, dst, imm);
-+              break;
-+      /* dst = imm64 */
-+      case BPF_LD | BPF_IMM | BPF_DW:
-+              emit_mov_i64(ctx, dst, (u32)imm | ((u64)insn[1].imm << 32));
-+              return 1;
-+      /* LDX: dst = *(size *)(src + off) */
-+      case BPF_LDX | BPF_MEM | BPF_W:
-+      case BPF_LDX | BPF_MEM | BPF_H:
-+      case BPF_LDX | BPF_MEM | BPF_B:
-+      case BPF_LDX | BPF_MEM | BPF_DW:
-+              emit_ldx(ctx, dst, src, off, BPF_SIZE(code));
-+              break;
-+      /* ST: *(size *)(dst + off) = imm */
-+      case BPF_ST | BPF_MEM | BPF_W:
-+      case BPF_ST | BPF_MEM | BPF_H:
-+      case BPF_ST | BPF_MEM | BPF_B:
-+      case BPF_ST | BPF_MEM | BPF_DW:
-+              emit_mov_i(ctx, MIPS_R_T4, imm);
-+              emit_stx(ctx, dst, MIPS_R_T4, off, BPF_SIZE(code));
-+              break;
-+      /* STX: *(size *)(dst + off) = src */
-+      case BPF_STX | BPF_MEM | BPF_W:
-+      case BPF_STX | BPF_MEM | BPF_H:
-+      case BPF_STX | BPF_MEM | BPF_B:
-+      case BPF_STX | BPF_MEM | BPF_DW:
-+              emit_stx(ctx, dst, src, off, BPF_SIZE(code));
-+              break;
-+      /* Speculation barrier */
-+      case BPF_ST | BPF_NOSPEC:
-+              break;
-+      /* Atomics */
-+      case BPF_STX | BPF_XADD | BPF_W:
-+      case BPF_STX | BPF_XADD | BPF_DW:
-+              switch (imm) {
-+              case BPF_ADD:
-+              case BPF_AND:
-+              case BPF_OR:
-+              case BPF_XOR:
-+                      if (BPF_SIZE(code) == BPF_DW) {
-+                              emit_atomic_r64(ctx, dst, src, off, imm);
-+                      } else { /* 32-bit, no fetch */
-+                              emit_sext(ctx, MIPS_R_T4, src);
-+                              emit_atomic_r(ctx, dst, MIPS_R_T4, off, imm);
-+                      }
-+                      break;
-+              default:
-+                      goto notyet;
-+              }
-+              break;
-+      /* PC += off if dst == src */
-+      /* PC += off if dst != src */
-+      /* PC += off if dst & src */
-+      /* PC += off if dst > src */
-+      /* PC += off if dst >= src */
-+      /* PC += off if dst < src */
-+      /* PC += off if dst <= src */
-+      /* PC += off if dst > src (signed) */
-+      /* PC += off if dst >= src (signed) */
-+      /* PC += off if dst < src (signed) */
-+      /* PC += off if dst <= src (signed) */
-+      case BPF_JMP32 | BPF_JEQ | BPF_X:
-+      case BPF_JMP32 | BPF_JNE | BPF_X:
-+      case BPF_JMP32 | BPF_JSET | BPF_X:
-+      case BPF_JMP32 | BPF_JGT | BPF_X:
-+      case BPF_JMP32 | BPF_JGE | BPF_X:
-+      case BPF_JMP32 | BPF_JLT | BPF_X:
-+      case BPF_JMP32 | BPF_JLE | BPF_X:
-+      case BPF_JMP32 | BPF_JSGT | BPF_X:
-+      case BPF_JMP32 | BPF_JSGE | BPF_X:
-+      case BPF_JMP32 | BPF_JSLT | BPF_X:
-+      case BPF_JMP32 | BPF_JSLE | BPF_X:
-+              if (off == 0)
-+                      break;
-+              setup_jmp_r(ctx, dst == src, BPF_OP(code), off, &jmp, &rel);
-+              emit_sext(ctx, MIPS_R_T4, dst); /* Sign-extended dst */
-+              emit_sext(ctx, MIPS_R_T5, src); /* Sign-extended src */
-+              emit_jmp_r(ctx, MIPS_R_T4, MIPS_R_T5, rel, jmp);
-+              if (finish_jmp(ctx, jmp, off) < 0)
-+                      goto toofar;
-+              break;
-+      /* PC += off if dst == imm */
-+      /* PC += off if dst != imm */
-+      /* PC += off if dst & imm */
-+      /* PC += off if dst > imm */
-+      /* PC += off if dst >= imm */
-+      /* PC += off if dst < imm */
-+      /* PC += off if dst <= imm */
-+      /* PC += off if dst > imm (signed) */
-+      /* PC += off if dst >= imm (signed) */
-+      /* PC += off if dst < imm (signed) */
-+      /* PC += off if dst <= imm (signed) */
-+      case BPF_JMP32 | BPF_JEQ | BPF_K:
-+      case BPF_JMP32 | BPF_JNE | BPF_K:
-+      case BPF_JMP32 | BPF_JSET | BPF_K:
-+      case BPF_JMP32 | BPF_JGT | BPF_K:
-+      case BPF_JMP32 | BPF_JGE | BPF_K:
-+      case BPF_JMP32 | BPF_JLT | BPF_K:
-+      case BPF_JMP32 | BPF_JLE | BPF_K:
-+      case BPF_JMP32 | BPF_JSGT | BPF_K:
-+      case BPF_JMP32 | BPF_JSGE | BPF_K:
-+      case BPF_JMP32 | BPF_JSLT | BPF_K:
-+      case BPF_JMP32 | BPF_JSLE | BPF_K:
-+              if (off == 0)
-+                      break;
-+              setup_jmp_i(ctx, imm, 32, BPF_OP(code), off, &jmp, &rel);
-+              emit_sext(ctx, MIPS_R_T4, dst); /* Sign-extended dst */
-+              if (valid_jmp_i(jmp, imm)) {
-+                      emit_jmp_i(ctx, MIPS_R_T4, imm, rel, jmp);
-+              } else {
-+                      /* Move large immediate to register, sign-extended */
-+                      emit_mov_i(ctx, MIPS_R_T5, imm);
-+                      emit_jmp_r(ctx, MIPS_R_T4, MIPS_R_T5, rel, jmp);
-+              }
-+              if (finish_jmp(ctx, jmp, off) < 0)
-+                      goto toofar;
-+              break;
-+      /* PC += off if dst == src */
-+      /* PC += off if dst != src */
-+      /* PC += off if dst & src */
-+      /* PC += off if dst > src */
-+      /* PC += off if dst >= src */
-+      /* PC += off if dst < src */
-+      /* PC += off if dst <= src */
-+      /* PC += off if dst > src (signed) */
-+      /* PC += off if dst >= src (signed) */
-+      /* PC += off if dst < src (signed) */
-+      /* PC += off if dst <= src (signed) */
-+      case BPF_JMP | BPF_JEQ | BPF_X:
-+      case BPF_JMP | BPF_JNE | BPF_X:
-+      case BPF_JMP | BPF_JSET | BPF_X:
-+      case BPF_JMP | BPF_JGT | BPF_X:
-+      case BPF_JMP | BPF_JGE | BPF_X:
-+      case BPF_JMP | BPF_JLT | BPF_X:
-+      case BPF_JMP | BPF_JLE | BPF_X:
-+      case BPF_JMP | BPF_JSGT | BPF_X:
-+      case BPF_JMP | BPF_JSGE | BPF_X:
-+      case BPF_JMP | BPF_JSLT | BPF_X:
-+      case BPF_JMP | BPF_JSLE | BPF_X:
-+              if (off == 0)
-+                      break;
-+              setup_jmp_r(ctx, dst == src, BPF_OP(code), off, &jmp, &rel);
-+              emit_jmp_r(ctx, dst, src, rel, jmp);
-+              if (finish_jmp(ctx, jmp, off) < 0)
-+                      goto toofar;
-+              break;
-+      /* PC += off if dst == imm */
-+      /* PC += off if dst != imm */
-+      /* PC += off if dst & imm */
-+      /* PC += off if dst > imm */
-+      /* PC += off if dst >= imm */
-+      /* PC += off if dst < imm */
-+      /* PC += off if dst <= imm */
-+      /* PC += off if dst > imm (signed) */
-+      /* PC += off if dst >= imm (signed) */
-+      /* PC += off if dst < imm (signed) */
-+      /* PC += off if dst <= imm (signed) */
-+      case BPF_JMP | BPF_JEQ | BPF_K:
-+      case BPF_JMP | BPF_JNE | BPF_K:
-+      case BPF_JMP | BPF_JSET | BPF_K:
-+      case BPF_JMP | BPF_JGT | BPF_K:
-+      case BPF_JMP | BPF_JGE | BPF_K:
-+      case BPF_JMP | BPF_JLT | BPF_K:
-+      case BPF_JMP | BPF_JLE | BPF_K:
-+      case BPF_JMP | BPF_JSGT | BPF_K:
-+      case BPF_JMP | BPF_JSGE | BPF_K:
-+      case BPF_JMP | BPF_JSLT | BPF_K:
-+      case BPF_JMP | BPF_JSLE | BPF_K:
-+              if (off == 0)
-+                      break;
-+              setup_jmp_i(ctx, imm, 64, BPF_OP(code), off, &jmp, &rel);
-+              if (valid_jmp_i(jmp, imm)) {
-+                      emit_jmp_i(ctx, dst, imm, rel, jmp);
-+              } else {
-+                      /* Move large immediate to register */
-+                      emit_mov_i(ctx, MIPS_R_T4, imm);
-+                      emit_jmp_r(ctx, dst, MIPS_R_T4, rel, jmp);
-+              }
-+              if (finish_jmp(ctx, jmp, off) < 0)
-+                      goto toofar;
-+              break;
-+      /* PC += off */
-+      case BPF_JMP | BPF_JA:
-+              if (off == 0)
-+                      break;
-+              if (emit_ja(ctx, off) < 0)
-+                      goto toofar;
-+              break;
-+      /* Tail call */
-+      case BPF_JMP | BPF_TAIL_CALL:
-+              if (emit_tail_call(ctx) < 0)
-+                      goto invalid;
-+              break;
-+      /* Function call */
-+      case BPF_JMP | BPF_CALL:
-+              if (emit_call(ctx, insn) < 0)
-+                      goto invalid;
-+              break;
-+      /* Function return */
-+      case BPF_JMP | BPF_EXIT:
-+              /*
-+               * Optimization: when last instruction is EXIT
-+               * simply continue to epilogue.
-+               */
-+              if (ctx->bpf_index == ctx->program->len - 1)
-+                      break;
-+              if (emit_exit(ctx) < 0)
-+                      goto toofar;
-+              break;
-+
-+      default:
-+invalid:
-+              pr_err_once("unknown opcode %02x\n", code);
-+              return -EINVAL;
-+notyet:
-+              pr_info_once("*** NOT YET: opcode %02x ***\n", code);
-+              return -EFAULT;
-+toofar:
-+              pr_info_once("*** TOO FAR: jump at %u opcode %02x ***\n",
-+                           ctx->bpf_index, code);
-+              return -E2BIG;
-+      }
-+      return 0;
-+}
diff --git a/target/linux/generic/backport-5.15/050-v5.16-04-mips-bpf-Add-JIT-workarounds-for-CPU-errata.patch b/target/linux/generic/backport-5.15/050-v5.16-04-mips-bpf-Add-JIT-workarounds-for-CPU-errata.patch
deleted file mode 100644 (file)
index 63553eb..0000000
+++ /dev/null
@@ -1,120 +0,0 @@
-From: Johan Almbladh <[email protected]>
-Date: Tue, 5 Oct 2021 18:54:06 +0200
-Subject: [PATCH] mips: bpf: Add JIT workarounds for CPU errata
-
-This patch adds workarounds for the following CPU errata to the MIPS
-eBPF JIT, if enabled in the kernel configuration.
-
-  - R10000 ll/sc weak ordering
-  - Loongson-3 ll/sc weak ordering
-  - Loongson-2F jump hang
-
-The Loongson-2F nop errata is implemented in uasm, which the JIT uses,
-so no additional mitigations are needed for that.
-
-Signed-off-by: Johan Almbladh <[email protected]>
-Reviewed-by: Jiaxun Yang <[email protected]>
----
-
---- a/arch/mips/net/bpf_jit_comp.c
-+++ b/arch/mips/net/bpf_jit_comp.c
-@@ -404,6 +404,7 @@ void emit_alu_r(struct jit_context *ctx,
- /* Atomic read-modify-write (32-bit) */
- void emit_atomic_r(struct jit_context *ctx, u8 dst, u8 src, s16 off, u8 code)
- {
-+      LLSC_sync(ctx);
-       emit(ctx, ll, MIPS_R_T9, off, dst);
-       switch (code) {
-       case BPF_ADD:
-@@ -420,18 +421,19 @@ void emit_atomic_r(struct jit_context *c
-               break;
-       }
-       emit(ctx, sc, MIPS_R_T8, off, dst);
--      emit(ctx, beqz, MIPS_R_T8, -16);
-+      emit(ctx, LLSC_beqz, MIPS_R_T8, -16 - LLSC_offset);
-       emit(ctx, nop); /* Delay slot */
- }
- /* Atomic compare-and-exchange (32-bit) */
- void emit_cmpxchg_r(struct jit_context *ctx, u8 dst, u8 src, u8 res, s16 off)
- {
-+      LLSC_sync(ctx);
-       emit(ctx, ll, MIPS_R_T9, off, dst);
-       emit(ctx, bne, MIPS_R_T9, res, 12);
-       emit(ctx, move, MIPS_R_T8, src);     /* Delay slot */
-       emit(ctx, sc, MIPS_R_T8, off, dst);
--      emit(ctx, beqz, MIPS_R_T8, -20);
-+      emit(ctx, LLSC_beqz, MIPS_R_T8, -20 - LLSC_offset);
-       emit(ctx, move, res, MIPS_R_T9);     /* Delay slot */
-       clobber_reg(ctx, res);
- }
---- a/arch/mips/net/bpf_jit_comp.h
-+++ b/arch/mips/net/bpf_jit_comp.h
-@@ -87,7 +87,7 @@ struct jit_context {
- };
- /* Emit the instruction if the JIT memory space has been allocated */
--#define emit(ctx, func, ...)                                  \
-+#define __emit(ctx, func, ...)                                        \
- do {                                                          \
-       if ((ctx)->target != NULL) {                            \
-               u32 *p = &(ctx)->target[ctx->jit_index];        \
-@@ -95,6 +95,30 @@ do {                                                                \
-       }                                                       \
-       (ctx)->jit_index++;                                     \
- } while (0)
-+#define emit(...) __emit(__VA_ARGS__)
-+
-+/* Workaround for R10000 ll/sc errata */
-+#ifdef CONFIG_WAR_R10000
-+#define LLSC_beqz     beqzl
-+#else
-+#define LLSC_beqz     beqz
-+#endif
-+
-+/* Workaround for Loongson-3 ll/sc errata */
-+#ifdef CONFIG_CPU_LOONGSON3_WORKAROUNDS
-+#define LLSC_sync(ctx)        emit(ctx, sync, 0)
-+#define LLSC_offset   4
-+#else
-+#define LLSC_sync(ctx)
-+#define LLSC_offset   0
-+#endif
-+
-+/* Workaround for Loongson-2F jump errata */
-+#ifdef CONFIG_CPU_JUMP_WORKAROUNDS
-+#define JALR_MASK     0xffffffffcfffffffULL
-+#else
-+#define JALR_MASK     (~0ULL)
-+#endif
- /*
-  * Mark a BPF register as accessed, it needs to be
---- a/arch/mips/net/bpf_jit_comp64.c
-+++ b/arch/mips/net/bpf_jit_comp64.c
-@@ -375,6 +375,7 @@ static void emit_atomic_r64(struct jit_c
-       u8 t1 = MIPS_R_T6;
-       u8 t2 = MIPS_R_T7;
-+      LLSC_sync(ctx);
-       emit(ctx, lld, t1, off, dst);
-       switch (code) {
-       case BPF_ADD:
-@@ -391,7 +392,7 @@ static void emit_atomic_r64(struct jit_c
-               break;
-       }
-       emit(ctx, scd, t2, off, dst);
--      emit(ctx, beqz, t2, -16);
-+      emit(ctx, LLSC_beqz, t2, -16 - LLSC_offset);
-       emit(ctx, nop); /* Delay slot */
- }
-@@ -414,7 +415,7 @@ static int emit_call(struct jit_context
-       push_regs(ctx, ctx->clobbered & JIT_CALLER_REGS, 0, 0);
-       /* Emit function call */
--      emit_mov_i64(ctx, tmp, addr);
-+      emit_mov_i64(ctx, tmp, addr & JALR_MASK);
-       emit(ctx, jalr, MIPS_R_RA, tmp);
-       emit(ctx, nop); /* Delay slot */
diff --git a/target/linux/generic/backport-5.15/050-v5.16-05-mips-bpf-Enable-eBPF-JITs.patch b/target/linux/generic/backport-5.15/050-v5.16-05-mips-bpf-Enable-eBPF-JITs.patch
deleted file mode 100644 (file)
index 24e4e90..0000000
+++ /dev/null
@@ -1,61 +0,0 @@
-From: Johan Almbladh <[email protected]>
-Date: Tue, 5 Oct 2021 18:54:07 +0200
-Subject: [PATCH] mips: bpf: Enable eBPF JITs
-
-This patch enables the new eBPF JITs for 32-bit and 64-bit MIPS. It also
-disables the old cBPF JIT to so cBPF programs are converted to use the
-new JIT.
-
-Workarounds for R4000 CPU errata are not implemented by the JIT, so the
-JIT is disabled if any of those workarounds are configured.
-
-Signed-off-by: Johan Almbladh <[email protected]>
----
-
---- a/MAINTAINERS
-+++ b/MAINTAINERS
-@@ -3431,6 +3431,7 @@ S:       Supported
- F:    arch/arm64/net/
- BPF JIT for MIPS (32-BIT AND 64-BIT)
-+M:    Johan Almbladh <[email protected]>
- M:    Paul Burton <[email protected]>
- L:    [email protected]
- L:    [email protected]
---- a/arch/mips/Kconfig
-+++ b/arch/mips/Kconfig
-@@ -58,7 +58,6 @@ config MIPS
-       select HAVE_ARCH_TRACEHOOK
-       select HAVE_ARCH_TRANSPARENT_HUGEPAGE if CPU_SUPPORTS_HUGEPAGES
-       select HAVE_ASM_MODVERSIONS
--      select HAVE_CBPF_JIT if !64BIT && !CPU_MICROMIPS
-       select HAVE_CONTEXT_TRACKING
-       select HAVE_TIF_NOHZ
-       select HAVE_C_RECORDMCOUNT
-@@ -66,7 +65,10 @@ config MIPS
-       select HAVE_DEBUG_STACKOVERFLOW
-       select HAVE_DMA_CONTIGUOUS
-       select HAVE_DYNAMIC_FTRACE
--      select HAVE_EBPF_JIT if 64BIT && !CPU_MICROMIPS && TARGET_ISA_REV >= 2
-+      select HAVE_EBPF_JIT if !CPU_MICROMIPS && \
-+                              !CPU_DADDI_WORKAROUNDS && \
-+                              !CPU_R4000_WORKAROUNDS && \
-+                              !CPU_R4400_WORKAROUNDS
-       select HAVE_EXIT_THREAD
-       select HAVE_FAST_GUP
-       select HAVE_FTRACE_MCOUNT_RECORD
---- a/arch/mips/net/Makefile
-+++ b/arch/mips/net/Makefile
-@@ -2,9 +2,10 @@
- # MIPS networking code
- obj-$(CONFIG_MIPS_CBPF_JIT) += bpf_jit.o bpf_jit_asm.o
-+obj-$(CONFIG_MIPS_EBPF_JIT) += bpf_jit_comp.o
- ifeq ($(CONFIG_32BIT),y)
--        obj-$(CONFIG_MIPS_EBPF_JIT) += bpf_jit_comp.o bpf_jit_comp32.o
-+        obj-$(CONFIG_MIPS_EBPF_JIT) += bpf_jit_comp32.o
- else
--        obj-$(CONFIG_MIPS_EBPF_JIT) += ebpf_jit.o
-+        obj-$(CONFIG_MIPS_EBPF_JIT) += bpf_jit_comp64.o
- endif
diff --git a/target/linux/generic/backport-5.15/050-v5.16-06-mips-bpf-Remove-old-BPF-JIT-implementations.patch b/target/linux/generic/backport-5.15/050-v5.16-06-mips-bpf-Remove-old-BPF-JIT-implementations.patch
deleted file mode 100644 (file)
index e25c336..0000000
+++ /dev/null
@@ -1,387 +0,0 @@
-From: Johan Almbladh <[email protected]>
-Date: Tue, 5 Oct 2021 18:54:08 +0200
-Subject: [PATCH] mips: bpf: Remove old BPF JIT implementations
-
-This patch removes the old 32-bit cBPF and 64-bit eBPF JIT implementations.
-They are replaced by a new eBPF implementation that supports both 32-bit
-and 64-bit MIPS CPUs.
-
-Signed-off-by: Johan Almbladh <[email protected]>
----
- delete mode 100644 arch/mips/net/bpf_jit.c
- delete mode 100644 arch/mips/net/bpf_jit.h
- delete mode 100644 arch/mips/net/bpf_jit_asm.S
- delete mode 100644 arch/mips/net/ebpf_jit.c
-
---- a/arch/mips/net/bpf_jit.h
-+++ /dev/null
-@@ -1,81 +0,0 @@
--/* SPDX-License-Identifier: GPL-2.0-only */
--/*
-- * Just-In-Time compiler for BPF filters on MIPS
-- *
-- * Copyright (c) 2014 Imagination Technologies Ltd.
-- * Author: Markos Chandras <[email protected]>
-- */
--
--#ifndef BPF_JIT_MIPS_OP_H
--#define BPF_JIT_MIPS_OP_H
--
--/* Registers used by JIT */
--#define MIPS_R_ZERO   0
--#define MIPS_R_V0     2
--#define MIPS_R_A0     4
--#define MIPS_R_A1     5
--#define MIPS_R_T4     12
--#define MIPS_R_T5     13
--#define MIPS_R_T6     14
--#define MIPS_R_T7     15
--#define MIPS_R_S0     16
--#define MIPS_R_S1     17
--#define MIPS_R_S2     18
--#define MIPS_R_S3     19
--#define MIPS_R_S4     20
--#define MIPS_R_S5     21
--#define MIPS_R_S6     22
--#define MIPS_R_S7     23
--#define MIPS_R_SP     29
--#define MIPS_R_RA     31
--
--/* Conditional codes */
--#define MIPS_COND_EQ  0x1
--#define MIPS_COND_GE  (0x1 << 1)
--#define MIPS_COND_GT  (0x1 << 2)
--#define MIPS_COND_NE  (0x1 << 3)
--#define MIPS_COND_ALL (0x1 << 4)
--/* Conditionals on X register or K immediate */
--#define MIPS_COND_X   (0x1 << 5)
--#define MIPS_COND_K   (0x1 << 6)
--
--#define r_ret MIPS_R_V0
--
--/*
-- * Use 2 scratch registers to avoid pipeline interlocks.
-- * There is no overhead during epilogue and prologue since
-- * any of the $s0-$s6 registers will only be preserved if
-- * they are going to actually be used.
-- */
--#define r_skb_hl      MIPS_R_S0 /* skb header length */
--#define r_skb_data    MIPS_R_S1 /* skb actual data */
--#define r_off         MIPS_R_S2
--#define r_A           MIPS_R_S3
--#define r_X           MIPS_R_S4
--#define r_skb         MIPS_R_S5
--#define r_M           MIPS_R_S6
--#define r_skb_len     MIPS_R_S7
--#define r_s0          MIPS_R_T4 /* scratch reg 1 */
--#define r_s1          MIPS_R_T5 /* scratch reg 2 */
--#define r_tmp_imm     MIPS_R_T6 /* No need to preserve this */
--#define r_tmp         MIPS_R_T7 /* No need to preserve this */
--#define r_zero                MIPS_R_ZERO
--#define r_sp          MIPS_R_SP
--#define r_ra          MIPS_R_RA
--
--#ifndef __ASSEMBLY__
--
--/* Declare ASM helpers */
--
--#define DECLARE_LOAD_FUNC(func) \
--      extern u8 func(unsigned long *skb, int offset); \
--      extern u8 func##_negative(unsigned long *skb, int offset); \
--      extern u8 func##_positive(unsigned long *skb, int offset)
--
--DECLARE_LOAD_FUNC(sk_load_word);
--DECLARE_LOAD_FUNC(sk_load_half);
--DECLARE_LOAD_FUNC(sk_load_byte);
--
--#endif
--
--#endif /* BPF_JIT_MIPS_OP_H */
---- a/arch/mips/net/bpf_jit_asm.S
-+++ /dev/null
-@@ -1,285 +0,0 @@
--/*
-- * bpf_jib_asm.S: Packet/header access helper functions for MIPS/MIPS64 BPF
-- * compiler.
-- *
-- * Copyright (C) 2015 Imagination Technologies Ltd.
-- * Author: Markos Chandras <[email protected]>
-- *
-- * This program is free software; you can redistribute it and/or modify it
-- * under the terms of the GNU General Public License as published by the
-- * Free Software Foundation; version 2 of the License.
-- */
--
--#include <asm/asm.h>
--#include <asm/isa-rev.h>
--#include <asm/regdef.h>
--#include "bpf_jit.h"
--
--/* ABI
-- *
-- * r_skb_hl   skb header length
-- * r_skb_data skb data
-- * r_off(a1)  offset register
-- * r_A                BPF register A
-- * r_X                PF register X
-- * r_skb(a0)  *skb
-- * r_M                *scratch memory
-- * r_skb_le   skb length
-- * r_s0               Scratch register 0
-- * r_s1               Scratch register 1
-- *
-- * On entry:
-- * a0: *skb
-- * a1: offset (imm or imm + X)
-- *
-- * All non-BPF-ABI registers are free for use. On return, we only
-- * care about r_ret. The BPF-ABI registers are assumed to remain
-- * unmodified during the entire filter operation.
-- */
--
--#define skb   a0
--#define offset        a1
--#define SKF_LL_OFF  (-0x200000) /* Can't include linux/filter.h in assembly */
--
--      /* We know better :) so prevent assembler reordering etc */
--      .set    noreorder
--
--#define is_offset_negative(TYPE)                              \
--      /* If offset is negative we have more work to do */     \
--      slti    t0, offset, 0;                                  \
--      bgtz    t0, bpf_slow_path_##TYPE##_neg;                 \
--      /* Be careful what follows in DS. */
--
--#define is_offset_in_header(SIZE, TYPE)                               \
--      /* Reading from header? */                              \
--      addiu   $r_s0, $r_skb_hl, -SIZE;                        \
--      slt     t0, $r_s0, offset;                              \
--      bgtz    t0, bpf_slow_path_##TYPE;                       \
--
--LEAF(sk_load_word)
--      is_offset_negative(word)
--FEXPORT(sk_load_word_positive)
--      is_offset_in_header(4, word)
--      /* Offset within header boundaries */
--      PTR_ADDU t1, $r_skb_data, offset
--      .set    reorder
--      lw      $r_A, 0(t1)
--      .set    noreorder
--#ifdef CONFIG_CPU_LITTLE_ENDIAN
--# if MIPS_ISA_REV >= 2
--      wsbh    t0, $r_A
--      rotr    $r_A, t0, 16
--# else
--      sll     t0, $r_A, 24
--      srl     t1, $r_A, 24
--      srl     t2, $r_A, 8
--      or      t0, t0, t1
--      andi    t2, t2, 0xff00
--      andi    t1, $r_A, 0xff00
--      or      t0, t0, t2
--      sll     t1, t1, 8
--      or      $r_A, t0, t1
--# endif
--#endif
--      jr      $r_ra
--       move   $r_ret, zero
--      END(sk_load_word)
--
--LEAF(sk_load_half)
--      is_offset_negative(half)
--FEXPORT(sk_load_half_positive)
--      is_offset_in_header(2, half)
--      /* Offset within header boundaries */
--      PTR_ADDU t1, $r_skb_data, offset
--      lhu     $r_A, 0(t1)
--#ifdef CONFIG_CPU_LITTLE_ENDIAN
--# if MIPS_ISA_REV >= 2
--      wsbh    $r_A, $r_A
--# else
--      sll     t0, $r_A, 8
--      srl     t1, $r_A, 8
--      andi    t0, t0, 0xff00
--      or      $r_A, t0, t1
--# endif
--#endif
--      jr      $r_ra
--       move   $r_ret, zero
--      END(sk_load_half)
--
--LEAF(sk_load_byte)
--      is_offset_negative(byte)
--FEXPORT(sk_load_byte_positive)
--      is_offset_in_header(1, byte)
--      /* Offset within header boundaries */
--      PTR_ADDU t1, $r_skb_data, offset
--      lbu     $r_A, 0(t1)
--      jr      $r_ra
--       move   $r_ret, zero
--      END(sk_load_byte)
--
--/*
-- * call skb_copy_bits:
-- * (prototype in linux/skbuff.h)
-- *
-- * int skb_copy_bits(sk_buff *skb, int offset, void *to, int len)
-- *
-- * o32 mandates we leave 4 spaces for argument registers in case
-- * the callee needs to use them. Even though we don't care about
-- * the argument registers ourselves, we need to allocate that space
-- * to remain ABI compliant since the callee may want to use that space.
-- * We also allocate 2 more spaces for $r_ra and our return register (*to).
-- *
-- * n64 is a bit different. The *caller* will allocate the space to preserve
-- * the arguments. So in 64-bit kernels, we allocate the 4-arg space for no
-- * good reason but it does not matter that much really.
-- *
-- * (void *to) is returned in r_s0
-- *
-- */
--#ifdef CONFIG_CPU_LITTLE_ENDIAN
--#define DS_OFFSET(SIZE) (4 * SZREG)
--#else
--#define DS_OFFSET(SIZE) ((4 * SZREG) + (4 - SIZE))
--#endif
--#define bpf_slow_path_common(SIZE)                            \
--      /* Quick check. Are we within reasonable boundaries? */ \
--      LONG_ADDIU      $r_s1, $r_skb_len, -SIZE;               \
--      sltu            $r_s0, offset, $r_s1;                   \
--      beqz            $r_s0, fault;                           \
--      /* Load 4th argument in DS */                           \
--       LONG_ADDIU     a3, zero, SIZE;                         \
--      PTR_ADDIU       $r_sp, $r_sp, -(6 * SZREG);             \
--      PTR_LA          t0, skb_copy_bits;                      \
--      PTR_S           $r_ra, (5 * SZREG)($r_sp);              \
--      /* Assign low slot to a2 */                             \
--      PTR_ADDIU       a2, $r_sp, DS_OFFSET(SIZE);             \
--      jalr            t0;                                     \
--      /* Reset our destination slot (DS but it's ok) */       \
--       INT_S          zero, (4 * SZREG)($r_sp);               \
--      /*                                                      \
--       * skb_copy_bits returns 0 on success and -EFAULT       \
--       * on error. Our data live in a2. Do not bother with    \
--       * our data if an error has been returned.              \
--       */                                                     \
--      /* Restore our frame */                                 \
--      PTR_L           $r_ra, (5 * SZREG)($r_sp);              \
--      INT_L           $r_s0, (4 * SZREG)($r_sp);              \
--      bltz            v0, fault;                              \
--       PTR_ADDIU      $r_sp, $r_sp, 6 * SZREG;                \
--      move            $r_ret, zero;                           \
--
--NESTED(bpf_slow_path_word, (6 * SZREG), $r_sp)
--      bpf_slow_path_common(4)
--#ifdef CONFIG_CPU_LITTLE_ENDIAN
--# if MIPS_ISA_REV >= 2
--      wsbh    t0, $r_s0
--      jr      $r_ra
--       rotr   $r_A, t0, 16
--# else
--      sll     t0, $r_s0, 24
--      srl     t1, $r_s0, 24
--      srl     t2, $r_s0, 8
--      or      t0, t0, t1
--      andi    t2, t2, 0xff00
--      andi    t1, $r_s0, 0xff00
--      or      t0, t0, t2
--      sll     t1, t1, 8
--      jr      $r_ra
--       or     $r_A, t0, t1
--# endif
--#else
--      jr      $r_ra
--       move   $r_A, $r_s0
--#endif
--
--      END(bpf_slow_path_word)
--
--NESTED(bpf_slow_path_half, (6 * SZREG), $r_sp)
--      bpf_slow_path_common(2)
--#ifdef CONFIG_CPU_LITTLE_ENDIAN
--# if MIPS_ISA_REV >= 2
--      jr      $r_ra
--       wsbh   $r_A, $r_s0
--# else
--      sll     t0, $r_s0, 8
--      andi    t1, $r_s0, 0xff00
--      andi    t0, t0, 0xff00
--      srl     t1, t1, 8
--      jr      $r_ra
--       or     $r_A, t0, t1
--# endif
--#else
--      jr      $r_ra
--       move   $r_A, $r_s0
--#endif
--
--      END(bpf_slow_path_half)
--
--NESTED(bpf_slow_path_byte, (6 * SZREG), $r_sp)
--      bpf_slow_path_common(1)
--      jr      $r_ra
--       move   $r_A, $r_s0
--
--      END(bpf_slow_path_byte)
--
--/*
-- * Negative entry points
-- */
--      .macro bpf_is_end_of_data
--      li      t0, SKF_LL_OFF
--      /* Reading link layer data? */
--      slt     t1, offset, t0
--      bgtz    t1, fault
--      /* Be careful what follows in DS. */
--      .endm
--/*
-- * call skb_copy_bits:
-- * (prototype in linux/filter.h)
-- *
-- * void *bpf_internal_load_pointer_neg_helper(const struct sk_buff *skb,
-- *                                            int k, unsigned int size)
-- *
-- * see above (bpf_slow_path_common) for ABI restrictions
-- */
--#define bpf_negative_common(SIZE)                                     \
--      PTR_ADDIU       $r_sp, $r_sp, -(6 * SZREG);                     \
--      PTR_LA          t0, bpf_internal_load_pointer_neg_helper;       \
--      PTR_S           $r_ra, (5 * SZREG)($r_sp);                      \
--      jalr            t0;                                             \
--       li             a2, SIZE;                                       \
--      PTR_L           $r_ra, (5 * SZREG)($r_sp);                      \
--      /* Check return pointer */                                      \
--      beqz            v0, fault;                                      \
--       PTR_ADDIU      $r_sp, $r_sp, 6 * SZREG;                        \
--      /* Preserve our pointer */                                      \
--      move            $r_s0, v0;                                      \
--      /* Set return value */                                          \
--      move            $r_ret, zero;                                   \
--
--bpf_slow_path_word_neg:
--      bpf_is_end_of_data
--NESTED(sk_load_word_negative, (6 * SZREG), $r_sp)
--      bpf_negative_common(4)
--      jr      $r_ra
--       lw     $r_A, 0($r_s0)
--      END(sk_load_word_negative)
--
--bpf_slow_path_half_neg:
--      bpf_is_end_of_data
--NESTED(sk_load_half_negative, (6 * SZREG), $r_sp)
--      bpf_negative_common(2)
--      jr      $r_ra
--       lhu    $r_A, 0($r_s0)
--      END(sk_load_half_negative)
--
--bpf_slow_path_byte_neg:
--      bpf_is_end_of_data
--NESTED(sk_load_byte_negative, (6 * SZREG), $r_sp)
--      bpf_negative_common(1)
--      jr      $r_ra
--       lbu    $r_A, 0($r_s0)
--      END(sk_load_byte_negative)
--
--fault:
--      jr      $r_ra
--       addiu $r_ret, zero, 1
diff --git a/target/linux/generic/backport-5.15/060-v5.18-01-bpf-selftests-Add-helpers-to-directly-use-the-capget.patch b/target/linux/generic/backport-5.15/060-v5.18-01-bpf-selftests-Add-helpers-to-directly-use-the-capget.patch
deleted file mode 100644 (file)
index 4d544a3..0000000
+++ /dev/null
@@ -1,123 +0,0 @@
-From 5287acc6f097c0c18e54401b611a877a3083b68c Mon Sep 17 00:00:00 2001
-From: Martin KaFai Lau <[email protected]>
-Date: Wed, 16 Mar 2022 10:38:23 -0700
-Subject: [PATCH 1/3] bpf: selftests: Add helpers to directly use the capget
- and capset syscall
-
-After upgrading to the newer libcap (>= 2.60),
-the libcap commit aca076443591 ("Make cap_t operations thread safe.")
-added a "__u8 mutex;" to the "struct _cap_struct".  It caused a few byte
-shift that breaks the assumption made in the "struct libcap" definition
-in test_verifier.c.
-
-The bpf selftest usage only needs to enable and disable the effective
-caps of the running task.  It is easier to directly syscall the
-capget and capset instead.  It can also remove the libcap
-library dependency.
-
-The cap_helpers.{c,h} is added.  One __u64 is used for all CAP_*
-bits instead of two __u32.
-
-Signed-off-by: Martin KaFai Lau <[email protected]>
-Signed-off-by: Alexei Starovoitov <[email protected]>
-Acked-by: John Fastabend <[email protected]>
-Link: https://lore.kernel.org/bpf/[email protected]
----
- tools/testing/selftests/bpf/cap_helpers.c | 67 +++++++++++++++++++++++
- tools/testing/selftests/bpf/cap_helpers.h | 19 +++++++
- 2 files changed, 86 insertions(+)
- create mode 100644 tools/testing/selftests/bpf/cap_helpers.c
- create mode 100644 tools/testing/selftests/bpf/cap_helpers.h
-
---- /dev/null
-+++ b/tools/testing/selftests/bpf/cap_helpers.c
-@@ -0,0 +1,67 @@
-+// SPDX-License-Identifier: GPL-2.0
-+#include "cap_helpers.h"
-+
-+/* Avoid including <sys/capability.h> from the libcap-devel package,
-+ * so directly declare them here and use them from glibc.
-+ */
-+int capget(cap_user_header_t header, cap_user_data_t data);
-+int capset(cap_user_header_t header, const cap_user_data_t data);
-+
-+int cap_enable_effective(__u64 caps, __u64 *old_caps)
-+{
-+      struct __user_cap_data_struct data[_LINUX_CAPABILITY_U32S_3];
-+      struct __user_cap_header_struct hdr = {
-+              .version = _LINUX_CAPABILITY_VERSION_3,
-+      };
-+      __u32 cap0 = caps;
-+      __u32 cap1 = caps >> 32;
-+      int err;
-+
-+      err = capget(&hdr, data);
-+      if (err)
-+              return err;
-+
-+      if (old_caps)
-+              *old_caps = (__u64)(data[1].effective) << 32 | data[0].effective;
-+
-+      if ((data[0].effective & cap0) == cap0 &&
-+          (data[1].effective & cap1) == cap1)
-+              return 0;
-+
-+      data[0].effective |= cap0;
-+      data[1].effective |= cap1;
-+      err = capset(&hdr, data);
-+      if (err)
-+              return err;
-+
-+      return 0;
-+}
-+
-+int cap_disable_effective(__u64 caps, __u64 *old_caps)
-+{
-+      struct __user_cap_data_struct data[_LINUX_CAPABILITY_U32S_3];
-+      struct __user_cap_header_struct hdr = {
-+              .version = _LINUX_CAPABILITY_VERSION_3,
-+      };
-+      __u32 cap0 = caps;
-+      __u32 cap1 = caps >> 32;
-+      int err;
-+
-+      err = capget(&hdr, data);
-+      if (err)
-+              return err;
-+
-+      if (old_caps)
-+              *old_caps = (__u64)(data[1].effective) << 32 | data[0].effective;
-+
-+      if (!(data[0].effective & cap0) && !(data[1].effective & cap1))
-+              return 0;
-+
-+      data[0].effective &= ~cap0;
-+      data[1].effective &= ~cap1;
-+      err = capset(&hdr, data);
-+      if (err)
-+              return err;
-+
-+      return 0;
-+}
---- /dev/null
-+++ b/tools/testing/selftests/bpf/cap_helpers.h
-@@ -0,0 +1,19 @@
-+/* SPDX-License-Identifier: GPL-2.0 */
-+#ifndef __CAP_HELPERS_H
-+#define __CAP_HELPERS_H
-+
-+#include <linux/types.h>
-+#include <linux/capability.h>
-+
-+#ifndef CAP_PERFMON
-+#define CAP_PERFMON           38
-+#endif
-+
-+#ifndef CAP_BPF
-+#define CAP_BPF                       39
-+#endif
-+
-+int cap_enable_effective(__u64 caps, __u64 *old_caps);
-+int cap_disable_effective(__u64 caps, __u64 *old_caps);
-+
-+#endif
diff --git a/target/linux/generic/backport-5.15/060-v5.18-02-bpf-selftests-Remove-libcap-usage-from-test_verifier.patch b/target/linux/generic/backport-5.15/060-v5.18-02-bpf-selftests-Remove-libcap-usage-from-test_verifier.patch
deleted file mode 100644 (file)
index cc60b54..0000000
+++ /dev/null
@@ -1,188 +0,0 @@
-From 847a6b7ee906be874f0cae279c8de902a7d3f092 Mon Sep 17 00:00:00 2001
-From: Martin KaFai Lau <[email protected]>
-Date: Wed, 16 Mar 2022 10:38:29 -0700
-Subject: [PATCH 2/3] bpf: selftests: Remove libcap usage from test_verifier
-
-This patch removes the libcap usage from test_verifier.
-The cap_*_effective() helpers added in the earlier patch are
-used instead.
-
-Signed-off-by: Martin KaFai Lau <[email protected]>
-Signed-off-by: Alexei Starovoitov <[email protected]>
-Acked-by: John Fastabend <[email protected]>
-Link: https://lore.kernel.org/bpf/[email protected]
----
- tools/testing/selftests/bpf/Makefile        | 31 +++++---
- tools/testing/selftests/bpf/test_verifier.c | 88 ++++++---------------
- 2 files changed, 46 insertions(+), 73 deletions(-)
-
---- a/tools/testing/selftests/bpf/Makefile
-+++ b/tools/testing/selftests/bpf/Makefile
-@@ -189,16 +189,27 @@ TEST_GEN_PROGS_EXTENDED += $(DEFAULT_BPF
- $(TEST_GEN_PROGS) $(TEST_GEN_PROGS_EXTENDED): $(OUTPUT)/test_stub.o $(BPFOBJ)
--$(OUTPUT)/test_dev_cgroup: cgroup_helpers.c
--$(OUTPUT)/test_skb_cgroup_id_user: cgroup_helpers.c
--$(OUTPUT)/test_sock: cgroup_helpers.c
--$(OUTPUT)/test_sock_addr: cgroup_helpers.c
--$(OUTPUT)/test_sockmap: cgroup_helpers.c
--$(OUTPUT)/test_tcpnotify_user: cgroup_helpers.c trace_helpers.c
--$(OUTPUT)/get_cgroup_id_user: cgroup_helpers.c
--$(OUTPUT)/test_cgroup_storage: cgroup_helpers.c
--$(OUTPUT)/test_sock_fields: cgroup_helpers.c
--$(OUTPUT)/test_sysctl: cgroup_helpers.c
-+CGROUP_HELPERS        := $(OUTPUT)/cgroup_helpers.o
-+TESTING_HELPERS       := $(OUTPUT)/testing_helpers.o
-+TRACE_HELPERS := $(OUTPUT)/trace_helpers.o
-+CAP_HELPERS   := $(OUTPUT)/cap_helpers.o
-+
-+$(OUTPUT)/test_dev_cgroup: $(CGROUP_HELPERS) $(TESTING_HELPERS)
-+$(OUTPUT)/test_skb_cgroup_id_user: $(CGROUP_HELPERS) $(TESTING_HELPERS)
-+$(OUTPUT)/test_sock: $(CGROUP_HELPERS) $(TESTING_HELPERS)
-+$(OUTPUT)/test_sock_addr: $(CGROUP_HELPERS) $(TESTING_HELPERS)
-+$(OUTPUT)/test_sockmap: $(CGROUP_HELPERS) $(TESTING_HELPERS)
-+$(OUTPUT)/test_tcpnotify_user: $(CGROUP_HELPERS) $(TESTING_HELPERS) $(TRACE_HELPERS)
-+$(OUTPUT)/get_cgroup_id_user: $(CGROUP_HELPERS) $(TESTING_HELPERS)
-+$(OUTPUT)/test_cgroup_storage: $(CGROUP_HELPERS) $(TESTING_HELPERS)
-+$(OUTPUT)/test_sock_fields: $(CGROUP_HELPERS) $(TESTING_HELPERS)
-+$(OUTPUT)/test_sysctl: $(CGROUP_HELPERS) $(TESTING_HELPERS)
-+$(OUTPUT)/test_tag: $(TESTING_HELPERS)
-+$(OUTPUT)/test_lirc_mode2_user: $(TESTING_HELPERS)
-+$(OUTPUT)/xdping: $(TESTING_HELPERS)
-+$(OUTPUT)/flow_dissector_load: $(TESTING_HELPERS)
-+$(OUTPUT)/test_maps: $(TESTING_HELPERS)
-+$(OUTPUT)/test_verifier: $(TESTING_HELPERS) $(CAP_HELPERS)
- BPFTOOL ?= $(DEFAULT_BPFTOOL)
- $(DEFAULT_BPFTOOL): $(wildcard $(BPFTOOLDIR)/*.[ch] $(BPFTOOLDIR)/Makefile)    \
---- a/tools/testing/selftests/bpf/test_verifier.c
-+++ b/tools/testing/selftests/bpf/test_verifier.c
-@@ -22,8 +22,6 @@
- #include <limits.h>
- #include <assert.h>
--#include <sys/capability.h>
--
- #include <linux/unistd.h>
- #include <linux/filter.h>
- #include <linux/bpf_perf_event.h>
-@@ -43,6 +41,7 @@
- # endif
- #endif
- #include "bpf_rlimit.h"
-+#include "cap_helpers.h"
- #include "bpf_rand.h"
- #include "bpf_util.h"
- #include "test_btf.h"
-@@ -59,6 +58,10 @@
- #define F_NEEDS_EFFICIENT_UNALIGNED_ACCESS    (1 << 0)
- #define F_LOAD_WITH_STRICT_ALIGNMENT          (1 << 1)
-+/* need CAP_BPF, CAP_NET_ADMIN, CAP_PERFMON to load progs */
-+#define ADMIN_CAPS (1ULL << CAP_NET_ADMIN |   \
-+                  1ULL << CAP_PERFMON |       \
-+                  1ULL << CAP_BPF)
- #define UNPRIV_SYSCTL "kernel/unprivileged_bpf_disabled"
- static bool unpriv_disabled = false;
- static int skips;
-@@ -940,47 +943,19 @@ struct libcap {
- static int set_admin(bool admin)
- {
--      cap_t caps;
--      /* need CAP_BPF, CAP_NET_ADMIN, CAP_PERFMON to load progs */
--      const cap_value_t cap_net_admin = CAP_NET_ADMIN;
--      const cap_value_t cap_sys_admin = CAP_SYS_ADMIN;
--      struct libcap *cap;
--      int ret = -1;
--
--      caps = cap_get_proc();
--      if (!caps) {
--              perror("cap_get_proc");
--              return -1;
--      }
--      cap = (struct libcap *)caps;
--      if (cap_set_flag(caps, CAP_EFFECTIVE, 1, &cap_sys_admin, CAP_CLEAR)) {
--              perror("cap_set_flag clear admin");
--              goto out;
--      }
--      if (cap_set_flag(caps, CAP_EFFECTIVE, 1, &cap_net_admin,
--                              admin ? CAP_SET : CAP_CLEAR)) {
--              perror("cap_set_flag set_or_clear net");
--              goto out;
--      }
--      /* libcap is likely old and simply ignores CAP_BPF and CAP_PERFMON,
--       * so update effective bits manually
--       */
-+      int err;
-+
-       if (admin) {
--              cap->data[1].effective |= 1 << (38 /* CAP_PERFMON */ - 32);
--              cap->data[1].effective |= 1 << (39 /* CAP_BPF */ - 32);
-+              err = cap_enable_effective(ADMIN_CAPS, NULL);
-+              if (err)
-+                      perror("cap_enable_effective(ADMIN_CAPS)");
-       } else {
--              cap->data[1].effective &= ~(1 << (38 - 32));
--              cap->data[1].effective &= ~(1 << (39 - 32));
-+              err = cap_disable_effective(ADMIN_CAPS, NULL);
-+              if (err)
-+                      perror("cap_disable_effective(ADMIN_CAPS)");
-       }
--      if (cap_set_proc(caps)) {
--              perror("cap_set_proc");
--              goto out;
--      }
--      ret = 0;
--out:
--      if (cap_free(caps))
--              perror("cap_free");
--      return ret;
-+
-+      return err;
- }
- static int do_prog_test_run(int fd_prog, bool unpriv, uint32_t expected_val,
-@@ -1246,31 +1221,18 @@ fail_log:
- static bool is_admin(void)
- {
--      cap_flag_value_t net_priv = CAP_CLEAR;
--      bool perfmon_priv = false;
--      bool bpf_priv = false;
--      struct libcap *cap;
--      cap_t caps;
--
--#ifdef CAP_IS_SUPPORTED
--      if (!CAP_IS_SUPPORTED(CAP_SETFCAP)) {
--              perror("cap_get_flag");
--              return false;
--      }
--#endif
--      caps = cap_get_proc();
--      if (!caps) {
--              perror("cap_get_proc");
-+      __u64 caps;
-+
-+      /* The test checks for finer cap as CAP_NET_ADMIN,
-+       * CAP_PERFMON, and CAP_BPF instead of CAP_SYS_ADMIN.
-+       * Thus, disable CAP_SYS_ADMIN at the beginning.
-+       */
-+      if (cap_disable_effective(1ULL << CAP_SYS_ADMIN, &caps)) {
-+              perror("cap_disable_effective(CAP_SYS_ADMIN)");
-               return false;
-       }
--      cap = (struct libcap *)caps;
--      bpf_priv = cap->data[1].effective & (1 << (39/* CAP_BPF */ - 32));
--      perfmon_priv = cap->data[1].effective & (1 << (38/* CAP_PERFMON */ - 32));
--      if (cap_get_flag(caps, CAP_NET_ADMIN, CAP_EFFECTIVE, &net_priv))
--              perror("cap_get_flag NET");
--      if (cap_free(caps))
--              perror("cap_free");
--      return bpf_priv && perfmon_priv && net_priv == CAP_SET;
-+
-+      return (caps & ADMIN_CAPS) == ADMIN_CAPS;
- }
- static void get_unpriv_disabled()
diff --git a/target/linux/generic/backport-5.15/060-v5.18-03-bpf-selftests-Remove-libcap-usage-from-test_progs.patch b/target/linux/generic/backport-5.15/060-v5.18-03-bpf-selftests-Remove-libcap-usage-from-test_progs.patch
deleted file mode 100644 (file)
index 9badba7..0000000
+++ /dev/null
@@ -1,122 +0,0 @@
-From 1ac00fea13c576e2b13dabf9a72ad3034e3bb804 Mon Sep 17 00:00:00 2001
-From: Martin KaFai Lau <[email protected]>
-Date: Wed, 16 Mar 2022 10:38:35 -0700
-Subject: [PATCH 3/3] bpf: selftests: Remove libcap usage from test_progs
-
-This patch removes the libcap usage from test_progs.
-bind_perm.c is the only user.  cap_*_effective() helpers added in the
-earlier patch are directly used instead.
-
-No other selftest binary is using libcap, so '-lcap' is also removed
-from the Makefile.
-
-Signed-off-by: Martin KaFai Lau <[email protected]>
-Signed-off-by: Alexei Starovoitov <[email protected]>
-Reviewed-by: Stanislav Fomichev <[email protected]>
-Acked-by: John Fastabend <[email protected]>
-Link: https://lore.kernel.org/bpf/[email protected]
----
- tools/testing/selftests/bpf/Makefile          |  5 ++-
- .../selftests/bpf/prog_tests/bind_perm.c      | 44 ++++---------------
- 2 files changed, 11 insertions(+), 38 deletions(-)
-
---- a/tools/testing/selftests/bpf/Makefile
-+++ b/tools/testing/selftests/bpf/Makefile
-@@ -26,7 +26,7 @@ CFLAGS += -g -O0 -rdynamic -Wall $(GENFL
-         -I$(TOOLSINCDIR) -I$(APIDIR) -I$(OUTPUT)                      \
-         -Dbpf_prog_load=bpf_prog_test_load                            \
-         -Dbpf_load_program=bpf_test_load_program
--LDLIBS += -lcap -lelf -lz -lrt -lpthread
-+LDLIBS += -lelf -lz -lrt -lpthread
- # Silence some warnings when compiled with clang
- ifneq ($(LLVM),)
-@@ -471,7 +471,8 @@ TRUNNER_TESTS_DIR := prog_tests
- TRUNNER_BPF_PROGS_DIR := progs
- TRUNNER_EXTRA_SOURCES := test_progs.c cgroup_helpers.c trace_helpers.c        \
-                        network_helpers.c testing_helpers.c            \
--                       btf_helpers.c  flow_dissector_load.h
-+                       btf_helpers.c flow_dissector_load.h            \
-+                       cap_helpers.c
- TRUNNER_EXTRA_FILES := $(OUTPUT)/urandom_read $(OUTPUT)/bpf_testmod.ko        \
-                      ima_setup.sh                                     \
-                      $(wildcard progs/btf_dump_test_case_*.c)
---- a/tools/testing/selftests/bpf/prog_tests/bind_perm.c
-+++ b/tools/testing/selftests/bpf/prog_tests/bind_perm.c
-@@ -4,9 +4,9 @@
- #include <stdlib.h>
- #include <sys/types.h>
- #include <sys/socket.h>
--#include <sys/capability.h>
- #include "test_progs.h"
-+#include "cap_helpers.h"
- #include "bind_perm.skel.h"
- static int duration;
-@@ -49,41 +49,11 @@ close_socket:
-               close(fd);
- }
--bool cap_net_bind_service(cap_flag_value_t flag)
--{
--      const cap_value_t cap_net_bind_service = CAP_NET_BIND_SERVICE;
--      cap_flag_value_t original_value;
--      bool was_effective = false;
--      cap_t caps;
--
--      caps = cap_get_proc();
--      if (CHECK(!caps, "cap_get_proc", "errno %d", errno))
--              goto free_caps;
--
--      if (CHECK(cap_get_flag(caps, CAP_NET_BIND_SERVICE, CAP_EFFECTIVE,
--                             &original_value),
--                "cap_get_flag", "errno %d", errno))
--              goto free_caps;
--
--      was_effective = (original_value == CAP_SET);
--
--      if (CHECK(cap_set_flag(caps, CAP_EFFECTIVE, 1, &cap_net_bind_service,
--                             flag),
--                "cap_set_flag", "errno %d", errno))
--              goto free_caps;
--
--      if (CHECK(cap_set_proc(caps), "cap_set_proc", "errno %d", errno))
--              goto free_caps;
--
--free_caps:
--      CHECK(cap_free(caps), "cap_free", "errno %d", errno);
--      return was_effective;
--}
--
- void test_bind_perm(void)
- {
--      bool cap_was_effective;
-+      const __u64 net_bind_svc_cap = 1ULL << CAP_NET_BIND_SERVICE;
-       struct bind_perm *skel;
-+      __u64 old_caps = 0;
-       int cgroup_fd;
-       if (create_netns())
-@@ -105,7 +75,8 @@ void test_bind_perm(void)
-       if (!ASSERT_OK_PTR(skel, "bind_v6_prog"))
-               goto close_skeleton;
--      cap_was_effective = cap_net_bind_service(CAP_CLEAR);
-+      ASSERT_OK(cap_disable_effective(net_bind_svc_cap, &old_caps),
-+                "cap_disable_effective");
-       try_bind(AF_INET, 110, EACCES);
-       try_bind(AF_INET6, 110, EACCES);
-@@ -113,8 +84,9 @@ void test_bind_perm(void)
-       try_bind(AF_INET, 111, 0);
-       try_bind(AF_INET6, 111, 0);
--      if (cap_was_effective)
--              cap_net_bind_service(CAP_SET);
-+      if (old_caps & net_bind_svc_cap)
-+              ASSERT_OK(cap_enable_effective(net_bind_svc_cap, NULL),
-+                        "cap_enable_effective");
- close_skeleton:
-       bind_perm__destroy(skel);
diff --git a/target/linux/generic/backport-5.15/080-v5.17-clk-gate-Add-devm_clk_hw_register_gate.patch b/target/linux/generic/backport-5.15/080-v5.17-clk-gate-Add-devm_clk_hw_register_gate.patch
deleted file mode 100644 (file)
index 819cc29..0000000
+++ /dev/null
@@ -1,105 +0,0 @@
-From 815f0e738a8d5663a02350e2580706829144a722 Mon Sep 17 00:00:00 2001
-From: Horatiu Vultur <[email protected]>
-Date: Wed, 3 Nov 2021 09:50:59 +0100
-Subject: [PATCH] clk: gate: Add devm_clk_hw_register_gate()
-
-Add devm_clk_hw_register_gate() - devres-managed version of
-clk_hw_register_gate()
-
-Suggested-by: Stephen Boyd <[email protected]>
-Signed-off-by: Horatiu Vultur <[email protected]>
-Acked-by: Nicolas Ferre <[email protected]>
-Signed-off-by: Nicolas Ferre <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
----
- drivers/clk/clk-gate.c       | 35 +++++++++++++++++++++++++++++++++++
- include/linux/clk-provider.h | 23 +++++++++++++++++++++++
- 2 files changed, 58 insertions(+)
-
---- a/drivers/clk/clk-gate.c
-+++ b/drivers/clk/clk-gate.c
-@@ -7,6 +7,7 @@
-  */
- #include <linux/clk-provider.h>
-+#include <linux/device.h>
- #include <linux/module.h>
- #include <linux/slab.h>
- #include <linux/io.h>
-@@ -222,3 +223,37 @@ void clk_hw_unregister_gate(struct clk_h
-       kfree(gate);
- }
- EXPORT_SYMBOL_GPL(clk_hw_unregister_gate);
-+
-+static void devm_clk_hw_release_gate(struct device *dev, void *res)
-+{
-+      clk_hw_unregister_gate(*(struct clk_hw **)res);
-+}
-+
-+struct clk_hw *__devm_clk_hw_register_gate(struct device *dev,
-+              struct device_node *np, const char *name,
-+              const char *parent_name, const struct clk_hw *parent_hw,
-+              const struct clk_parent_data *parent_data,
-+              unsigned long flags,
-+              void __iomem *reg, u8 bit_idx,
-+              u8 clk_gate_flags, spinlock_t *lock)
-+{
-+      struct clk_hw **ptr, *hw;
-+
-+      ptr = devres_alloc(devm_clk_hw_release_gate, sizeof(*ptr), GFP_KERNEL);
-+      if (!ptr)
-+              return ERR_PTR(-ENOMEM);
-+
-+      hw = __clk_hw_register_gate(dev, np, name, parent_name, parent_hw,
-+                                  parent_data, flags, reg, bit_idx,
-+                                  clk_gate_flags, lock);
-+
-+      if (!IS_ERR(hw)) {
-+              *ptr = hw;
-+              devres_add(dev, ptr);
-+      } else {
-+              devres_free(ptr);
-+      }
-+
-+      return hw;
-+}
-+EXPORT_SYMBOL_GPL(__devm_clk_hw_register_gate);
---- a/include/linux/clk-provider.h
-+++ b/include/linux/clk-provider.h
-@@ -517,6 +517,13 @@ struct clk_hw *__clk_hw_register_gate(st
-               unsigned long flags,
-               void __iomem *reg, u8 bit_idx,
-               u8 clk_gate_flags, spinlock_t *lock);
-+struct clk_hw *__devm_clk_hw_register_gate(struct device *dev,
-+              struct device_node *np, const char *name,
-+              const char *parent_name, const struct clk_hw *parent_hw,
-+              const struct clk_parent_data *parent_data,
-+              unsigned long flags,
-+              void __iomem *reg, u8 bit_idx,
-+              u8 clk_gate_flags, spinlock_t *lock);
- struct clk *clk_register_gate(struct device *dev, const char *name,
-               const char *parent_name, unsigned long flags,
-               void __iomem *reg, u8 bit_idx,
-@@ -571,6 +578,22 @@ struct clk *clk_register_gate(struct dev
-       __clk_hw_register_gate((dev), NULL, (name), NULL, NULL, (parent_data), \
-                              (flags), (reg), (bit_idx),                     \
-                              (clk_gate_flags), (lock))
-+/**
-+ * devm_clk_hw_register_gate - register a gate clock with the clock framework
-+ * @dev: device that is registering this clock
-+ * @name: name of this clock
-+ * @parent_name: name of this clock's parent
-+ * @flags: framework-specific flags for this clock
-+ * @reg: register address to control gating of this clock
-+ * @bit_idx: which bit in the register controls gating of this clock
-+ * @clk_gate_flags: gate-specific flags for this clock
-+ * @lock: shared register lock for this clock
-+ */
-+#define devm_clk_hw_register_gate(dev, name, parent_name, flags, reg, bit_idx,\
-+                                clk_gate_flags, lock)                       \
-+      __devm_clk_hw_register_gate((dev), NULL, (name), (parent_name), NULL, \
-+                             NULL, (flags), (reg), (bit_idx),               \
-+                             (clk_gate_flags), (lock))
- void clk_unregister_gate(struct clk *clk);
- void clk_hw_unregister_gate(struct clk_hw *hw);
- int clk_gate_is_enabled(struct clk_hw *hw);
diff --git a/target/linux/generic/backport-5.15/100-v5.18-tty-serial-bcm63xx-use-more-precise-Kconfig-symbol.patch b/target/linux/generic/backport-5.15/100-v5.18-tty-serial-bcm63xx-use-more-precise-Kconfig-symbol.patch
deleted file mode 100644 (file)
index 7de3cbb..0000000
+++ /dev/null
@@ -1,37 +0,0 @@
-From 0dc0da881b4574d1e04a079ab2ea75da61f5ad2e Mon Sep 17 00:00:00 2001
-From: =?UTF-8?q?Rafa=C5=82=20Mi=C5=82ecki?= <[email protected]>
-Date: Fri, 11 Mar 2022 10:32:33 +0100
-Subject: [PATCH] tty: serial: bcm63xx: use more precise Kconfig symbol
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-Patches lowering SERIAL_BCM63XX dependencies led to a discussion and
-documentation change regarding "depends" usage. Adjust Kconfig entry to
-match current guidelines. Make this symbol available for relevant
-architectures only.
-
-Cc: Geert Uytterhoeven <[email protected]>
-Reviewed-by: Geert Uytterhoeven <[email protected]>
-Acked-by: Florian Fainelli <[email protected]>
-Signed-off-by: Rafał Miłecki <[email protected]>
-Ref: f35a07f92616 ("tty: serial: bcm63xx: lower driver dependencies")
-Ref: 18084e435ff6 ("Documentation/kbuild: Document platform dependency practises")
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/tty/serial/Kconfig | 3 ++-
- 1 file changed, 2 insertions(+), 1 deletion(-)
-
---- a/drivers/tty/serial/Kconfig
-+++ b/drivers/tty/serial/Kconfig
-@@ -1098,7 +1098,8 @@ config SERIAL_TIMBERDALE
- config SERIAL_BCM63XX
-       tristate "Broadcom BCM63xx/BCM33xx UART support"
-       select SERIAL_CORE
--      depends on COMMON_CLK
-+      depends on ARCH_BCM4908 || ARCH_BCM_63XX || BCM63XX || BMIPS_GENERIC || COMPILE_TEST
-+      default ARCH_BCM4908 || ARCH_BCM_63XX || BCM63XX || BMIPS_GENERIC
-       help
-         This enables the driver for the onchip UART core found on
-         the following chipsets:
diff --git a/target/linux/generic/backport-5.15/200-v5.18-tools-resolve_btfids-Build-with-host-flags.patch b/target/linux/generic/backport-5.15/200-v5.18-tools-resolve_btfids-Build-with-host-flags.patch
deleted file mode 100644 (file)
index caec8db..0000000
+++ /dev/null
@@ -1,49 +0,0 @@
-From cdbc4e3399ed8cdcf234a85f7a2482b622379e82 Mon Sep 17 00:00:00 2001
-From: Connor O'Brien <[email protected]>
-Date: Wed, 12 Jan 2022 00:25:03 +0000
-Subject: [PATCH] tools/resolve_btfids: Build with host flags
-
-resolve_btfids is built using $(HOSTCC) and $(HOSTLD) but does not
-pick up the corresponding flags. As a result, host-specific settings
-(such as a sysroot specified via HOSTCFLAGS=--sysroot=..., or a linker
-specified via HOSTLDFLAGS=-fuse-ld=...) will not be respected.
-
-Fix this by setting CFLAGS to KBUILD_HOSTCFLAGS and LDFLAGS to
-KBUILD_HOSTLDFLAGS.
-
-Also pass the cflags through to libbpf via EXTRA_CFLAGS to ensure that
-the host libbpf is built with flags consistent with resolve_btfids.
-
-Signed-off-by: Connor O'Brien <[email protected]>
-Signed-off-by: Andrii Nakryiko <[email protected]>
-Acked-by: Song Liu <[email protected]>
-Link: https://lore.kernel.org/bpf/[email protected]
-(cherry picked from commit 0e3a1c902ffb56e9fe4416f0cd382c97b09ecbf6)
-Signed-off-by: Stijn Tintel <[email protected]>
----
- tools/bpf/resolve_btfids/Makefile | 6 ++++--
- 1 file changed, 4 insertions(+), 2 deletions(-)
-
---- a/tools/bpf/resolve_btfids/Makefile
-+++ b/tools/bpf/resolve_btfids/Makefile
-@@ -23,6 +23,8 @@ CC       = $(HOSTCC)
- LD       = $(HOSTLD)
- ARCH     = $(HOSTARCH)
- RM      ?= rm
-+CFLAGS  := $(KBUILD_HOSTCFLAGS)
-+LDFLAGS := $(KBUILD_HOSTLDFLAGS)
- OUTPUT ?= $(srctree)/tools/bpf/resolve_btfids/
-@@ -45,9 +47,9 @@ $(SUBCMDOBJ): fixdep FORCE | $(OUTPUT)/l
-       $(Q)$(MAKE) -C $(SUBCMD_SRC) OUTPUT=$(abspath $(dir $@))/ $(abspath $@)
- $(BPFOBJ): $(wildcard $(LIBBPF_SRC)/*.[ch] $(LIBBPF_SRC)/Makefile) | $(OUTPUT)/libbpf
--      $(Q)$(MAKE) $(submake_extras) -C $(LIBBPF_SRC)  OUTPUT=$(abspath $(dir $@))/ $(abspath $@)
-+      $(Q)$(MAKE) $(submake_extras) -C $(LIBBPF_SRC)  OUTPUT=$(abspath $(dir $@))/ EXTRA_CFLAGS="$(CFLAGS)" $(abspath $@)
--CFLAGS := -g \
-+CFLAGS += -g \
-           -I$(srctree)/tools/include \
-           -I$(srctree)/tools/include/uapi \
-           -I$(LIBBPF_SRC) \
diff --git a/target/linux/generic/backport-5.15/201-v5.16-scripts-dtc-Update-to-upstream-version-v1.6.1-19-g0a.patch b/target/linux/generic/backport-5.15/201-v5.16-scripts-dtc-Update-to-upstream-version-v1.6.1-19-g0a.patch
deleted file mode 100644 (file)
index d1bef74..0000000
+++ /dev/null
@@ -1,997 +0,0 @@
-From a77725a9a3c5924e2fd4cd5b3557dd92a8e46f87 Mon Sep 17 00:00:00 2001
-From: Rob Herring <[email protected]>
-Date: Mon, 25 Oct 2021 11:05:45 -0500
-Subject: [PATCH 1/1] scripts/dtc: Update to upstream version
- v1.6.1-19-g0a3a9d3449c8
-
-This adds the following commits from upstream:
-
-0a3a9d3449c8 checks: Add an interrupt-map check
-8fd24744e361 checks: Ensure '#interrupt-cells' only exists in interrupt providers
-d8d1a9a77863 checks: Drop interrupt provider '#address-cells' check
-52a16fd72824 checks: Make interrupt_provider check dependent on interrupts_extended_is_cell
-37fd700685da treesource: Maintain phandle label/path on output
-e33ce1d6a8c7 flattree: Use '\n', not ';' to separate asm pseudo-ops
-d24cc189dca6 asm: Use assembler macros instead of cpp macros
-ff3a30c115ad asm: Use .asciz and .ascii instead of .string
-5eb5927d81ee fdtdump: fix -Werror=int-to-pointer-cast
-0869f8269161 libfdt: Add ALIGNMENT error string
-69595a167f06 checks: Fix bus-range check
-72d09e2682a4 Makefile: add -Wsign-compare to warning options
-b587787ef388 checks: Fix signedness comparisons warnings
-69bed6c2418f dtc: Wrap phandle validity check
-910221185560 fdtget: Fix signedness comparisons warnings
-d966f08fcd21 tests: Fix signedness comparisons warnings
-ecfb438c07fa dtc: Fix signedness comparisons warnings: pointer diff
-5bec74a6d135 dtc: Fix signedness comparisons warnings: reservednum
-24e7f511fd4a fdtdump: Fix signedness comparisons warnings
-b6910bec1161 Bump version to v1.6.1
-21d61d18f968 Fix CID 1461557
-4c2ef8f4d14c checks: Introduce is_multiple_of()
-e59ca36fb70e Make handling of cpp line information more tolerant
-0c3fd9b6aceb checks: Drop interrupt_cells_is_cell check
-6b3081abc4ac checks: Add check_is_cell() for all phandle+arg properties
-2dffc192a77f yamltree: Remove marker ordering dependency
-61e513439e40 pylibfdt: Rework "avoid unused variable warning" lines
-c8bddd106095 tests: add a positive gpio test case
-ad4abfadb687 checks: replace strstr and strrchr with strends
-09c6a6e88718 dtc.h: add strends for suffix matching
-9bb9b8d0b4a0 checks: tigthen up nr-gpios prop exception
-b07b62ee3342 libfdt: Add FDT alignment check to fdt_check_header()
-a2def5479950 libfdt: Check that the root-node name is empty
-4ca61f84dc21 libfdt: Check that there is only one root node
-34d708249a91 dtc: Remove -O dtbo support
-8e7ff260f755 libfdt: Fix a possible "unchecked return value" warning
-88875268c05c checks: Warn on node-name and property name being the same
-9d2279e7e6ee checks: Change node-name check to match devicetree spec
-f527c867a8c6 util: limit gnu_printf format attribute to gcc >= 4.4.0
-
-Reviewed-by: Frank Rowand <[email protected]>
-Tested-by: Frank Rowand <[email protected]>
-Signed-off-by: Rob Herring <[email protected]>
----
- scripts/dtc/checks.c              | 222 ++++++++++++++++++++++--------
- scripts/dtc/dtc-lexer.l           |   2 +-
- scripts/dtc/dtc.c                 |   6 +-
- scripts/dtc/dtc.h                 |  40 +++++-
- scripts/dtc/flattree.c            |  11 +-
- scripts/dtc/libfdt/fdt.c          |   4 +
- scripts/dtc/libfdt/fdt_rw.c       |  18 ++-
- scripts/dtc/libfdt/fdt_strerror.c |   1 +
- scripts/dtc/libfdt/libfdt.h       |   7 +
- scripts/dtc/livetree.c            |   6 +-
- scripts/dtc/treesource.c          |  48 +++----
- scripts/dtc/util.h                |   6 +-
- scripts/dtc/version_gen.h         |   2 +-
- scripts/dtc/yamltree.c            |  16 ++-
- 14 files changed, 275 insertions(+), 114 deletions(-)
-
---- a/scripts/dtc/checks.c
-+++ b/scripts/dtc/checks.c
-@@ -143,6 +143,14 @@ static void check_nodes_props(struct che
-               check_nodes_props(c, dti, child);
- }
-+static bool is_multiple_of(int multiple, int divisor)
-+{
-+      if (divisor == 0)
-+              return multiple == 0;
-+      else
-+              return (multiple % divisor) == 0;
-+}
-+
- static bool run_check(struct check *c, struct dt_info *dti)
- {
-       struct node *dt = dti->dt;
-@@ -297,19 +305,20 @@ ERROR(duplicate_property_names, check_du
- #define LOWERCASE     "abcdefghijklmnopqrstuvwxyz"
- #define UPPERCASE     "ABCDEFGHIJKLMNOPQRSTUVWXYZ"
- #define DIGITS                "0123456789"
--#define PROPNODECHARS LOWERCASE UPPERCASE DIGITS ",._+*#?-"
-+#define NODECHARS     LOWERCASE UPPERCASE DIGITS ",._+-@"
-+#define PROPCHARS     LOWERCASE UPPERCASE DIGITS ",._+*#?-"
- #define PROPNODECHARSSTRICT   LOWERCASE UPPERCASE DIGITS ",-"
- static void check_node_name_chars(struct check *c, struct dt_info *dti,
-                                 struct node *node)
- {
--      int n = strspn(node->name, c->data);
-+      size_t n = strspn(node->name, c->data);
-       if (n < strlen(node->name))
-               FAIL(c, dti, node, "Bad character '%c' in node name",
-                    node->name[n]);
- }
--ERROR(node_name_chars, check_node_name_chars, PROPNODECHARS "@");
-+ERROR(node_name_chars, check_node_name_chars, NODECHARS);
- static void check_node_name_chars_strict(struct check *c, struct dt_info *dti,
-                                        struct node *node)
-@@ -330,6 +339,20 @@ static void check_node_name_format(struc
- }
- ERROR(node_name_format, check_node_name_format, NULL, &node_name_chars);
-+static void check_node_name_vs_property_name(struct check *c,
-+                                           struct dt_info *dti,
-+                                           struct node *node)
-+{
-+      if (!node->parent)
-+              return;
-+
-+      if (get_property(node->parent, node->name)) {
-+              FAIL(c, dti, node, "node name and property name conflict");
-+      }
-+}
-+WARNING(node_name_vs_property_name, check_node_name_vs_property_name,
-+      NULL, &node_name_chars);
-+
- static void check_unit_address_vs_reg(struct check *c, struct dt_info *dti,
-                                     struct node *node)
- {
-@@ -363,14 +386,14 @@ static void check_property_name_chars(st
-       struct property *prop;
-       for_each_property(node, prop) {
--              int n = strspn(prop->name, c->data);
-+              size_t n = strspn(prop->name, c->data);
-               if (n < strlen(prop->name))
-                       FAIL_PROP(c, dti, node, prop, "Bad character '%c' in property name",
-                                 prop->name[n]);
-       }
- }
--ERROR(property_name_chars, check_property_name_chars, PROPNODECHARS);
-+ERROR(property_name_chars, check_property_name_chars, PROPCHARS);
- static void check_property_name_chars_strict(struct check *c,
-                                            struct dt_info *dti,
-@@ -380,7 +403,7 @@ static void check_property_name_chars_st
-       for_each_property(node, prop) {
-               const char *name = prop->name;
--              int n = strspn(name, c->data);
-+              size_t n = strspn(name, c->data);
-               if (n == strlen(prop->name))
-                       continue;
-@@ -497,7 +520,7 @@ static cell_t check_phandle_prop(struct
-       phandle = propval_cell(prop);
--      if ((phandle == 0) || (phandle == -1)) {
-+      if (!phandle_is_valid(phandle)) {
-               FAIL_PROP(c, dti, node, prop, "bad value (0x%x) in %s property",
-                    phandle, prop->name);
-               return 0;
-@@ -556,7 +579,7 @@ static void check_name_properties(struct
-       if (!prop)
-               return; /* No name property, that's fine */
--      if ((prop->val.len != node->basenamelen+1)
-+      if ((prop->val.len != node->basenamelen + 1U)
-           || (memcmp(prop->val.val, node->name, node->basenamelen) != 0)) {
-               FAIL(c, dti, node, "\"name\" property is incorrect (\"%s\" instead"
-                    " of base node name)", prop->val.val);
-@@ -657,7 +680,6 @@ ERROR(omit_unused_nodes, fixup_omit_unus
-  */
- WARNING_IF_NOT_CELL(address_cells_is_cell, "#address-cells");
- WARNING_IF_NOT_CELL(size_cells_is_cell, "#size-cells");
--WARNING_IF_NOT_CELL(interrupt_cells_is_cell, "#interrupt-cells");
- WARNING_IF_NOT_STRING(device_type_is_string, "device_type");
- WARNING_IF_NOT_STRING(model_is_string, "model");
-@@ -672,8 +694,7 @@ static void check_names_is_string_list(s
-       struct property *prop;
-       for_each_property(node, prop) {
--              const char *s = strrchr(prop->name, '-');
--              if (!s || !streq(s, "-names"))
-+              if (!strends(prop->name, "-names"))
-                       continue;
-               c->data = prop->name;
-@@ -753,7 +774,7 @@ static void check_reg_format(struct chec
-       size_cells = node_size_cells(node->parent);
-       entrylen = (addr_cells + size_cells) * sizeof(cell_t);
--      if (!entrylen || (prop->val.len % entrylen) != 0)
-+      if (!is_multiple_of(prop->val.len, entrylen))
-               FAIL_PROP(c, dti, node, prop, "property has invalid length (%d bytes) "
-                         "(#address-cells == %d, #size-cells == %d)",
-                         prop->val.len, addr_cells, size_cells);
-@@ -794,7 +815,7 @@ static void check_ranges_format(struct c
-                                 "#size-cells (%d) differs from %s (%d)",
-                                 ranges, c_size_cells, node->parent->fullpath,
-                                 p_size_cells);
--      } else if ((prop->val.len % entrylen) != 0) {
-+      } else if (!is_multiple_of(prop->val.len, entrylen)) {
-               FAIL_PROP(c, dti, node, prop, "\"%s\" property has invalid length (%d bytes) "
-                         "(parent #address-cells == %d, child #address-cells == %d, "
-                         "#size-cells == %d)", ranges, prop->val.len,
-@@ -871,7 +892,7 @@ static void check_pci_device_bus_num(str
-       } else {
-               cells = (cell_t *)prop->val.val;
-               min_bus = fdt32_to_cpu(cells[0]);
--              max_bus = fdt32_to_cpu(cells[0]);
-+              max_bus = fdt32_to_cpu(cells[1]);
-       }
-       if ((bus_num < min_bus) || (bus_num > max_bus))
-               FAIL_PROP(c, dti, node, prop, "PCI bus number %d out of range, expected (%d - %d)",
-@@ -1367,9 +1388,9 @@ static void check_property_phandle_args(
-                                         const struct provider *provider)
- {
-       struct node *root = dti->dt;
--      int cell, cellsize = 0;
-+      unsigned int cell, cellsize = 0;
--      if (prop->val.len % sizeof(cell_t)) {
-+      if (!is_multiple_of(prop->val.len, sizeof(cell_t))) {
-               FAIL_PROP(c, dti, node, prop,
-                         "property size (%d) is invalid, expected multiple of %zu",
-                         prop->val.len, sizeof(cell_t));
-@@ -1379,14 +1400,14 @@ static void check_property_phandle_args(
-       for (cell = 0; cell < prop->val.len / sizeof(cell_t); cell += cellsize + 1) {
-               struct node *provider_node;
-               struct property *cellprop;
--              int phandle;
-+              cell_t phandle;
-               phandle = propval_cell_n(prop, cell);
-               /*
-                * Some bindings use a cell value 0 or -1 to skip over optional
-                * entries when each index position has a specific definition.
-                */
--              if (phandle == 0 || phandle == -1) {
-+              if (!phandle_is_valid(phandle)) {
-                       /* Give up if this is an overlay with external references */
-                       if (dti->dtsflags & DTSF_PLUGIN)
-                               break;
-@@ -1452,7 +1473,8 @@ static void check_provider_cells_propert
- }
- #define WARNING_PROPERTY_PHANDLE_CELLS(nm, propname, cells_name, ...) \
-       static struct provider nm##_provider = { (propname), (cells_name), __VA_ARGS__ }; \
--      WARNING(nm##_property, check_provider_cells_property, &nm##_provider, &phandle_references);
-+      WARNING_IF_NOT_CELL(nm##_is_cell, cells_name); \
-+      WARNING(nm##_property, check_provider_cells_property, &nm##_provider, &nm##_is_cell, &phandle_references);
- WARNING_PROPERTY_PHANDLE_CELLS(clocks, "clocks", "#clock-cells");
- WARNING_PROPERTY_PHANDLE_CELLS(cooling_device, "cooling-device", "#cooling-cells");
-@@ -1473,24 +1495,17 @@ WARNING_PROPERTY_PHANDLE_CELLS(thermal_s
- static bool prop_is_gpio(struct property *prop)
- {
--      char *str;
--
-       /*
-        * *-gpios and *-gpio can appear in property names,
-        * so skip over any false matches (only one known ATM)
-        */
--      if (strstr(prop->name, "nr-gpio"))
-+      if (strends(prop->name, ",nr-gpios"))
-               return false;
--      str = strrchr(prop->name, '-');
--      if (str)
--              str++;
--      else
--              str = prop->name;
--      if (!(streq(str, "gpios") || streq(str, "gpio")))
--              return false;
--
--      return true;
-+      return strends(prop->name, "-gpios") ||
-+              streq(prop->name, "gpios") ||
-+              strends(prop->name, "-gpio") ||
-+              streq(prop->name, "gpio");
- }
- static void check_gpios_property(struct check *c,
-@@ -1525,13 +1540,10 @@ static void check_deprecated_gpio_proper
-       struct property *prop;
-       for_each_property(node, prop) {
--              char *str;
--
-               if (!prop_is_gpio(prop))
-                       continue;
--              str = strstr(prop->name, "gpio");
--              if (!streq(str, "gpio"))
-+              if (!strends(prop->name, "gpio"))
-                       continue;
-               FAIL_PROP(c, dti, node, prop,
-@@ -1561,21 +1573,106 @@ static void check_interrupt_provider(str
-                                    struct node *node)
- {
-       struct property *prop;
-+      bool irq_provider = node_is_interrupt_provider(node);
--      if (!node_is_interrupt_provider(node))
-+      prop = get_property(node, "#interrupt-cells");
-+      if (irq_provider && !prop) {
-+              FAIL(c, dti, node,
-+                   "Missing '#interrupt-cells' in interrupt provider");
-               return;
-+      }
--      prop = get_property(node, "#interrupt-cells");
--      if (!prop)
-+      if (!irq_provider && prop) {
-               FAIL(c, dti, node,
--                   "Missing #interrupt-cells in interrupt provider");
-+                   "'#interrupt-cells' found, but node is not an interrupt provider");
-+              return;
-+      }
-+}
-+WARNING(interrupt_provider, check_interrupt_provider, NULL, &interrupts_extended_is_cell);
--      prop = get_property(node, "#address-cells");
--      if (!prop)
-+static void check_interrupt_map(struct check *c,
-+                              struct dt_info *dti,
-+                              struct node *node)
-+{
-+      struct node *root = dti->dt;
-+      struct property *prop, *irq_map_prop;
-+      size_t cellsize, cell, map_cells;
-+
-+      irq_map_prop = get_property(node, "interrupt-map");
-+      if (!irq_map_prop)
-+              return;
-+
-+      if (node->addr_cells < 0) {
-               FAIL(c, dti, node,
--                   "Missing #address-cells in interrupt provider");
-+                   "Missing '#address-cells' in interrupt-map provider");
-+              return;
-+      }
-+      cellsize = node_addr_cells(node);
-+      cellsize += propval_cell(get_property(node, "#interrupt-cells"));
-+
-+      prop = get_property(node, "interrupt-map-mask");
-+      if (prop && (prop->val.len != (cellsize * sizeof(cell_t))))
-+              FAIL_PROP(c, dti, node, prop,
-+                        "property size (%d) is invalid, expected %zu",
-+                        prop->val.len, cellsize * sizeof(cell_t));
-+
-+      if (!is_multiple_of(irq_map_prop->val.len, sizeof(cell_t))) {
-+              FAIL_PROP(c, dti, node, irq_map_prop,
-+                        "property size (%d) is invalid, expected multiple of %zu",
-+                        irq_map_prop->val.len, sizeof(cell_t));
-+              return;
-+      }
-+
-+      map_cells = irq_map_prop->val.len / sizeof(cell_t);
-+      for (cell = 0; cell < map_cells; ) {
-+              struct node *provider_node;
-+              struct property *cellprop;
-+              int phandle;
-+              size_t parent_cellsize;
-+
-+              if ((cell + cellsize) >= map_cells) {
-+                      FAIL_PROP(c, dti, node, irq_map_prop,
-+                                "property size (%d) too small, expected > %zu",
-+                                irq_map_prop->val.len, (cell + cellsize) * sizeof(cell_t));
-+                      break;
-+              }
-+              cell += cellsize;
-+
-+              phandle = propval_cell_n(irq_map_prop, cell);
-+              if (!phandle_is_valid(phandle)) {
-+                      /* Give up if this is an overlay with external references */
-+                      if (!(dti->dtsflags & DTSF_PLUGIN))
-+                              FAIL_PROP(c, dti, node, irq_map_prop,
-+                                        "Cell %zu is not a phandle(%d)",
-+                                        cell, phandle);
-+                      break;
-+              }
-+
-+              provider_node = get_node_by_phandle(root, phandle);
-+              if (!provider_node) {
-+                      FAIL_PROP(c, dti, node, irq_map_prop,
-+                                "Could not get phandle(%d) node for (cell %zu)",
-+                                phandle, cell);
-+                      break;
-+              }
-+
-+              cellprop = get_property(provider_node, "#interrupt-cells");
-+              if (cellprop) {
-+                      parent_cellsize = propval_cell(cellprop);
-+              } else {
-+                      FAIL(c, dti, node, "Missing property '#interrupt-cells' in node %s or bad phandle (referred from interrupt-map[%zu])",
-+                           provider_node->fullpath, cell);
-+                      break;
-+              }
-+
-+              cellprop = get_property(provider_node, "#address-cells");
-+              if (cellprop)
-+                      parent_cellsize += propval_cell(cellprop);
-+
-+              cell += 1 + parent_cellsize;
-+      }
- }
--WARNING(interrupt_provider, check_interrupt_provider, NULL);
-+WARNING(interrupt_map, check_interrupt_map, NULL, &phandle_references, &addr_size_cells, &interrupt_provider);
- static void check_interrupts_property(struct check *c,
-                                     struct dt_info *dti,
-@@ -1584,13 +1681,13 @@ static void check_interrupts_property(st
-       struct node *root = dti->dt;
-       struct node *irq_node = NULL, *parent = node;
-       struct property *irq_prop, *prop = NULL;
--      int irq_cells, phandle;
-+      cell_t irq_cells, phandle;
-       irq_prop = get_property(node, "interrupts");
-       if (!irq_prop)
-               return;
--      if (irq_prop->val.len % sizeof(cell_t))
-+      if (!is_multiple_of(irq_prop->val.len, sizeof(cell_t)))
-               FAIL_PROP(c, dti, node, irq_prop, "size (%d) is invalid, expected multiple of %zu",
-                    irq_prop->val.len, sizeof(cell_t));
-@@ -1603,7 +1700,7 @@ static void check_interrupts_property(st
-               prop = get_property(parent, "interrupt-parent");
-               if (prop) {
-                       phandle = propval_cell(prop);
--                      if ((phandle == 0) || (phandle == -1)) {
-+                      if (!phandle_is_valid(phandle)) {
-                               /* Give up if this is an overlay with
-                                * external references */
-                               if (dti->dtsflags & DTSF_PLUGIN)
-@@ -1639,7 +1736,7 @@ static void check_interrupts_property(st
-       }
-       irq_cells = propval_cell(prop);
--      if (irq_prop->val.len % (irq_cells * sizeof(cell_t))) {
-+      if (!is_multiple_of(irq_prop->val.len, irq_cells * sizeof(cell_t))) {
-               FAIL_PROP(c, dti, node, prop,
-                         "size is (%d), expected multiple of %d",
-                         irq_prop->val.len, (int)(irq_cells * sizeof(cell_t)));
-@@ -1750,7 +1847,7 @@ WARNING(graph_port, check_graph_port, NU
- static struct node *get_remote_endpoint(struct check *c, struct dt_info *dti,
-                                       struct node *endpoint)
- {
--      int phandle;
-+      cell_t phandle;
-       struct node *node;
-       struct property *prop;
-@@ -1760,7 +1857,7 @@ static struct node *get_remote_endpoint(
-       phandle = propval_cell(prop);
-       /* Give up if this is an overlay with external references */
--      if (phandle == 0 || phandle == -1)
-+      if (!phandle_is_valid(phandle))
-               return NULL;
-       node = get_node_by_phandle(dti->dt, phandle);
-@@ -1796,7 +1893,7 @@ WARNING(graph_endpoint, check_graph_endp
- static struct check *check_table[] = {
-       &duplicate_node_names, &duplicate_property_names,
-       &node_name_chars, &node_name_format, &property_name_chars,
--      &name_is_string, &name_properties,
-+      &name_is_string, &name_properties, &node_name_vs_property_name,
-       &duplicate_label,
-@@ -1804,7 +1901,7 @@ static struct check *check_table[] = {
-       &phandle_references, &path_references,
-       &omit_unused_nodes,
--      &address_cells_is_cell, &size_cells_is_cell, &interrupt_cells_is_cell,
-+      &address_cells_is_cell, &size_cells_is_cell,
-       &device_type_is_string, &model_is_string, &status_is_string,
-       &label_is_string,
-@@ -1839,26 +1936,43 @@ static struct check *check_table[] = {
-       &chosen_node_is_root, &chosen_node_bootargs, &chosen_node_stdout_path,
-       &clocks_property,
-+      &clocks_is_cell,
-       &cooling_device_property,
-+      &cooling_device_is_cell,
-       &dmas_property,
-+      &dmas_is_cell,
-       &hwlocks_property,
-+      &hwlocks_is_cell,
-       &interrupts_extended_property,
-+      &interrupts_extended_is_cell,
-       &io_channels_property,
-+      &io_channels_is_cell,
-       &iommus_property,
-+      &iommus_is_cell,
-       &mboxes_property,
-+      &mboxes_is_cell,
-       &msi_parent_property,
-+      &msi_parent_is_cell,
-       &mux_controls_property,
-+      &mux_controls_is_cell,
-       &phys_property,
-+      &phys_is_cell,
-       &power_domains_property,
-+      &power_domains_is_cell,
-       &pwms_property,
-+      &pwms_is_cell,
-       &resets_property,
-+      &resets_is_cell,
-       &sound_dai_property,
-+      &sound_dai_is_cell,
-       &thermal_sensors_property,
-+      &thermal_sensors_is_cell,
-       &deprecated_gpio_property,
-       &gpios_property,
-       &interrupts_property,
-       &interrupt_provider,
-+      &interrupt_map,
-       &alias_paths,
-@@ -1882,7 +1996,7 @@ static void enable_warning_error(struct
- static void disable_warning_error(struct check *c, bool warn, bool error)
- {
--      int i;
-+      unsigned int i;
-       /* Lowering level, also lower it for things this is the prereq
-        * for */
-@@ -1903,7 +2017,7 @@ static void disable_warning_error(struct
- void parse_checks_option(bool warn, bool error, const char *arg)
- {
--      int i;
-+      unsigned int i;
-       const char *name = arg;
-       bool enable = true;
-@@ -1930,7 +2044,7 @@ void parse_checks_option(bool warn, bool
- void process_checks(bool force, struct dt_info *dti)
- {
--      int i;
-+      unsigned int i;
-       int error = 0;
-       for (i = 0; i < ARRAY_SIZE(check_table); i++) {
---- a/scripts/dtc/dtc-lexer.l
-+++ b/scripts/dtc/dtc-lexer.l
-@@ -57,7 +57,7 @@ static void PRINTF(1, 2) lexical_error(c
-                       push_input_file(name);
-               }
--<*>^"#"(line)?[ \t]+[0-9]+[ \t]+{STRING}([ \t]+[0-9]+)? {
-+<*>^"#"(line)?[ \t]+[0-9]+[ \t]+{STRING}([ \t]+[0-9]+)* {
-                       char *line, *fnstart, *fnend;
-                       struct data fn;
-                       /* skip text before line # */
---- a/scripts/dtc/dtc.c
-+++ b/scripts/dtc/dtc.c
-@@ -12,7 +12,7 @@
-  * Command line options
-  */
- int quiet;            /* Level of quietness */
--int reservenum;               /* Number of memory reservation slots */
-+unsigned int reservenum;/* Number of memory reservation slots */
- int minsize;          /* Minimum blob size */
- int padsize;          /* Additional padding to blob */
- int alignsize;                /* Additional padding to blob accroding to the alignsize */
-@@ -197,7 +197,7 @@ int main(int argc, char *argv[])
-                       depname = optarg;
-                       break;
-               case 'R':
--                      reservenum = strtol(optarg, NULL, 0);
-+                      reservenum = strtoul(optarg, NULL, 0);
-                       break;
-               case 'S':
-                       minsize = strtol(optarg, NULL, 0);
-@@ -359,8 +359,6 @@ int main(int argc, char *argv[])
- #endif
-       } else if (streq(outform, "dtb")) {
-               dt_to_blob(outf, dti, outversion);
--      } else if (streq(outform, "dtbo")) {
--              dt_to_blob(outf, dti, outversion);
-       } else if (streq(outform, "asm")) {
-               dt_to_asm(outf, dti, outversion);
-       } else if (streq(outform, "null")) {
---- a/scripts/dtc/dtc.h
-+++ b/scripts/dtc/dtc.h
-@@ -35,7 +35,7 @@
-  * Command line options
-  */
- extern int quiet;             /* Level of quietness */
--extern int reservenum;                /* Number of memory reservation slots */
-+extern unsigned int reservenum;       /* Number of memory reservation slots */
- extern int minsize;           /* Minimum blob size */
- extern int padsize;           /* Additional padding to blob */
- extern int alignsize;         /* Additional padding to blob accroding to the alignsize */
-@@ -51,6 +51,11 @@ extern int annotate;                /* annotate .dts w
- typedef uint32_t cell_t;
-+static inline bool phandle_is_valid(cell_t phandle)
-+{
-+      return phandle != 0 && phandle != ~0U;
-+}
-+
- static inline uint16_t dtb_ld16(const void *p)
- {
-       const uint8_t *bp = (const uint8_t *)p;
-@@ -86,6 +91,16 @@ static inline uint64_t dtb_ld64(const vo
- #define streq(a, b)   (strcmp((a), (b)) == 0)
- #define strstarts(s, prefix)  (strncmp((s), (prefix), strlen(prefix)) == 0)
- #define strprefixeq(a, n, b)  (strlen(b) == (n) && (memcmp(a, b, n) == 0))
-+static inline bool strends(const char *str, const char *suffix)
-+{
-+      unsigned int len, suffix_len;
-+
-+      len = strlen(str);
-+      suffix_len = strlen(suffix);
-+      if (len < suffix_len)
-+              return false;
-+      return streq(str + len - suffix_len, suffix);
-+}
- #define ALIGN(x, a)   (((x) + (a) - 1) & ~((a) - 1))
-@@ -101,6 +116,12 @@ enum markertype {
-       TYPE_UINT64,
-       TYPE_STRING,
- };
-+
-+static inline bool is_type_marker(enum markertype type)
-+{
-+      return type >= TYPE_UINT8;
-+}
-+
- extern const char *markername(enum markertype markertype);
- struct  marker {
-@@ -125,7 +146,22 @@ struct data {
-       for_each_marker(m) \
-               if ((m)->type == (t))
--size_t type_marker_length(struct marker *m);
-+static inline struct marker *next_type_marker(struct marker *m)
-+{
-+      for_each_marker(m)
-+              if (is_type_marker(m->type))
-+                      break;
-+      return m;
-+}
-+
-+static inline size_t type_marker_length(struct marker *m)
-+{
-+      struct marker *next = next_type_marker(m->next);
-+
-+      if (next)
-+              return next->offset - m->offset;
-+      return 0;
-+}
- void data_free(struct data d);
---- a/scripts/dtc/flattree.c
-+++ b/scripts/dtc/flattree.c
-@@ -124,7 +124,8 @@ static void asm_emit_cell(void *e, cell_
- {
-       FILE *f = e;
--      fprintf(f, "\t.byte 0x%02x; .byte 0x%02x; .byte 0x%02x; .byte 0x%02x\n",
-+      fprintf(f, "\t.byte\t0x%02x\n" "\t.byte\t0x%02x\n"
-+              "\t.byte\t0x%02x\n" "\t.byte\t0x%02x\n",
-               (val >> 24) & 0xff, (val >> 16) & 0xff,
-               (val >> 8) & 0xff, val & 0xff);
- }
-@@ -134,9 +135,9 @@ static void asm_emit_string(void *e, con
-       FILE *f = e;
-       if (len != 0)
--              fprintf(f, "\t.string\t\"%.*s\"\n", len, str);
-+              fprintf(f, "\t.asciz\t\"%.*s\"\n", len, str);
-       else
--              fprintf(f, "\t.string\t\"%s\"\n", str);
-+              fprintf(f, "\t.asciz\t\"%s\"\n", str);
- }
- static void asm_emit_align(void *e, int a)
-@@ -295,7 +296,7 @@ static struct data flatten_reserve_list(
- {
-       struct reserve_info *re;
-       struct data d = empty_data;
--      int    j;
-+      unsigned int j;
-       for (re = reservelist; re; re = re->next) {
-               d = data_append_re(d, re->address, re->size);
-@@ -438,7 +439,7 @@ static void dump_stringtable_asm(FILE *f
-       while (p < (strbuf.val + strbuf.len)) {
-               len = strlen(p);
--              fprintf(f, "\t.string \"%s\"\n", p);
-+              fprintf(f, "\t.asciz \"%s\"\n", p);
-               p += len+1;
-       }
- }
---- a/scripts/dtc/libfdt/fdt.c
-+++ b/scripts/dtc/libfdt/fdt.c
-@@ -90,6 +90,10 @@ int fdt_check_header(const void *fdt)
- {
-       size_t hdrsize;
-+      /* The device tree must be at an 8-byte aligned address */
-+      if ((uintptr_t)fdt & 7)
-+              return -FDT_ERR_ALIGNMENT;
-+
-       if (fdt_magic(fdt) != FDT_MAGIC)
-               return -FDT_ERR_BADMAGIC;
-       if (!can_assume(LATEST)) {
---- a/scripts/dtc/libfdt/fdt_rw.c
-+++ b/scripts/dtc/libfdt/fdt_rw.c
-@@ -349,7 +349,10 @@ int fdt_add_subnode_namelen(void *fdt, i
-               return offset;
-       /* Try to place the new node after the parent's properties */
--      fdt_next_tag(fdt, parentoffset, &nextoffset); /* skip the BEGIN_NODE */
-+      tag = fdt_next_tag(fdt, parentoffset, &nextoffset);
-+      /* the fdt_subnode_offset_namelen() should ensure this never hits */
-+      if (!can_assume(LIBFDT_FLAWLESS) && (tag != FDT_BEGIN_NODE))
-+              return -FDT_ERR_INTERNAL;
-       do {
-               offset = nextoffset;
-               tag = fdt_next_tag(fdt, offset, &nextoffset);
-@@ -391,7 +394,9 @@ int fdt_del_node(void *fdt, int nodeoffs
- }
- static void fdt_packblocks_(const char *old, char *new,
--                          int mem_rsv_size, int struct_size)
-+                          int mem_rsv_size,
-+                          int struct_size,
-+                          int strings_size)
- {
-       int mem_rsv_off, struct_off, strings_off;
-@@ -406,8 +411,7 @@ static void fdt_packblocks_(const char *
-       fdt_set_off_dt_struct(new, struct_off);
-       fdt_set_size_dt_struct(new, struct_size);
--      memmove(new + strings_off, old + fdt_off_dt_strings(old),
--              fdt_size_dt_strings(old));
-+      memmove(new + strings_off, old + fdt_off_dt_strings(old), strings_size);
-       fdt_set_off_dt_strings(new, strings_off);
-       fdt_set_size_dt_strings(new, fdt_size_dt_strings(old));
- }
-@@ -467,7 +471,8 @@ int fdt_open_into(const void *fdt, void
-                       return -FDT_ERR_NOSPACE;
-       }
--      fdt_packblocks_(fdt, tmp, mem_rsv_size, struct_size);
-+      fdt_packblocks_(fdt, tmp, mem_rsv_size, struct_size,
-+                      fdt_size_dt_strings(fdt));
-       memmove(buf, tmp, newsize);
-       fdt_set_magic(buf, FDT_MAGIC);
-@@ -487,7 +492,8 @@ int fdt_pack(void *fdt)
-       mem_rsv_size = (fdt_num_mem_rsv(fdt)+1)
-               * sizeof(struct fdt_reserve_entry);
--      fdt_packblocks_(fdt, fdt, mem_rsv_size, fdt_size_dt_struct(fdt));
-+      fdt_packblocks_(fdt, fdt, mem_rsv_size, fdt_size_dt_struct(fdt),
-+                      fdt_size_dt_strings(fdt));
-       fdt_set_totalsize(fdt, fdt_data_size_(fdt));
-       return 0;
---- a/scripts/dtc/libfdt/fdt_strerror.c
-+++ b/scripts/dtc/libfdt/fdt_strerror.c
-@@ -39,6 +39,7 @@ static struct fdt_errtabent fdt_errtable
-       FDT_ERRTABENT(FDT_ERR_BADOVERLAY),
-       FDT_ERRTABENT(FDT_ERR_NOPHANDLES),
-       FDT_ERRTABENT(FDT_ERR_BADFLAGS),
-+      FDT_ERRTABENT(FDT_ERR_ALIGNMENT),
- };
- #define FDT_ERRTABSIZE        ((int)(sizeof(fdt_errtable) / sizeof(fdt_errtable[0])))
---- a/scripts/dtc/libfdt/libfdt.h
-+++ b/scripts/dtc/libfdt/libfdt.h
-@@ -131,6 +131,13 @@ uint32_t fdt_next_tag(const void *fdt, i
-  * to work even with unaligned pointers on platforms (such as ARMv5) that don't
-  * like unaligned loads and stores.
-  */
-+static inline uint16_t fdt16_ld(const fdt16_t *p)
-+{
-+      const uint8_t *bp = (const uint8_t *)p;
-+
-+      return ((uint16_t)bp[0] << 8) | bp[1];
-+}
-+
- static inline uint32_t fdt32_ld(const fdt32_t *p)
- {
-       const uint8_t *bp = (const uint8_t *)p;
---- a/scripts/dtc/livetree.c
-+++ b/scripts/dtc/livetree.c
-@@ -526,7 +526,7 @@ struct node *get_node_by_path(struct nod
-       p = strchr(path, '/');
-       for_each_child(tree, child) {
--              if (p && strprefixeq(path, p - path, child->name))
-+              if (p && strprefixeq(path, (size_t)(p - path), child->name))
-                       return get_node_by_path(child, p+1);
-               else if (!p && streq(path, child->name))
-                       return child;
-@@ -559,7 +559,7 @@ struct node *get_node_by_phandle(struct
- {
-       struct node *child, *node;
--      if ((phandle == 0) || (phandle == -1)) {
-+      if (!phandle_is_valid(phandle)) {
-               assert(generate_fixups);
-               return NULL;
-       }
-@@ -594,7 +594,7 @@ cell_t get_node_phandle(struct node *roo
-       static cell_t phandle = 1; /* FIXME: ick, static local */
-       struct data d = empty_data;
--      if ((node->phandle != 0) && (node->phandle != -1))
-+      if (phandle_is_valid(node->phandle))
-               return node->phandle;
-       while (get_node_by_phandle(root, phandle))
---- a/scripts/dtc/treesource.c
-+++ b/scripts/dtc/treesource.c
-@@ -124,27 +124,6 @@ static void write_propval_int(FILE *f, c
-       }
- }
--static bool has_data_type_information(struct marker *m)
--{
--      return m->type >= TYPE_UINT8;
--}
--
--static struct marker *next_type_marker(struct marker *m)
--{
--      while (m && !has_data_type_information(m))
--              m = m->next;
--      return m;
--}
--
--size_t type_marker_length(struct marker *m)
--{
--      struct marker *next = next_type_marker(m->next);
--
--      if (next)
--              return next->offset - m->offset;
--      return 0;
--}
--
- static const char *delim_start[] = {
-       [TYPE_UINT8] = "[",
-       [TYPE_UINT16] = "/bits/ 16 <",
-@@ -229,26 +208,39 @@ static void write_propval(FILE *f, struc
-               size_t chunk_len = (m->next ? m->next->offset : len) - m->offset;
-               size_t data_len = type_marker_length(m) ? : len - m->offset;
-               const char *p = &prop->val.val[m->offset];
-+              struct marker *m_phandle;
--              if (has_data_type_information(m)) {
-+              if (is_type_marker(m->type)) {
-                       emit_type = m->type;
-                       fprintf(f, " %s", delim_start[emit_type]);
-               } else if (m->type == LABEL)
-                       fprintf(f, " %s:", m->ref);
--              else if (m->offset)
--                      fputc(' ', f);
--              if (emit_type == TYPE_NONE) {
--                      assert(chunk_len == 0);
-+              if (emit_type == TYPE_NONE || chunk_len == 0)
-                       continue;
--              }
-               switch(emit_type) {
-               case TYPE_UINT16:
-                       write_propval_int(f, p, chunk_len, 2);
-                       break;
-               case TYPE_UINT32:
--                      write_propval_int(f, p, chunk_len, 4);
-+                      m_phandle = prop->val.markers;
-+                      for_each_marker_of_type(m_phandle, REF_PHANDLE)
-+                              if (m->offset == m_phandle->offset)
-+                                      break;
-+
-+                      if (m_phandle) {
-+                              if (m_phandle->ref[0] == '/')
-+                                      fprintf(f, "&{%s}", m_phandle->ref);
-+                              else
-+                                      fprintf(f, "&%s", m_phandle->ref);
-+                              if (chunk_len > 4) {
-+                                      fputc(' ', f);
-+                                      write_propval_int(f, p + 4, chunk_len - 4, 4);
-+                              }
-+                      } else {
-+                              write_propval_int(f, p, chunk_len, 4);
-+                      }
-                       break;
-               case TYPE_UINT64:
-                       write_propval_int(f, p, chunk_len, 8);
---- a/scripts/dtc/util.h
-+++ b/scripts/dtc/util.h
-@@ -13,10 +13,10 @@
-  */
- #ifdef __GNUC__
--#ifdef __clang__
--#define PRINTF(i, j)  __attribute__((format (printf, i, j)))
--#else
-+#if __GNUC__ >= 5 || (__GNUC__ == 4 && __GNUC_MINOR__ >= 4)
- #define PRINTF(i, j)  __attribute__((format (gnu_printf, i, j)))
-+#else
-+#define PRINTF(i, j)  __attribute__((format (printf, i, j)))
- #endif
- #define NORETURN      __attribute__((noreturn))
- #else
---- a/scripts/dtc/version_gen.h
-+++ b/scripts/dtc/version_gen.h
-@@ -1 +1 @@
--#define DTC_VERSION "DTC 1.6.0-g183df9e9"
-+#define DTC_VERSION "DTC 1.6.1-g0a3a9d34"
---- a/scripts/dtc/yamltree.c
-+++ b/scripts/dtc/yamltree.c
-@@ -29,11 +29,12 @@ char *yaml_error_name[] = {
-                   (emitter)->problem, __func__, __LINE__);            \
- })
--static void yaml_propval_int(yaml_emitter_t *emitter, struct marker *markers, char *data, unsigned int len, int width)
-+static void yaml_propval_int(yaml_emitter_t *emitter, struct marker *markers,
-+      char *data, unsigned int seq_offset, unsigned int len, int width)
- {
-       yaml_event_t event;
-       void *tag;
--      unsigned int off, start_offset = markers->offset;
-+      unsigned int off;
-       switch(width) {
-               case 1: tag = "!u8"; break;
-@@ -66,7 +67,7 @@ static void yaml_propval_int(yaml_emitte
-                       m = markers;
-                       is_phandle = false;
-                       for_each_marker_of_type(m, REF_PHANDLE) {
--                              if (m->offset == (start_offset + off)) {
-+                              if (m->offset == (seq_offset + off)) {
-                                       is_phandle = true;
-                                       break;
-                               }
-@@ -114,6 +115,7 @@ static void yaml_propval(yaml_emitter_t
-       yaml_event_t event;
-       unsigned int len = prop->val.len;
-       struct marker *m = prop->val.markers;
-+      struct marker *markers = prop->val.markers;
-       /* Emit the property name */
-       yaml_scalar_event_initialize(&event, NULL,
-@@ -151,19 +153,19 @@ static void yaml_propval(yaml_emitter_t
-               switch(m->type) {
-               case TYPE_UINT16:
--                      yaml_propval_int(emitter, m, data, chunk_len, 2);
-+                      yaml_propval_int(emitter, markers, data, m->offset, chunk_len, 2);
-                       break;
-               case TYPE_UINT32:
--                      yaml_propval_int(emitter, m, data, chunk_len, 4);
-+                      yaml_propval_int(emitter, markers, data, m->offset, chunk_len, 4);
-                       break;
-               case TYPE_UINT64:
--                      yaml_propval_int(emitter, m, data, chunk_len, 8);
-+                      yaml_propval_int(emitter, markers, data, m->offset, chunk_len, 8);
-                       break;
-               case TYPE_STRING:
-                       yaml_propval_string(emitter, data, chunk_len);
-                       break;
-               default:
--                      yaml_propval_int(emitter, m, data, chunk_len, 1);
-+                      yaml_propval_int(emitter, markers, data, m->offset, chunk_len, 1);
-                       break;
-               }
-       }
diff --git a/target/linux/generic/backport-5.15/202-v6.1-kallsyms-support-big-kernel-symbols.patch b/target/linux/generic/backport-5.15/202-v6.1-kallsyms-support-big-kernel-symbols.patch
deleted file mode 100644 (file)
index 786a2d9..0000000
+++ /dev/null
@@ -1,128 +0,0 @@
-From 73bbb94466fd3f8b313eeb0b0467314a262dddb3 Mon Sep 17 00:00:00 2001
-From: Miguel Ojeda <[email protected]>
-Date: Mon, 5 Apr 2021 04:58:39 +0200
-Subject: [PATCH] kallsyms: support "big" kernel symbols
-
-Rust symbols can become quite long due to namespacing introduced
-by modules, types, traits, generics, etc.
-
-Increasing to 255 is not enough in some cases, therefore
-introduce longer lengths to the symbol table.
-
-In order to avoid increasing all lengths to 2 bytes (since most
-of them are small, including many Rust ones), use ULEB128 to
-keep smaller symbols in 1 byte, with the rest in 2 bytes.
-
-Reviewed-by: Kees Cook <[email protected]>
-Reviewed-by: Greg Kroah-Hartman <[email protected]>
-Co-developed-by: Alex Gaynor <[email protected]>
-Signed-off-by: Alex Gaynor <[email protected]>
-Co-developed-by: Wedson Almeida Filho <[email protected]>
-Signed-off-by: Wedson Almeida Filho <[email protected]>
-Co-developed-by: Gary Guo <[email protected]>
-Signed-off-by: Gary Guo <[email protected]>
-Co-developed-by: Boqun Feng <[email protected]>
-Signed-off-by: Boqun Feng <[email protected]>
-Co-developed-by: Matthew Wilcox <[email protected]>
-Signed-off-by: Matthew Wilcox <[email protected]>
-Signed-off-by: Miguel Ojeda <[email protected]>
----
- kernel/kallsyms.c  | 26 ++++++++++++++++++++++----
- scripts/kallsyms.c | 29 ++++++++++++++++++++++++++---
- 2 files changed, 48 insertions(+), 7 deletions(-)
-
---- a/kernel/kallsyms.c
-+++ b/kernel/kallsyms.c
-@@ -69,12 +69,20 @@ static unsigned int kallsyms_expand_symb
-       data = &kallsyms_names[off];
-       len = *data;
-       data++;
-+      off++;
-+
-+      /* If MSB is 1, it is a "big" symbol, so needs an additional byte. */
-+      if ((len & 0x80) != 0) {
-+              len = (len & 0x7F) | (*data << 7);
-+              data++;
-+              off++;
-+      }
-       /*
-        * Update the offset to return the offset for the next symbol on
-        * the compressed stream.
-        */
--      off += len + 1;
-+      off += len;
-       /*
-        * For every byte on the compressed symbol data, copy the table
-@@ -127,7 +135,7 @@ static char kallsyms_get_symbol_type(uns
- static unsigned int get_symbol_offset(unsigned long pos)
- {
-       const u8 *name;
--      int i;
-+      int i, len;
-       /*
-        * Use the closest marker we have. We have markers every 256 positions,
-@@ -141,8 +149,18 @@ static unsigned int get_symbol_offset(un
-        * so we just need to add the len to the current pointer for every
-        * symbol we wish to skip.
-        */
--      for (i = 0; i < (pos & 0xFF); i++)
--              name = name + (*name) + 1;
-+      for (i = 0; i < (pos & 0xFF); i++) {
-+              len = *name;
-+
-+              /*
-+               * If MSB is 1, it is a "big" symbol, so we need to look into
-+               * the next byte (and skip it, too).
-+               */
-+              if ((len & 0x80) != 0)
-+                      len = ((len & 0x7F) | (name[1] << 7)) + 1;
-+
-+              name = name + len + 1;
-+      }
-       return name - kallsyms_names;
- }
---- a/scripts/kallsyms.c
-+++ b/scripts/kallsyms.c
-@@ -470,12 +470,35 @@ static void write_src(void)
-               if ((i & 0xFF) == 0)
-                       markers[i >> 8] = off;
--              printf("\t.byte 0x%02x", table[i]->len);
-+              /* There cannot be any symbol of length zero. */
-+              if (table[i]->len == 0) {
-+                      fprintf(stderr, "kallsyms failure: "
-+                              "unexpected zero symbol length\n");
-+                      exit(EXIT_FAILURE);
-+              }
-+
-+              /* Only lengths that fit in up-to-two-byte ULEB128 are supported. */
-+              if (table[i]->len > 0x3FFF) {
-+                      fprintf(stderr, "kallsyms failure: "
-+                              "unexpected huge symbol length\n");
-+                      exit(EXIT_FAILURE);
-+              }
-+
-+              /* Encode length with ULEB128. */
-+              if (table[i]->len <= 0x7F) {
-+                      /* Most symbols use a single byte for the length. */
-+                      printf("\t.byte 0x%02x", table[i]->len);
-+                      off += table[i]->len + 1;
-+              } else {
-+                      /* "Big" symbols use two bytes. */
-+                      printf("\t.byte 0x%02x, 0x%02x",
-+                              (table[i]->len & 0x7F) | 0x80,
-+                              (table[i]->len >> 7) & 0x7F);
-+                      off += table[i]->len + 2;
-+              }
-               for (k = 0; k < table[i]->len; k++)
-                       printf(", 0x%02x", table[i]->sym[k]);
-               printf("\n");
--
--              off += table[i]->len + 1;
-       }
-       printf("\n");
diff --git a/target/linux/generic/backport-5.15/300-v5.18-pinctrl-qcom-Return--EINVAL-for-setting-affinity-if-no-IRQ-parent.patch b/target/linux/generic/backport-5.15/300-v5.18-pinctrl-qcom-Return--EINVAL-for-setting-affinity-if-no-IRQ-parent.patch
deleted file mode 100644 (file)
index 18a8752..0000000
+++ /dev/null
@@ -1,48 +0,0 @@
-From: Manivannan Sadhasivam <[email protected]>
-        [email protected],
-        Manivannan Sadhasivam <[email protected]>
-Subject: [PATCH] pinctrl: qcom: Return -EINVAL for setting affinity if no IRQ
- parent
-Date: Thu, 13 Jan 2022 21:56:17 +0530
-Message-Id: <[email protected]>
-
-The MSM GPIO IRQ controller relies on the parent IRQ controller to set the
-CPU affinity for the IRQ. And this is only valid if there is any wakeup
-parent available and defined in DT.
-
-For the case of no parent IRQ controller defined in DT,
-msm_gpio_irq_set_affinity() and msm_gpio_irq_set_vcpu_affinity() should
-return -EINVAL instead of 0 as the affinity can't be set.
-
-Otherwise, below warning will be printed by genirq:
-
-genirq: irq_chip msmgpio did not update eff. affinity mask of irq 70
-
-Signed-off-by: Manivannan Sadhasivam <[email protected]>
----
- drivers/pinctrl/qcom/pinctrl-msm.c | 4 ++--
- 1 file changed, 2 insertions(+), 2 deletions(-)
-
---- a/drivers/pinctrl/qcom/pinctrl-msm.c
-+++ b/drivers/pinctrl/qcom/pinctrl-msm.c
-@@ -1157,7 +1157,7 @@ static int msm_gpio_irq_set_affinity(str
-       if (d->parent_data && test_bit(d->hwirq, pctrl->skip_wake_irqs))
-               return irq_chip_set_affinity_parent(d, dest, force);
--      return 0;
-+      return -EINVAL;
- }
- static int msm_gpio_irq_set_vcpu_affinity(struct irq_data *d, void *vcpu_info)
-@@ -1168,7 +1168,7 @@ static int msm_gpio_irq_set_vcpu_affinit
-       if (d->parent_data && test_bit(d->hwirq, pctrl->skip_wake_irqs))
-               return irq_chip_set_vcpu_affinity_parent(d, vcpu_info);
--      return 0;
-+      return -EINVAL;
- }
- static void msm_gpio_irq_handler(struct irq_desc *desc)
diff --git a/target/linux/generic/backport-5.15/301-v5.16-soc-qcom-smem-Support-reserved-memory-description.patch b/target/linux/generic/backport-5.15/301-v5.16-soc-qcom-smem-Support-reserved-memory-description.patch
deleted file mode 100644 (file)
index ee0bf93..0000000
+++ /dev/null
@@ -1,166 +0,0 @@
-From b5af64fceb04dc298c5e69c517b4d83893ff060b Mon Sep 17 00:00:00 2001
-From: Bjorn Andersson <[email protected]>
-Date: Thu, 30 Sep 2021 11:21:10 -0700
-Subject: [PATCH 1/1] soc: qcom: smem: Support reserved-memory description
-
-Practically all modern Qualcomm platforms has a single reserved-memory
-region for SMEM. So rather than having to describe SMEM in the form of a
-node with a reference to a reserved-memory node, allow the SMEM device
-to be instantiated directly from the reserved-memory node.
-
-The current means of falling back to dereferencing the "memory-region"
-is kept as a fallback, if it's determined that the SMEM node is a
-reserved-memory node.
-
-The "qcom,smem" compatible is added to the reserved_mem_matches list, to
-allow the reserved-memory device to be probed.
-
-In order to retain the readability of the code, the resolution of
-resources is split from the actual ioremapping.
-
-Signed-off-by: Bjorn Andersson <[email protected]>
-Acked-by: Rob Herring <[email protected]>
-Reviewed-by: Vladimir Zapolskiy <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
----
- drivers/of/platform.c   |  1 +
- drivers/soc/qcom/smem.c | 57 ++++++++++++++++++++++++++++-------------
- 2 files changed, 40 insertions(+), 18 deletions(-)
-
---- a/drivers/of/platform.c
-+++ b/drivers/of/platform.c
-@@ -509,6 +509,7 @@ EXPORT_SYMBOL_GPL(of_platform_default_po
- static const struct of_device_id reserved_mem_matches[] = {
-       { .compatible = "qcom,rmtfs-mem" },
-       { .compatible = "qcom,cmd-db" },
-+      { .compatible = "qcom,smem" },
-       { .compatible = "ramoops" },
-       { .compatible = "nvmem-rmem" },
-       {}
---- a/drivers/soc/qcom/smem.c
-+++ b/drivers/soc/qcom/smem.c
-@@ -9,6 +9,7 @@
- #include <linux/module.h>
- #include <linux/of.h>
- #include <linux/of_address.h>
-+#include <linux/of_reserved_mem.h>
- #include <linux/platform_device.h>
- #include <linux/sizes.h>
- #include <linux/slab.h>
-@@ -240,7 +241,7 @@ static const u8 SMEM_INFO_MAGIC[] = { 0x
-  * @size:     size of the memory region
-  */
- struct smem_region {
--      u32 aux_base;
-+      phys_addr_t aux_base;
-       void __iomem *virt_base;
-       size_t size;
- };
-@@ -499,7 +500,7 @@ static void *qcom_smem_get_global(struct
-       for (i = 0; i < smem->num_regions; i++) {
-               region = &smem->regions[i];
--              if (region->aux_base == aux_base || !aux_base) {
-+              if ((u32)region->aux_base == aux_base || !aux_base) {
-                       if (size != NULL)
-                               *size = le32_to_cpu(entry->size);
-                       return region->virt_base + le32_to_cpu(entry->offset);
-@@ -664,7 +665,7 @@ phys_addr_t qcom_smem_virt_to_phys(void
-               if (p < region->virt_base + region->size) {
-                       u64 offset = p - region->virt_base;
--                      return (phys_addr_t)region->aux_base + offset;
-+                      return region->aux_base + offset;
-               }
-       }
-@@ -863,12 +864,12 @@ qcom_smem_enumerate_partitions(struct qc
-       return 0;
- }
--static int qcom_smem_map_memory(struct qcom_smem *smem, struct device *dev,
--                              const char *name, int i)
-+static int qcom_smem_resolve_mem(struct qcom_smem *smem, const char *name,
-+                               struct smem_region *region)
- {
-+      struct device *dev = smem->dev;
-       struct device_node *np;
-       struct resource r;
--      resource_size_t size;
-       int ret;
-       np = of_parse_phandle(dev->of_node, name, 0);
-@@ -881,13 +882,9 @@ static int qcom_smem_map_memory(struct q
-       of_node_put(np);
-       if (ret)
-               return ret;
--      size = resource_size(&r);
--      smem->regions[i].virt_base = devm_ioremap_wc(dev, r.start, size);
--      if (!smem->regions[i].virt_base)
--              return -ENOMEM;
--      smem->regions[i].aux_base = (u32)r.start;
--      smem->regions[i].size = size;
-+      region->aux_base = r.start;
-+      region->size = resource_size(&r);
-       return 0;
- }
-@@ -895,12 +892,14 @@ static int qcom_smem_map_memory(struct q
- static int qcom_smem_probe(struct platform_device *pdev)
- {
-       struct smem_header *header;
-+      struct reserved_mem *rmem;
-       struct qcom_smem *smem;
-       size_t array_size;
-       int num_regions;
-       int hwlock_id;
-       u32 version;
-       int ret;
-+      int i;
-       num_regions = 1;
-       if (of_find_property(pdev->dev.of_node, "qcom,rpm-msg-ram", NULL))
-@@ -914,13 +913,35 @@ static int qcom_smem_probe(struct platfo
-       smem->dev = &pdev->dev;
-       smem->num_regions = num_regions;
--      ret = qcom_smem_map_memory(smem, &pdev->dev, "memory-region", 0);
--      if (ret)
--              return ret;
--
--      if (num_regions > 1 && (ret = qcom_smem_map_memory(smem, &pdev->dev,
--                                      "qcom,rpm-msg-ram", 1)))
--              return ret;
-+      rmem = of_reserved_mem_lookup(pdev->dev.of_node);
-+      if (rmem) {
-+              smem->regions[0].aux_base = rmem->base;
-+              smem->regions[0].size = rmem->size;
-+      } else {
-+              /*
-+               * Fall back to the memory-region reference, if we're not a
-+               * reserved-memory node.
-+               */
-+              ret = qcom_smem_resolve_mem(smem, "memory-region", &smem->regions[0]);
-+              if (ret)
-+                      return ret;
-+      }
-+
-+      if (num_regions > 1) {
-+              ret = qcom_smem_resolve_mem(smem, "qcom,rpm-msg-ram", &smem->regions[1]);
-+              if (ret)
-+                      return ret;
-+      }
-+
-+      for (i = 0; i < num_regions; i++) {
-+              smem->regions[i].virt_base = devm_ioremap_wc(&pdev->dev,
-+                                                           smem->regions[i].aux_base,
-+                                                           smem->regions[i].size);
-+              if (!smem->regions[i].virt_base) {
-+                      dev_err(&pdev->dev, "failed to remap %pa\n", &smem->regions[i].aux_base);
-+                      return -ENOMEM;
-+              }
-+      }
-       header = smem->regions[0].virt_base;
-       if (le32_to_cpu(header->initialized) != 1 ||
diff --git a/target/linux/generic/backport-5.15/302-v5.16-watchdog-bcm63xx_wdt-fix-fallthrough-warning.patch b/target/linux/generic/backport-5.15/302-v5.16-watchdog-bcm63xx_wdt-fix-fallthrough-warning.patch
deleted file mode 100644 (file)
index 84ae5a7..0000000
+++ /dev/null
@@ -1,33 +0,0 @@
-From ee1a0696934a8b77a6a2098f92832c46d34ec5da Mon Sep 17 00:00:00 2001
-From: =?UTF-8?q?Rafa=C5=82=20Mi=C5=82ecki?= <[email protected]>
-Date: Wed, 27 Oct 2021 14:31:35 +0200
-Subject: [PATCH] watchdog: bcm63xx_wdt: fix fallthrough warning
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-This fixes:
-drivers/watchdog/bcm63xx_wdt.c: In function 'bcm63xx_wdt_ioctl':
-drivers/watchdog/bcm63xx_wdt.c:208:17: warning: this statement may fall through [-Wimplicit-fallthrough=]
-
-Signed-off-by: Rafał Miłecki <[email protected]>
-Reviewed-by: Florian Fainelli <[email protected]>
-Reviewed-by: Guenter Roeck <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Guenter Roeck <[email protected]>
-Signed-off-by: Wim Van Sebroeck <[email protected]>
----
- drivers/watchdog/bcm63xx_wdt.c | 2 ++
- 1 file changed, 2 insertions(+)
-
---- a/drivers/watchdog/bcm63xx_wdt.c
-+++ b/drivers/watchdog/bcm63xx_wdt.c
-@@ -207,6 +207,8 @@ static long bcm63xx_wdt_ioctl(struct fil
-               bcm63xx_wdt_pet();
-+              fallthrough;
-+
-       case WDIOC_GETTIMEOUT:
-               return put_user(wdt_time, p);
diff --git a/target/linux/generic/backport-5.15/303-v6.2-powerpc-suppress-some-linker-warnings-in-recent-link.patch b/target/linux/generic/backport-5.15/303-v6.2-powerpc-suppress-some-linker-warnings-in-recent-link.patch
deleted file mode 100644 (file)
index 7c1507b..0000000
+++ /dev/null
@@ -1,63 +0,0 @@
-From 579aee9fc594af94c242068c011b0233563d4bbf Mon Sep 17 00:00:00 2001
-From: Stephen Rothwell <[email protected]>
-Date: Mon, 10 Oct 2022 16:57:21 +1100
-Subject: [PATCH] powerpc: suppress some linker warnings in recent linker
- versions
-
-This is a follow on from commit
-
-  0d362be5b142 ("Makefile: link with -z noexecstack --no-warn-rwx-segments")
-
-for arch/powerpc/boot to address wanrings like:
-
-  ld: warning: opal-calls.o: missing .note.GNU-stack section implies executable stack
-  ld: NOTE: This behaviour is deprecated and will be removed in a future version of the linker
-  ld: warning: arch/powerpc/boot/zImage.epapr has a LOAD segment with RWX permissions
-
-This fixes issue https://github.com/linuxppc/issues/issues/417
-
-Signed-off-by: Stephen Rothwell <[email protected]>
-Signed-off-by: Michael Ellerman <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
----
- arch/powerpc/boot/wrapper | 15 ++++++++++++++-
- 1 file changed, 14 insertions(+), 1 deletion(-)
-
---- a/arch/powerpc/boot/wrapper
-+++ b/arch/powerpc/boot/wrapper
-@@ -213,6 +213,11 @@ ld_version()
-     }'
- }
-+ld_is_lld()
-+{
-+      ${CROSS}ld -V 2>&1 | grep -q LLD
-+}
-+
- # Do not include PT_INTERP segment when linking pie. Non-pie linking
- # just ignores this option.
- LD_VERSION=$(${CROSS}ld --version | ld_version)
-@@ -221,6 +226,14 @@ if [ "$LD_VERSION" -ge "$LD_NO_DL_MIN_VE
-       nodl="--no-dynamic-linker"
- fi
-+# suppress some warnings in recent ld versions
-+nowarn="-z noexecstack"
-+if ! ld_is_lld; then
-+      if [ "$LD_VERSION" -ge "$(echo 2.39 | ld_version)" ]; then
-+              nowarn="$nowarn --no-warn-rwx-segments"
-+      fi
-+fi
-+
- platformo=$object/"$platform".o
- lds=$object/zImage.lds
- ext=strip
-@@ -502,7 +515,7 @@ if [ "$platform" != "miboot" ]; then
-         text_start="-Ttext $link_address"
-     fi
- #link everything
--    ${CROSS}ld -m $format -T $lds $text_start $pie $nodl $rodynamic $notext -o "$ofile" $map \
-+    ${CROSS}ld -m $format -T $lds $text_start $pie $nodl $nowarn $rodynamic $notext -o "$ofile" $map \
-       $platformo $tmp $object/wrapper.a
-     rm $tmp
- fi
diff --git a/target/linux/generic/backport-5.15/330-v5.16-01-MIPS-kernel-proc-add-CPU-option-reporting.patch b/target/linux/generic/backport-5.15/330-v5.16-01-MIPS-kernel-proc-add-CPU-option-reporting.patch
deleted file mode 100644 (file)
index c66a3f1..0000000
+++ /dev/null
@@ -1,162 +0,0 @@
-From 626bfa03729959ea9917181fb3d8ffaa1594d02a Mon Sep 17 00:00:00 2001
-From: Hauke Mehrtens <[email protected]>
-Date: Wed, 13 Oct 2021 22:40:18 -0700
-Subject: [PATCH 1/1] MIPS: kernel: proc: add CPU option reporting
-
-Many MIPS CPUs have optional CPU features which are not activated for
-all CPU cores. Print the CPU options, which are implemented in the core,
-in /proc/cpuinfo. This makes it possible to see which features are
-supported and which are not supported. This should cover all standard
-MIPS extensions. Before, it only printed information about the main MIPS
-ASEs.
-
-Signed-off-by: Hauke Mehrtens <[email protected]>
-
-Changes from original patch[0]:
-- Remove cpu_has_6k_cache and cpu_has_8k_cache due to commit 6ce91ba8589a
-  ("MIPS: Remove cpu_has_6k_cache and cpu_has_8k_cache in cpu_cache_init()")
-- Add new options: mac2008_only, ftlbparex, gsexcex, mmid, mm_sysad,
-  mm_full
-- Use seq_puts instead of seq_printf as suggested by checkpatch
-- Minor commit message reword
-
-[0]: https://lore.kernel.org/linux-mips/[email protected]/
-
-Signed-off-by: Ilya Lipnitskiy <[email protected]>
-Acked-by: Hauke Mehrtens <[email protected]>
-Signed-off-by: Thomas Bogendoerfer <[email protected]>
----
- arch/mips/kernel/proc.c | 122 ++++++++++++++++++++++++++++++++++++++++
- 1 file changed, 122 insertions(+)
-
---- a/arch/mips/kernel/proc.c
-+++ b/arch/mips/kernel/proc.c
-@@ -138,6 +138,128 @@ static int show_cpuinfo(struct seq_file
-               seq_printf(m, "micromips kernel\t: %s\n",
-                     (read_c0_config3() & MIPS_CONF3_ISA_OE) ?  "yes" : "no");
-       }
-+
-+      seq_puts(m, "Options implemented\t:");
-+      if (cpu_has_tlb)
-+              seq_puts(m, " tlb");
-+      if (cpu_has_ftlb)
-+              seq_puts(m, " ftlb");
-+      if (cpu_has_tlbinv)
-+              seq_puts(m, " tlbinv");
-+      if (cpu_has_segments)
-+              seq_puts(m, " segments");
-+      if (cpu_has_rixiex)
-+              seq_puts(m, " rixiex");
-+      if (cpu_has_ldpte)
-+              seq_puts(m, " ldpte");
-+      if (cpu_has_maar)
-+              seq_puts(m, " maar");
-+      if (cpu_has_rw_llb)
-+              seq_puts(m, " rw_llb");
-+      if (cpu_has_4kex)
-+              seq_puts(m, " 4kex");
-+      if (cpu_has_3k_cache)
-+              seq_puts(m, " 3k_cache");
-+      if (cpu_has_4k_cache)
-+              seq_puts(m, " 4k_cache");
-+      if (cpu_has_tx39_cache)
-+              seq_puts(m, " tx39_cache");
-+      if (cpu_has_octeon_cache)
-+              seq_puts(m, " octeon_cache");
-+      if (cpu_has_fpu)
-+              seq_puts(m, " fpu");
-+      if (cpu_has_32fpr)
-+              seq_puts(m, " 32fpr");
-+      if (cpu_has_cache_cdex_p)
-+              seq_puts(m, " cache_cdex_p");
-+      if (cpu_has_cache_cdex_s)
-+              seq_puts(m, " cache_cdex_s");
-+      if (cpu_has_prefetch)
-+              seq_puts(m, " prefetch");
-+      if (cpu_has_mcheck)
-+              seq_puts(m, " mcheck");
-+      if (cpu_has_ejtag)
-+              seq_puts(m, " ejtag");
-+      if (cpu_has_llsc)
-+              seq_puts(m, " llsc");
-+      if (cpu_has_guestctl0ext)
-+              seq_puts(m, " guestctl0ext");
-+      if (cpu_has_guestctl1)
-+              seq_puts(m, " guestctl1");
-+      if (cpu_has_guestctl2)
-+              seq_puts(m, " guestctl2");
-+      if (cpu_has_guestid)
-+              seq_puts(m, " guestid");
-+      if (cpu_has_drg)
-+              seq_puts(m, " drg");
-+      if (cpu_has_rixi)
-+              seq_puts(m, " rixi");
-+      if (cpu_has_lpa)
-+              seq_puts(m, " lpa");
-+      if (cpu_has_mvh)
-+              seq_puts(m, " mvh");
-+      if (cpu_has_vtag_icache)
-+              seq_puts(m, " vtag_icache");
-+      if (cpu_has_dc_aliases)
-+              seq_puts(m, " dc_aliases");
-+      if (cpu_has_ic_fills_f_dc)
-+              seq_puts(m, " ic_fills_f_dc");
-+      if (cpu_has_pindexed_dcache)
-+              seq_puts(m, " pindexed_dcache");
-+      if (cpu_has_userlocal)
-+              seq_puts(m, " userlocal");
-+      if (cpu_has_nofpuex)
-+              seq_puts(m, " nofpuex");
-+      if (cpu_has_vint)
-+              seq_puts(m, " vint");
-+      if (cpu_has_veic)
-+              seq_puts(m, " veic");
-+      if (cpu_has_inclusive_pcaches)
-+              seq_puts(m, " inclusive_pcaches");
-+      if (cpu_has_perf_cntr_intr_bit)
-+              seq_puts(m, " perf_cntr_intr_bit");
-+      if (cpu_has_ufr)
-+              seq_puts(m, " ufr");
-+      if (cpu_has_fre)
-+              seq_puts(m, " fre");
-+      if (cpu_has_cdmm)
-+              seq_puts(m, " cdmm");
-+      if (cpu_has_small_pages)
-+              seq_puts(m, " small_pages");
-+      if (cpu_has_nan_legacy)
-+              seq_puts(m, " nan_legacy");
-+      if (cpu_has_nan_2008)
-+              seq_puts(m, " nan_2008");
-+      if (cpu_has_ebase_wg)
-+              seq_puts(m, " ebase_wg");
-+      if (cpu_has_badinstr)
-+              seq_puts(m, " badinstr");
-+      if (cpu_has_badinstrp)
-+              seq_puts(m, " badinstrp");
-+      if (cpu_has_contextconfig)
-+              seq_puts(m, " contextconfig");
-+      if (cpu_has_perf)
-+              seq_puts(m, " perf");
-+      if (cpu_has_mac2008_only)
-+              seq_puts(m, " mac2008_only");
-+      if (cpu_has_ftlbparex)
-+              seq_puts(m, " ftlbparex");
-+      if (cpu_has_gsexcex)
-+              seq_puts(m, " gsexcex");
-+      if (cpu_has_shared_ftlb_ram)
-+              seq_puts(m, " shared_ftlb_ram");
-+      if (cpu_has_shared_ftlb_entries)
-+              seq_puts(m, " shared_ftlb_entries");
-+      if (cpu_has_mipsmt_pertccounters)
-+              seq_puts(m, " mipsmt_pertccounters");
-+      if (cpu_has_mmid)
-+              seq_puts(m, " mmid");
-+      if (cpu_has_mm_sysad)
-+              seq_puts(m, " mm_sysad");
-+      if (cpu_has_mm_full)
-+              seq_puts(m, " mm_full");
-+      seq_puts(m, "\n");
-+
-       seq_printf(m, "shadow register sets\t: %d\n",
-                     cpu_data[n].srsets);
-       seq_printf(m, "kscratch registers\t: %d\n",
diff --git a/target/linux/generic/backport-5.15/330-v5.16-02-MIPS-Fix-using-smp_processor_id-in-preemptible-in-sh.patch b/target/linux/generic/backport-5.15/330-v5.16-02-MIPS-Fix-using-smp_processor_id-in-preemptible-in-sh.patch
deleted file mode 100644 (file)
index 6caf7d0..0000000
+++ /dev/null
@@ -1,62 +0,0 @@
-From 1cab5bd69eb1f995ced2d7576cb15f8a8941fd85 Mon Sep 17 00:00:00 2001
-From: Tiezhu Yang <[email protected]>
-Date: Thu, 25 Nov 2021 19:39:32 +0800
-Subject: [PATCH 1/1] MIPS: Fix using smp_processor_id() in preemptible in
- show_cpuinfo()
-
-There exists the following issue under DEBUG_PREEMPT:
-
- BUG: using smp_processor_id() in preemptible [00000000] code: systemd/1
- caller is show_cpuinfo+0x460/0xea0
- ...
- Call Trace:
- [<ffffffff8020f0dc>] show_stack+0x94/0x128
- [<ffffffff80e6cab4>] dump_stack_lvl+0x94/0xd8
- [<ffffffff80e74c5c>] check_preemption_disabled+0x104/0x110
- [<ffffffff802209c8>] show_cpuinfo+0x460/0xea0
- [<ffffffff80539d54>] seq_read_iter+0xfc/0x4f8
- [<ffffffff804fcc10>] new_sync_read+0x110/0x1b8
- [<ffffffff804ff57c>] vfs_read+0x1b4/0x1d0
- [<ffffffff804ffb18>] ksys_read+0xd0/0x110
- [<ffffffff8021c090>] syscall_common+0x34/0x58
-
-We can see the following call trace:
- show_cpuinfo()
-   cpu_has_fpu
-     current_cpu_data
-       smp_processor_id()
-
- $ addr2line -f -e vmlinux 0xffffffff802209c8
- show_cpuinfo
- arch/mips/kernel/proc.c:188
-
- $ head -188 arch/mips/kernel/proc.c | tail -1
-        if (cpu_has_fpu)
-
- arch/mips/include/asm/cpu-features.h
- #  define cpu_has_fpu         (current_cpu_data.options & MIPS_CPU_FPU)
-
- arch/mips/include/asm/cpu-info.h
- #define current_cpu_data cpu_data[smp_processor_id()]
-
-Based on the above analysis, fix the issue by using raw_cpu_has_fpu
-which calls raw_smp_processor_id() in show_cpuinfo().
-
-Fixes: 626bfa037299 ("MIPS: kernel: proc: add CPU option reporting")
-Signed-off-by: Tiezhu Yang <[email protected]>
-Signed-off-by: Thomas Bogendoerfer <[email protected]>
----
- arch/mips/kernel/proc.c | 2 +-
- 1 file changed, 1 insertion(+), 1 deletion(-)
-
---- a/arch/mips/kernel/proc.c
-+++ b/arch/mips/kernel/proc.c
-@@ -166,7 +166,7 @@ static int show_cpuinfo(struct seq_file
-               seq_puts(m, " tx39_cache");
-       if (cpu_has_octeon_cache)
-               seq_puts(m, " octeon_cache");
--      if (cpu_has_fpu)
-+      if (raw_cpu_has_fpu)
-               seq_puts(m, " fpu");
-       if (cpu_has_32fpr)
-               seq_puts(m, " 32fpr");
diff --git a/target/linux/generic/backport-5.15/331-v5.19-mtd-spinand-Add-support-for-XTX-XT26G0xA.patch b/target/linux/generic/backport-5.15/331-v5.19-mtd-spinand-Add-support-for-XTX-XT26G0xA.patch
deleted file mode 100644 (file)
index 541d247..0000000
+++ /dev/null
@@ -1,186 +0,0 @@
-From f4c5c7f9d2e5ab005d57826b740b694b042a737c Mon Sep 17 00:00:00 2001
-From: Felix Matouschek <[email protected]>
-Date: Mon, 18 Apr 2022 15:28:03 +0200
-Subject: [PATCH 1/1] mtd: spinand: Add support for XTX XT26G0xA
-
-Add support for XTX Technology XT26G01AXXXXX, XTX26G02AXXXXX and
-XTX26G04AXXXXX SPI NAND.
-
-These are 3V, 1G/2G/4Gbit serial SLC NAND flash devices with on-die ECC
-(8bit strength per 512bytes).
-
-Tested on Teltonika RUTX10 flashed with OpenWrt.
-
-Links:
-  - http://www.xtxtech.com/download/?AId=225
-  - https://datasheet.lcsc.com/szlcsc/2005251034_XTX-XT26G01AWSEGA_C558841.pdf
-Signed-off-by: Felix Matouschek <[email protected]>
-Signed-off-by: Miquel Raynal <[email protected]>
-Link: https://lore.kernel.org/linux-mtd/[email protected]
----
- drivers/mtd/nand/spi/Makefile |   2 +-
- drivers/mtd/nand/spi/core.c   |   1 +
- drivers/mtd/nand/spi/xtx.c    | 129 ++++++++++++++++++++++++++++++++++
- include/linux/mtd/spinand.h   |   1 +
- 4 files changed, 132 insertions(+), 1 deletion(-)
- create mode 100644 drivers/mtd/nand/spi/xtx.c
-
---- a/drivers/mtd/nand/spi/Makefile
-+++ b/drivers/mtd/nand/spi/Makefile
-@@ -1,3 +1,3 @@
- # SPDX-License-Identifier: GPL-2.0
--spinand-objs := core.o gigadevice.o macronix.o micron.o paragon.o toshiba.o winbond.o
-+spinand-objs := core.o gigadevice.o macronix.o micron.o paragon.o toshiba.o winbond.o xtx.o
- obj-$(CONFIG_MTD_SPI_NAND) += spinand.o
---- a/drivers/mtd/nand/spi/core.c
-+++ b/drivers/mtd/nand/spi/core.c
-@@ -902,6 +902,7 @@ static const struct spinand_manufacturer
-       &paragon_spinand_manufacturer,
-       &toshiba_spinand_manufacturer,
-       &winbond_spinand_manufacturer,
-+      &xtx_spinand_manufacturer,
- };
- static int spinand_manufacturer_match(struct spinand_device *spinand,
---- /dev/null
-+++ b/drivers/mtd/nand/spi/xtx.c
-@@ -0,0 +1,129 @@
-+// SPDX-License-Identifier: GPL-2.0
-+/*
-+ * Author:
-+ * Felix Matouschek <[email protected]>
-+ */
-+
-+#include <linux/device.h>
-+#include <linux/kernel.h>
-+#include <linux/mtd/spinand.h>
-+
-+#define SPINAND_MFR_XTX       0x0B
-+
-+#define XT26G0XA_STATUS_ECC_MASK      GENMASK(5, 2)
-+#define XT26G0XA_STATUS_ECC_NO_DETECTED       (0 << 2)
-+#define XT26G0XA_STATUS_ECC_8_CORRECTED       (3 << 4)
-+#define XT26G0XA_STATUS_ECC_UNCOR_ERROR       (2 << 4)
-+
-+static SPINAND_OP_VARIANTS(read_cache_variants,
-+              SPINAND_PAGE_READ_FROM_CACHE_QUADIO_OP(0, 1, NULL, 0),
-+              SPINAND_PAGE_READ_FROM_CACHE_X4_OP(0, 1, NULL, 0),
-+              SPINAND_PAGE_READ_FROM_CACHE_DUALIO_OP(0, 1, NULL, 0),
-+              SPINAND_PAGE_READ_FROM_CACHE_X2_OP(0, 1, NULL, 0),
-+              SPINAND_PAGE_READ_FROM_CACHE_OP(true, 0, 1, NULL, 0),
-+              SPINAND_PAGE_READ_FROM_CACHE_OP(false, 0, 1, NULL, 0));
-+
-+static SPINAND_OP_VARIANTS(write_cache_variants,
-+              SPINAND_PROG_LOAD_X4(true, 0, NULL, 0),
-+              SPINAND_PROG_LOAD(true, 0, NULL, 0));
-+
-+static SPINAND_OP_VARIANTS(update_cache_variants,
-+              SPINAND_PROG_LOAD_X4(false, 0, NULL, 0),
-+              SPINAND_PROG_LOAD(false, 0, NULL, 0));
-+
-+static int xt26g0xa_ooblayout_ecc(struct mtd_info *mtd, int section,
-+                                 struct mtd_oob_region *region)
-+{
-+      if (section)
-+              return -ERANGE;
-+
-+      region->offset = 48;
-+      region->length = 16;
-+
-+      return 0;
-+}
-+
-+static int xt26g0xa_ooblayout_free(struct mtd_info *mtd, int section,
-+                                 struct mtd_oob_region *region)
-+{
-+      if (section)
-+              return -ERANGE;
-+
-+      region->offset = 1;
-+      region->length = 47;
-+
-+      return 0;
-+}
-+
-+static const struct mtd_ooblayout_ops xt26g0xa_ooblayout = {
-+      .ecc = xt26g0xa_ooblayout_ecc,
-+      .free = xt26g0xa_ooblayout_free,
-+};
-+
-+static int xt26g0xa_ecc_get_status(struct spinand_device *spinand,
-+                                       u8 status)
-+{
-+      status = status & XT26G0XA_STATUS_ECC_MASK;
-+
-+      switch (status) {
-+      case XT26G0XA_STATUS_ECC_NO_DETECTED:
-+              return 0;
-+      case XT26G0XA_STATUS_ECC_8_CORRECTED:
-+              return 8;
-+      case XT26G0XA_STATUS_ECC_UNCOR_ERROR:
-+              return -EBADMSG;
-+      default:
-+              break;
-+      }
-+
-+      /* At this point values greater than (2 << 4) are invalid  */
-+      if (status > XT26G0XA_STATUS_ECC_UNCOR_ERROR)
-+              return -EINVAL;
-+
-+      /* (1 << 2) through (7 << 2) are 1-7 corrected errors */
-+      return status >> 2;
-+}
-+
-+static const struct spinand_info xtx_spinand_table[] = {
-+      SPINAND_INFO("XT26G01A",
-+                   SPINAND_ID(SPINAND_READID_METHOD_OPCODE_ADDR, 0xE1),
-+                   NAND_MEMORG(1, 2048, 64, 64, 1024, 20, 1, 1, 1),
-+                   NAND_ECCREQ(8, 512),
-+                   SPINAND_INFO_OP_VARIANTS(&read_cache_variants,
-+                                            &write_cache_variants,
-+                                            &update_cache_variants),
-+                   SPINAND_HAS_QE_BIT,
-+                   SPINAND_ECCINFO(&xt26g0xa_ooblayout,
-+                                   xt26g0xa_ecc_get_status)),
-+      SPINAND_INFO("XT26G02A",
-+                   SPINAND_ID(SPINAND_READID_METHOD_OPCODE_ADDR, 0xE2),
-+                   NAND_MEMORG(1, 2048, 64, 64, 2048, 40, 1, 1, 1),
-+                   NAND_ECCREQ(8, 512),
-+                   SPINAND_INFO_OP_VARIANTS(&read_cache_variants,
-+                                            &write_cache_variants,
-+                                            &update_cache_variants),
-+                   SPINAND_HAS_QE_BIT,
-+                   SPINAND_ECCINFO(&xt26g0xa_ooblayout,
-+                                   xt26g0xa_ecc_get_status)),
-+      SPINAND_INFO("XT26G04A",
-+                   SPINAND_ID(SPINAND_READID_METHOD_OPCODE_ADDR, 0xE3),
-+                   NAND_MEMORG(1, 2048, 64, 128, 2048, 40, 1, 1, 1),
-+                   NAND_ECCREQ(8, 512),
-+                   SPINAND_INFO_OP_VARIANTS(&read_cache_variants,
-+                                            &write_cache_variants,
-+                                            &update_cache_variants),
-+                   SPINAND_HAS_QE_BIT,
-+                   SPINAND_ECCINFO(&xt26g0xa_ooblayout,
-+                                   xt26g0xa_ecc_get_status)),
-+};
-+
-+static const struct spinand_manufacturer_ops xtx_spinand_manuf_ops = {
-+};
-+
-+const struct spinand_manufacturer xtx_spinand_manufacturer = {
-+      .id = SPINAND_MFR_XTX,
-+      .name = "XTX",
-+      .chips = xtx_spinand_table,
-+      .nchips = ARRAY_SIZE(xtx_spinand_table),
-+      .ops = &xtx_spinand_manuf_ops,
-+};
---- a/include/linux/mtd/spinand.h
-+++ b/include/linux/mtd/spinand.h
-@@ -266,6 +266,7 @@ extern const struct spinand_manufacturer
- extern const struct spinand_manufacturer paragon_spinand_manufacturer;
- extern const struct spinand_manufacturer toshiba_spinand_manufacturer;
- extern const struct spinand_manufacturer winbond_spinand_manufacturer;
-+extern const struct spinand_manufacturer xtx_spinand_manufacturer;
- /**
-  * struct spinand_op_variants - SPI NAND operation variants
diff --git a/target/linux/generic/backport-5.15/344-v5.18-01-phy-marvell-phy-mvebu-a3700-comphy-Remove-port-from-.patch b/target/linux/generic/backport-5.15/344-v5.18-01-phy-marvell-phy-mvebu-a3700-comphy-Remove-port-from-.patch
deleted file mode 100644 (file)
index d6c4b4f..0000000
+++ /dev/null
@@ -1,219 +0,0 @@
-From 4bf18d5a2dd02db8c5b16a2cfae513510506df5b Mon Sep 17 00:00:00 2001
-From: =?UTF-8?q?Pali=20Roh=C3=A1r?= <[email protected]>
-Date: Thu, 3 Feb 2022 22:44:40 +0100
-Subject: [PATCH 1/2] phy: marvell: phy-mvebu-a3700-comphy: Remove port from
- driver configuration
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-Port number is encoded into argument for SMC call. It is zero for SATA,
-PCIe and also both USB 3.0 PHYs. It is non-zero only for Ethernet PHY
-(incorrectly called SGMII) on lane 0. Ethernet PHY on lane 1 also uses zero
-port number.
-
-So construct "port" bits for SMC call argument can be constructed directly
-from PHY type and lane number.
-
-Change driver code to always pass zero port number for non-ethernet PHYs
-and for ethernet PHYs determinate port number from lane number. This
-simplifies the driver.
-
-As port number from DT PHY configuration is not used anymore, remove whole
-driver code which parses it. This also simplifies the driver.
-
-Signed-off-by: Pali Rohár <[email protected]>
-Signed-off-by: Marek Behún <[email protected]>
-Reviewed-by: Miquel Raynal <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Vinod Koul <[email protected]>
----
- drivers/phy/marvell/phy-mvebu-a3700-comphy.c | 62 +++++++++-----------
- 1 file changed, 29 insertions(+), 33 deletions(-)
-
---- a/drivers/phy/marvell/phy-mvebu-a3700-comphy.c
-+++ b/drivers/phy/marvell/phy-mvebu-a3700-comphy.c
-@@ -20,7 +20,6 @@
- #include <linux/platform_device.h>
- #define MVEBU_A3700_COMPHY_LANES              3
--#define MVEBU_A3700_COMPHY_PORTS              2
- /* COMPHY Fast SMC function identifiers */
- #define COMPHY_SIP_POWER_ON                   0x82000001
-@@ -45,51 +44,47 @@
- #define COMPHY_FW_NET(mode, idx, speed)               (COMPHY_FW_MODE(mode) | \
-                                                ((idx) << 8) | \
-                                                ((speed) << 2))
--#define COMPHY_FW_PCIE(mode, idx, speed, width)       (COMPHY_FW_NET(mode, idx, speed) | \
-+#define COMPHY_FW_PCIE(mode, speed, width)    (COMPHY_FW_NET(mode, 0, speed) | \
-                                                ((width) << 18))
- struct mvebu_a3700_comphy_conf {
-       unsigned int lane;
-       enum phy_mode mode;
-       int submode;
--      unsigned int port;
-       u32 fw_mode;
- };
--#define MVEBU_A3700_COMPHY_CONF(_lane, _mode, _smode, _port, _fw)     \
-+#define MVEBU_A3700_COMPHY_CONF(_lane, _mode, _smode, _fw)            \
-       {                                                               \
-               .lane = _lane,                                          \
-               .mode = _mode,                                          \
-               .submode = _smode,                                      \
--              .port = _port,                                          \
-               .fw_mode = _fw,                                         \
-       }
--#define MVEBU_A3700_COMPHY_CONF_GEN(_lane, _mode, _port, _fw) \
--      MVEBU_A3700_COMPHY_CONF(_lane, _mode, PHY_INTERFACE_MODE_NA, _port, _fw)
-+#define MVEBU_A3700_COMPHY_CONF_GEN(_lane, _mode, _fw) \
-+      MVEBU_A3700_COMPHY_CONF(_lane, _mode, PHY_INTERFACE_MODE_NA, _fw)
--#define MVEBU_A3700_COMPHY_CONF_ETH(_lane, _smode, _port, _fw) \
--      MVEBU_A3700_COMPHY_CONF(_lane, PHY_MODE_ETHERNET, _smode, _port, _fw)
-+#define MVEBU_A3700_COMPHY_CONF_ETH(_lane, _smode, _fw) \
-+      MVEBU_A3700_COMPHY_CONF(_lane, PHY_MODE_ETHERNET, _smode, _fw)
- static const struct mvebu_a3700_comphy_conf mvebu_a3700_comphy_modes[] = {
-       /* lane 0 */
--      MVEBU_A3700_COMPHY_CONF_GEN(0, PHY_MODE_USB_HOST_SS, 0,
-+      MVEBU_A3700_COMPHY_CONF_GEN(0, PHY_MODE_USB_HOST_SS,
-                                   COMPHY_FW_MODE_USB3H),
--      MVEBU_A3700_COMPHY_CONF_ETH(0, PHY_INTERFACE_MODE_SGMII, 1,
-+      MVEBU_A3700_COMPHY_CONF_ETH(0, PHY_INTERFACE_MODE_SGMII,
-                                   COMPHY_FW_MODE_SGMII),
--      MVEBU_A3700_COMPHY_CONF_ETH(0, PHY_INTERFACE_MODE_2500BASEX, 1,
-+      MVEBU_A3700_COMPHY_CONF_ETH(0, PHY_INTERFACE_MODE_2500BASEX,
-                                   COMPHY_FW_MODE_2500BASEX),
-       /* lane 1 */
--      MVEBU_A3700_COMPHY_CONF_GEN(1, PHY_MODE_PCIE, 0,
--                                  COMPHY_FW_MODE_PCIE),
--      MVEBU_A3700_COMPHY_CONF_ETH(1, PHY_INTERFACE_MODE_SGMII, 0,
-+      MVEBU_A3700_COMPHY_CONF_GEN(1, PHY_MODE_PCIE, COMPHY_FW_MODE_PCIE),
-+      MVEBU_A3700_COMPHY_CONF_ETH(1, PHY_INTERFACE_MODE_SGMII,
-                                   COMPHY_FW_MODE_SGMII),
--      MVEBU_A3700_COMPHY_CONF_ETH(1, PHY_INTERFACE_MODE_2500BASEX, 0,
-+      MVEBU_A3700_COMPHY_CONF_ETH(1, PHY_INTERFACE_MODE_2500BASEX,
-                                   COMPHY_FW_MODE_2500BASEX),
-       /* lane 2 */
--      MVEBU_A3700_COMPHY_CONF_GEN(2, PHY_MODE_SATA, 0,
--                                  COMPHY_FW_MODE_SATA),
--      MVEBU_A3700_COMPHY_CONF_GEN(2, PHY_MODE_USB_HOST_SS, 0,
-+      MVEBU_A3700_COMPHY_CONF_GEN(2, PHY_MODE_SATA, COMPHY_FW_MODE_SATA),
-+      MVEBU_A3700_COMPHY_CONF_GEN(2, PHY_MODE_USB_HOST_SS,
-                                   COMPHY_FW_MODE_USB3H),
- };
-@@ -98,7 +93,6 @@ struct mvebu_a3700_comphy_lane {
-       unsigned int id;
-       enum phy_mode mode;
-       int submode;
--      int port;
- };
- static int mvebu_a3700_comphy_smc(unsigned long function, unsigned long lane,
-@@ -120,7 +114,7 @@ static int mvebu_a3700_comphy_smc(unsign
-       }
- }
--static int mvebu_a3700_comphy_get_fw_mode(int lane, int port,
-+static int mvebu_a3700_comphy_get_fw_mode(int lane,
-                                         enum phy_mode mode,
-                                         int submode)
- {
-@@ -132,7 +126,6 @@ static int mvebu_a3700_comphy_get_fw_mod
-       for (i = 0; i < n; i++) {
-               if (mvebu_a3700_comphy_modes[i].lane == lane &&
--                  mvebu_a3700_comphy_modes[i].port == port &&
-                   mvebu_a3700_comphy_modes[i].mode == mode &&
-                   mvebu_a3700_comphy_modes[i].submode == submode)
-                       break;
-@@ -153,7 +146,7 @@ static int mvebu_a3700_comphy_set_mode(s
-       if (submode == PHY_INTERFACE_MODE_1000BASEX)
-               submode = PHY_INTERFACE_MODE_SGMII;
--      fw_mode = mvebu_a3700_comphy_get_fw_mode(lane->id, lane->port, mode,
-+      fw_mode = mvebu_a3700_comphy_get_fw_mode(lane->id, mode,
-                                                submode);
-       if (fw_mode < 0) {
-               dev_err(lane->dev, "invalid COMPHY mode\n");
-@@ -172,9 +165,10 @@ static int mvebu_a3700_comphy_power_on(s
-       struct mvebu_a3700_comphy_lane *lane = phy_get_drvdata(phy);
-       u32 fw_param;
-       int fw_mode;
-+      int fw_port;
-       int ret;
--      fw_mode = mvebu_a3700_comphy_get_fw_mode(lane->id, lane->port,
-+      fw_mode = mvebu_a3700_comphy_get_fw_mode(lane->id,
-                                                lane->mode, lane->submode);
-       if (fw_mode < 0) {
-               dev_err(lane->dev, "invalid COMPHY mode\n");
-@@ -191,17 +185,18 @@ static int mvebu_a3700_comphy_power_on(s
-               fw_param = COMPHY_FW_MODE(fw_mode);
-               break;
-       case PHY_MODE_ETHERNET:
-+              fw_port = (lane->id == 0) ? 1 : 0;
-               switch (lane->submode) {
-               case PHY_INTERFACE_MODE_SGMII:
-                       dev_dbg(lane->dev, "set lane %d to SGMII mode\n",
-                               lane->id);
--                      fw_param = COMPHY_FW_NET(fw_mode, lane->port,
-+                      fw_param = COMPHY_FW_NET(fw_mode, fw_port,
-                                                COMPHY_FW_SPEED_1_25G);
-                       break;
-               case PHY_INTERFACE_MODE_2500BASEX:
-                       dev_dbg(lane->dev, "set lane %d to 2500BASEX mode\n",
-                               lane->id);
--                      fw_param = COMPHY_FW_NET(fw_mode, lane->port,
-+                      fw_param = COMPHY_FW_NET(fw_mode, fw_port,
-                                                COMPHY_FW_SPEED_3_125G);
-                       break;
-               default:
-@@ -212,8 +207,7 @@ static int mvebu_a3700_comphy_power_on(s
-               break;
-       case PHY_MODE_PCIE:
-               dev_dbg(lane->dev, "set lane %d to PCIe mode\n", lane->id);
--              fw_param = COMPHY_FW_PCIE(fw_mode, lane->port,
--                                        COMPHY_FW_SPEED_5G,
-+              fw_param = COMPHY_FW_PCIE(fw_mode, COMPHY_FW_SPEED_5G,
-                                         phy->attrs.bus_width);
-               break;
-       default:
-@@ -247,17 +241,20 @@ static struct phy *mvebu_a3700_comphy_xl
-                                           struct of_phandle_args *args)
- {
-       struct mvebu_a3700_comphy_lane *lane;
-+      unsigned int port;
-       struct phy *phy;
--      if (WARN_ON(args->args[0] >= MVEBU_A3700_COMPHY_PORTS))
--              return ERR_PTR(-EINVAL);
--
-       phy = of_phy_simple_xlate(dev, args);
-       if (IS_ERR(phy))
-               return phy;
-       lane = phy_get_drvdata(phy);
--      lane->port = args->args[0];
-+
-+      port = args->args[0];
-+      if (port != 0 && (port != 1 || lane->id != 0)) {
-+              dev_err(lane->dev, "invalid port number %u\n", port);
-+              return ERR_PTR(-EINVAL);
-+      }
-       return phy;
- }
-@@ -302,7 +299,6 @@ static int mvebu_a3700_comphy_probe(stru
-               lane->mode = PHY_MODE_INVALID;
-               lane->submode = PHY_INTERFACE_MODE_NA;
-               lane->id = lane_id;
--              lane->port = -1;
-               phy_set_drvdata(phy, lane);
-       }
diff --git a/target/linux/generic/backport-5.15/344-v5.18-02-phy-marvell-phy-mvebu-a3700-comphy-Add-native-kernel.patch b/target/linux/generic/backport-5.15/344-v5.18-02-phy-marvell-phy-mvebu-a3700-comphy-Add-native-kernel.patch
deleted file mode 100644 (file)
index 4593d14..0000000
+++ /dev/null
@@ -1,1552 +0,0 @@
-From 934337080c6c59b75db76b180b509f218640ad48 Mon Sep 17 00:00:00 2001
-From: =?UTF-8?q?Pali=20Roh=C3=A1r?= <[email protected]>
-Date: Thu, 3 Feb 2022 22:44:41 +0100
-Subject: [PATCH 2/2] phy: marvell: phy-mvebu-a3700-comphy: Add native kernel
- implementation
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-Remove old RPC implementation and add a new native kernel implementation.
-
-The old implementation uses ARM SMC API to issue RPC calls to ARM Trusted
-Firmware which provides real implementation of PHY configuration.
-
-But older versions of ARM Trusted Firmware do not provide this PHY
-configuration functionality, simply returning: operation not supported; or
-worse, some versions provide the configuration functionality incorrectly.
-
-For example the firmware shipped in ESPRESSObin board has this older
-version of ARM Trusted Firmware and therefore SATA, USB 3.0 and PCIe
-functionality do not work with newer versions of Linux kernel.
-
-Due to the above reasons, the following commits were introduced into Linux,
-to workaround these issues by ignoring -EOPNOTSUPP error code from
-phy-mvebu-a3700-comphy driver function phy_power_on():
-
-commit 45aefe3d2251 ("ata: ahci: mvebu: Make SATA PHY optional for Armada
-3720")
-commit 3241929b67d2 ("usb: host: xhci: mvebu: make USB 3.0 PHY optional for
-Armada 3720")
-commit b0c6ae0f8948 ("PCI: aardvark: Fix initialization with old Marvell's
-Arm Trusted Firmware")
-
-Replace this RPC implementation with proper native kernel implementation,
-which is independent on the firmware. Never return -EOPNOTSUPP for proper
-arguments.
-
-This should solve multiple issues with real-world boards, where it is not
-possible or really inconvenient to change the firmware. Let's eliminate
-these issues.
-
-This implementation is ported directly from Armada 3720 comphy driver found
-in newest version of ARM Trusted Firmware source code, but with various
-fixes of register names, some added comments, some refactoring due to the
-original code not conforming to kernel standards. Also PCIe mode poweroff
-support was added here, and PHY reset support. These changes are also going
-to be sent to ARM Trusted Firmware.
-
-[ Pali did the porting from ATF.
-  I (Marek) then fixed some register names, some various other things,
-  added some comments and refactored the code to kernel standards. Also
-  fixed PHY poweroff and added PHY reset. ]
-
-Signed-off-by: Pali Rohár <[email protected]>
-Acked-by: Miquel Raynal <[email protected]>
-Signed-off-by: Marek Behún <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Vinod Koul <[email protected]>
----
- drivers/phy/marvell/phy-mvebu-a3700-comphy.c | 1332 ++++++++++++++++--
- 1 file changed, 1215 insertions(+), 117 deletions(-)
-
---- a/drivers/phy/marvell/phy-mvebu-a3700-comphy.c
-+++ b/drivers/phy/marvell/phy-mvebu-a3700-comphy.c
-@@ -5,12 +5,16 @@
-  * Authors:
-  *   Evan Wang <[email protected]>
-  *   Miquèl Raynal <[email protected]>
-+ *   Pali Rohár <[email protected]>
-+ *   Marek Behún <[email protected]>
-  *
-  * Structure inspired from phy-mvebu-cp110-comphy.c written by Antoine Tenart.
-- * SMC call initial support done by Grzegorz Jaszczyk.
-+ * Comphy code from ARM Trusted Firmware ported by Pali Rohár <[email protected]>
-+ * and Marek Behún <[email protected]>.
-  */
--#include <linux/arm-smccc.h>
-+#include <linux/bitfield.h>
-+#include <linux/clk.h>
- #include <linux/io.h>
- #include <linux/iopoll.h>
- #include <linux/mfd/syscon.h>
-@@ -18,103 +22,1118 @@
- #include <linux/phy.h>
- #include <linux/phy/phy.h>
- #include <linux/platform_device.h>
-+#include <linux/spinlock.h>
--#define MVEBU_A3700_COMPHY_LANES              3
-+#define PLL_SET_DELAY_US              600
-+#define COMPHY_PLL_SLEEP              1000
-+#define COMPHY_PLL_TIMEOUT            150000
-+
-+/* Comphy lane2 indirect access register offset */
-+#define COMPHY_LANE2_INDIR_ADDR               0x0
-+#define COMPHY_LANE2_INDIR_DATA               0x4
-+
-+/* SATA and USB3 PHY offset compared to SATA PHY */
-+#define COMPHY_LANE2_REGS_BASE                0x200
-+
-+/*
-+ * When accessing common PHY lane registers directly, we need to shift by 1,
-+ * since the registers are 16-bit.
-+ */
-+#define COMPHY_LANE_REG_DIRECT(reg)   (((reg) & 0x7FF) << 1)
-+
-+/* COMPHY registers */
-+#define COMPHY_POWER_PLL_CTRL         0x01
-+#define PU_IVREF_BIT                  BIT(15)
-+#define PU_PLL_BIT                    BIT(14)
-+#define PU_RX_BIT                     BIT(13)
-+#define PU_TX_BIT                     BIT(12)
-+#define PU_TX_INTP_BIT                        BIT(11)
-+#define PU_DFE_BIT                    BIT(10)
-+#define RESET_DTL_RX_BIT              BIT(9)
-+#define PLL_LOCK_BIT                  BIT(8)
-+#define REF_FREF_SEL_MASK             GENMASK(4, 0)
-+#define REF_FREF_SEL_SERDES_25MHZ     FIELD_PREP(REF_FREF_SEL_MASK, 0x1)
-+#define REF_FREF_SEL_SERDES_40MHZ     FIELD_PREP(REF_FREF_SEL_MASK, 0x3)
-+#define REF_FREF_SEL_SERDES_50MHZ     FIELD_PREP(REF_FREF_SEL_MASK, 0x4)
-+#define REF_FREF_SEL_PCIE_USB3_25MHZ  FIELD_PREP(REF_FREF_SEL_MASK, 0x2)
-+#define REF_FREF_SEL_PCIE_USB3_40MHZ  FIELD_PREP(REF_FREF_SEL_MASK, 0x3)
-+#define COMPHY_MODE_MASK              GENMASK(7, 5)
-+#define COMPHY_MODE_SATA              FIELD_PREP(COMPHY_MODE_MASK, 0x0)
-+#define COMPHY_MODE_PCIE              FIELD_PREP(COMPHY_MODE_MASK, 0x3)
-+#define COMPHY_MODE_SERDES            FIELD_PREP(COMPHY_MODE_MASK, 0x4)
-+#define COMPHY_MODE_USB3              FIELD_PREP(COMPHY_MODE_MASK, 0x5)
-+
-+#define COMPHY_KVCO_CAL_CTRL          0x02
-+#define USE_MAX_PLL_RATE_BIT          BIT(12)
-+#define SPEED_PLL_MASK                        GENMASK(7, 2)
-+#define SPEED_PLL_VALUE_16            FIELD_PREP(SPEED_PLL_MASK, 0x10)
-+
-+#define COMPHY_DIG_LOOPBACK_EN                0x23
-+#define SEL_DATA_WIDTH_MASK           GENMASK(11, 10)
-+#define DATA_WIDTH_10BIT              FIELD_PREP(SEL_DATA_WIDTH_MASK, 0x0)
-+#define DATA_WIDTH_20BIT              FIELD_PREP(SEL_DATA_WIDTH_MASK, 0x1)
-+#define DATA_WIDTH_40BIT              FIELD_PREP(SEL_DATA_WIDTH_MASK, 0x2)
-+#define PLL_READY_TX_BIT              BIT(4)
-+
-+#define COMPHY_SYNC_PATTERN           0x24
-+#define TXD_INVERT_BIT                        BIT(10)
-+#define RXD_INVERT_BIT                        BIT(11)
-+
-+#define COMPHY_SYNC_MASK_GEN          0x25
-+#define PHY_GEN_MAX_MASK              GENMASK(11, 10)
-+#define PHY_GEN_MAX_USB3_5G           FIELD_PREP(PHY_GEN_MAX_MASK, 0x1)
-+
-+#define COMPHY_ISOLATION_CTRL         0x26
-+#define PHY_ISOLATE_MODE              BIT(15)
-+
-+#define COMPHY_GEN2_SET2              0x3e
-+#define GS2_TX_SSC_AMP_MASK           GENMASK(15, 9)
-+#define GS2_TX_SSC_AMP_4128           FIELD_PREP(GS2_TX_SSC_AMP_MASK, 0x20)
-+#define GS2_VREG_RXTX_MAS_ISET_MASK   GENMASK(8, 7)
-+#define GS2_VREG_RXTX_MAS_ISET_60U    FIELD_PREP(GS2_VREG_RXTX_MAS_ISET_MASK,\
-+                                                 0x0)
-+#define GS2_VREG_RXTX_MAS_ISET_80U    FIELD_PREP(GS2_VREG_RXTX_MAS_ISET_MASK,\
-+                                                 0x1)
-+#define GS2_VREG_RXTX_MAS_ISET_100U   FIELD_PREP(GS2_VREG_RXTX_MAS_ISET_MASK,\
-+                                                 0x2)
-+#define GS2_VREG_RXTX_MAS_ISET_120U   FIELD_PREP(GS2_VREG_RXTX_MAS_ISET_MASK,\
-+                                                 0x3)
-+#define GS2_RSVD_6_0_MASK             GENMASK(6, 0)
-+
-+#define COMPHY_GEN3_SET2              0x3f
-+
-+#define COMPHY_IDLE_SYNC_EN           0x48
-+#define IDLE_SYNC_EN                  BIT(12)
-+
-+#define COMPHY_MISC_CTRL0             0x4F
-+#define CLK100M_125M_EN                       BIT(4)
-+#define TXDCLK_2X_SEL                 BIT(6)
-+#define CLK500M_EN                    BIT(7)
-+#define PHY_REF_CLK_SEL                       BIT(10)
-+
-+#define COMPHY_SFT_RESET              0x52
-+#define SFT_RST                               BIT(9)
-+#define SFT_RST_NO_REG                        BIT(10)
-+
-+#define COMPHY_MISC_CTRL1             0x73
-+#define SEL_BITS_PCIE_FORCE           BIT(15)
-+
-+#define COMPHY_GEN2_SET3              0x112
-+#define GS3_FFE_CAP_SEL_MASK          GENMASK(3, 0)
-+#define GS3_FFE_CAP_SEL_VALUE         FIELD_PREP(GS3_FFE_CAP_SEL_MASK, 0xF)
-+
-+/* PIPE registers */
-+#define COMPHY_PIPE_LANE_CFG0         0x180
-+#define PRD_TXDEEMPH0_MASK            BIT(0)
-+#define PRD_TXMARGIN_MASK             GENMASK(3, 1)
-+#define PRD_TXSWING_MASK              BIT(4)
-+#define CFG_TX_ALIGN_POS_MASK         GENMASK(8, 5)
-+
-+#define COMPHY_PIPE_LANE_CFG1         0x181
-+#define PRD_TXDEEMPH1_MASK            BIT(15)
-+#define USE_MAX_PLL_RATE_EN           BIT(9)
-+#define TX_DET_RX_MODE                        BIT(6)
-+#define GEN2_TX_DATA_DLY_MASK         GENMASK(4, 3)
-+#define GEN2_TX_DATA_DLY_DEFT         FIELD_PREP(GEN2_TX_DATA_DLY_MASK, 2)
-+#define TX_ELEC_IDLE_MODE_EN          BIT(0)
-+
-+#define COMPHY_PIPE_LANE_STAT1                0x183
-+#define TXDCLK_PCLK_EN                        BIT(0)
-+
-+#define COMPHY_PIPE_LANE_CFG4         0x188
-+#define SPREAD_SPECTRUM_CLK_EN                BIT(7)
-+
-+#define COMPHY_PIPE_RST_CLK_CTRL      0x1C1
-+#define PIPE_SOFT_RESET                       BIT(0)
-+#define PIPE_REG_RESET                        BIT(1)
-+#define MODE_CORE_CLK_FREQ_SEL                BIT(9)
-+#define MODE_PIPE_WIDTH_32            BIT(3)
-+#define MODE_REFDIV_MASK              GENMASK(5, 4)
-+#define MODE_REFDIV_BY_4              FIELD_PREP(MODE_REFDIV_MASK, 0x2)
-+
-+#define COMPHY_PIPE_TEST_MODE_CTRL    0x1C2
-+#define MODE_MARGIN_OVERRIDE          BIT(2)
-+
-+#define COMPHY_PIPE_CLK_SRC_LO                0x1C3
-+#define MODE_CLK_SRC                  BIT(0)
-+#define BUNDLE_PERIOD_SEL             BIT(1)
-+#define BUNDLE_PERIOD_SCALE_MASK      GENMASK(3, 2)
-+#define BUNDLE_SAMPLE_CTRL            BIT(4)
-+#define PLL_READY_DLY_MASK            GENMASK(7, 5)
-+#define CFG_SEL_20B                   BIT(15)
-+
-+#define COMPHY_PIPE_PWR_MGM_TIM1      0x1D0
-+#define CFG_PM_OSCCLK_WAIT_MASK               GENMASK(15, 12)
-+#define CFG_PM_RXDEN_WAIT_MASK                GENMASK(11, 8)
-+#define CFG_PM_RXDEN_WAIT_1_UNIT      FIELD_PREP(CFG_PM_RXDEN_WAIT_MASK, 0x1)
-+#define CFG_PM_RXDLOZ_WAIT_MASK               GENMASK(7, 0)
-+#define CFG_PM_RXDLOZ_WAIT_7_UNIT     FIELD_PREP(CFG_PM_RXDLOZ_WAIT_MASK, 0x7)
-+#define CFG_PM_RXDLOZ_WAIT_12_UNIT    FIELD_PREP(CFG_PM_RXDLOZ_WAIT_MASK, 0xC)
-+
-+/*
-+ * This register is not from PHY lane register space. It only exists in the
-+ * indirect register space, before the actual PHY lane 2 registers. So the
-+ * offset is absolute, not relative to COMPHY_LANE2_REGS_BASE.
-+ * It is used only for SATA PHY initialization.
-+ */
-+#define COMPHY_RESERVED_REG           0x0E
-+#define PHYCTRL_FRM_PIN_BIT           BIT(13)
--/* COMPHY Fast SMC function identifiers */
--#define COMPHY_SIP_POWER_ON                   0x82000001
--#define COMPHY_SIP_POWER_OFF                  0x82000002
--#define COMPHY_SIP_PLL_LOCK                   0x82000003
--
--#define COMPHY_FW_MODE_SATA                   0x1
--#define COMPHY_FW_MODE_SGMII                  0x2
--#define COMPHY_FW_MODE_2500BASEX              0x3
--#define COMPHY_FW_MODE_USB3H                  0x4
--#define COMPHY_FW_MODE_USB3D                  0x5
--#define COMPHY_FW_MODE_PCIE                   0x6
--#define COMPHY_FW_MODE_USB3                   0xa
--
--#define COMPHY_FW_SPEED_1_25G                 0 /* SGMII 1G */
--#define COMPHY_FW_SPEED_2_5G                  1
--#define COMPHY_FW_SPEED_3_125G                        2 /* 2500BASE-X */
--#define COMPHY_FW_SPEED_5G                    3
--#define COMPHY_FW_SPEED_MAX                   0x3F
--
--#define COMPHY_FW_MODE(mode)                  ((mode) << 12)
--#define COMPHY_FW_NET(mode, idx, speed)               (COMPHY_FW_MODE(mode) | \
--                                               ((idx) << 8) | \
--                                               ((speed) << 2))
--#define COMPHY_FW_PCIE(mode, speed, width)    (COMPHY_FW_NET(mode, 0, speed) | \
--                                               ((width) << 18))
-+/* South Bridge PHY Configuration Registers */
-+#define COMPHY_PHY_REG(lane, reg)     (((1 - (lane)) * 0x28) + ((reg) & 0x3f))
-+
-+/*
-+ * lane0: USB3/GbE1 PHY Configuration 1
-+ * lane1: PCIe/GbE0 PHY Configuration 1
-+ * (used only by SGMII code)
-+ */
-+#define COMPHY_PHY_CFG1                       0x0
-+#define PIN_PU_IVREF_BIT              BIT(1)
-+#define PIN_RESET_CORE_BIT            BIT(11)
-+#define PIN_RESET_COMPHY_BIT          BIT(12)
-+#define PIN_PU_PLL_BIT                        BIT(16)
-+#define PIN_PU_RX_BIT                 BIT(17)
-+#define PIN_PU_TX_BIT                 BIT(18)
-+#define PIN_TX_IDLE_BIT                       BIT(19)
-+#define GEN_RX_SEL_MASK                       GENMASK(25, 22)
-+#define GEN_RX_SEL_VALUE(val)         FIELD_PREP(GEN_RX_SEL_MASK, (val))
-+#define GEN_TX_SEL_MASK                       GENMASK(29, 26)
-+#define GEN_TX_SEL_VALUE(val)         FIELD_PREP(GEN_TX_SEL_MASK, (val))
-+#define SERDES_SPEED_1_25_G           0x6
-+#define SERDES_SPEED_3_125_G          0x8
-+#define PHY_RX_INIT_BIT                       BIT(30)
-+
-+/*
-+ * lane0: USB3/GbE1 PHY Status 1
-+ * lane1: PCIe/GbE0 PHY Status 1
-+ * (used only by SGMII code)
-+ */
-+#define COMPHY_PHY_STAT1              0x18
-+#define PHY_RX_INIT_DONE_BIT          BIT(0)
-+#define PHY_PLL_READY_RX_BIT          BIT(2)
-+#define PHY_PLL_READY_TX_BIT          BIT(3)
-+
-+/* PHY Selector */
-+#define COMPHY_SELECTOR_PHY_REG                       0xFC
-+/* bit0: 0: Lane1 is GbE0; 1: Lane1 is PCIe */
-+#define COMPHY_SELECTOR_PCIE_GBE0_SEL_BIT     BIT(0)
-+/* bit4: 0: Lane0 is GbE1; 1: Lane0 is USB3 */
-+#define COMPHY_SELECTOR_USB3_GBE1_SEL_BIT     BIT(4)
-+/* bit8: 0: Lane0 is USB3 instead of GbE1, Lane2 is SATA; 1: Lane2 is USB3 */
-+#define COMPHY_SELECTOR_USB3_PHY_SEL_BIT      BIT(8)
- struct mvebu_a3700_comphy_conf {
-       unsigned int lane;
-       enum phy_mode mode;
-       int submode;
--      u32 fw_mode;
- };
--#define MVEBU_A3700_COMPHY_CONF(_lane, _mode, _smode, _fw)            \
-+#define MVEBU_A3700_COMPHY_CONF(_lane, _mode, _smode)                 \
-       {                                                               \
-               .lane = _lane,                                          \
-               .mode = _mode,                                          \
-               .submode = _smode,                                      \
--              .fw_mode = _fw,                                         \
-       }
--#define MVEBU_A3700_COMPHY_CONF_GEN(_lane, _mode, _fw) \
--      MVEBU_A3700_COMPHY_CONF(_lane, _mode, PHY_INTERFACE_MODE_NA, _fw)
-+#define MVEBU_A3700_COMPHY_CONF_GEN(_lane, _mode) \
-+      MVEBU_A3700_COMPHY_CONF(_lane, _mode, PHY_INTERFACE_MODE_NA)
--#define MVEBU_A3700_COMPHY_CONF_ETH(_lane, _smode, _fw) \
--      MVEBU_A3700_COMPHY_CONF(_lane, PHY_MODE_ETHERNET, _smode, _fw)
-+#define MVEBU_A3700_COMPHY_CONF_ETH(_lane, _smode) \
-+      MVEBU_A3700_COMPHY_CONF(_lane, PHY_MODE_ETHERNET, _smode)
- static const struct mvebu_a3700_comphy_conf mvebu_a3700_comphy_modes[] = {
-       /* lane 0 */
--      MVEBU_A3700_COMPHY_CONF_GEN(0, PHY_MODE_USB_HOST_SS,
--                                  COMPHY_FW_MODE_USB3H),
--      MVEBU_A3700_COMPHY_CONF_ETH(0, PHY_INTERFACE_MODE_SGMII,
--                                  COMPHY_FW_MODE_SGMII),
--      MVEBU_A3700_COMPHY_CONF_ETH(0, PHY_INTERFACE_MODE_2500BASEX,
--                                  COMPHY_FW_MODE_2500BASEX),
-+      MVEBU_A3700_COMPHY_CONF_GEN(0, PHY_MODE_USB_HOST_SS),
-+      MVEBU_A3700_COMPHY_CONF_ETH(0, PHY_INTERFACE_MODE_SGMII),
-+      MVEBU_A3700_COMPHY_CONF_ETH(0, PHY_INTERFACE_MODE_1000BASEX),
-+      MVEBU_A3700_COMPHY_CONF_ETH(0, PHY_INTERFACE_MODE_2500BASEX),
-       /* lane 1 */
--      MVEBU_A3700_COMPHY_CONF_GEN(1, PHY_MODE_PCIE, COMPHY_FW_MODE_PCIE),
--      MVEBU_A3700_COMPHY_CONF_ETH(1, PHY_INTERFACE_MODE_SGMII,
--                                  COMPHY_FW_MODE_SGMII),
--      MVEBU_A3700_COMPHY_CONF_ETH(1, PHY_INTERFACE_MODE_2500BASEX,
--                                  COMPHY_FW_MODE_2500BASEX),
-+      MVEBU_A3700_COMPHY_CONF_GEN(1, PHY_MODE_PCIE),
-+      MVEBU_A3700_COMPHY_CONF_ETH(1, PHY_INTERFACE_MODE_SGMII),
-+      MVEBU_A3700_COMPHY_CONF_ETH(1, PHY_INTERFACE_MODE_1000BASEX),
-+      MVEBU_A3700_COMPHY_CONF_ETH(1, PHY_INTERFACE_MODE_2500BASEX),
-       /* lane 2 */
--      MVEBU_A3700_COMPHY_CONF_GEN(2, PHY_MODE_SATA, COMPHY_FW_MODE_SATA),
--      MVEBU_A3700_COMPHY_CONF_GEN(2, PHY_MODE_USB_HOST_SS,
--                                  COMPHY_FW_MODE_USB3H),
-+      MVEBU_A3700_COMPHY_CONF_GEN(2, PHY_MODE_SATA),
-+      MVEBU_A3700_COMPHY_CONF_GEN(2, PHY_MODE_USB_HOST_SS),
-+};
-+
-+struct mvebu_a3700_comphy_priv {
-+      void __iomem *comphy_regs;
-+      void __iomem *lane0_phy_regs; /* USB3 and GbE1 */
-+      void __iomem *lane1_phy_regs; /* PCIe and GbE0 */
-+      void __iomem *lane2_phy_indirect; /* SATA and USB3 */
-+      spinlock_t lock; /* for PHY selector access */
-+      bool xtal_is_40m;
- };
- struct mvebu_a3700_comphy_lane {
-+      struct mvebu_a3700_comphy_priv *priv;
-       struct device *dev;
-       unsigned int id;
-       enum phy_mode mode;
-       int submode;
-+      bool invert_tx;
-+      bool invert_rx;
-+      bool needs_reset;
-+};
-+
-+struct gbe_phy_init_data_fix {
-+      u16 addr;
-+      u16 value;
-+};
-+
-+/* Changes to 40M1G25 mode data required for running 40M3G125 init mode */
-+static struct gbe_phy_init_data_fix gbe_phy_init_fix[] = {
-+      { 0x005, 0x07CC }, { 0x015, 0x0000 }, { 0x01B, 0x0000 },
-+      { 0x01D, 0x0000 }, { 0x01E, 0x0000 }, { 0x01F, 0x0000 },
-+      { 0x020, 0x0000 }, { 0x021, 0x0030 }, { 0x026, 0x0888 },
-+      { 0x04D, 0x0152 }, { 0x04F, 0xA020 }, { 0x050, 0x07CC },
-+      { 0x053, 0xE9CA }, { 0x055, 0xBD97 }, { 0x071, 0x3015 },
-+      { 0x076, 0x03AA }, { 0x07C, 0x0FDF }, { 0x0C2, 0x3030 },
-+      { 0x0C3, 0x8000 }, { 0x0E2, 0x5550 }, { 0x0E3, 0x12A4 },
-+      { 0x0E4, 0x7D00 }, { 0x0E6, 0x0C83 }, { 0x101, 0xFCC0 },
-+      { 0x104, 0x0C10 }
- };
--static int mvebu_a3700_comphy_smc(unsigned long function, unsigned long lane,
--                                unsigned long mode)
-+/* 40M1G25 mode init data */
-+static u16 gbe_phy_init[512] = {
-+      /* 0       1       2       3       4       5       6       7 */
-+      /*-----------------------------------------------------------*/
-+      /* 8       9       A       B       C       D       E       F */
-+      0x3110, 0xFD83, 0x6430, 0x412F, 0x82C0, 0x06FA, 0x4500, 0x6D26, /* 00 */
-+      0xAFC0, 0x8000, 0xC000, 0x0000, 0x2000, 0x49CC, 0x0BC9, 0x2A52, /* 08 */
-+      0x0BD2, 0x0CDE, 0x13D2, 0x0CE8, 0x1149, 0x10E0, 0x0000, 0x0000, /* 10 */
-+      0x0000, 0x0000, 0x0000, 0x0001, 0x0000, 0x4134, 0x0D2D, 0xFFFF, /* 18 */
-+      0xFFE0, 0x4030, 0x1016, 0x0030, 0x0000, 0x0800, 0x0866, 0x0000, /* 20 */
-+      0x0000, 0x0000, 0xFFFF, 0xFFFF, 0xFFFF, 0xFFFF, 0xFFFF, 0xFFFF, /* 28 */
-+      0xFFFF, 0xFFFF, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, /* 30 */
-+      0x0000, 0x0000, 0x000F, 0x6A62, 0x1988, 0x3100, 0x3100, 0x3100, /* 38 */
-+      0x3100, 0xA708, 0x2430, 0x0830, 0x1030, 0x4610, 0xFF00, 0xFF00, /* 40 */
-+      0x0060, 0x1000, 0x0400, 0x0040, 0x00F0, 0x0155, 0x1100, 0xA02A, /* 48 */
-+      0x06FA, 0x0080, 0xB008, 0xE3ED, 0x5002, 0xB592, 0x7A80, 0x0001, /* 50 */
-+      0x020A, 0x8820, 0x6014, 0x8054, 0xACAA, 0xFC88, 0x2A02, 0x45CF, /* 58 */
-+      0x000F, 0x1817, 0x2860, 0x064F, 0x0000, 0x0204, 0x1800, 0x6000, /* 60 */
-+      0x810F, 0x4F23, 0x4000, 0x4498, 0x0850, 0x0000, 0x000E, 0x1002, /* 68 */
-+      0x9D3A, 0x3009, 0xD066, 0x0491, 0x0001, 0x6AB0, 0x0399, 0x3780, /* 70 */
-+      0x0040, 0x5AC0, 0x4A80, 0x0000, 0x01DF, 0x0000, 0x0007, 0x0000, /* 78 */
-+      0x2D54, 0x00A1, 0x4000, 0x0100, 0xA20A, 0x0000, 0x0000, 0x0000, /* 80 */
-+      0x0000, 0x0000, 0x0000, 0x7400, 0x0E81, 0x1000, 0x1242, 0x0210, /* 88 */
-+      0x80DF, 0x0F1F, 0x2F3F, 0x4F5F, 0x6F7F, 0x0F1F, 0x2F3F, 0x4F5F, /* 90 */
-+      0x6F7F, 0x4BAD, 0x0000, 0x0000, 0x0800, 0x0000, 0x2400, 0xB651, /* 98 */
-+      0xC9E0, 0x4247, 0x0A24, 0x0000, 0xAF19, 0x1004, 0x0000, 0x0000, /* A0 */
-+      0x0000, 0x0013, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, /* A8 */
-+      0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, /* B0 */
-+      0x0000, 0x0000, 0x0000, 0x0060, 0x0000, 0x0000, 0x0000, 0x0000, /* B8 */
-+      0x0000, 0x0000, 0x3010, 0xFA00, 0x0000, 0x0000, 0x0000, 0x0003, /* C0 */
-+      0x1618, 0x8200, 0x8000, 0x0400, 0x050F, 0x0000, 0x0000, 0x0000, /* C8 */
-+      0x4C93, 0x0000, 0x1000, 0x1120, 0x0010, 0x1242, 0x1242, 0x1E00, /* D0 */
-+      0x0000, 0x0000, 0x0000, 0x00F8, 0x0000, 0x0041, 0x0800, 0x0000, /* D8 */
-+      0x82A0, 0x572E, 0x2490, 0x14A9, 0x4E00, 0x0000, 0x0803, 0x0541, /* E0 */
-+      0x0C15, 0x0000, 0x0000, 0x0400, 0x2626, 0x0000, 0x0000, 0x4200, /* E8 */
-+      0x0000, 0xAA55, 0x1020, 0x0000, 0x0000, 0x5010, 0x0000, 0x0000, /* F0 */
-+      0x0000, 0x0000, 0x5000, 0x0000, 0x0000, 0x0000, 0x02F2, 0x0000, /* F8 */
-+      0x101F, 0xFDC0, 0x4000, 0x8010, 0x0110, 0x0006, 0x0000, 0x0000, /*100 */
-+      0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, /*108 */
-+      0x04CF, 0x0000, 0x04CF, 0x0000, 0x04CF, 0x0000, 0x04C6, 0x0000, /*110 */
-+      0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, /*118 */
-+      0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, /*120 */
-+      0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, /*128 */
-+      0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, /*130 */
-+      0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, /*138 */
-+      0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, /*140 */
-+      0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, /*148 */
-+      0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, /*150 */
-+      0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, /*158 */
-+      0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, /*160 */
-+      0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, /*168 */
-+      0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, /*170 */
-+      0x0000, 0x0000, 0x0000, 0x00F0, 0x08A2, 0x3112, 0x0A14, 0x0000, /*178 */
-+      0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, /*180 */
-+      0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, /*188 */
-+      0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, /*190 */
-+      0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, /*198 */
-+      0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, /*1A0 */
-+      0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, /*1A8 */
-+      0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, /*1B0 */
-+      0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, /*1B8 */
-+      0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, /*1C0 */
-+      0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, /*1C8 */
-+      0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, /*1D0 */
-+      0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, /*1D8 */
-+      0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, /*1E0 */
-+      0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, /*1E8 */
-+      0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, /*1F0 */
-+      0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000  /*1F8 */
-+};
-+
-+static inline void comphy_reg_set(void __iomem *addr, u32 data, u32 mask)
- {
--      struct arm_smccc_res res;
--      s32 ret;
-+      u32 val;
-+
-+      val = readl(addr);
-+      val = (val & ~mask) | (data & mask);
-+      writel(val, addr);
-+}
--      arm_smccc_smc(function, lane, mode, 0, 0, 0, 0, 0, &res);
--      ret = res.a0;
-+static inline void comphy_reg_set16(void __iomem *addr, u16 data, u16 mask)
-+{
-+      u16 val;
--      switch (ret) {
--      case SMCCC_RET_SUCCESS:
--              return 0;
--      case SMCCC_RET_NOT_SUPPORTED:
--              return -EOPNOTSUPP;
-+      val = readw(addr);
-+      val = (val & ~mask) | (data & mask);
-+      writew(val, addr);
-+}
-+
-+/* Used for accessing lane 2 registers (SATA/USB3 PHY) */
-+static void comphy_set_indirect(struct mvebu_a3700_comphy_priv *priv,
-+                              u32 offset, u16 data, u16 mask)
-+{
-+      writel(offset,
-+             priv->lane2_phy_indirect + COMPHY_LANE2_INDIR_ADDR);
-+      comphy_reg_set(priv->lane2_phy_indirect + COMPHY_LANE2_INDIR_DATA,
-+                     data, mask);
-+}
-+
-+static void comphy_lane_reg_set(struct mvebu_a3700_comphy_lane *lane,
-+                              u16 reg, u16 data, u16 mask)
-+{
-+      if (lane->id == 2) {
-+              /* lane 2 PHY registers are accessed indirectly */
-+              comphy_set_indirect(lane->priv,
-+                                  reg + COMPHY_LANE2_REGS_BASE,
-+                                  data, mask);
-+      } else {
-+              void __iomem *base = lane->id == 1 ?
-+                                   lane->priv->lane1_phy_regs :
-+                                   lane->priv->lane0_phy_regs;
-+
-+              comphy_reg_set16(base + COMPHY_LANE_REG_DIRECT(reg),
-+                               data, mask);
-+      }
-+}
-+
-+static int comphy_lane_reg_poll(struct mvebu_a3700_comphy_lane *lane,
-+                              u16 reg, u16 bits,
-+                              ulong sleep_us, ulong timeout_us)
-+{
-+      int ret;
-+
-+      if (lane->id == 2) {
-+              u32 data;
-+
-+              /* lane 2 PHY registers are accessed indirectly */
-+              writel(reg + COMPHY_LANE2_REGS_BASE,
-+                     lane->priv->lane2_phy_indirect +
-+                     COMPHY_LANE2_INDIR_ADDR);
-+
-+              ret = readl_poll_timeout(lane->priv->lane2_phy_indirect +
-+                                       COMPHY_LANE2_INDIR_DATA,
-+                                       data, (data & bits) == bits,
-+                                       sleep_us, timeout_us);
-+      } else {
-+              void __iomem *base = lane->id == 1 ?
-+                                   lane->priv->lane1_phy_regs :
-+                                   lane->priv->lane0_phy_regs;
-+              u16 data;
-+
-+              ret = readw_poll_timeout(base + COMPHY_LANE_REG_DIRECT(reg),
-+                                       data, (data & bits) == bits,
-+                                       sleep_us, timeout_us);
-+      }
-+
-+      return ret;
-+}
-+
-+static void comphy_periph_reg_set(struct mvebu_a3700_comphy_lane *lane,
-+                                u8 reg, u32 data, u32 mask)
-+{
-+      comphy_reg_set(lane->priv->comphy_regs + COMPHY_PHY_REG(lane->id, reg),
-+                     data, mask);
-+}
-+
-+static int comphy_periph_reg_poll(struct mvebu_a3700_comphy_lane *lane,
-+                                u8 reg, u32 bits,
-+                                ulong sleep_us, ulong timeout_us)
-+{
-+      u32 data;
-+
-+      return readl_poll_timeout(lane->priv->comphy_regs +
-+                                COMPHY_PHY_REG(lane->id, reg),
-+                                data, (data & bits) == bits,
-+                                sleep_us, timeout_us);
-+}
-+
-+/* PHY selector configures with corresponding modes */
-+static int
-+mvebu_a3700_comphy_set_phy_selector(struct mvebu_a3700_comphy_lane *lane)
-+{
-+      u32 old, new, clr = 0, set = 0;
-+      unsigned long flags;
-+
-+      switch (lane->mode) {
-+      case PHY_MODE_SATA:
-+              /* SATA must be in Lane2 */
-+              if (lane->id == 2)
-+                      clr = COMPHY_SELECTOR_USB3_PHY_SEL_BIT;
-+              else
-+                      goto error;
-+              break;
-+
-+      case PHY_MODE_ETHERNET:
-+              if (lane->id == 0)
-+                      clr = COMPHY_SELECTOR_USB3_GBE1_SEL_BIT;
-+              else if (lane->id == 1)
-+                      clr = COMPHY_SELECTOR_PCIE_GBE0_SEL_BIT;
-+              else
-+                      goto error;
-+              break;
-+
-+      case PHY_MODE_USB_HOST_SS:
-+              if (lane->id == 2)
-+                      set = COMPHY_SELECTOR_USB3_PHY_SEL_BIT;
-+              else if (lane->id == 0)
-+                      set = COMPHY_SELECTOR_USB3_GBE1_SEL_BIT;
-+              else
-+                      goto error;
-+              break;
-+
-+      case PHY_MODE_PCIE:
-+              /* PCIE must be in Lane1 */
-+              if (lane->id == 1)
-+                      set = COMPHY_SELECTOR_PCIE_GBE0_SEL_BIT;
-+              else
-+                      goto error;
-+              break;
-+
-+      default:
-+              goto error;
-+      }
-+
-+      spin_lock_irqsave(&lane->priv->lock, flags);
-+
-+      old = readl(lane->priv->comphy_regs + COMPHY_SELECTOR_PHY_REG);
-+      new = (old & ~clr) | set;
-+      writel(new, lane->priv->comphy_regs + COMPHY_SELECTOR_PHY_REG);
-+
-+      spin_unlock_irqrestore(&lane->priv->lock, flags);
-+
-+      dev_dbg(lane->dev,
-+              "COMPHY[%d] mode[%d] changed PHY selector 0x%08x -> 0x%08x\n",
-+              lane->id, lane->mode, old, new);
-+
-+      return 0;
-+error:
-+      dev_err(lane->dev, "COMPHY[%d] mode[%d] is invalid\n", lane->id,
-+              lane->mode);
-+      return -EINVAL;
-+}
-+
-+static int
-+mvebu_a3700_comphy_sata_power_on(struct mvebu_a3700_comphy_lane *lane)
-+{
-+      u32 mask, data, ref_clk;
-+      int ret;
-+
-+      /* Configure phy selector for SATA */
-+      ret = mvebu_a3700_comphy_set_phy_selector(lane);
-+      if (ret)
-+              return ret;
-+
-+      /* Clear phy isolation mode to make it work in normal mode */
-+      comphy_lane_reg_set(lane, COMPHY_ISOLATION_CTRL,
-+                          0x0, PHY_ISOLATE_MODE);
-+
-+      /* 0. Check the Polarity invert bits */
-+      data = 0x0;
-+      if (lane->invert_tx)
-+              data |= TXD_INVERT_BIT;
-+      if (lane->invert_rx)
-+              data |= RXD_INVERT_BIT;
-+      mask = TXD_INVERT_BIT | RXD_INVERT_BIT;
-+      comphy_lane_reg_set(lane, COMPHY_SYNC_PATTERN, data, mask);
-+
-+      /* 1. Select 40-bit data width */
-+      comphy_lane_reg_set(lane, COMPHY_DIG_LOOPBACK_EN,
-+                          DATA_WIDTH_40BIT, SEL_DATA_WIDTH_MASK);
-+
-+      /* 2. Select reference clock(25M) and PHY mode (SATA) */
-+      if (lane->priv->xtal_is_40m)
-+              ref_clk = REF_FREF_SEL_SERDES_40MHZ;
-+      else
-+              ref_clk = REF_FREF_SEL_SERDES_25MHZ;
-+
-+      data = ref_clk | COMPHY_MODE_SATA;
-+      mask = REF_FREF_SEL_MASK | COMPHY_MODE_MASK;
-+      comphy_lane_reg_set(lane, COMPHY_POWER_PLL_CTRL, data, mask);
-+
-+      /* 3. Use maximum PLL rate (no power save) */
-+      comphy_lane_reg_set(lane, COMPHY_KVCO_CAL_CTRL,
-+                          USE_MAX_PLL_RATE_BIT, USE_MAX_PLL_RATE_BIT);
-+
-+      /* 4. Reset reserved bit */
-+      comphy_set_indirect(lane->priv, COMPHY_RESERVED_REG,
-+                          0x0, PHYCTRL_FRM_PIN_BIT);
-+
-+      /* 5. Set vendor-specific configuration (It is done in sata driver) */
-+      /* XXX: in U-Boot below sequence was executed in this place, in Linux
-+       * not.  Now it is done only in U-Boot before this comphy
-+       * initialization - tests shows that it works ok, but in case of any
-+       * future problem it is left for reference.
-+       *   reg_set(MVEBU_REGS_BASE + 0xe00a0, 0, 0xffffffff);
-+       *   reg_set(MVEBU_REGS_BASE + 0xe00a4, BIT(6), BIT(6));
-+       */
-+
-+      /* Wait for > 55 us to allow PLL be enabled */
-+      udelay(PLL_SET_DELAY_US);
-+
-+      /* Polling status */
-+      ret = comphy_lane_reg_poll(lane, COMPHY_DIG_LOOPBACK_EN,
-+                                 PLL_READY_TX_BIT, COMPHY_PLL_SLEEP,
-+                                 COMPHY_PLL_TIMEOUT);
-+      if (ret)
-+              dev_err(lane->dev, "Failed to lock SATA PLL\n");
-+
-+      return ret;
-+}
-+
-+static void comphy_gbe_phy_init(struct mvebu_a3700_comphy_lane *lane,
-+                              bool is_1gbps)
-+{
-+      int addr, fix_idx;
-+      u16 val;
-+
-+      fix_idx = 0;
-+      for (addr = 0; addr < 512; addr++) {
-+              /*
-+               * All PHY register values are defined in full for 3.125Gbps
-+               * SERDES speed. The values required for 1.25 Gbps are almost
-+               * the same and only few registers should be "fixed" in
-+               * comparison to 3.125 Gbps values. These register values are
-+               * stored in "gbe_phy_init_fix" array.
-+               */
-+              if (!is_1gbps && gbe_phy_init_fix[fix_idx].addr == addr) {
-+                      /* Use new value */
-+                      val = gbe_phy_init_fix[fix_idx].value;
-+                      if (fix_idx < ARRAY_SIZE(gbe_phy_init_fix))
-+                              fix_idx++;
-+              } else {
-+                      val = gbe_phy_init[addr];
-+              }
-+
-+              comphy_lane_reg_set(lane, addr, val, 0xFFFF);
-+      }
-+}
-+
-+static int
-+mvebu_a3700_comphy_ethernet_power_on(struct mvebu_a3700_comphy_lane *lane)
-+{
-+      u32 mask, data, speed_sel;
-+      int ret;
-+
-+      /* Set selector */
-+      ret = mvebu_a3700_comphy_set_phy_selector(lane);
-+      if (ret)
-+              return ret;
-+
-+      /*
-+       * 1. Reset PHY by setting PHY input port PIN_RESET=1.
-+       * 2. Set PHY input port PIN_TX_IDLE=1, PIN_PU_IVREF=1 to keep
-+       *    PHY TXP/TXN output to idle state during PHY initialization
-+       * 3. Set PHY input port PIN_PU_PLL=0, PIN_PU_RX=0, PIN_PU_TX=0.
-+       */
-+      data = PIN_PU_IVREF_BIT | PIN_TX_IDLE_BIT | PIN_RESET_COMPHY_BIT;
-+      mask = data | PIN_RESET_CORE_BIT | PIN_PU_PLL_BIT | PIN_PU_RX_BIT |
-+             PIN_PU_TX_BIT | PHY_RX_INIT_BIT;
-+      comphy_periph_reg_set(lane, COMPHY_PHY_CFG1, data, mask);
-+
-+      /* 4. Release reset to the PHY by setting PIN_RESET=0. */
-+      data = 0x0;
-+      mask = PIN_RESET_COMPHY_BIT;
-+      comphy_periph_reg_set(lane, COMPHY_PHY_CFG1, data, mask);
-+
-+      /*
-+       * 5. Set PIN_PHY_GEN_TX[3:0] and PIN_PHY_GEN_RX[3:0] to decide COMPHY
-+       * bit rate
-+       */
-+      switch (lane->submode) {
-+      case PHY_INTERFACE_MODE_SGMII:
-+      case PHY_INTERFACE_MODE_1000BASEX:
-+              /* SGMII 1G, SerDes speed 1.25G */
-+              speed_sel = SERDES_SPEED_1_25_G;
-+              break;
-+      case PHY_INTERFACE_MODE_2500BASEX:
-+              /* 2500Base-X, SerDes speed 3.125G */
-+              speed_sel = SERDES_SPEED_3_125_G;
-+              break;
-       default:
-+              /* Other rates are not supported */
-+              dev_err(lane->dev,
-+                      "unsupported phy speed %d on comphy lane%d\n",
-+                      lane->submode, lane->id);
-               return -EINVAL;
-       }
-+      data = GEN_RX_SEL_VALUE(speed_sel) | GEN_TX_SEL_VALUE(speed_sel);
-+      mask = GEN_RX_SEL_MASK | GEN_TX_SEL_MASK;
-+      comphy_periph_reg_set(lane, COMPHY_PHY_CFG1, data, mask);
-+
-+      /*
-+       * 6. Wait 10mS for bandgap and reference clocks to stabilize; then
-+       * start SW programming.
-+       */
-+      mdelay(10);
-+
-+      /* 7. Program COMPHY register PHY_MODE */
-+      data = COMPHY_MODE_SERDES;
-+      mask = COMPHY_MODE_MASK;
-+      comphy_lane_reg_set(lane, COMPHY_POWER_PLL_CTRL, data, mask);
-+
-+      /*
-+       * 8. Set COMPHY register REFCLK_SEL to select the correct REFCLK
-+       * source
-+       */
-+      data = 0x0;
-+      mask = PHY_REF_CLK_SEL;
-+      comphy_lane_reg_set(lane, COMPHY_MISC_CTRL0, data, mask);
-+
-+      /*
-+       * 9. Set correct reference clock frequency in COMPHY register
-+       * REF_FREF_SEL.
-+       */
-+      if (lane->priv->xtal_is_40m)
-+              data = REF_FREF_SEL_SERDES_50MHZ;
-+      else
-+              data = REF_FREF_SEL_SERDES_25MHZ;
-+
-+      mask = REF_FREF_SEL_MASK;
-+      comphy_lane_reg_set(lane, COMPHY_POWER_PLL_CTRL, data, mask);
-+
-+      /*
-+       * 10. Program COMPHY register PHY_GEN_MAX[1:0]
-+       * This step is mentioned in the flow received from verification team.
-+       * However the PHY_GEN_MAX value is only meaningful for other interfaces
-+       * (not SERDES). For instance, it selects SATA speed 1.5/3/6 Gbps or
-+       * PCIe speed 2.5/5 Gbps
-+       */
-+
-+      /*
-+       * 11. Program COMPHY register SEL_BITS to set correct parallel data
-+       * bus width
-+       */
-+      data = DATA_WIDTH_10BIT;
-+      mask = SEL_DATA_WIDTH_MASK;
-+      comphy_lane_reg_set(lane, COMPHY_DIG_LOOPBACK_EN, data, mask);
-+
-+      /*
-+       * 12. As long as DFE function needs to be enabled in any mode,
-+       * COMPHY register DFE_UPDATE_EN[5:0] shall be programmed to 0x3F
-+       * for real chip during COMPHY power on.
-+       * The value of the DFE_UPDATE_EN already is 0x3F, because it is the
-+       * default value after reset of the PHY.
-+       */
-+
-+      /*
-+       * 13. Program COMPHY GEN registers.
-+       * These registers should be programmed based on the lab testing result
-+       * to achieve optimal performance. Please contact the CEA group to get
-+       * the related GEN table during real chip bring-up. We only required to
-+       * run though the entire registers programming flow defined by
-+       * "comphy_gbe_phy_init" when the REF clock is 40 MHz. For REF clock
-+       * 25 MHz the default values stored in PHY registers are OK.
-+       */
-+      dev_dbg(lane->dev, "Running C-DPI phy init %s mode\n",
-+              lane->submode == PHY_INTERFACE_MODE_2500BASEX ? "2G5" : "1G");
-+      if (lane->priv->xtal_is_40m)
-+              comphy_gbe_phy_init(lane,
-+                                  lane->submode != PHY_INTERFACE_MODE_2500BASEX);
-+
-+      /*
-+       * 14. Check the PHY Polarity invert bit
-+       */
-+      data = 0x0;
-+      if (lane->invert_tx)
-+              data |= TXD_INVERT_BIT;
-+      if (lane->invert_rx)
-+              data |= RXD_INVERT_BIT;
-+      mask = TXD_INVERT_BIT | RXD_INVERT_BIT;
-+      comphy_lane_reg_set(lane, COMPHY_SYNC_PATTERN, data, mask);
-+
-+      /*
-+       * 15. Set PHY input ports PIN_PU_PLL, PIN_PU_TX and PIN_PU_RX to 1 to
-+       * start PHY power up sequence. All the PHY register programming should
-+       * be done before PIN_PU_PLL=1. There should be no register programming
-+       * for normal PHY operation from this point.
-+       */
-+      data = PIN_PU_PLL_BIT | PIN_PU_RX_BIT | PIN_PU_TX_BIT;
-+      mask = data;
-+      comphy_periph_reg_set(lane, COMPHY_PHY_CFG1, data, mask);
-+
-+      /*
-+       * 16. Wait for PHY power up sequence to finish by checking output ports
-+       * PIN_PLL_READY_TX=1 and PIN_PLL_READY_RX=1.
-+       */
-+      ret = comphy_periph_reg_poll(lane, COMPHY_PHY_STAT1,
-+                                   PHY_PLL_READY_TX_BIT |
-+                                   PHY_PLL_READY_RX_BIT,
-+                                   COMPHY_PLL_SLEEP, COMPHY_PLL_TIMEOUT);
-+      if (ret) {
-+              dev_err(lane->dev, "Failed to lock PLL for SERDES PHY %d\n",
-+                      lane->id);
-+              return ret;
-+      }
-+
-+      /*
-+       * 17. Set COMPHY input port PIN_TX_IDLE=0
-+       */
-+      comphy_periph_reg_set(lane, COMPHY_PHY_CFG1, 0x0, PIN_TX_IDLE_BIT);
-+
-+      /*
-+       * 18. After valid data appear on PIN_RXDATA bus, set PIN_RX_INIT=1. To
-+       * start RX initialization. PIN_RX_INIT_DONE will be cleared to 0 by the
-+       * PHY After RX initialization is done, PIN_RX_INIT_DONE will be set to
-+       * 1 by COMPHY Set PIN_RX_INIT=0 after PIN_RX_INIT_DONE= 1. Please
-+       * refer to RX initialization part for details.
-+       */
-+      comphy_periph_reg_set(lane, COMPHY_PHY_CFG1,
-+                            PHY_RX_INIT_BIT, PHY_RX_INIT_BIT);
-+
-+      ret = comphy_periph_reg_poll(lane, COMPHY_PHY_STAT1,
-+                                   PHY_PLL_READY_TX_BIT |
-+                                   PHY_PLL_READY_RX_BIT,
-+                                   COMPHY_PLL_SLEEP, COMPHY_PLL_TIMEOUT);
-+      if (ret) {
-+              dev_err(lane->dev, "Failed to lock PLL for SERDES PHY %d\n",
-+                      lane->id);
-+              return ret;
-+      }
-+
-+      ret = comphy_periph_reg_poll(lane, COMPHY_PHY_STAT1,
-+                                   PHY_RX_INIT_DONE_BIT,
-+                                   COMPHY_PLL_SLEEP, COMPHY_PLL_TIMEOUT);
-+      if (ret)
-+              dev_err(lane->dev, "Failed to init RX of SERDES PHY %d\n",
-+                      lane->id);
-+
-+      return ret;
- }
--static int mvebu_a3700_comphy_get_fw_mode(int lane,
-+static int
-+mvebu_a3700_comphy_usb3_power_on(struct mvebu_a3700_comphy_lane *lane)
-+{
-+      u32 mask, data, cfg, ref_clk;
-+      int ret;
-+
-+      /* Set phy seclector */
-+      ret = mvebu_a3700_comphy_set_phy_selector(lane);
-+      if (ret)
-+              return ret;
-+
-+      /*
-+       * 0. Set PHY OTG Control(0x5d034), bit 4, Power up OTG module The
-+       * register belong to UTMI module, so it is set in UTMI phy driver.
-+       */
-+
-+      /*
-+       * 1. Set PRD_TXDEEMPH (3.5db de-emph)
-+       */
-+      data = PRD_TXDEEMPH0_MASK;
-+      mask = PRD_TXDEEMPH0_MASK | PRD_TXMARGIN_MASK | PRD_TXSWING_MASK |
-+             CFG_TX_ALIGN_POS_MASK;
-+      comphy_lane_reg_set(lane, COMPHY_PIPE_LANE_CFG0, data, mask);
-+
-+      /*
-+       * 2. Set BIT0: enable transmitter in high impedance mode
-+       *    Set BIT[3:4]: delay 2 clock cycles for HiZ off latency
-+       *    Set BIT6: Tx detect Rx at HiZ mode
-+       *    Unset BIT15: set to 0 to set USB3 De-emphasize level to -3.5db
-+       *            together with bit 0 of COMPHY_PIPE_LANE_CFG0 register
-+       */
-+      data = TX_DET_RX_MODE | GEN2_TX_DATA_DLY_DEFT | TX_ELEC_IDLE_MODE_EN;
-+      mask = PRD_TXDEEMPH1_MASK | TX_DET_RX_MODE | GEN2_TX_DATA_DLY_MASK |
-+             TX_ELEC_IDLE_MODE_EN;
-+      comphy_lane_reg_set(lane, COMPHY_PIPE_LANE_CFG1, data, mask);
-+
-+      /*
-+       * 3. Set Spread Spectrum Clock Enabled
-+       */
-+      comphy_lane_reg_set(lane, COMPHY_PIPE_LANE_CFG4,
-+                          SPREAD_SPECTRUM_CLK_EN, SPREAD_SPECTRUM_CLK_EN);
-+
-+      /*
-+       * 4. Set Override Margining Controls From the MAC:
-+       *    Use margining signals from lane configuration
-+       */
-+      comphy_lane_reg_set(lane, COMPHY_PIPE_TEST_MODE_CTRL,
-+                          MODE_MARGIN_OVERRIDE, 0xFFFF);
-+
-+      /*
-+       * 5. Set Lane-to-Lane Bundle Clock Sampling Period = per PCLK cycles
-+       *    set Mode Clock Source = PCLK is generated from REFCLK
-+       */
-+      data = 0x0;
-+      mask = MODE_CLK_SRC | BUNDLE_PERIOD_SEL | BUNDLE_PERIOD_SCALE_MASK |
-+             BUNDLE_SAMPLE_CTRL | PLL_READY_DLY_MASK;
-+      comphy_lane_reg_set(lane, COMPHY_PIPE_CLK_SRC_LO, data, mask);
-+
-+      /*
-+       * 6. Set G2 Spread Spectrum Clock Amplitude at 4K
-+       */
-+      comphy_lane_reg_set(lane, COMPHY_GEN2_SET2,
-+                          GS2_TX_SSC_AMP_4128, GS2_TX_SSC_AMP_MASK);
-+
-+      /*
-+       * 7. Unset G3 Spread Spectrum Clock Amplitude
-+       *    set G3 TX and RX Register Master Current Select
-+       */
-+      data = GS2_VREG_RXTX_MAS_ISET_60U;
-+      mask = GS2_TX_SSC_AMP_MASK | GS2_VREG_RXTX_MAS_ISET_MASK |
-+             GS2_RSVD_6_0_MASK;
-+      comphy_lane_reg_set(lane, COMPHY_GEN3_SET2, data, mask);
-+
-+      /*
-+       * 8. Check crystal jumper setting and program the Power and PLL Control
-+       * accordingly Change RX wait
-+       */
-+      if (lane->priv->xtal_is_40m) {
-+              ref_clk = REF_FREF_SEL_PCIE_USB3_40MHZ;
-+              cfg = CFG_PM_RXDLOZ_WAIT_12_UNIT;
-+      } else {
-+              ref_clk = REF_FREF_SEL_PCIE_USB3_25MHZ;
-+              cfg = CFG_PM_RXDLOZ_WAIT_7_UNIT;
-+      }
-+
-+      data = PU_IVREF_BIT | PU_PLL_BIT | PU_RX_BIT | PU_TX_BIT |
-+             PU_TX_INTP_BIT | PU_DFE_BIT | COMPHY_MODE_USB3 | ref_clk;
-+      mask = PU_IVREF_BIT | PU_PLL_BIT | PU_RX_BIT | PU_TX_BIT |
-+             PU_TX_INTP_BIT | PU_DFE_BIT | PLL_LOCK_BIT | COMPHY_MODE_MASK |
-+             REF_FREF_SEL_MASK;
-+      comphy_lane_reg_set(lane, COMPHY_POWER_PLL_CTRL, data, mask);
-+
-+      data = CFG_PM_RXDEN_WAIT_1_UNIT | cfg;
-+      mask = CFG_PM_OSCCLK_WAIT_MASK | CFG_PM_RXDEN_WAIT_MASK |
-+             CFG_PM_RXDLOZ_WAIT_MASK;
-+      comphy_lane_reg_set(lane, COMPHY_PIPE_PWR_MGM_TIM1, data, mask);
-+
-+      /*
-+       * 9. Enable idle sync
-+       */
-+      comphy_lane_reg_set(lane, COMPHY_IDLE_SYNC_EN,
-+                          IDLE_SYNC_EN, IDLE_SYNC_EN);
-+
-+      /*
-+       * 10. Enable the output of 500M clock
-+       */
-+      comphy_lane_reg_set(lane, COMPHY_MISC_CTRL0, CLK500M_EN, CLK500M_EN);
-+
-+      /*
-+       * 11. Set 20-bit data width
-+       */
-+      comphy_lane_reg_set(lane, COMPHY_DIG_LOOPBACK_EN,
-+                          DATA_WIDTH_20BIT, 0xFFFF);
-+
-+      /*
-+       * 12. Override Speed_PLL value and use MAC PLL
-+       */
-+      data = SPEED_PLL_VALUE_16 | USE_MAX_PLL_RATE_BIT;
-+      mask = 0xFFFF;
-+      comphy_lane_reg_set(lane, COMPHY_KVCO_CAL_CTRL, data, mask);
-+
-+      /*
-+       * 13. Check the Polarity invert bit
-+       */
-+      data = 0x0;
-+      if (lane->invert_tx)
-+              data |= TXD_INVERT_BIT;
-+      if (lane->invert_rx)
-+              data |= RXD_INVERT_BIT;
-+      mask = TXD_INVERT_BIT | RXD_INVERT_BIT;
-+      comphy_lane_reg_set(lane, COMPHY_SYNC_PATTERN, data, mask);
-+
-+      /*
-+       * 14. Set max speed generation to USB3.0 5Gbps
-+       */
-+      comphy_lane_reg_set(lane, COMPHY_SYNC_MASK_GEN,
-+                          PHY_GEN_MAX_USB3_5G, PHY_GEN_MAX_MASK);
-+
-+      /*
-+       * 15. Set capacitor value for FFE gain peaking to 0xF
-+       */
-+      comphy_lane_reg_set(lane, COMPHY_GEN2_SET3,
-+                          GS3_FFE_CAP_SEL_VALUE, GS3_FFE_CAP_SEL_MASK);
-+
-+      /*
-+       * 16. Release SW reset
-+       */
-+      data = MODE_CORE_CLK_FREQ_SEL | MODE_PIPE_WIDTH_32 | MODE_REFDIV_BY_4;
-+      mask = 0xFFFF;
-+      comphy_lane_reg_set(lane, COMPHY_PIPE_RST_CLK_CTRL, data, mask);
-+
-+      /* Wait for > 55 us to allow PCLK be enabled */
-+      udelay(PLL_SET_DELAY_US);
-+
-+      ret = comphy_lane_reg_poll(lane, COMPHY_PIPE_LANE_STAT1, TXDCLK_PCLK_EN,
-+                                 COMPHY_PLL_SLEEP, COMPHY_PLL_TIMEOUT);
-+      if (ret)
-+              dev_err(lane->dev, "Failed to lock USB3 PLL\n");
-+
-+      return ret;
-+}
-+
-+static int
-+mvebu_a3700_comphy_pcie_power_on(struct mvebu_a3700_comphy_lane *lane)
-+{
-+      u32 mask, data, ref_clk;
-+      int ret;
-+
-+      /* Configure phy selector for PCIe */
-+      ret = mvebu_a3700_comphy_set_phy_selector(lane);
-+      if (ret)
-+              return ret;
-+
-+      /* 1. Enable max PLL. */
-+      comphy_lane_reg_set(lane, COMPHY_PIPE_LANE_CFG1,
-+                          USE_MAX_PLL_RATE_EN, USE_MAX_PLL_RATE_EN);
-+
-+      /* 2. Select 20 bit SERDES interface. */
-+      comphy_lane_reg_set(lane, COMPHY_PIPE_CLK_SRC_LO,
-+                          CFG_SEL_20B, CFG_SEL_20B);
-+
-+      /* 3. Force to use reg setting for PCIe mode */
-+      comphy_lane_reg_set(lane, COMPHY_MISC_CTRL1,
-+                          SEL_BITS_PCIE_FORCE, SEL_BITS_PCIE_FORCE);
-+
-+      /* 4. Change RX wait */
-+      data = CFG_PM_RXDEN_WAIT_1_UNIT | CFG_PM_RXDLOZ_WAIT_12_UNIT;
-+      mask = CFG_PM_OSCCLK_WAIT_MASK | CFG_PM_RXDEN_WAIT_MASK |
-+             CFG_PM_RXDLOZ_WAIT_MASK;
-+      comphy_lane_reg_set(lane, COMPHY_PIPE_PWR_MGM_TIM1, data, mask);
-+
-+      /* 5. Enable idle sync */
-+      comphy_lane_reg_set(lane, COMPHY_IDLE_SYNC_EN,
-+                          IDLE_SYNC_EN, IDLE_SYNC_EN);
-+
-+      /* 6. Enable the output of 100M/125M/500M clock */
-+      data = CLK500M_EN | TXDCLK_2X_SEL | CLK100M_125M_EN;
-+      mask = data;
-+      comphy_lane_reg_set(lane, COMPHY_MISC_CTRL0, data, mask);
-+
-+      /*
-+       * 7. Enable TX, PCIE global register, 0xd0074814, it is done in
-+       * PCI-E driver
-+       */
-+
-+      /*
-+       * 8. Check crystal jumper setting and program the Power and PLL
-+       * Control accordingly
-+       */
-+
-+      if (lane->priv->xtal_is_40m)
-+              ref_clk = REF_FREF_SEL_PCIE_USB3_40MHZ;
-+      else
-+              ref_clk = REF_FREF_SEL_PCIE_USB3_25MHZ;
-+
-+      data = PU_IVREF_BIT | PU_PLL_BIT | PU_RX_BIT | PU_TX_BIT |
-+             PU_TX_INTP_BIT | PU_DFE_BIT | COMPHY_MODE_PCIE | ref_clk;
-+      mask = 0xFFFF;
-+      comphy_lane_reg_set(lane, COMPHY_POWER_PLL_CTRL, data, mask);
-+
-+      /* 9. Override Speed_PLL value and use MAC PLL */
-+      comphy_lane_reg_set(lane, COMPHY_KVCO_CAL_CTRL,
-+                          SPEED_PLL_VALUE_16 | USE_MAX_PLL_RATE_BIT,
-+                          0xFFFF);
-+
-+      /* 10. Check the Polarity invert bit */
-+      data = 0x0;
-+      if (lane->invert_tx)
-+              data |= TXD_INVERT_BIT;
-+      if (lane->invert_rx)
-+              data |= RXD_INVERT_BIT;
-+      mask = TXD_INVERT_BIT | RXD_INVERT_BIT;
-+      comphy_lane_reg_set(lane, COMPHY_SYNC_PATTERN, data, mask);
-+
-+      /* 11. Release SW reset */
-+      data = MODE_CORE_CLK_FREQ_SEL | MODE_PIPE_WIDTH_32;
-+      mask = data | PIPE_SOFT_RESET | MODE_REFDIV_MASK;
-+      comphy_lane_reg_set(lane, COMPHY_PIPE_RST_CLK_CTRL, data, mask);
-+
-+      /* Wait for > 55 us to allow PCLK be enabled */
-+      udelay(PLL_SET_DELAY_US);
-+
-+      ret = comphy_lane_reg_poll(lane, COMPHY_PIPE_LANE_STAT1, TXDCLK_PCLK_EN,
-+                                 COMPHY_PLL_SLEEP, COMPHY_PLL_TIMEOUT);
-+      if (ret)
-+              dev_err(lane->dev, "Failed to lock PCIE PLL\n");
-+
-+      return ret;
-+}
-+
-+static void
-+mvebu_a3700_comphy_sata_power_off(struct mvebu_a3700_comphy_lane *lane)
-+{
-+      /* Set phy isolation mode */
-+      comphy_lane_reg_set(lane, COMPHY_ISOLATION_CTRL,
-+                          PHY_ISOLATE_MODE, PHY_ISOLATE_MODE);
-+
-+      /* Power off PLL, Tx, Rx */
-+      comphy_lane_reg_set(lane, COMPHY_POWER_PLL_CTRL,
-+                          0x0, PU_PLL_BIT | PU_RX_BIT | PU_TX_BIT);
-+}
-+
-+static void
-+mvebu_a3700_comphy_ethernet_power_off(struct mvebu_a3700_comphy_lane *lane)
-+{
-+      u32 mask, data;
-+
-+      data = PIN_RESET_CORE_BIT | PIN_RESET_COMPHY_BIT | PIN_PU_IVREF_BIT |
-+             PHY_RX_INIT_BIT;
-+      mask = data;
-+      comphy_periph_reg_set(lane, COMPHY_PHY_CFG1, data, mask);
-+}
-+
-+static void
-+mvebu_a3700_comphy_pcie_power_off(struct mvebu_a3700_comphy_lane *lane)
-+{
-+      /* Power off PLL, Tx, Rx */
-+      comphy_lane_reg_set(lane, COMPHY_POWER_PLL_CTRL,
-+                          0x0, PU_PLL_BIT | PU_RX_BIT | PU_TX_BIT);
-+}
-+
-+static int mvebu_a3700_comphy_reset(struct phy *phy)
-+{
-+      struct mvebu_a3700_comphy_lane *lane = phy_get_drvdata(phy);
-+      u16 mask, data;
-+
-+      dev_dbg(lane->dev, "resetting lane %d\n", lane->id);
-+
-+      /* COMPHY reset for internal logic */
-+      comphy_lane_reg_set(lane, COMPHY_SFT_RESET,
-+                          SFT_RST_NO_REG, SFT_RST_NO_REG);
-+
-+      /* COMPHY register reset (cleared automatically) */
-+      comphy_lane_reg_set(lane, COMPHY_SFT_RESET, SFT_RST, SFT_RST);
-+
-+      /* PIPE soft and register reset */
-+      data = PIPE_SOFT_RESET | PIPE_REG_RESET;
-+      mask = data;
-+      comphy_lane_reg_set(lane, COMPHY_PIPE_RST_CLK_CTRL, data, mask);
-+
-+      /* Release PIPE register reset */
-+      comphy_lane_reg_set(lane, COMPHY_PIPE_RST_CLK_CTRL,
-+                          0x0, PIPE_REG_RESET);
-+
-+      /* Reset SB configuration register (only for lanes 0 and 1) */
-+      if (lane->id == 0 || lane->id == 1) {
-+              u32 mask, data;
-+
-+              data = PIN_RESET_CORE_BIT | PIN_RESET_COMPHY_BIT |
-+                     PIN_PU_PLL_BIT | PIN_PU_RX_BIT | PIN_PU_TX_BIT;
-+              mask = data | PIN_PU_IVREF_BIT | PIN_TX_IDLE_BIT;
-+              comphy_periph_reg_set(lane, COMPHY_PHY_CFG1, data, mask);
-+      }
-+
-+      return 0;
-+}
-+
-+static bool mvebu_a3700_comphy_check_mode(int lane,
-                                         enum phy_mode mode,
-                                         int submode)
- {
-@@ -122,7 +1141,7 @@ static int mvebu_a3700_comphy_get_fw_mod
-       /* Unused PHY mux value is 0x0 */
-       if (mode == PHY_MODE_INVALID)
--              return -EINVAL;
-+              return false;
-       for (i = 0; i < n; i++) {
-               if (mvebu_a3700_comphy_modes[i].lane == lane &&
-@@ -132,27 +1151,30 @@ static int mvebu_a3700_comphy_get_fw_mod
-       }
-       if (i == n)
--              return -EINVAL;
-+              return false;
--      return mvebu_a3700_comphy_modes[i].fw_mode;
-+      return true;
- }
- static int mvebu_a3700_comphy_set_mode(struct phy *phy, enum phy_mode mode,
-                                      int submode)
- {
-       struct mvebu_a3700_comphy_lane *lane = phy_get_drvdata(phy);
--      int fw_mode;
--      if (submode == PHY_INTERFACE_MODE_1000BASEX)
--              submode = PHY_INTERFACE_MODE_SGMII;
--
--      fw_mode = mvebu_a3700_comphy_get_fw_mode(lane->id, mode,
--                                               submode);
--      if (fw_mode < 0) {
-+      if (!mvebu_a3700_comphy_check_mode(lane->id, mode, submode)) {
-               dev_err(lane->dev, "invalid COMPHY mode\n");
--              return fw_mode;
-+              return -EINVAL;
-       }
-+      /* Mode cannot be changed while the PHY is powered on */
-+      if (phy->power_count &&
-+          (lane->mode != mode || lane->submode != submode))
-+              return -EBUSY;
-+
-+      /* If changing mode, ensure reset is called */
-+      if (lane->mode != PHY_MODE_INVALID && lane->mode != mode)
-+              lane->needs_reset = true;
-+
-       /* Just remember the mode, ->power_on() will do the real setup */
-       lane->mode = mode;
-       lane->submode = submode;
-@@ -163,76 +1185,77 @@ static int mvebu_a3700_comphy_set_mode(s
- static int mvebu_a3700_comphy_power_on(struct phy *phy)
- {
-       struct mvebu_a3700_comphy_lane *lane = phy_get_drvdata(phy);
--      u32 fw_param;
--      int fw_mode;
--      int fw_port;
-       int ret;
--      fw_mode = mvebu_a3700_comphy_get_fw_mode(lane->id,
--                                               lane->mode, lane->submode);
--      if (fw_mode < 0) {
-+      if (!mvebu_a3700_comphy_check_mode(lane->id, lane->mode,
-+                                         lane->submode)) {
-               dev_err(lane->dev, "invalid COMPHY mode\n");
--              return fw_mode;
-+              return -EINVAL;
-+      }
-+
-+      if (lane->needs_reset) {
-+              ret = mvebu_a3700_comphy_reset(phy);
-+              if (ret)
-+                      return ret;
-+
-+              lane->needs_reset = false;
-       }
-       switch (lane->mode) {
-       case PHY_MODE_USB_HOST_SS:
-               dev_dbg(lane->dev, "set lane %d to USB3 host mode\n", lane->id);
--              fw_param = COMPHY_FW_MODE(fw_mode);
--              break;
-+              return mvebu_a3700_comphy_usb3_power_on(lane);
-       case PHY_MODE_SATA:
-               dev_dbg(lane->dev, "set lane %d to SATA mode\n", lane->id);
--              fw_param = COMPHY_FW_MODE(fw_mode);
--              break;
-+              return mvebu_a3700_comphy_sata_power_on(lane);
-       case PHY_MODE_ETHERNET:
--              fw_port = (lane->id == 0) ? 1 : 0;
--              switch (lane->submode) {
--              case PHY_INTERFACE_MODE_SGMII:
--                      dev_dbg(lane->dev, "set lane %d to SGMII mode\n",
--                              lane->id);
--                      fw_param = COMPHY_FW_NET(fw_mode, fw_port,
--                                               COMPHY_FW_SPEED_1_25G);
--                      break;
--              case PHY_INTERFACE_MODE_2500BASEX:
--                      dev_dbg(lane->dev, "set lane %d to 2500BASEX mode\n",
--                              lane->id);
--                      fw_param = COMPHY_FW_NET(fw_mode, fw_port,
--                                               COMPHY_FW_SPEED_3_125G);
--                      break;
--              default:
--                      dev_err(lane->dev, "unsupported PHY submode (%d)\n",
--                              lane->submode);
--                      return -ENOTSUPP;
--              }
--              break;
-+              dev_dbg(lane->dev, "set lane %d to Ethernet mode\n", lane->id);
-+              return mvebu_a3700_comphy_ethernet_power_on(lane);
-       case PHY_MODE_PCIE:
-               dev_dbg(lane->dev, "set lane %d to PCIe mode\n", lane->id);
--              fw_param = COMPHY_FW_PCIE(fw_mode, COMPHY_FW_SPEED_5G,
--                                        phy->attrs.bus_width);
--              break;
-+              return mvebu_a3700_comphy_pcie_power_on(lane);
-       default:
-               dev_err(lane->dev, "unsupported PHY mode (%d)\n", lane->mode);
--              return -ENOTSUPP;
-+              return -EOPNOTSUPP;
-       }
--
--      ret = mvebu_a3700_comphy_smc(COMPHY_SIP_POWER_ON, lane->id, fw_param);
--      if (ret == -EOPNOTSUPP)
--              dev_err(lane->dev,
--                      "unsupported SMC call, try updating your firmware\n");
--
--      return ret;
- }
- static int mvebu_a3700_comphy_power_off(struct phy *phy)
- {
-       struct mvebu_a3700_comphy_lane *lane = phy_get_drvdata(phy);
--      return mvebu_a3700_comphy_smc(COMPHY_SIP_POWER_OFF, lane->id, 0);
-+      switch (lane->mode) {
-+      case PHY_MODE_USB_HOST_SS:
-+              /*
-+               * The USB3 MAC sets the USB3 PHY to low state, so we do not
-+               * need to power off USB3 PHY again.
-+               */
-+              break;
-+
-+      case PHY_MODE_SATA:
-+              mvebu_a3700_comphy_sata_power_off(lane);
-+              break;
-+
-+      case PHY_MODE_ETHERNET:
-+              mvebu_a3700_comphy_ethernet_power_off(lane);
-+              break;
-+
-+      case PHY_MODE_PCIE:
-+              mvebu_a3700_comphy_pcie_power_off(lane);
-+              break;
-+
-+      default:
-+              dev_err(lane->dev, "invalid COMPHY mode\n");
-+              return -EINVAL;
-+      }
-+
-+      return 0;
- }
- static const struct phy_ops mvebu_a3700_comphy_ops = {
-       .power_on       = mvebu_a3700_comphy_power_on,
-       .power_off      = mvebu_a3700_comphy_power_off,
-+      .reset          = mvebu_a3700_comphy_reset,
-       .set_mode       = mvebu_a3700_comphy_set_mode,
-       .owner          = THIS_MODULE,
- };
-@@ -256,13 +1279,75 @@ static struct phy *mvebu_a3700_comphy_xl
-               return ERR_PTR(-EINVAL);
-       }
-+      lane->invert_tx = args->args[1] & BIT(0);
-+      lane->invert_rx = args->args[1] & BIT(1);
-+
-       return phy;
- }
- static int mvebu_a3700_comphy_probe(struct platform_device *pdev)
- {
-+      struct mvebu_a3700_comphy_priv *priv;
-       struct phy_provider *provider;
-       struct device_node *child;
-+      struct resource *res;
-+      struct clk *clk;
-+      int ret;
-+
-+      priv = devm_kzalloc(&pdev->dev, sizeof(*priv), GFP_KERNEL);
-+      if (!priv)
-+              return -ENOMEM;
-+
-+      spin_lock_init(&priv->lock);
-+
-+      res = platform_get_resource_byname(pdev, IORESOURCE_MEM, "comphy");
-+      priv->comphy_regs = devm_ioremap_resource(&pdev->dev, res);
-+      if (IS_ERR(priv->comphy_regs))
-+              return PTR_ERR(priv->comphy_regs);
-+
-+      res = platform_get_resource_byname(pdev, IORESOURCE_MEM,
-+                                         "lane1_pcie_gbe");
-+      priv->lane1_phy_regs = devm_ioremap_resource(&pdev->dev, res);
-+      if (IS_ERR(priv->lane1_phy_regs))
-+              return PTR_ERR(priv->lane1_phy_regs);
-+
-+      res = platform_get_resource_byname(pdev, IORESOURCE_MEM,
-+                                         "lane0_usb3_gbe");
-+      priv->lane0_phy_regs = devm_ioremap_resource(&pdev->dev, res);
-+      if (IS_ERR(priv->lane0_phy_regs))
-+              return PTR_ERR(priv->lane0_phy_regs);
-+
-+      res = platform_get_resource_byname(pdev, IORESOURCE_MEM,
-+                                         "lane2_sata_usb3");
-+      priv->lane2_phy_indirect = devm_ioremap_resource(&pdev->dev, res);
-+      if (IS_ERR(priv->lane2_phy_indirect))
-+              return PTR_ERR(priv->lane2_phy_indirect);
-+
-+      /*
-+       * Driver needs to know if reference xtal clock is 40MHz or 25MHz.
-+       * Old DT bindings do not have xtal clk present. So do not fail here
-+       * and expects that default 25MHz reference clock is used.
-+       */
-+      clk = clk_get(&pdev->dev, "xtal");
-+      if (IS_ERR(clk)) {
-+              if (PTR_ERR(clk) == -EPROBE_DEFER)
-+                      return -EPROBE_DEFER;
-+              dev_warn(&pdev->dev, "missing 'xtal' clk (%ld)\n",
-+                       PTR_ERR(clk));
-+      } else {
-+              ret = clk_prepare_enable(clk);
-+              if (ret) {
-+                      dev_warn(&pdev->dev, "enabling xtal clk failed (%d)\n",
-+                               ret);
-+              } else {
-+                      if (clk_get_rate(clk) == 40000000)
-+                              priv->xtal_is_40m = true;
-+                      clk_disable_unprepare(clk);
-+              }
-+              clk_put(clk);
-+      }
-+
-+      dev_set_drvdata(&pdev->dev, priv);
-       for_each_available_child_of_node(pdev->dev.of_node, child) {
-               struct mvebu_a3700_comphy_lane *lane;
-@@ -277,7 +1362,7 @@ static int mvebu_a3700_comphy_probe(stru
-                       continue;
-               }
--              if (lane_id >= MVEBU_A3700_COMPHY_LANES) {
-+              if (lane_id >= 3) {
-                       dev_err(&pdev->dev, "invalid 'reg' property\n");
-                       continue;
-               }
-@@ -295,15 +1380,26 @@ static int mvebu_a3700_comphy_probe(stru
-                       return PTR_ERR(phy);
-               }
-+              lane->priv = priv;
-               lane->dev = &pdev->dev;
-               lane->mode = PHY_MODE_INVALID;
-               lane->submode = PHY_INTERFACE_MODE_NA;
-               lane->id = lane_id;
-+              lane->invert_tx = false;
-+              lane->invert_rx = false;
-               phy_set_drvdata(phy, lane);
-+
-+              /*
-+               * To avoid relying on the bootloader/firmware configuration,
-+               * power off all comphys.
-+               */
-+              mvebu_a3700_comphy_reset(phy);
-+              lane->needs_reset = false;
-       }
-       provider = devm_of_phy_provider_register(&pdev->dev,
-                                                mvebu_a3700_comphy_xlate);
-+
-       return PTR_ERR_OR_ZERO(provider);
- }
-@@ -323,5 +1419,7 @@ static struct platform_driver mvebu_a370
- module_platform_driver(mvebu_a3700_comphy_driver);
- MODULE_AUTHOR("Miquèl Raynal <[email protected]>");
-+MODULE_AUTHOR("Pali Rohár <[email protected]>");
-+MODULE_AUTHOR("Marek Behún <[email protected]>");
- MODULE_DESCRIPTION("Common PHY driver for A3700");
- MODULE_LICENSE("GPL v2");
diff --git a/target/linux/generic/backport-5.15/345-v5.17-arm64-dts-marvell-armada-37xx-Add-xtal-clock-to-comp.patch b/target/linux/generic/backport-5.15/345-v5.17-arm64-dts-marvell-armada-37xx-Add-xtal-clock-to-comp.patch
deleted file mode 100644 (file)
index 03b6a57..0000000
+++ /dev/null
@@ -1,32 +0,0 @@
-From 73a78b6130d9e13daca22b86ad52f063b9403e03 Mon Sep 17 00:00:00 2001
-From: =?UTF-8?q?Pali=20Roh=C3=A1r?= <[email protected]>
-Date: Wed, 8 Dec 2021 03:40:35 +0100
-Subject: [PATCH 1/1] arm64: dts: marvell: armada-37xx: Add xtal clock to
- comphy node
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-Kernel driver phy-mvebu-a3700-comphy.c needs to know the rate of the
-reference xtal clock. So add missing xtal clock source into comphy device
-tree node. If the property is not present, the driver defaults to 25 MHz
-xtal rate (which, as far as we know, is used by all the existing boards).
-
-Signed-off-by: Pali Rohár <[email protected]>
-Signed-off-by: Marek Behún <[email protected]>
-Signed-off-by: Gregory CLEMENT <[email protected]>
----
- arch/arm64/boot/dts/marvell/armada-37xx.dtsi | 2 ++
- 1 file changed, 2 insertions(+)
-
---- a/arch/arm64/boot/dts/marvell/armada-37xx.dtsi
-+++ b/arch/arm64/boot/dts/marvell/armada-37xx.dtsi
-@@ -265,6 +265,8 @@
-                                           "lane2_sata_usb3";
-                               #address-cells = <1>;
-                               #size-cells = <0>;
-+                              clocks = <&xtalclk>;
-+                              clock-names = "xtal";
-                               comphy0: phy@0 {
-                                       reg = <0>;
diff --git a/target/linux/generic/backport-5.15/346-v5.18-01-Revert-ata-ahci-mvebu-Make-SATA-PHY-optional-for-Arm.patch b/target/linux/generic/backport-5.15/346-v5.18-01-Revert-ata-ahci-mvebu-Make-SATA-PHY-optional-for-Arm.patch
deleted file mode 100644 (file)
index 35bc19c..0000000
+++ /dev/null
@@ -1,64 +0,0 @@
-From ee995101fde67f85a3cd4c74f4f92fc4592e726b Mon Sep 17 00:00:00 2001
-From: =?UTF-8?q?Pali=20Roh=C3=A1r?= <[email protected]>
-Date: Thu, 3 Feb 2022 22:44:42 +0100
-Subject: [PATCH 1/3] Revert "ata: ahci: mvebu: Make SATA PHY optional for
- Armada 3720"
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-This reverts commit 45aefe3d2251e4e229d7662052739f96ad1d08d9.
-
-Armada 3720 PHY driver (phy-mvebu-a3700-comphy.c) does not return
--EOPNOTSUPP from phy_power_on() callback anymore.
-
-So remove AHCI_HFLAG_IGN_NOTSUPP_POWER_ON flag from Armada 3720 plat data.
-
-AHCI_HFLAG_IGN_NOTSUPP_POWER_ON is not used by any other ahci driver, so
-remove this flag completely.
-
-Signed-off-by: Pali Rohár <[email protected]>
-Signed-off-by: Marek Behún <[email protected]>
-Acked-by: Miquel Raynal <[email protected]>
-Acked-by: Damien Le Moal <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Vinod Koul <[email protected]>
----
- drivers/ata/ahci.h             | 2 --
- drivers/ata/ahci_mvebu.c       | 2 +-
- drivers/ata/libahci_platform.c | 2 +-
- 3 files changed, 2 insertions(+), 4 deletions(-)
-
---- a/drivers/ata/ahci.h
-+++ b/drivers/ata/ahci.h
-@@ -240,8 +240,6 @@ enum {
-                                                     as default lpm_policy */
-       AHCI_HFLAG_SUSPEND_PHYS         = BIT(26), /* handle PHYs during
-                                                     suspend/resume */
--      AHCI_HFLAG_IGN_NOTSUPP_POWER_ON = BIT(27), /* ignore -EOPNOTSUPP
--                                                    from phy_power_on() */
-       AHCI_HFLAG_NO_SXS               = BIT(28), /* SXS not supported */
-       AHCI_HFLAG_43BIT_ONLY           = BIT(29), /* 43bit DMA addr limit */
---- a/drivers/ata/ahci_mvebu.c
-+++ b/drivers/ata/ahci_mvebu.c
-@@ -227,7 +227,7 @@ static const struct ahci_mvebu_plat_data
- static const struct ahci_mvebu_plat_data ahci_mvebu_armada_3700_plat_data = {
-       .plat_config = ahci_mvebu_armada_3700_config,
--      .flags = AHCI_HFLAG_SUSPEND_PHYS | AHCI_HFLAG_IGN_NOTSUPP_POWER_ON,
-+      .flags = AHCI_HFLAG_SUSPEND_PHYS,
- };
- static const struct of_device_id ahci_mvebu_of_match[] = {
---- a/drivers/ata/libahci_platform.c
-+++ b/drivers/ata/libahci_platform.c
-@@ -59,7 +59,7 @@ int ahci_platform_enable_phys(struct ahc
-               }
-               rc = phy_power_on(hpriv->phys[i]);
--              if (rc && !(rc == -EOPNOTSUPP && (hpriv->flags & AHCI_HFLAG_IGN_NOTSUPP_POWER_ON))) {
-+              if (rc) {
-                       phy_exit(hpriv->phys[i]);
-                       goto disable_phys;
-               }
diff --git a/target/linux/generic/backport-5.15/346-v5.18-02-Revert-usb-host-xhci-mvebu-make-USB-3.0-PHY-optional.patch b/target/linux/generic/backport-5.15/346-v5.18-02-Revert-usb-host-xhci-mvebu-make-USB-3.0-PHY-optional.patch
deleted file mode 100644 (file)
index 0c28221..0000000
+++ /dev/null
@@ -1,166 +0,0 @@
-From 8e10548f7f4814e530857d2049d6af6bc78add53 Mon Sep 17 00:00:00 2001
-From: =?UTF-8?q?Pali=20Roh=C3=A1r?= <[email protected]>
-Date: Thu, 3 Feb 2022 22:44:43 +0100
-Subject: [PATCH 2/3] Revert "usb: host: xhci: mvebu: make USB 3.0 PHY optional
- for Armada 3720"
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-This reverts commit 3241929b67d28c83945d3191c6816a3271fd6b85.
-
-Armada 3720 phy driver (phy-mvebu-a3700-comphy.c) does not return
--EOPNOTSUPP from phy_power_on() callback anymore.
-
-So remove XHCI_SKIP_PHY_INIT flag from xhci_mvebu_a3700_plat_setup() and
-then also whole xhci_mvebu_a3700_plat_setup() function which is there just
-to handle -EOPNOTSUPP for XHCI_SKIP_PHY_INIT.
-
-xhci plat_setup callback is not used by any other xhci plat driver, so
-remove this callback completely.
-
-Signed-off-by: Pali Rohár <[email protected]>
-Signed-off-by: Marek Behún <[email protected]>
-Acked-by: Miquel Raynal <[email protected]>
-Acked-by: Greg Kroah-Hartman <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Vinod Koul <[email protected]>
----
- drivers/usb/host/xhci-mvebu.c | 42 -----------------------------------
- drivers/usb/host/xhci-mvebu.h |  6 -----
- drivers/usb/host/xhci-plat.c  | 20 +----------------
- drivers/usb/host/xhci-plat.h  |  1 -
- 4 files changed, 1 insertion(+), 68 deletions(-)
-
---- a/drivers/usb/host/xhci-mvebu.c
-+++ b/drivers/usb/host/xhci-mvebu.c
-@@ -8,7 +8,6 @@
- #include <linux/mbus.h>
- #include <linux/of.h>
- #include <linux/platform_device.h>
--#include <linux/phy/phy.h>
- #include <linux/usb.h>
- #include <linux/usb/hcd.h>
-@@ -74,47 +73,6 @@ int xhci_mvebu_mbus_init_quirk(struct us
-       return 0;
- }
--
--int xhci_mvebu_a3700_plat_setup(struct usb_hcd *hcd)
--{
--      struct xhci_hcd *xhci = hcd_to_xhci(hcd);
--      struct device *dev = hcd->self.controller;
--      struct phy *phy;
--      int ret;
--
--      /* Old bindings miss the PHY handle */
--      phy = of_phy_get(dev->of_node, "usb3-phy");
--      if (IS_ERR(phy) && PTR_ERR(phy) == -EPROBE_DEFER)
--              return -EPROBE_DEFER;
--      else if (IS_ERR(phy))
--              goto phy_out;
--
--      ret = phy_init(phy);
--      if (ret)
--              goto phy_put;
--
--      ret = phy_set_mode(phy, PHY_MODE_USB_HOST_SS);
--      if (ret)
--              goto phy_exit;
--
--      ret = phy_power_on(phy);
--      if (ret == -EOPNOTSUPP) {
--              /* Skip initializatin of XHCI PHY when it is unsupported by firmware */
--              dev_warn(dev, "PHY unsupported by firmware\n");
--              xhci->quirks |= XHCI_SKIP_PHY_INIT;
--      }
--      if (ret)
--              goto phy_exit;
--
--      phy_power_off(phy);
--phy_exit:
--      phy_exit(phy);
--phy_put:
--      of_phy_put(phy);
--phy_out:
--
--      return 0;
--}
- int xhci_mvebu_a3700_init_quirk(struct usb_hcd *hcd)
- {
---- a/drivers/usb/host/xhci-mvebu.h
-+++ b/drivers/usb/host/xhci-mvebu.h
-@@ -12,18 +12,12 @@ struct usb_hcd;
- #if IS_ENABLED(CONFIG_USB_XHCI_MVEBU)
- int xhci_mvebu_mbus_init_quirk(struct usb_hcd *hcd);
--int xhci_mvebu_a3700_plat_setup(struct usb_hcd *hcd);
- int xhci_mvebu_a3700_init_quirk(struct usb_hcd *hcd);
- #else
- static inline int xhci_mvebu_mbus_init_quirk(struct usb_hcd *hcd)
- {
-       return 0;
- }
--
--static inline int xhci_mvebu_a3700_plat_setup(struct usb_hcd *hcd)
--{
--      return 0;
--}
- static inline int xhci_mvebu_a3700_init_quirk(struct usb_hcd *hcd)
- {
---- a/drivers/usb/host/xhci-plat.c
-+++ b/drivers/usb/host/xhci-plat.c
-@@ -44,16 +44,6 @@ static void xhci_priv_plat_start(struct
-               priv->plat_start(hcd);
- }
--static int xhci_priv_plat_setup(struct usb_hcd *hcd)
--{
--      struct xhci_plat_priv *priv = hcd_to_xhci_priv(hcd);
--
--      if (!priv->plat_setup)
--              return 0;
--
--      return priv->plat_setup(hcd);
--}
--
- static int xhci_priv_init_quirk(struct usb_hcd *hcd)
- {
-       struct xhci_plat_priv *priv = hcd_to_xhci_priv(hcd);
-@@ -121,7 +111,6 @@ static const struct xhci_plat_priv xhci_
- };
- static const struct xhci_plat_priv xhci_plat_marvell_armada3700 = {
--      .plat_setup = xhci_mvebu_a3700_plat_setup,
-       .init_quirk = xhci_mvebu_a3700_init_quirk,
- };
-@@ -344,14 +333,7 @@ static int xhci_plat_probe(struct platfo
-       hcd->tpl_support = of_usb_host_tpl_support(sysdev->of_node);
-       xhci->shared_hcd->tpl_support = hcd->tpl_support;
--
--      if (priv) {
--              ret = xhci_priv_plat_setup(hcd);
--              if (ret)
--                      goto disable_usb_phy;
--      }
--
--      if ((xhci->quirks & XHCI_SKIP_PHY_INIT) || (priv && (priv->quirks & XHCI_SKIP_PHY_INIT)))
-+      if (priv && (priv->quirks & XHCI_SKIP_PHY_INIT))
-               hcd->skip_phy_initialization = 1;
-       if (priv && (priv->quirks & XHCI_SG_TRB_CACHE_SIZE_QUIRK))
---- a/drivers/usb/host/xhci-plat.h
-+++ b/drivers/usb/host/xhci-plat.h
-@@ -15,7 +15,6 @@ struct usb_hcd;
- struct xhci_plat_priv {
-       const char *firmware_name;
-       unsigned long long quirks;
--      int (*plat_setup)(struct usb_hcd *);
-       void (*plat_start)(struct usb_hcd *);
-       int (*init_quirk)(struct usb_hcd *);
-       int (*suspend_quirk)(struct usb_hcd *);
diff --git a/target/linux/generic/backport-5.15/346-v5.18-03-Revert-PCI-aardvark-Fix-initialization-with-old-Marv.patch b/target/linux/generic/backport-5.15/346-v5.18-03-Revert-PCI-aardvark-Fix-initialization-with-old-Marv.patch
deleted file mode 100644 (file)
index fcfb02d..0000000
+++ /dev/null
@@ -1,39 +0,0 @@
-From 9a4556dad7bd0a6b8339cb72e169f5c76f2af6f1 Mon Sep 17 00:00:00 2001
-From: =?UTF-8?q?Pali=20Roh=C3=A1r?= <[email protected]>
-Date: Thu, 3 Feb 2022 22:44:44 +0100
-Subject: [PATCH 3/3] Revert "PCI: aardvark: Fix initialization with old
- Marvell's Arm Trusted Firmware"
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-This reverts commit b0c6ae0f8948a2be6bf4e8b4bbab9ca1343289b6.
-
-Armada 3720 phy driver (phy-mvebu-a3700-comphy.c) does not return
--EOPNOTSUPP from phy_power_on() callback anymore.
-
-So remove dead code which handles -EOPNOTSUPP return value.
-
-Signed-off-by: Pali Rohár <[email protected]>
-Signed-off-by: Marek Behún <[email protected]>
-Acked-by: Miquel Raynal <[email protected]>
-Acked-by: Lorenzo Pieralisi <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Vinod Koul <[email protected]>
----
- drivers/pci/controller/pci-aardvark.c | 4 +---
- 1 file changed, 1 insertion(+), 3 deletions(-)
-
---- a/drivers/pci/controller/pci-aardvark.c
-+++ b/drivers/pci/controller/pci-aardvark.c
-@@ -1642,9 +1642,7 @@ static int advk_pcie_enable_phy(struct a
-       }
-       ret = phy_power_on(pcie->phy);
--      if (ret == -EOPNOTSUPP) {
--              dev_warn(&pcie->pdev->dev, "PHY unsupported by firmware\n");
--      } else if (ret) {
-+      if (ret) {
-               phy_exit(pcie->phy);
-               return ret;
-       }
diff --git a/target/linux/generic/backport-5.15/347-v6.0-phy-marvell-phy-mvebu-a3700-comphy-Remove-broken-res.patch b/target/linux/generic/backport-5.15/347-v6.0-phy-marvell-phy-mvebu-a3700-comphy-Remove-broken-res.patch
deleted file mode 100644 (file)
index a2c897b..0000000
+++ /dev/null
@@ -1,194 +0,0 @@
-From 0a6fc70d76bddf98278af2ac000379c82aec8f11 Mon Sep 17 00:00:00 2001
-From: =?UTF-8?q?Pali=20Roh=C3=A1r?= <[email protected]>
-Date: Mon, 29 Aug 2022 10:30:46 +0200
-Subject: [PATCH] phy: marvell: phy-mvebu-a3700-comphy: Remove broken reset
- support
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-Reset support for SATA PHY is somehow broken and after calling it, kernel
-is not able to detect and initialize SATA disk Samsung SSD 850 EMT0 [1].
-
-Reset support was introduced in commit 934337080c6c ("phy: marvell:
-phy-mvebu-a3700-comphy: Add native kernel implementation") as part of
-complete rewrite of this driver. v1 patch series of that commit [2] did
-not contain reset support and was tested that is working fine with
-Ethernet, SATA and USB PHYs without issues too.
-
-So for now remove broken reset support and change implementation of
-power_off callback to power off all functions on specified lane (and not
-only selected function) because during startup kernel does not know which
-function was selected and configured by bootloader. Same logic was used
-also in v1 patch series of that commit.
-
-This change fixes issues with initialization of SATA disk Samsung SSD 850
-and disk is working again, like before mentioned commit.
-
-Once problem with PHY reset callback is solved its functionality could be
-re-introduced. But for now it is unknown why it does not work.
-
-[1] - https://lore.kernel.org/r/20220531124159.3e4lgn2v462irbtz@shindev/
-[2] - https://lore.kernel.org/r/[email protected]/
-
-Reported-by: Shinichiro Kawasaki <[email protected]>
-Fixes: 934337080c6c ("phy: marvell: phy-mvebu-a3700-comphy: Add native kernel implementation")
-Cc: [email protected] # v5.18+
-Signed-off-by: Pali Rohár <[email protected]>
-Tested-by: Shinichiro Kawasaki <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Vinod Koul <[email protected]>
----
- drivers/phy/marvell/phy-mvebu-a3700-comphy.c | 87 ++++----------------
- 1 file changed, 17 insertions(+), 70 deletions(-)
-
---- a/drivers/phy/marvell/phy-mvebu-a3700-comphy.c
-+++ b/drivers/phy/marvell/phy-mvebu-a3700-comphy.c
-@@ -274,7 +274,6 @@ struct mvebu_a3700_comphy_lane {
-       int submode;
-       bool invert_tx;
-       bool invert_rx;
--      bool needs_reset;
- };
- struct gbe_phy_init_data_fix {
-@@ -1097,40 +1096,12 @@ mvebu_a3700_comphy_pcie_power_off(struct
-                           0x0, PU_PLL_BIT | PU_RX_BIT | PU_TX_BIT);
- }
--static int mvebu_a3700_comphy_reset(struct phy *phy)
-+static void mvebu_a3700_comphy_usb3_power_off(struct mvebu_a3700_comphy_lane *lane)
- {
--      struct mvebu_a3700_comphy_lane *lane = phy_get_drvdata(phy);
--      u16 mask, data;
--
--      dev_dbg(lane->dev, "resetting lane %d\n", lane->id);
--
--      /* COMPHY reset for internal logic */
--      comphy_lane_reg_set(lane, COMPHY_SFT_RESET,
--                          SFT_RST_NO_REG, SFT_RST_NO_REG);
--
--      /* COMPHY register reset (cleared automatically) */
--      comphy_lane_reg_set(lane, COMPHY_SFT_RESET, SFT_RST, SFT_RST);
--
--      /* PIPE soft and register reset */
--      data = PIPE_SOFT_RESET | PIPE_REG_RESET;
--      mask = data;
--      comphy_lane_reg_set(lane, COMPHY_PIPE_RST_CLK_CTRL, data, mask);
--
--      /* Release PIPE register reset */
--      comphy_lane_reg_set(lane, COMPHY_PIPE_RST_CLK_CTRL,
--                          0x0, PIPE_REG_RESET);
--
--      /* Reset SB configuration register (only for lanes 0 and 1) */
--      if (lane->id == 0 || lane->id == 1) {
--              u32 mask, data;
--
--              data = PIN_RESET_CORE_BIT | PIN_RESET_COMPHY_BIT |
--                     PIN_PU_PLL_BIT | PIN_PU_RX_BIT | PIN_PU_TX_BIT;
--              mask = data | PIN_PU_IVREF_BIT | PIN_TX_IDLE_BIT;
--              comphy_periph_reg_set(lane, COMPHY_PHY_CFG1, data, mask);
--      }
--
--      return 0;
-+      /*
-+       * The USB3 MAC sets the USB3 PHY to low state, so we do not
-+       * need to power off USB3 PHY again.
-+       */
- }
- static bool mvebu_a3700_comphy_check_mode(int lane,
-@@ -1171,10 +1142,6 @@ static int mvebu_a3700_comphy_set_mode(s
-           (lane->mode != mode || lane->submode != submode))
-               return -EBUSY;
--      /* If changing mode, ensure reset is called */
--      if (lane->mode != PHY_MODE_INVALID && lane->mode != mode)
--              lane->needs_reset = true;
--
-       /* Just remember the mode, ->power_on() will do the real setup */
-       lane->mode = mode;
-       lane->submode = submode;
-@@ -1185,7 +1152,6 @@ static int mvebu_a3700_comphy_set_mode(s
- static int mvebu_a3700_comphy_power_on(struct phy *phy)
- {
-       struct mvebu_a3700_comphy_lane *lane = phy_get_drvdata(phy);
--      int ret;
-       if (!mvebu_a3700_comphy_check_mode(lane->id, lane->mode,
-                                          lane->submode)) {
-@@ -1193,14 +1159,6 @@ static int mvebu_a3700_comphy_power_on(s
-               return -EINVAL;
-       }
--      if (lane->needs_reset) {
--              ret = mvebu_a3700_comphy_reset(phy);
--              if (ret)
--                      return ret;
--
--              lane->needs_reset = false;
--      }
--
-       switch (lane->mode) {
-       case PHY_MODE_USB_HOST_SS:
-               dev_dbg(lane->dev, "set lane %d to USB3 host mode\n", lane->id);
-@@ -1224,38 +1182,28 @@ static int mvebu_a3700_comphy_power_off(
- {
-       struct mvebu_a3700_comphy_lane *lane = phy_get_drvdata(phy);
--      switch (lane->mode) {
--      case PHY_MODE_USB_HOST_SS:
--              /*
--               * The USB3 MAC sets the USB3 PHY to low state, so we do not
--               * need to power off USB3 PHY again.
--               */
--              break;
--
--      case PHY_MODE_SATA:
--              mvebu_a3700_comphy_sata_power_off(lane);
--              break;
--
--      case PHY_MODE_ETHERNET:
-+      switch (lane->id) {
-+      case 0:
-+              mvebu_a3700_comphy_usb3_power_off(lane);
-               mvebu_a3700_comphy_ethernet_power_off(lane);
--              break;
--
--      case PHY_MODE_PCIE:
-+              return 0;
-+      case 1:
-               mvebu_a3700_comphy_pcie_power_off(lane);
--              break;
--
-+              mvebu_a3700_comphy_ethernet_power_off(lane);
-+              return 0;
-+      case 2:
-+              mvebu_a3700_comphy_usb3_power_off(lane);
-+              mvebu_a3700_comphy_sata_power_off(lane);
-+              return 0;
-       default:
-               dev_err(lane->dev, "invalid COMPHY mode\n");
-               return -EINVAL;
-       }
--
--      return 0;
- }
- static const struct phy_ops mvebu_a3700_comphy_ops = {
-       .power_on       = mvebu_a3700_comphy_power_on,
-       .power_off      = mvebu_a3700_comphy_power_off,
--      .reset          = mvebu_a3700_comphy_reset,
-       .set_mode       = mvebu_a3700_comphy_set_mode,
-       .owner          = THIS_MODULE,
- };
-@@ -1393,8 +1341,7 @@ static int mvebu_a3700_comphy_probe(stru
-                * To avoid relying on the bootloader/firmware configuration,
-                * power off all comphys.
-                */
--              mvebu_a3700_comphy_reset(phy);
--              lane->needs_reset = false;
-+              mvebu_a3700_comphy_power_off(phy);
-       }
-       provider = devm_of_phy_provider_register(&pdev->dev,
diff --git a/target/linux/generic/backport-5.15/350-v5.18-regmap-add-configurable-downshift-for-addresses.patch b/target/linux/generic/backport-5.15/350-v5.18-regmap-add-configurable-downshift-for-addresses.patch
deleted file mode 100644 (file)
index 175df15..0000000
+++ /dev/null
@@ -1,90 +0,0 @@
-From 86fc59ef818beb0e1945d17f8e734898baba7e4e Mon Sep 17 00:00:00 2001
-From: Colin Foster <[email protected]>
-Date: Sun, 13 Mar 2022 15:45:23 -0700
-Subject: [PATCH 1/2] regmap: add configurable downshift for addresses
-
-Add an additional reg_downshift to be applied to register addresses before
-any register accesses. An example of a device that uses this is a VSC7514
-chip, which require each register address to be downshifted by two if the
-access is performed over a SPI bus.
-
-Signed-off-by: Colin Foster <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Mark Brown <[email protected]>
----
- drivers/base/regmap/internal.h | 1 +
- drivers/base/regmap/regmap.c   | 5 +++++
- include/linux/regmap.h         | 3 +++
- 3 files changed, 9 insertions(+)
-
---- a/drivers/base/regmap/internal.h
-+++ b/drivers/base/regmap/internal.h
-@@ -31,6 +31,7 @@ struct regmap_format {
-       size_t buf_size;
-       size_t reg_bytes;
-       size_t pad_bytes;
-+      size_t reg_downshift;
-       size_t val_bytes;
-       void (*format_write)(struct regmap *map,
-                            unsigned int reg, unsigned int val);
---- a/drivers/base/regmap/regmap.c
-+++ b/drivers/base/regmap/regmap.c
-@@ -823,6 +823,7 @@ struct regmap *__regmap_init(struct devi
-       map->format.reg_bytes = DIV_ROUND_UP(config->reg_bits, 8);
-       map->format.pad_bytes = config->pad_bits / 8;
-+      map->format.reg_downshift = config->reg_downshift;
-       map->format.val_bytes = DIV_ROUND_UP(config->val_bits, 8);
-       map->format.buf_size = DIV_ROUND_UP(config->reg_bits +
-                       config->val_bits + config->pad_bits, 8);
-@@ -1750,6 +1751,7 @@ static int _regmap_raw_write_impl(struct
-                       return ret;
-       }
-+      reg >>= map->format.reg_downshift;
-       map->format.format_reg(map->work_buf, reg, map->reg_shift);
-       regmap_set_work_buf_flag_mask(map, map->format.reg_bytes,
-                                     map->write_flag_mask);
-@@ -1920,6 +1922,7 @@ static int _regmap_bus_formatted_write(v
-                       return ret;
-       }
-+      reg >>= map->format.reg_downshift;
-       map->format.format_write(map, reg, val);
-       trace_regmap_hw_write_start(map, reg, 1);
-@@ -2360,6 +2363,7 @@ static int _regmap_raw_multi_reg_write(s
-               unsigned int reg = regs[i].reg;
-               unsigned int val = regs[i].def;
-               trace_regmap_hw_write_start(map, reg, 1);
-+              reg >>= map->format.reg_downshift;
-               map->format.format_reg(u8, reg, map->reg_shift);
-               u8 += reg_bytes + pad_bytes;
-               map->format.format_val(u8, val, 0);
-@@ -2685,6 +2689,7 @@ static int _regmap_raw_read(struct regma
-                       return ret;
-       }
-+      reg >>= map->format.reg_downshift;
-       map->format.format_reg(map->work_buf, reg, map->reg_shift);
-       regmap_set_work_buf_flag_mask(map, map->format.reg_bytes,
-                                     map->read_flag_mask);
---- a/include/linux/regmap.h
-+++ b/include/linux/regmap.h
-@@ -237,6 +237,8 @@ typedef void (*regmap_unlock)(void *);
-  * @reg_stride: The register address stride. Valid register addresses are a
-  *              multiple of this value. If set to 0, a value of 1 will be
-  *              used.
-+ * @reg_downshift: The number of bits to downshift the register before
-+ *               performing any operations.
-  * @pad_bits: Number of bits of padding between register and value.
-  * @val_bits: Number of bits in a register value, mandatory.
-  *
-@@ -366,6 +368,7 @@ struct regmap_config {
-       int reg_bits;
-       int reg_stride;
-+      int reg_downshift;
-       int pad_bits;
-       int val_bits;
diff --git a/target/linux/generic/backport-5.15/351-v5.18-regmap-allow-a-defined-reg_base-to-be-added-to-every.patch b/target/linux/generic/backport-5.15/351-v5.18-regmap-allow-a-defined-reg_base-to-be-added-to-every.patch
deleted file mode 100644 (file)
index df716c4..0000000
+++ /dev/null
@@ -1,95 +0,0 @@
-From 0074f3f2b1e43d3cedd97e47fb6980db6d2ba79e Mon Sep 17 00:00:00 2001
-From: Colin Foster <[email protected]>
-Date: Sun, 13 Mar 2022 15:45:24 -0700
-Subject: [PATCH 2/2] regmap: allow a defined reg_base to be added to every
- address
-
-There's an inconsistency that arises when a register set can be accessed
-internally via MMIO, or externally via SPI. The VSC7514 chip allows both
-modes of operation. When internally accessed, the system utilizes __iomem,
-devm_ioremap_resource, and devm_regmap_init_mmio.
-
-For SPI it isn't possible to utilize memory-mapped IO. To properly operate,
-the resource base must be added to the register before every operation.
-
-Signed-off-by: Colin Foster <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Mark Brown <[email protected]>
----
- drivers/base/regmap/internal.h | 1 +
- drivers/base/regmap/regmap.c   | 6 ++++++
- include/linux/regmap.h         | 3 +++
- 3 files changed, 10 insertions(+)
-
---- a/drivers/base/regmap/internal.h
-+++ b/drivers/base/regmap/internal.h
-@@ -63,6 +63,7 @@ struct regmap {
-       regmap_unlock unlock;
-       void *lock_arg; /* This is passed to lock/unlock functions */
-       gfp_t alloc_flags;
-+      unsigned int reg_base;
-       struct device *dev; /* Device we do I/O on */
-       void *work_buf;     /* Scratch buffer used to format I/O */
---- a/drivers/base/regmap/regmap.c
-+++ b/drivers/base/regmap/regmap.c
-@@ -821,6 +821,8 @@ struct regmap *__regmap_init(struct devi
-       else
-               map->alloc_flags = GFP_KERNEL;
-+      map->reg_base = config->reg_base;
-+
-       map->format.reg_bytes = DIV_ROUND_UP(config->reg_bits, 8);
-       map->format.pad_bytes = config->pad_bits / 8;
-       map->format.reg_downshift = config->reg_downshift;
-@@ -1751,6 +1753,7 @@ static int _regmap_raw_write_impl(struct
-                       return ret;
-       }
-+      reg += map->reg_base;
-       reg >>= map->format.reg_downshift;
-       map->format.format_reg(map->work_buf, reg, map->reg_shift);
-       regmap_set_work_buf_flag_mask(map, map->format.reg_bytes,
-@@ -1922,6 +1925,7 @@ static int _regmap_bus_formatted_write(v
-                       return ret;
-       }
-+      reg += map->reg_base;
-       reg >>= map->format.reg_downshift;
-       map->format.format_write(map, reg, val);
-@@ -2363,6 +2367,7 @@ static int _regmap_raw_multi_reg_write(s
-               unsigned int reg = regs[i].reg;
-               unsigned int val = regs[i].def;
-               trace_regmap_hw_write_start(map, reg, 1);
-+              reg += map->reg_base;
-               reg >>= map->format.reg_downshift;
-               map->format.format_reg(u8, reg, map->reg_shift);
-               u8 += reg_bytes + pad_bytes;
-@@ -2689,6 +2694,7 @@ static int _regmap_raw_read(struct regma
-                       return ret;
-       }
-+      reg += map->reg_base;
-       reg >>= map->format.reg_downshift;
-       map->format.format_reg(map->work_buf, reg, map->reg_shift);
-       regmap_set_work_buf_flag_mask(map, map->format.reg_bytes,
---- a/include/linux/regmap.h
-+++ b/include/linux/regmap.h
-@@ -239,6 +239,8 @@ typedef void (*regmap_unlock)(void *);
-  *              used.
-  * @reg_downshift: The number of bits to downshift the register before
-  *               performing any operations.
-+ * @reg_base: Value to be added to every register address before performing any
-+ *          operation.
-  * @pad_bits: Number of bits of padding between register and value.
-  * @val_bits: Number of bits in a register value, mandatory.
-  *
-@@ -369,6 +371,7 @@ struct regmap_config {
-       int reg_bits;
-       int reg_stride;
-       int reg_downshift;
-+      unsigned int reg_base;
-       int pad_bits;
-       int val_bits;
diff --git a/target/linux/generic/backport-5.15/352-v6.3-regmap-apply-reg_base-and-reg_downshift-for-single-r.patch b/target/linux/generic/backport-5.15/352-v6.3-regmap-apply-reg_base-and-reg_downshift-for-single-r.patch
deleted file mode 100644 (file)
index 33de94c..0000000
+++ /dev/null
@@ -1,57 +0,0 @@
-From 697c3892d825fb78f42ec8e53bed065dd728db3e Mon Sep 17 00:00:00 2001
-From: Daniel Golle <[email protected]>
-Date: Mon, 30 Jan 2023 02:04:57 +0000
-Subject: [PATCH] regmap: apply reg_base and reg_downshift for single register
- ops
-
-reg_base and reg_downshift currently don't have any effect if used with
-a regmap_bus or regmap_config which only offers single register
-operations (ie. reg_read, reg_write and optionally reg_update_bits).
-
-Fix that and take them into account also for regmap_bus with only
-reg_read and read_write operations by applying reg_base and
-reg_downshift in _regmap_bus_reg_write, _regmap_bus_reg_read.
-
-Also apply reg_base and reg_downshift in _regmap_update_bits, but only
-in case the operation is carried out with a reg_update_bits call
-defined in either regmap_bus or regmap_config.
-
-Fixes: 0074f3f2b1e43d ("regmap: allow a defined reg_base to be added to every address")
-Fixes: 86fc59ef818beb ("regmap: add configurable downshift for addresses")
-Signed-off-by: Daniel Golle <[email protected]>
-Tested-by: Colin Foster <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Mark Brown <[email protected]>
----
- drivers/base/regmap/regmap.c | 6 ++++++
- 1 file changed, 6 insertions(+)
-
---- a/drivers/base/regmap/regmap.c
-+++ b/drivers/base/regmap/regmap.c
-@@ -1943,6 +1943,8 @@ static int _regmap_bus_reg_write(void *c
- {
-       struct regmap *map = context;
-+      reg += map->reg_base;
-+      reg >>= map->format.reg_downshift;
-       return map->bus->reg_write(map->bus_context, reg, val);
- }
-@@ -2715,6 +2717,8 @@ static int _regmap_bus_reg_read(void *co
- {
-       struct regmap *map = context;
-+      reg += map->reg_base;
-+      reg >>= map->format.reg_downshift;
-       return map->bus->reg_read(map->bus_context, reg, val);
- }
-@@ -3084,6 +3088,8 @@ static int _regmap_update_bits(struct re
-               *change = false;
-       if (regmap_volatile(map, reg) && map->reg_update_bits) {
-+              reg += map->reg_base;
-+              reg >>= map->format.reg_downshift;
-               ret = map->reg_update_bits(map->bus_context, reg, mask, val);
-               if (ret == 0 && change)
-                       *change = true;
diff --git a/target/linux/generic/backport-5.15/360-v6.1-powerpc-vdso-link-with-z-noexecstack.patch b/target/linux/generic/backport-5.15/360-v6.1-powerpc-vdso-link-with-z-noexecstack.patch
deleted file mode 100644 (file)
index 82e712e..0000000
+++ /dev/null
@@ -1,49 +0,0 @@
-From 78391fb5b1b5318900725c72f1db25b2ae92894f Mon Sep 17 00:00:00 2001
-From: Christophe Leroy <[email protected]>
-Date: Wed, 7 Jun 2023 09:50:52 +0200
-Subject: [PATCH] powerpc/vdso: link with -z noexecstack
-
-With recent binutils, the following warning appears:
-
-  VDSO32L arch/powerpc/kernel/vdso/vdso32.so.dbg
-/opt/gcc-12.2.0-nolibc/powerpc64-linux/bin/../lib/gcc/powerpc64-linux/12.2.0/../../../../powerpc64-linux/bin/ld: warning: arch/powerpc/kernel/vdso/getcpu-32.o: missing .note.GNU-stack section implies executable stack
-/opt/gcc-12.2.0-nolibc/powerpc64-linux/bin/../lib/gcc/powerpc64-linux/12.2.0/../../../../powerpc64-linux/bin/ld: NOTE: This behaviour is deprecated and will be removed in a future version of the linker
-
-To avoid that, explicitly tell the linker we don't want executable
-stack.
-
-For more explanations, see commit ffcf9c5700e4 ("x86: link vdso
-and boot with -z noexecstack --no-warn-rwx-segments")
-
-Commit was adapted for 5.15 as VDSO32 and VDSO64 were merged later so it
-does not directly apply.
-
-Signed-off-by: Christophe Leroy <[email protected]>
-Signed-off-by: Michael Ellerman <[email protected]>
-Link: https://lore.kernel.org/r/b95f2e3216a574837dd61208444e9515c3423da4.1662132312.git.christophe.leroy@csgroup.eu
-Signed-off-by: Robert Marko <[email protected]>
-[Adapt to 5.15 as it has VDSO split for 32 and 64bit]
----
- arch/powerpc/kernel/vdso32/Makefile | 2 +-
- arch/powerpc/kernel/vdso64/Makefile | 2 +-
- 2 files changed, 2 insertions(+), 2 deletions(-)
-
---- a/arch/powerpc/kernel/vdso32/Makefile
-+++ b/arch/powerpc/kernel/vdso32/Makefile
-@@ -66,7 +66,7 @@ include/generated/vdso32-offsets.h: $(ob
- # actual build commands
- quiet_cmd_vdso32ld_and_check = VDSO32L $@
--      cmd_vdso32ld_and_check = $(VDSOCC) $(c_flags) $(CC32FLAGS) -o $@ -Wl,-T$(filter %.lds,$^) $(filter %.o,$^) ; $(cmd_vdso_check)
-+      cmd_vdso32ld_and_check = $(VDSOCC) $(c_flags) $(CC32FLAGS) -o $@ -Wl,-T$(filter %.lds,$^) $(filter %.o,$^) -z noexecstack ; $(cmd_vdso_check)
- quiet_cmd_vdso32as = VDSO32A $@
-       cmd_vdso32as = $(VDSOCC) $(a_flags) $(CC32FLAGS) -c -o $@ $<
- quiet_cmd_vdso32cc = VDSO32C $@
---- a/arch/powerpc/kernel/vdso64/Makefile
-+++ b/arch/powerpc/kernel/vdso64/Makefile
-@@ -53,4 +53,4 @@ include/generated/vdso64-offsets.h: $(ob
- # actual build commands
- quiet_cmd_vdso64ld_and_check = VDSO64L $@
--      cmd_vdso64ld_and_check = $(CC) $(c_flags) -o $@ -Wl,-T$(filter %.lds,$^) $(filter %.o,$^); $(cmd_vdso_check)
-+      cmd_vdso64ld_and_check = $(CC) $(c_flags) -o $@ -Wl,-T$(filter %.lds,$^) $(filter %.o,$^) -z noexecstack ; $(cmd_vdso_check)
diff --git a/target/linux/generic/backport-5.15/400-v5.19-mtd-call-of_platform_populate-for-MTD-partitions.patch b/target/linux/generic/backport-5.15/400-v5.19-mtd-call-of_platform_populate-for-MTD-partitions.patch
deleted file mode 100644 (file)
index 1f3aae1..0000000
+++ /dev/null
@@ -1,72 +0,0 @@
-From bcdf0315a61a29eb753a607d3a85a4032de72d94 Mon Sep 17 00:00:00 2001
-From: =?UTF-8?q?Rafa=C5=82=20Mi=C5=82ecki?= <[email protected]>
-Date: Tue, 10 May 2022 15:12:59 +0200
-Subject: [PATCH] mtd: call of_platform_populate() for MTD partitions
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-Until this change MTD subsystem supported handling partitions only with
-MTD partitions parsers. That's a specific / limited API designed around
-partitions.
-
-Some MTD partitions may however require different handling. They may
-contain specific data that needs to be parsed and somehow extracted. For
-that purpose MTD subsystem should allow binding of standard platform
-drivers.
-
-An example can be U-Boot (sub)partition with environment variables.
-There exist a "u-boot,env" DT binding for MTD (sub)partition that
-requires an NVMEM driver.
-
-Ref: 5db1c2dbc04c ("dt-bindings: nvmem: add U-Boot environment variables binding")
-Signed-off-by: Rafał Miłecki <[email protected]>
-Signed-off-by: Miquel Raynal <[email protected]>
-Link: https://lore.kernel.org/linux-mtd/[email protected]
----
- drivers/mtd/mtdpart.c | 9 +++++++++
- 1 file changed, 9 insertions(+)
-
---- a/drivers/mtd/mtdpart.c
-+++ b/drivers/mtd/mtdpart.c
-@@ -17,6 +17,7 @@
- #include <linux/mtd/partitions.h>
- #include <linux/err.h>
- #include <linux/of.h>
-+#include <linux/of_platform.h>
- #include "mtdcore.h"
-@@ -577,10 +578,16 @@ static int mtd_part_of_parse(struct mtd_
-       struct mtd_part_parser *parser;
-       struct device_node *np;
-       struct property *prop;
-+      struct device *dev;
-       const char *compat;
-       const char *fixed = "fixed-partitions";
-       int ret, err = 0;
-+      dev = &master->dev;
-+      /* Use parent device (controller) if the top level MTD is not registered */
-+      if (!IS_ENABLED(CONFIG_MTD_PARTITIONED_MASTER) && !mtd_is_partition(master))
-+              dev = master->dev.parent;
-+
-       np = mtd_get_of_node(master);
-       if (mtd_is_partition(master))
-               of_node_get(np);
-@@ -593,6 +600,7 @@ static int mtd_part_of_parse(struct mtd_
-                       continue;
-               ret = mtd_part_do_parse(parser, master, pparts, NULL);
-               if (ret > 0) {
-+                      of_platform_populate(np, NULL, NULL, dev);
-                       of_node_put(np);
-                       return ret;
-               }
-@@ -600,6 +608,7 @@ static int mtd_part_of_parse(struct mtd_
-               if (ret < 0 && !err)
-                       err = ret;
-       }
-+      of_platform_populate(np, NULL, NULL, dev);
-       of_node_put(np);
-       /*
diff --git a/target/linux/generic/backport-5.15/401-v6.0-mtd-parsers-add-support-for-Sercomm-partitions.patch b/target/linux/generic/backport-5.15/401-v6.0-mtd-parsers-add-support-for-Sercomm-partitions.patch
deleted file mode 100644 (file)
index 113a96a..0000000
+++ /dev/null
@@ -1,302 +0,0 @@
-From 9b78ef0c7997052e9eaa0f7a4513d546fa17358c Mon Sep 17 00:00:00 2001
-From: Mikhail Zhilkin <[email protected]>
-Date: Sun, 29 May 2022 11:07:14 +0000
-Subject: [PATCH] mtd: parsers: add support for Sercomm partitions
-
-This adds an MTD partition parser for the Sercomm partition table that
-is used in some Beeline, Netgear and Sercomm routers.
-
-The Sercomm partition map table contains real partition offsets, which
-may differ from device to device depending on the number and location of
-bad blocks on NAND.
-
-Original patch (proposed by NOGUCHI Hiroshi):
-Link: https://github.com/openwrt/openwrt/pull/1318#issuecomment-420607394
-
-Signed-off-by: NOGUCHI Hiroshi <[email protected]>
-Signed-off-by: Mikhail Zhilkin <[email protected]>
-Signed-off-by: Miquel Raynal <[email protected]>
-Link: https://lore.kernel.org/linux-mtd/[email protected]
----
- drivers/mtd/parsers/Kconfig  |   9 ++
- drivers/mtd/parsers/Makefile |   1 +
- drivers/mtd/parsers/scpart.c | 248 +++++++++++++++++++++++++++++++++++
- 3 files changed, 258 insertions(+)
- create mode 100644 drivers/mtd/parsers/scpart.c
-
---- a/drivers/mtd/parsers/Kconfig
-+++ b/drivers/mtd/parsers/Kconfig
-@@ -186,3 +186,12 @@ config MTD_QCOMSMEM_PARTS
-       help
-         This provides support for parsing partitions from Shared Memory (SMEM)
-         for NAND and SPI flash on Qualcomm platforms.
-+
-+config MTD_SERCOMM_PARTS
-+      tristate "Sercomm partition table parser"
-+      depends on MTD && RALINK
-+      help
-+        This provides partitions table parser for devices with Sercomm
-+        partition map. This partition table contains real partition
-+        offsets, which may differ from device to device depending on the
-+        number and location of bad blocks on NAND.
---- a/drivers/mtd/parsers/Makefile
-+++ b/drivers/mtd/parsers/Makefile
-@@ -10,6 +10,7 @@ ofpart-$(CONFIG_MTD_OF_PARTS_LINKSYS_NS)
- obj-$(CONFIG_MTD_PARSER_IMAGETAG)     += parser_imagetag.o
- obj-$(CONFIG_MTD_AFS_PARTS)           += afs.o
- obj-$(CONFIG_MTD_PARSER_TRX)          += parser_trx.o
-+obj-$(CONFIG_MTD_SERCOMM_PARTS)               += scpart.o
- obj-$(CONFIG_MTD_SHARPSL_PARTS)               += sharpslpart.o
- obj-$(CONFIG_MTD_REDBOOT_PARTS)               += redboot.o
- obj-$(CONFIG_MTD_QCOMSMEM_PARTS)      += qcomsmempart.o
---- /dev/null
-+++ b/drivers/mtd/parsers/scpart.c
-@@ -0,0 +1,248 @@
-+// SPDX-License-Identifier: GPL-2.0-or-later
-+/*
-+ *    drivers/mtd/scpart.c: Sercomm Partition Parser
-+ *
-+ *    Copyright (C) 2018 NOGUCHI Hiroshi
-+ *    Copyright (C) 2022 Mikhail Zhilkin
-+ */
-+
-+#include <linux/kernel.h>
-+#include <linux/slab.h>
-+#include <linux/mtd/mtd.h>
-+#include <linux/mtd/partitions.h>
-+#include <linux/module.h>
-+
-+#define       MOD_NAME        "scpart"
-+
-+#ifdef pr_fmt
-+#undef pr_fmt
-+#endif
-+
-+#define pr_fmt(fmt) MOD_NAME ": " fmt
-+
-+#define       ID_ALREADY_FOUND        0xffffffffUL
-+
-+#define       MAP_OFFS_IN_BLK         0x800
-+#define       MAP_MIRROR_NUM          2
-+
-+static const char sc_part_magic[] = {
-+      'S', 'C', 'F', 'L', 'M', 'A', 'P', 'O', 'K', '\0',
-+};
-+#define       PART_MAGIC_LEN          sizeof(sc_part_magic)
-+
-+/* assumes that all fields are set by CPU native endian */
-+struct sc_part_desc {
-+      uint32_t        part_id;
-+      uint32_t        part_offs;
-+      uint32_t        part_bytes;
-+};
-+
-+static uint32_t scpart_desc_is_valid(struct sc_part_desc *pdesc)
-+{
-+      return ((pdesc->part_id != 0xffffffffUL) &&
-+              (pdesc->part_offs != 0xffffffffUL) &&
-+              (pdesc->part_bytes != 0xffffffffUL));
-+}
-+
-+static int scpart_scan_partmap(struct mtd_info *master, loff_t partmap_offs,
-+                             struct sc_part_desc **ppdesc)
-+{
-+      int cnt = 0;
-+      int res = 0;
-+      int res2;
-+      loff_t offs;
-+      size_t retlen;
-+      struct sc_part_desc *pdesc = NULL;
-+      struct sc_part_desc *tmpdesc;
-+      uint8_t *buf;
-+
-+      buf = kzalloc(master->erasesize, GFP_KERNEL);
-+      if (!buf) {
-+              res = -ENOMEM;
-+              goto out;
-+      }
-+
-+      res2 = mtd_read(master, partmap_offs, master->erasesize, &retlen, buf);
-+      if (res2 || retlen != master->erasesize) {
-+              res = -EIO;
-+              goto free;
-+      }
-+
-+      for (offs = MAP_OFFS_IN_BLK;
-+           offs < master->erasesize - sizeof(*tmpdesc);
-+           offs += sizeof(*tmpdesc)) {
-+              tmpdesc = (struct sc_part_desc *)&buf[offs];
-+              if (!scpart_desc_is_valid(tmpdesc))
-+                      break;
-+              cnt++;
-+      }
-+
-+      if (cnt > 0) {
-+              int bytes = cnt * sizeof(*pdesc);
-+
-+              pdesc = kcalloc(cnt, sizeof(*pdesc), GFP_KERNEL);
-+              if (!pdesc) {
-+                      res = -ENOMEM;
-+                      goto free;
-+              }
-+              memcpy(pdesc, &(buf[MAP_OFFS_IN_BLK]), bytes);
-+
-+              *ppdesc = pdesc;
-+              res = cnt;
-+      }
-+
-+free:
-+      kfree(buf);
-+
-+out:
-+      return res;
-+}
-+
-+static int scpart_find_partmap(struct mtd_info *master,
-+                             struct sc_part_desc **ppdesc)
-+{
-+      int magic_found = 0;
-+      int res = 0;
-+      int res2;
-+      loff_t offs = 0;
-+      size_t retlen;
-+      uint8_t rdbuf[PART_MAGIC_LEN];
-+
-+      while ((magic_found < MAP_MIRROR_NUM) &&
-+                      (offs < master->size) &&
-+                       !mtd_block_isbad(master, offs)) {
-+              res2 = mtd_read(master, offs, PART_MAGIC_LEN, &retlen, rdbuf);
-+              if (res2 || retlen != PART_MAGIC_LEN) {
-+                      res = -EIO;
-+                      goto out;
-+              }
-+              if (!memcmp(rdbuf, sc_part_magic, PART_MAGIC_LEN)) {
-+                      pr_debug("Signature found at 0x%llx\n", offs);
-+                      magic_found++;
-+                      res = scpart_scan_partmap(master, offs, ppdesc);
-+                      if (res > 0)
-+                              goto out;
-+              }
-+              offs += master->erasesize;
-+      }
-+
-+out:
-+      if (res > 0)
-+              pr_info("Valid 'SC PART MAP' (%d partitions) found at 0x%llx\n", res, offs);
-+      else
-+              pr_info("No valid 'SC PART MAP' was found\n");
-+
-+      return res;
-+}
-+
-+static int scpart_parse(struct mtd_info *master,
-+                      const struct mtd_partition **pparts,
-+                      struct mtd_part_parser_data *data)
-+{
-+      const char *partname;
-+      int n;
-+      int nr_scparts;
-+      int nr_parts = 0;
-+      int res = 0;
-+      struct sc_part_desc *scpart_map = NULL;
-+      struct mtd_partition *parts = NULL;
-+      struct device_node *mtd_node;
-+      struct device_node *ofpart_node;
-+      struct device_node *pp;
-+
-+      mtd_node = mtd_get_of_node(master);
-+      if (!mtd_node) {
-+              res = -ENOENT;
-+              goto out;
-+      }
-+
-+      ofpart_node = of_get_child_by_name(mtd_node, "partitions");
-+      if (!ofpart_node) {
-+              pr_info("%s: 'partitions' subnode not found on %pOF.\n",
-+                              master->name, mtd_node);
-+              res = -ENOENT;
-+              goto out;
-+      }
-+
-+      nr_scparts = scpart_find_partmap(master, &scpart_map);
-+      if (nr_scparts <= 0) {
-+              pr_info("No any partitions was found in 'SC PART MAP'.\n");
-+              res = -ENOENT;
-+              goto free;
-+      }
-+
-+      parts = kcalloc(of_get_child_count(ofpart_node), sizeof(*parts),
-+              GFP_KERNEL);
-+      if (!parts) {
-+              res = -ENOMEM;
-+              goto free;
-+      }
-+
-+      for_each_child_of_node(ofpart_node, pp) {
-+              u32 scpart_id;
-+
-+              if (of_property_read_u32(pp, "sercomm,scpart-id", &scpart_id))
-+                      continue;
-+
-+              for (n = 0 ; n < nr_scparts ; n++)
-+                      if ((scpart_map[n].part_id != ID_ALREADY_FOUND) &&
-+                                      (scpart_id == scpart_map[n].part_id))
-+                              break;
-+              if (n >= nr_scparts)
-+                      /* not match */
-+                      continue;
-+
-+              /* add the partition found in OF into MTD partition array */
-+              parts[nr_parts].offset = scpart_map[n].part_offs;
-+              parts[nr_parts].size = scpart_map[n].part_bytes;
-+              parts[nr_parts].of_node = pp;
-+
-+              if (!of_property_read_string(pp, "label", &partname))
-+                      parts[nr_parts].name = partname;
-+              if (of_property_read_bool(pp, "read-only"))
-+                      parts[nr_parts].mask_flags |= MTD_WRITEABLE;
-+              if (of_property_read_bool(pp, "lock"))
-+                      parts[nr_parts].mask_flags |= MTD_POWERUP_LOCK;
-+
-+              /* mark as 'done' */
-+              scpart_map[n].part_id = ID_ALREADY_FOUND;
-+
-+              nr_parts++;
-+      }
-+
-+      if (nr_parts > 0) {
-+              *pparts = parts;
-+              res = nr_parts;
-+      } else
-+              pr_info("No partition in OF matches partition ID with 'SC PART MAP'.\n");
-+
-+      of_node_put(pp);
-+
-+free:
-+      kfree(scpart_map);
-+      if (res <= 0)
-+              kfree(parts);
-+
-+out:
-+      return res;
-+}
-+
-+static const struct of_device_id scpart_parser_of_match_table[] = {
-+      { .compatible = "sercomm,sc-partitions" },
-+      {},
-+};
-+MODULE_DEVICE_TABLE(of, scpart_parser_of_match_table);
-+
-+static struct mtd_part_parser scpart_parser = {
-+      .parse_fn = scpart_parse,
-+      .name = "scpart",
-+      .of_match_table = scpart_parser_of_match_table,
-+};
-+module_mtd_part_parser(scpart_parser);
-+
-+/* mtd parsers will request the module by parser name */
-+MODULE_ALIAS("scpart");
-+MODULE_LICENSE("GPL");
-+MODULE_AUTHOR("NOGUCHI Hiroshi <[email protected]>");
-+MODULE_AUTHOR("Mikhail Zhilkin <[email protected]>");
-+MODULE_DESCRIPTION("Sercomm partition parser");
diff --git a/target/linux/generic/backport-5.15/402-v6.0-mtd-next-mtd-core-introduce-of-support-for-dynamic-partitions.patch b/target/linux/generic/backport-5.15/402-v6.0-mtd-next-mtd-core-introduce-of-support-for-dynamic-partitions.patch
deleted file mode 100644 (file)
index ee38541..0000000
+++ /dev/null
@@ -1,106 +0,0 @@
-From ad9b10d1eaada169bd764abcab58f08538877e26 Mon Sep 17 00:00:00 2001
-From: Christian Marangi <[email protected]>
-Date: Wed, 22 Jun 2022 03:06:28 +0200
-Subject: mtd: core: introduce of support for dynamic partitions
-
-We have many parser that register mtd partitions at runtime. One example
-is the cmdlinepart or the smem-part parser where the compatible is defined
-in the dts and the partitions gets detected and registered by the
-parser. This is problematic for the NVMEM subsystem that requires an OF
-node to detect NVMEM cells.
-
-To fix this problem, introduce an additional logic that will try to
-assign an OF node to the MTD if declared.
-
-On MTD addition, it will be checked if the MTD has an OF node and if
-not declared will check if a partition with the same label / node name is
-declared in DTS. If an exact match is found, the partition dynamically
-allocated by the parser will have a connected OF node.
-
-The NVMEM subsystem will detect the OF node and register any NVMEM cells
-declared statically in the DTS.
-
-Signed-off-by: Christian Marangi <[email protected]>
-Signed-off-by: Miquel Raynal <[email protected]>
-Link: https://lore.kernel.org/linux-mtd/[email protected]
----
- drivers/mtd/mtdcore.c | 61 +++++++++++++++++++++++++++++++++++++++++++
- 1 file changed, 61 insertions(+)
-
---- a/drivers/mtd/mtdcore.c
-+++ b/drivers/mtd/mtdcore.c
-@@ -564,6 +564,66 @@ static int mtd_nvmem_add(struct mtd_info
-       return 0;
- }
-+static void mtd_check_of_node(struct mtd_info *mtd)
-+{
-+      struct device_node *partitions, *parent_dn, *mtd_dn = NULL;
-+      const char *pname, *prefix = "partition-";
-+      int plen, mtd_name_len, offset, prefix_len;
-+      struct mtd_info *parent;
-+      bool found = false;
-+
-+      /* Check if MTD already has a device node */
-+      if (dev_of_node(&mtd->dev))
-+              return;
-+
-+      /* Check if a partitions node exist */
-+      parent = mtd->parent;
-+      parent_dn = dev_of_node(&parent->dev);
-+      if (!parent_dn)
-+              return;
-+
-+      partitions = of_get_child_by_name(parent_dn, "partitions");
-+      if (!partitions)
-+              goto exit_parent;
-+
-+      prefix_len = strlen(prefix);
-+      mtd_name_len = strlen(mtd->name);
-+
-+      /* Search if a partition is defined with the same name */
-+      for_each_child_of_node(partitions, mtd_dn) {
-+              offset = 0;
-+
-+              /* Skip partition with no/wrong prefix */
-+              if (!of_node_name_prefix(mtd_dn, "partition-"))
-+                      continue;
-+
-+              /* Label have priority. Check that first */
-+              if (of_property_read_string(mtd_dn, "label", &pname)) {
-+                      of_property_read_string(mtd_dn, "name", &pname);
-+                      offset = prefix_len;
-+              }
-+
-+              plen = strlen(pname) - offset;
-+              if (plen == mtd_name_len &&
-+                  !strncmp(mtd->name, pname + offset, plen)) {
-+                      found = true;
-+                      break;
-+              }
-+      }
-+
-+      if (!found)
-+              goto exit_partitions;
-+
-+      /* Set of_node only for nvmem */
-+      if (of_device_is_compatible(mtd_dn, "nvmem-cells"))
-+              mtd_set_of_node(mtd, mtd_dn);
-+
-+exit_partitions:
-+      of_node_put(partitions);
-+exit_parent:
-+      of_node_put(parent_dn);
-+}
-+
- /**
-  *    add_mtd_device - register an MTD device
-  *    @mtd: pointer to new MTD device info structure
-@@ -669,6 +729,7 @@ int add_mtd_device(struct mtd_info *mtd)
-       mtd->dev.devt = MTD_DEVT(i);
-       dev_set_name(&mtd->dev, "mtd%d", i);
-       dev_set_drvdata(&mtd->dev, mtd);
-+      mtd_check_of_node(mtd);
-       of_node_get(mtd_get_of_node(mtd));
-       error = device_register(&mtd->dev);
-       if (error) {
diff --git a/target/linux/generic/backport-5.15/403-v6.1-mtd-allow-getting-MTD-device-associated-with-a-speci.patch b/target/linux/generic/backport-5.15/403-v6.1-mtd-allow-getting-MTD-device-associated-with-a-speci.patch
deleted file mode 100644 (file)
index c8a7d28..0000000
+++ /dev/null
@@ -1,72 +0,0 @@
-From b0321721be50b80c03a51866a94fde4f94690e18 Mon Sep 17 00:00:00 2001
-From: =?UTF-8?q?Rafa=C5=82=20Mi=C5=82ecki?= <[email protected]>
-Date: Wed, 15 Jun 2022 21:42:59 +0200
-Subject: [PATCH] mtd: allow getting MTD device associated with a specific DT
- node
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-MTD subsystem API allows interacting with MTD devices (e.g. reading,
-writing, handling bad blocks). So far a random driver could get MTD
-device only by its name (get_mtd_device_nm()). This change allows
-getting them also by a DT node.
-
-This API is required for drivers handling DT defined MTD partitions in a
-specific way (e.g. U-Boot (sub)partition with environment variables).
-
-Signed-off-by: Rafał Miłecki <[email protected]>
-Acked-by: Miquel Raynal <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
----
- drivers/mtd/mtdcore.c   | 28 ++++++++++++++++++++++++++++
- include/linux/mtd/mtd.h |  1 +
- 2 files changed, 29 insertions(+)
-
---- a/drivers/mtd/mtdcore.c
-+++ b/drivers/mtd/mtdcore.c
-@@ -1238,6 +1238,34 @@ int __get_mtd_device(struct mtd_info *mt
- EXPORT_SYMBOL_GPL(__get_mtd_device);
- /**
-+ * of_get_mtd_device_by_node - obtain an MTD device associated with a given node
-+ *
-+ * @np: device tree node
-+ */
-+struct mtd_info *of_get_mtd_device_by_node(struct device_node *np)
-+{
-+      struct mtd_info *mtd = NULL;
-+      struct mtd_info *tmp;
-+      int err;
-+
-+      mutex_lock(&mtd_table_mutex);
-+
-+      err = -EPROBE_DEFER;
-+      mtd_for_each_device(tmp) {
-+              if (mtd_get_of_node(tmp) == np) {
-+                      mtd = tmp;
-+                      err = __get_mtd_device(mtd);
-+                      break;
-+              }
-+      }
-+
-+      mutex_unlock(&mtd_table_mutex);
-+
-+      return err ? ERR_PTR(err) : mtd;
-+}
-+EXPORT_SYMBOL_GPL(of_get_mtd_device_by_node);
-+
-+/**
-  *    get_mtd_device_nm - obtain a validated handle for an MTD device by
-  *    device name
-  *    @name: MTD device name to open
---- a/include/linux/mtd/mtd.h
-+++ b/include/linux/mtd/mtd.h
-@@ -682,6 +682,7 @@ extern int mtd_device_unregister(struct
- extern struct mtd_info *get_mtd_device(struct mtd_info *mtd, int num);
- extern int __get_mtd_device(struct mtd_info *mtd);
- extern void __put_mtd_device(struct mtd_info *mtd);
-+extern struct mtd_info *of_get_mtd_device_by_node(struct device_node *np);
- extern struct mtd_info *get_mtd_device_nm(const char *name);
- extern void put_mtd_device(struct mtd_info *mtd);
diff --git a/target/linux/generic/backport-5.15/404-v6.0-mtd-core-check-partition-before-dereference.patch b/target/linux/generic/backport-5.15/404-v6.0-mtd-core-check-partition-before-dereference.patch
deleted file mode 100644 (file)
index e45e2ab..0000000
+++ /dev/null
@@ -1,30 +0,0 @@
-From 7ec4cdb321738d44ae5d405e7b6ac73dfbf99caa Mon Sep 17 00:00:00 2001
-From: Tetsuo Handa <[email protected]>
-Date: Mon, 25 Jul 2022 22:49:25 +0900
-Subject: [PATCH] mtd: core: check partition before dereference
-
-syzbot is reporting NULL pointer dereference at mtd_check_of_node() [1],
-for mtdram test device (CONFIG_MTD_MTDRAM) is not partition.
-
-Link: https://syzkaller.appspot.com/bug?extid=fe013f55a2814a9e8cfd [1]
-Reported-by: syzbot <[email protected]>
-Reported-by: kernel test robot <[email protected]>
-Fixes: ad9b10d1eaada169 ("mtd: core: introduce of support for dynamic partitions")
-Signed-off-by: Tetsuo Handa <[email protected]>
-Signed-off-by: Richard Weinberger <[email protected]>
----
- drivers/mtd/mtdcore.c | 2 ++
- 1 file changed, 2 insertions(+)
-
---- a/drivers/mtd/mtdcore.c
-+++ b/drivers/mtd/mtdcore.c
-@@ -577,6 +577,8 @@ static void mtd_check_of_node(struct mtd
-               return;
-       /* Check if a partitions node exist */
-+      if (!mtd_is_partition(mtd))
-+              return;
-       parent = mtd->parent;
-       parent_dn = dev_of_node(&parent->dev);
-       if (!parent_dn)
diff --git a/target/linux/generic/backport-5.15/405-v6.1-mtd-core-add-missing-of_node_get-in-dynamic-partitio.patch b/target/linux/generic/backport-5.15/405-v6.1-mtd-core-add-missing-of_node_get-in-dynamic-partitio.patch
deleted file mode 100644 (file)
index 9399a00..0000000
+++ /dev/null
@@ -1,101 +0,0 @@
-From 12b58961de0bd88b3c7dfa5d21f6d67f4678b780 Mon Sep 17 00:00:00 2001
-From: =?UTF-8?q?Rafa=C5=82=20Mi=C5=82ecki?= <[email protected]>
-Date: Tue, 18 Oct 2022 07:18:22 +0200
-Subject: [PATCH] mtd: core: add missing of_node_get() in dynamic partitions
- code
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-This fixes unbalanced of_node_put():
-[    1.078910] 6 cmdlinepart partitions found on MTD device gpmi-nand
-[    1.085116] Creating 6 MTD partitions on "gpmi-nand":
-[    1.090181] 0x000000000000-0x000008000000 : "nandboot"
-[    1.096952] 0x000008000000-0x000009000000 : "nandfit"
-[    1.103547] 0x000009000000-0x00000b000000 : "nandkernel"
-[    1.110317] 0x00000b000000-0x00000c000000 : "nanddtb"
-[    1.115525] ------------[ cut here ]------------
-[    1.120141] refcount_t: addition on 0; use-after-free.
-[    1.125328] WARNING: CPU: 0 PID: 1 at lib/refcount.c:25 refcount_warn_saturate+0xdc/0x148
-[    1.133528] Modules linked in:
-[    1.136589] CPU: 0 PID: 1 Comm: swapper/0 Not tainted 6.0.0-rc7-next-20220930-04543-g8cf3f7
-[    1.146342] Hardware name: Freescale i.MX8DXL DDR3L EVK (DT)
-[    1.151999] pstate: 600000c5 (nZCv daIF -PAN -UAO -TCO -DIT -SSBS BTYPE=--)
-[    1.158965] pc : refcount_warn_saturate+0xdc/0x148
-[    1.163760] lr : refcount_warn_saturate+0xdc/0x148
-[    1.168556] sp : ffff800009ddb080
-[    1.171866] x29: ffff800009ddb080 x28: ffff800009ddb35a x27: 0000000000000002
-[    1.179015] x26: ffff8000098b06ad x25: ffffffffffffffff x24: ffff0a00ffffff05
-[    1.186165] x23: ffff00001fdf6470 x22: ffff800009ddb367 x21: 0000000000000000
-[    1.193314] x20: ffff00001fdfebe8 x19: ffff00001fdfec50 x18: ffffffffffffffff
-[    1.200464] x17: 0000000000000000 x16: 0000000000000118 x15: 0000000000000004
-[    1.207614] x14: 0000000000000fff x13: ffff800009bca248 x12: 0000000000000003
-[    1.214764] x11: 00000000ffffefff x10: c0000000ffffefff x9 : 4762cb2ccb52de00
-[    1.221914] x8 : 4762cb2ccb52de00 x7 : 205d313431303231 x6 : 312e31202020205b
-[    1.229063] x5 : ffff800009d55c1f x4 : 0000000000000001 x3 : 0000000000000000
-[    1.236213] x2 : 0000000000000000 x1 : ffff800009954be6 x0 : 000000000000002a
-[    1.243365] Call trace:
-[    1.245806]  refcount_warn_saturate+0xdc/0x148
-[    1.250253]  kobject_get+0x98/0x9c
-[    1.253658]  of_node_get+0x20/0x34
-[    1.257072]  of_fwnode_get+0x3c/0x54
-[    1.260652]  fwnode_get_nth_parent+0xd8/0xf4
-[    1.264926]  fwnode_full_name_string+0x3c/0xb4
-[    1.269373]  device_node_string+0x498/0x5b4
-[    1.273561]  pointer+0x41c/0x5d0
-[    1.276793]  vsnprintf+0x4d8/0x694
-[    1.280198]  vprintk_store+0x164/0x528
-[    1.283951]  vprintk_emit+0x98/0x164
-[    1.287530]  vprintk_default+0x44/0x6c
-[    1.291284]  vprintk+0xf0/0x134
-[    1.294428]  _printk+0x54/0x7c
-[    1.297486]  of_node_release+0xe8/0x128
-[    1.301326]  kobject_put+0x98/0xfc
-[    1.304732]  of_node_put+0x1c/0x28
-[    1.308137]  add_mtd_device+0x484/0x6d4
-[    1.311977]  add_mtd_partitions+0xf0/0x1d0
-[    1.316078]  parse_mtd_partitions+0x45c/0x518
-[    1.320439]  mtd_device_parse_register+0xb0/0x274
-[    1.325147]  gpmi_nand_probe+0x51c/0x650
-[    1.329074]  platform_probe+0xa8/0xd0
-[    1.332740]  really_probe+0x130/0x334
-[    1.336406]  __driver_probe_device+0xb4/0xe0
-[    1.340681]  driver_probe_device+0x3c/0x1f8
-[    1.344869]  __driver_attach+0xdc/0x1a4
-[    1.348708]  bus_for_each_dev+0x80/0xcc
-[    1.352548]  driver_attach+0x24/0x30
-[    1.356127]  bus_add_driver+0x108/0x1f4
-[    1.359967]  driver_register+0x78/0x114
-[    1.363807]  __platform_driver_register+0x24/0x30
-[    1.368515]  gpmi_nand_driver_init+0x1c/0x28
-[    1.372798]  do_one_initcall+0xbc/0x238
-[    1.376638]  do_initcall_level+0x94/0xb4
-[    1.380565]  do_initcalls+0x54/0x94
-[    1.384058]  do_basic_setup+0x1c/0x28
-[    1.387724]  kernel_init_freeable+0x110/0x188
-[    1.392084]  kernel_init+0x20/0x1a0
-[    1.395578]  ret_from_fork+0x10/0x20
-[    1.399157] ---[ end trace 0000000000000000 ]---
-[    1.403782] ------------[ cut here ]------------
-
-Reported-by: Han Xu <[email protected]>
-Fixes: ad9b10d1eaada169 ("mtd: core: introduce of support for dynamic partitions")
-Signed-off-by: Rafał Miłecki <[email protected]>
-Tested-by: Han Xu <[email protected]>
-Signed-off-by: Miquel Raynal <[email protected]>
-Link: https://lore.kernel.org/linux-mtd/[email protected]
----
- drivers/mtd/mtdcore.c | 2 +-
- 1 file changed, 1 insertion(+), 1 deletion(-)
-
---- a/drivers/mtd/mtdcore.c
-+++ b/drivers/mtd/mtdcore.c
-@@ -580,7 +580,7 @@ static void mtd_check_of_node(struct mtd
-       if (!mtd_is_partition(mtd))
-               return;
-       parent = mtd->parent;
--      parent_dn = dev_of_node(&parent->dev);
-+      parent_dn = of_node_get(dev_of_node(&parent->dev));
-       if (!parent_dn)
-               return;
diff --git a/target/linux/generic/backport-5.15/406-v6.2-0001-mtd-core-simplify-a-bit-code-find-partition-matching.patch b/target/linux/generic/backport-5.15/406-v6.2-0001-mtd-core-simplify-a-bit-code-find-partition-matching.patch
deleted file mode 100644 (file)
index 7e9645e..0000000
+++ /dev/null
@@ -1,65 +0,0 @@
-From 63db0cb35e1cb3b3c134906d1062f65513fdda2d Mon Sep 17 00:00:00 2001
-From: =?UTF-8?q?Rafa=C5=82=20Mi=C5=82ecki?= <[email protected]>
-Date: Tue, 4 Oct 2022 10:37:09 +0200
-Subject: [PATCH] mtd: core: simplify (a bit) code find partition-matching
- dynamic OF node
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-1. Don't hardcode "partition-" string twice
-2. Use simpler logic & use ->name to avoid of_property_read_string()
-3. Use mtd_get_of_node() helper
-
-Cc: Christian Marangi <[email protected]>
-Signed-off-by: Rafał Miłecki <[email protected]>
-Signed-off-by: Miquel Raynal <[email protected]>
-Link: https://lore.kernel.org/linux-mtd/[email protected]
----
- drivers/mtd/mtdcore.c | 16 +++++++---------
- 1 file changed, 7 insertions(+), 9 deletions(-)
-
---- a/drivers/mtd/mtdcore.c
-+++ b/drivers/mtd/mtdcore.c
-@@ -569,18 +569,16 @@ static void mtd_check_of_node(struct mtd
-       struct device_node *partitions, *parent_dn, *mtd_dn = NULL;
-       const char *pname, *prefix = "partition-";
-       int plen, mtd_name_len, offset, prefix_len;
--      struct mtd_info *parent;
-       bool found = false;
-       /* Check if MTD already has a device node */
--      if (dev_of_node(&mtd->dev))
-+      if (mtd_get_of_node(mtd))
-               return;
-       /* Check if a partitions node exist */
-       if (!mtd_is_partition(mtd))
-               return;
--      parent = mtd->parent;
--      parent_dn = of_node_get(dev_of_node(&parent->dev));
-+      parent_dn = of_node_get(mtd_get_of_node(mtd->parent));
-       if (!parent_dn)
-               return;
-@@ -593,15 +591,15 @@ static void mtd_check_of_node(struct mtd
-       /* Search if a partition is defined with the same name */
-       for_each_child_of_node(partitions, mtd_dn) {
--              offset = 0;
--
-               /* Skip partition with no/wrong prefix */
--              if (!of_node_name_prefix(mtd_dn, "partition-"))
-+              if (!of_node_name_prefix(mtd_dn, prefix))
-                       continue;
-               /* Label have priority. Check that first */
--              if (of_property_read_string(mtd_dn, "label", &pname)) {
--                      of_property_read_string(mtd_dn, "name", &pname);
-+              if (!of_property_read_string(mtd_dn, "label", &pname)) {
-+                      offset = 0;
-+              } else {
-+                      pname = mtd_dn->name;
-                       offset = prefix_len;
-               }
diff --git a/target/linux/generic/backport-5.15/406-v6.2-0002-mtd-core-try-to-find-OF-node-for-every-MTD-partition.patch b/target/linux/generic/backport-5.15/406-v6.2-0002-mtd-core-try-to-find-OF-node-for-every-MTD-partition.patch
deleted file mode 100644 (file)
index 48a7c13..0000000
+++ /dev/null
@@ -1,84 +0,0 @@
-From ddb8cefb7af288950447ca6eeeafb09977dab56f Mon Sep 17 00:00:00 2001
-From: =?UTF-8?q?Rafa=C5=82=20Mi=C5=82ecki?= <[email protected]>
-Date: Tue, 4 Oct 2022 10:37:10 +0200
-Subject: [PATCH] mtd: core: try to find OF node for every MTD partition
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-So far this feature was limited to the top-level "nvmem-cells" node.
-There are multiple parsers creating partitions and subpartitions
-dynamically. Extend that code to handle them too.
-
-This allows finding partition-* node for every MTD (sub)partition.
-
-Random example:
-
-partitions {
-       compatible = "brcm,bcm947xx-cfe-partitions";
-
-       partition-firmware {
-               compatible = "brcm,trx";
-
-               partition-loader {
-               };
-       };
-};
-
-Cc: Christian Marangi <[email protected]>
-Signed-off-by: Rafał Miłecki <[email protected]>
-Signed-off-by: Miquel Raynal <[email protected]>
-Link: https://lore.kernel.org/linux-mtd/[email protected]
----
- drivers/mtd/mtdcore.c | 18 ++++++------------
- 1 file changed, 6 insertions(+), 12 deletions(-)
-
---- a/drivers/mtd/mtdcore.c
-+++ b/drivers/mtd/mtdcore.c
-@@ -569,20 +569,22 @@ static void mtd_check_of_node(struct mtd
-       struct device_node *partitions, *parent_dn, *mtd_dn = NULL;
-       const char *pname, *prefix = "partition-";
-       int plen, mtd_name_len, offset, prefix_len;
--      bool found = false;
-       /* Check if MTD already has a device node */
-       if (mtd_get_of_node(mtd))
-               return;
--      /* Check if a partitions node exist */
-       if (!mtd_is_partition(mtd))
-               return;
-+
-       parent_dn = of_node_get(mtd_get_of_node(mtd->parent));
-       if (!parent_dn)
-               return;
--      partitions = of_get_child_by_name(parent_dn, "partitions");
-+      if (mtd_is_partition(mtd->parent))
-+              partitions = of_node_get(parent_dn);
-+      else
-+              partitions = of_get_child_by_name(parent_dn, "partitions");
-       if (!partitions)
-               goto exit_parent;
-@@ -606,19 +608,11 @@ static void mtd_check_of_node(struct mtd
-               plen = strlen(pname) - offset;
-               if (plen == mtd_name_len &&
-                   !strncmp(mtd->name, pname + offset, plen)) {
--                      found = true;
-+                      mtd_set_of_node(mtd, mtd_dn);
-                       break;
-               }
-       }
--      if (!found)
--              goto exit_partitions;
--
--      /* Set of_node only for nvmem */
--      if (of_device_is_compatible(mtd_dn, "nvmem-cells"))
--              mtd_set_of_node(mtd, mtd_dn);
--
--exit_partitions:
-       of_node_put(partitions);
- exit_parent:
-       of_node_put(parent_dn);
diff --git a/target/linux/generic/backport-5.15/407-v5.17-mtd-parsers-qcom-Don-t-print-error-message-on-EPROBE.patch b/target/linux/generic/backport-5.15/407-v5.17-mtd-parsers-qcom-Don-t-print-error-message-on-EPROBE.patch
deleted file mode 100644 (file)
index 0efad99..0000000
+++ /dev/null
@@ -1,32 +0,0 @@
-From 26bccc9671ba5e01f7153addbe94e7dc3f677375 Mon Sep 17 00:00:00 2001
-From: Bryan O'Donoghue <[email protected]>
-Date: Mon, 3 Jan 2022 03:03:16 +0000
-Subject: [PATCH 13/14] mtd: parsers: qcom: Don't print error message on
- -EPROBE_DEFER
-
-Its possible for the main smem driver to not be loaded by the time we come
-along to parse the smem partition description but, this is a perfectly
-normal thing.
-
-No need to print out an error message in this case.
-
-Signed-off-by: Bryan O'Donoghue <[email protected]>
-Reviewed-by: Manivannan Sadhasivam <[email protected]>
-Signed-off-by: Miquel Raynal <[email protected]>
-Link: https://lore.kernel.org/linux-mtd/[email protected]
----
- drivers/mtd/parsers/qcomsmempart.c | 3 ++-
- 1 file changed, 2 insertions(+), 1 deletion(-)
-
---- a/drivers/mtd/parsers/qcomsmempart.c
-+++ b/drivers/mtd/parsers/qcomsmempart.c
-@@ -75,7 +75,8 @@ static int parse_qcomsmem_part(struct mt
-       pr_debug("Parsing partition table info from SMEM\n");
-       ptable = qcom_smem_get(SMEM_APPS, SMEM_AARM_PARTITION_TABLE, &len);
-       if (IS_ERR(ptable)) {
--              pr_err("Error reading partition table header\n");
-+              if (PTR_ERR(ptable) != -EPROBE_DEFER)
-+                      pr_err("Error reading partition table header\n");
-               return PTR_ERR(ptable);
-       }
diff --git a/target/linux/generic/backport-5.15/408-v6.2-mtd-core-set-ROOT_DEV-for-partitions-marked-as-rootf.patch b/target/linux/generic/backport-5.15/408-v6.2-mtd-core-set-ROOT_DEV-for-partitions-marked-as-rootf.patch
deleted file mode 100644 (file)
index 505e347..0000000
+++ /dev/null
@@ -1,47 +0,0 @@
-From 26422ac78e9d8767bd4aabfbae616b15edbf6a1b Mon Sep 17 00:00:00 2001
-From: =?UTF-8?q?Rafa=C5=82=20Mi=C5=82ecki?= <[email protected]>
-Date: Sat, 22 Oct 2022 23:13:18 +0200
-Subject: [PATCH] mtd: core: set ROOT_DEV for partitions marked as rootfs in DT
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-This adds support for "linux,rootfs" binding that is used to mark flash
-partition containing rootfs. It's useful for devices using device tree
-that don't have bootloader passing root info in cmdline.
-
-Signed-off-by: Rafał Miłecki <[email protected]>
-Signed-off-by: Miquel Raynal <[email protected]>
-Link: https://lore.kernel.org/linux-mtd/[email protected]
----
- drivers/mtd/mtdcore.c | 12 ++++++++++++
- 1 file changed, 12 insertions(+)
-
---- a/drivers/mtd/mtdcore.c
-+++ b/drivers/mtd/mtdcore.c
-@@ -28,6 +28,7 @@
- #include <linux/leds.h>
- #include <linux/debugfs.h>
- #include <linux/nvmem-provider.h>
-+#include <linux/root_dev.h>
- #include <linux/mtd/mtd.h>
- #include <linux/mtd/partitions.h>
-@@ -748,6 +749,17 @@ int add_mtd_device(struct mtd_info *mtd)
-               not->add(mtd);
-       mutex_unlock(&mtd_table_mutex);
-+
-+      if (of_find_property(mtd_get_of_node(mtd), "linux,rootfs", NULL)) {
-+              if (IS_BUILTIN(CONFIG_MTD)) {
-+                      pr_info("mtd: setting mtd%d (%s) as root device\n", mtd->index, mtd->name);
-+                      ROOT_DEV = MKDEV(MTD_BLOCK_MAJOR, mtd->index);
-+              } else {
-+                      pr_warn("mtd: can't set mtd%d (%s) as root device - mtd must be builtin\n",
-+                              mtd->index, mtd->name);
-+              }
-+      }
-+
-       /* We _know_ we aren't being removed, because
-          our caller is still holding us here. So none
-          of this try_ nonsense, and no bitching about it
diff --git a/target/linux/generic/backport-5.15/409-v6.3-mtd-mtdpart-Don-t-create-platform-device-that-ll-nev.patch b/target/linux/generic/backport-5.15/409-v6.3-mtd-mtdpart-Don-t-create-platform-device-that-ll-nev.patch
deleted file mode 100644 (file)
index ba14ae0..0000000
+++ /dev/null
@@ -1,54 +0,0 @@
-From fb42378dcc7f247df56f0ecddfdae85487495fbc Mon Sep 17 00:00:00 2001
-From: Saravana Kannan <[email protected]>
-Date: Mon, 6 Feb 2023 17:42:04 -0800
-Subject: [PATCH] mtd: mtdpart: Don't create platform device that'll never
- probe
-
-These "nvmem-cells" platform devices never get probed because there's no
-platform driver for it and it's never used anywhere else. So it's a
-waste of memory. These devices also cause fw_devlink to block nvmem
-consumers of "nvmem-cells" partition from probing because the supplier
-device never probes.
-
-So stop creating platform devices for nvmem-cells partitions to avoid
-wasting memory and to avoid blocking probing of consumers.
-
-Reported-by: Maxim Kiselev <[email protected]>
-Fixes: bcdf0315a61a ("mtd: call of_platform_populate() for MTD partitions")
-Signed-off-by: Saravana Kannan <[email protected]>
-Tested-by: Maksim Kiselev <[email protected]>
-Tested-by: Douglas Anderson <[email protected]>
-Tested-by: Geert Uytterhoeven <[email protected]>
-Tested-by: Luca Weiss <[email protected]> # qcom/sm7225-fairphone-fp4
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/mtd/mtdpart.c | 10 ++++++++++
- 1 file changed, 10 insertions(+)
-
---- a/drivers/mtd/mtdpart.c
-+++ b/drivers/mtd/mtdpart.c
-@@ -577,6 +577,7 @@ static int mtd_part_of_parse(struct mtd_
- {
-       struct mtd_part_parser *parser;
-       struct device_node *np;
-+      struct device_node *child;
-       struct property *prop;
-       struct device *dev;
-       const char *compat;
-@@ -594,6 +595,15 @@ static int mtd_part_of_parse(struct mtd_
-       else
-               np = of_get_child_by_name(np, "partitions");
-+      /*
-+       * Don't create devices that are added to a bus but will never get
-+       * probed. That'll cause fw_devlink to block probing of consumers of
-+       * this partition until the partition device is probed.
-+       */
-+      for_each_child_of_node(np, child)
-+              if (of_device_is_compatible(child, "nvmem-cells"))
-+                      of_node_set_flag(child, OF_POPULATED);
-+
-       of_property_for_each_string(np, "compatible", prop, compat) {
-               parser = mtd_part_get_compatible_parser(compat);
-               if (!parser)
diff --git a/target/linux/generic/backport-5.15/410-v5.18-mtd-parsers-trx-allow-to-use-on-MediaTek-MIPS-SoCs.patch b/target/linux/generic/backport-5.15/410-v5.18-mtd-parsers-trx-allow-to-use-on-MediaTek-MIPS-SoCs.patch
deleted file mode 100644 (file)
index 5c49841..0000000
+++ /dev/null
@@ -1,33 +0,0 @@
-From 2365f91c861cbfeef7141c69842848c7b2d3c2db Mon Sep 17 00:00:00 2001
-From: INAGAKI Hiroshi <[email protected]>
-Date: Sun, 13 Feb 2022 15:40:44 +0900
-Subject: [PATCH] mtd: parsers: trx: allow to use on MediaTek MIPS SoCs
-
-Buffalo sells some router devices which have trx-formatted firmware,
-based on MediaTek MIPS SoCs. To use parser_trx on those devices, add
-"RALINK" to dependency and allow to compile for MediaTek MIPS SoCs.
-
-examples:
-
-- WCR-1166DS  (MT7628)
-- WSR-1166DHP (MT7621)
-- WSR-2533DHP (MT7621)
-
-Signed-off-by: INAGAKI Hiroshi <[email protected]>
-Signed-off-by: Miquel Raynal <[email protected]>
-Link: https://lore.kernel.org/linux-mtd/[email protected]
----
- drivers/mtd/parsers/Kconfig | 2 +-
- 1 file changed, 1 insertion(+), 1 deletion(-)
-
---- a/drivers/mtd/parsers/Kconfig
-+++ b/drivers/mtd/parsers/Kconfig
-@@ -115,7 +115,7 @@ config MTD_AFS_PARTS
- config MTD_PARSER_TRX
-       tristate "Parser for TRX format partitions"
--      depends on MTD && (BCM47XX || ARCH_BCM_5301X || ARCH_MEDIATEK || COMPILE_TEST)
-+      depends on MTD && (BCM47XX || ARCH_BCM_5301X || ARCH_MEDIATEK || RALINK || COMPILE_TEST)
-       help
-         TRX is a firmware format used by Broadcom on their devices. It
-         may contain up to 3/4 partitions (depending on the version).
diff --git a/target/linux/generic/backport-5.15/411-v6.9-mtd-rawnand-brcmnand-Support-write-protection-settin.patch b/target/linux/generic/backport-5.15/411-v6.9-mtd-rawnand-brcmnand-Support-write-protection-settin.patch
deleted file mode 100644 (file)
index dce2c91..0000000
+++ /dev/null
@@ -1,36 +0,0 @@
-From 8e7daa85641c9559c113f6b217bdc923397de77c Mon Sep 17 00:00:00 2001
-From: William Zhang <[email protected]>
-Date: Thu, 22 Feb 2024 19:47:58 -0800
-Subject: [PATCH] mtd: rawnand: brcmnand: Support write protection setting from
- dts
-
-The write protection feature is controlled by the module parameter wp_on
-with default set to enabled. But not all the board use this feature
-especially in BCMBCA broadband board. And module parameter is not
-sufficient as different board can have different option.  Add a device
-tree property and allow this feature to be configured through the board
-dts on per board basis.
-
-Signed-off-by: William Zhang <[email protected]>
-Reviewed-by: Florian Fainelli <[email protected]>
-Reviewed-by: Kamal Dasu <[email protected]>
-Reviewed-by: David Regan <[email protected]>
-Signed-off-by: Miquel Raynal <[email protected]>
-Link: https://lore.kernel.org/linux-mtd/[email protected]
----
- drivers/mtd/nand/raw/brcmnand/brcmnand.c | 4 ++++
- 1 file changed, 4 insertions(+)
-
---- a/drivers/mtd/nand/raw/brcmnand/brcmnand.c
-+++ b/drivers/mtd/nand/raw/brcmnand/brcmnand.c
-@@ -3184,6 +3184,10 @@ int brcmnand_probe(struct platform_devic
-       /* Disable XOR addressing */
-       brcmnand_rmw_reg(ctrl, BRCMNAND_CS_XOR, 0xff, 0, 0);
-+      /* Check if the board connects the WP pin */
-+      if (of_property_read_bool(dn, "brcm,wp-not-connected"))
-+              wp_on = 0;
-+
-       if (ctrl->features & BRCMNAND_HAS_WP) {
-               /* Permanently disable write protection */
-               if (wp_on == 2)
diff --git a/target/linux/generic/backport-5.15/412-v6.3-01-spidev-Add-Silicon-Labs-EM3581-device-compatible.patch b/target/linux/generic/backport-5.15/412-v6.3-01-spidev-Add-Silicon-Labs-EM3581-device-compatible.patch
deleted file mode 100644 (file)
index 1531915..0000000
+++ /dev/null
@@ -1,32 +0,0 @@
-From c67d90e058550403a3e6f9b05bfcdcfa12b1815c Mon Sep 17 00:00:00 2001
-From: Vincent Tremblay <[email protected]>
-Date: Mon, 26 Dec 2022 21:35:48 -0500
-Subject: [PATCH] spidev: Add Silicon Labs EM3581 device compatible
-
-Add compatible string for Silicon Labs EM3581 device.
-
-Signed-off-by: Vincent Tremblay <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Mark Brown <[email protected]>
----
- drivers/spi/spidev.c | 2 ++
- 1 file changed, 2 insertions(+)
-
---- a/drivers/spi/spidev.c
-+++ b/drivers/spi/spidev.c
-@@ -691,6 +691,7 @@ static const struct spi_device_id spidev
-       { .name = "m53cpld" },
-       { .name = "spi-petra" },
-       { .name = "spi-authenta" },
-+      { .name = "em3581" },
-       {},
- };
- MODULE_DEVICE_TABLE(spi, spidev_spi_ids);
-@@ -705,6 +706,7 @@ static const struct of_device_id spidev_
-       { .compatible = "menlo,m53cpld" },
-       { .compatible = "cisco,spi-petra" },
-       { .compatible = "micron,spi-authenta" },
-+      { .compatible = "silabs,em3581" },
-       {},
- };
- MODULE_DEVICE_TABLE(of, spidev_dt_ids);
diff --git a/target/linux/generic/backport-5.15/412-v6.3-02-spidev-Add-Silicon-Labs-SI3210-device-compatible.patch b/target/linux/generic/backport-5.15/412-v6.3-02-spidev-Add-Silicon-Labs-SI3210-device-compatible.patch
deleted file mode 100644 (file)
index ef36c82..0000000
+++ /dev/null
@@ -1,32 +0,0 @@
-From 6c9d1fd52956c3148e847a214bae9102b1811de5 Mon Sep 17 00:00:00 2001
-From: Vincent Tremblay <[email protected]>
-Date: Tue, 27 Dec 2022 09:10:08 -0500
-Subject: [PATCH] spidev: Add Silicon Labs SI3210 device compatible
-
-Add compatible string for Silicon Labs SI3210 device.
-
-Signed-off-by: Vincent Tremblay <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Mark Brown <[email protected]>
----
- drivers/spi/spidev.c | 2 ++
- 1 file changed, 2 insertions(+)
-
---- a/drivers/spi/spidev.c
-+++ b/drivers/spi/spidev.c
-@@ -692,6 +692,7 @@ static const struct spi_device_id spidev
-       { .name = "spi-petra" },
-       { .name = "spi-authenta" },
-       { .name = "em3581" },
-+      { .name = "si3210" },
-       {},
- };
- MODULE_DEVICE_TABLE(spi, spidev_spi_ids);
-@@ -707,6 +708,7 @@ static const struct of_device_id spidev_
-       { .compatible = "cisco,spi-petra" },
-       { .compatible = "micron,spi-authenta" },
-       { .compatible = "silabs,em3581" },
-+      { .compatible = "silabs,si3210" },
-       {},
- };
- MODULE_DEVICE_TABLE(of, spidev_dt_ids);
diff --git a/target/linux/generic/backport-5.15/420-v5.19-02-mtd-spinand-gigadevice-add-support-for-GD5FxGQ4xExxG.patch b/target/linux/generic/backport-5.15/420-v5.19-02-mtd-spinand-gigadevice-add-support-for-GD5FxGQ4xExxG.patch
deleted file mode 100644 (file)
index 94863b8..0000000
+++ /dev/null
@@ -1,58 +0,0 @@
-From 573eec222bc82fb5e724586267fbbb1aed9ffd03 Mon Sep 17 00:00:00 2001
-From: Chuanhong Guo <[email protected]>
-Date: Sun, 20 Mar 2022 17:59:58 +0800
-Subject: [PATCH 2/5] mtd: spinand: gigadevice: add support for GD5FxGQ4xExxG
-
-Add support for:
- GD5F1GQ4RExxG
- GD5F2GQ4{U,R}ExxG
-
-These chips differ from GD5F1GQ4UExxG only in chip ID, voltage
-and capacity.
-
-Signed-off-by: Chuanhong Guo <[email protected]>
-Signed-off-by: Miquel Raynal <[email protected]>
-Link: https://lore.kernel.org/linux-mtd/[email protected]
----
- drivers/mtd/nand/spi/gigadevice.c | 30 ++++++++++++++++++++++++++++++
- 1 file changed, 30 insertions(+)
-
---- a/drivers/mtd/nand/spi/gigadevice.c
-+++ b/drivers/mtd/nand/spi/gigadevice.c
-@@ -335,6 +335,36 @@ static const struct spinand_info gigadev
-                    SPINAND_HAS_QE_BIT,
-                    SPINAND_ECCINFO(&gd5fxgqx_variant2_ooblayout,
-                                    gd5fxgq4uexxg_ecc_get_status)),
-+      SPINAND_INFO("GD5F1GQ4RExxG",
-+                   SPINAND_ID(SPINAND_READID_METHOD_OPCODE_ADDR, 0xc1),
-+                   NAND_MEMORG(1, 2048, 128, 64, 1024, 20, 1, 1, 1),
-+                   NAND_ECCREQ(8, 512),
-+                   SPINAND_INFO_OP_VARIANTS(&read_cache_variants,
-+                                            &write_cache_variants,
-+                                            &update_cache_variants),
-+                   SPINAND_HAS_QE_BIT,
-+                   SPINAND_ECCINFO(&gd5fxgqx_variant2_ooblayout,
-+                                   gd5fxgq4uexxg_ecc_get_status)),
-+      SPINAND_INFO("GD5F2GQ4UExxG",
-+                   SPINAND_ID(SPINAND_READID_METHOD_OPCODE_ADDR, 0xd2),
-+                   NAND_MEMORG(1, 2048, 128, 64, 2048, 40, 1, 1, 1),
-+                   NAND_ECCREQ(8, 512),
-+                   SPINAND_INFO_OP_VARIANTS(&read_cache_variants,
-+                                            &write_cache_variants,
-+                                            &update_cache_variants),
-+                   SPINAND_HAS_QE_BIT,
-+                   SPINAND_ECCINFO(&gd5fxgqx_variant2_ooblayout,
-+                                   gd5fxgq4uexxg_ecc_get_status)),
-+      SPINAND_INFO("GD5F2GQ4RExxG",
-+                   SPINAND_ID(SPINAND_READID_METHOD_OPCODE_ADDR, 0xc2),
-+                   NAND_MEMORG(1, 2048, 128, 64, 2048, 40, 1, 1, 1),
-+                   NAND_ECCREQ(8, 512),
-+                   SPINAND_INFO_OP_VARIANTS(&read_cache_variants,
-+                                            &write_cache_variants,
-+                                            &update_cache_variants),
-+                   SPINAND_HAS_QE_BIT,
-+                   SPINAND_ECCINFO(&gd5fxgqx_variant2_ooblayout,
-+                                   gd5fxgq4uexxg_ecc_get_status)),
-       SPINAND_INFO("GD5F1GQ4UFxxG",
-                    SPINAND_ID(SPINAND_READID_METHOD_OPCODE, 0xb1, 0x48),
-                    NAND_MEMORG(1, 2048, 128, 64, 1024, 20, 1, 1, 1),
diff --git a/target/linux/generic/backport-5.15/420-v5.19-03-mtd-spinand-gigadevice-add-support-for-GD5F1GQ5RExxG.patch b/target/linux/generic/backport-5.15/420-v5.19-03-mtd-spinand-gigadevice-add-support-for-GD5F1GQ5RExxG.patch
deleted file mode 100644 (file)
index 287a062..0000000
+++ /dev/null
@@ -1,33 +0,0 @@
-From 620a988813403318023296b61228ee8f3fcdb8e0 Mon Sep 17 00:00:00 2001
-From: Chuanhong Guo <[email protected]>
-Date: Sun, 20 Mar 2022 17:59:59 +0800
-Subject: [PATCH 3/5] mtd: spinand: gigadevice: add support for GD5F1GQ5RExxG
-
-This chip is the 1.8v version of GD5F1GQ5UExxG.
-
-Signed-off-by: Chuanhong Guo <[email protected]>
-Signed-off-by: Miquel Raynal <[email protected]>
-Link: https://lore.kernel.org/linux-mtd/[email protected]
----
- drivers/mtd/nand/spi/gigadevice.c | 10 ++++++++++
- 1 file changed, 10 insertions(+)
-
---- a/drivers/mtd/nand/spi/gigadevice.c
-+++ b/drivers/mtd/nand/spi/gigadevice.c
-@@ -385,6 +385,16 @@ static const struct spinand_info gigadev
-                    SPINAND_HAS_QE_BIT,
-                    SPINAND_ECCINFO(&gd5fxgqx_variant2_ooblayout,
-                                    gd5fxgq5xexxg_ecc_get_status)),
-+      SPINAND_INFO("GD5F1GQ5RExxG",
-+                   SPINAND_ID(SPINAND_READID_METHOD_OPCODE_DUMMY, 0x41),
-+                   NAND_MEMORG(1, 2048, 128, 64, 1024, 20, 1, 1, 1),
-+                   NAND_ECCREQ(4, 512),
-+                   SPINAND_INFO_OP_VARIANTS(&read_cache_variants_1gq5,
-+                                            &write_cache_variants,
-+                                            &update_cache_variants),
-+                   SPINAND_HAS_QE_BIT,
-+                   SPINAND_ECCINFO(&gd5fxgqx_variant2_ooblayout,
-+                                   gd5fxgq5xexxg_ecc_get_status)),
- };
- static const struct spinand_manufacturer_ops gigadevice_spinand_manuf_ops = {
diff --git a/target/linux/generic/backport-5.15/420-v5.19-04-mtd-spinand-gigadevice-add-support-for-GD5F-2-4-GQ5x.patch b/target/linux/generic/backport-5.15/420-v5.19-04-mtd-spinand-gigadevice-add-support-for-GD5F-2-4-GQ5x.patch
deleted file mode 100644 (file)
index b1cf476..0000000
+++ /dev/null
@@ -1,84 +0,0 @@
-From 194ec04b3a9e7fa97d1fbef296410631bc3cf1c8 Mon Sep 17 00:00:00 2001
-From: Chuanhong Guo <[email protected]>
-Date: Sun, 20 Mar 2022 18:00:00 +0800
-Subject: [PATCH 4/5] mtd: spinand: gigadevice: add support for GD5F{2,
- 4}GQ5xExxG
-
-Add support for:
- GD5F2GQ5{U,R}ExxG
- GD5F4GQ6{U,R}ExxG
-
-These chips uses 4 dummy bytes for quad io and 2 dummy bytes for dual io.
-Besides that and memory layout, they are identical to their 1G variant.
-
-Signed-off-by: Chuanhong Guo <[email protected]>
-Signed-off-by: Miquel Raynal <[email protected]>
-Link: https://lore.kernel.org/linux-mtd/[email protected]
----
- drivers/mtd/nand/spi/gigadevice.c | 48 +++++++++++++++++++++++++++++++
- 1 file changed, 48 insertions(+)
-
---- a/drivers/mtd/nand/spi/gigadevice.c
-+++ b/drivers/mtd/nand/spi/gigadevice.c
-@@ -47,6 +47,14 @@ static SPINAND_OP_VARIANTS(read_cache_va
-               SPINAND_PAGE_READ_FROM_CACHE_OP(true, 0, 1, NULL, 0),
-               SPINAND_PAGE_READ_FROM_CACHE_OP(false, 0, 1, NULL, 0));
-+static SPINAND_OP_VARIANTS(read_cache_variants_2gq5,
-+              SPINAND_PAGE_READ_FROM_CACHE_QUADIO_OP(0, 4, NULL, 0),
-+              SPINAND_PAGE_READ_FROM_CACHE_X4_OP(0, 1, NULL, 0),
-+              SPINAND_PAGE_READ_FROM_CACHE_DUALIO_OP(0, 2, NULL, 0),
-+              SPINAND_PAGE_READ_FROM_CACHE_X2_OP(0, 1, NULL, 0),
-+              SPINAND_PAGE_READ_FROM_CACHE_OP(true, 0, 1, NULL, 0),
-+              SPINAND_PAGE_READ_FROM_CACHE_OP(false, 0, 1, NULL, 0));
-+
- static SPINAND_OP_VARIANTS(write_cache_variants,
-               SPINAND_PROG_LOAD_X4(true, 0, NULL, 0),
-               SPINAND_PROG_LOAD(true, 0, NULL, 0));
-@@ -393,6 +401,46 @@ static const struct spinand_info gigadev
-                                             &write_cache_variants,
-                                             &update_cache_variants),
-                    SPINAND_HAS_QE_BIT,
-+                   SPINAND_ECCINFO(&gd5fxgqx_variant2_ooblayout,
-+                                   gd5fxgq5xexxg_ecc_get_status)),
-+      SPINAND_INFO("GD5F2GQ5UExxG",
-+                   SPINAND_ID(SPINAND_READID_METHOD_OPCODE_DUMMY, 0x52),
-+                   NAND_MEMORG(1, 2048, 128, 64, 2048, 40, 1, 1, 1),
-+                   NAND_ECCREQ(4, 512),
-+                   SPINAND_INFO_OP_VARIANTS(&read_cache_variants_2gq5,
-+                                            &write_cache_variants,
-+                                            &update_cache_variants),
-+                   SPINAND_HAS_QE_BIT,
-+                   SPINAND_ECCINFO(&gd5fxgqx_variant2_ooblayout,
-+                                   gd5fxgq5xexxg_ecc_get_status)),
-+      SPINAND_INFO("GD5F2GQ5RExxG",
-+                   SPINAND_ID(SPINAND_READID_METHOD_OPCODE_DUMMY, 0x42),
-+                   NAND_MEMORG(1, 2048, 128, 64, 2048, 40, 1, 1, 1),
-+                   NAND_ECCREQ(4, 512),
-+                   SPINAND_INFO_OP_VARIANTS(&read_cache_variants_2gq5,
-+                                            &write_cache_variants,
-+                                            &update_cache_variants),
-+                   SPINAND_HAS_QE_BIT,
-+                   SPINAND_ECCINFO(&gd5fxgqx_variant2_ooblayout,
-+                                   gd5fxgq5xexxg_ecc_get_status)),
-+      SPINAND_INFO("GD5F4GQ6UExxG",
-+                   SPINAND_ID(SPINAND_READID_METHOD_OPCODE_DUMMY, 0x55),
-+                   NAND_MEMORG(1, 2048, 128, 64, 2048, 40, 1, 2, 1),
-+                   NAND_ECCREQ(4, 512),
-+                   SPINAND_INFO_OP_VARIANTS(&read_cache_variants_2gq5,
-+                                            &write_cache_variants,
-+                                            &update_cache_variants),
-+                   SPINAND_HAS_QE_BIT,
-+                   SPINAND_ECCINFO(&gd5fxgqx_variant2_ooblayout,
-+                                   gd5fxgq5xexxg_ecc_get_status)),
-+      SPINAND_INFO("GD5F4GQ6RExxG",
-+                   SPINAND_ID(SPINAND_READID_METHOD_OPCODE_DUMMY, 0x45),
-+                   NAND_MEMORG(1, 2048, 128, 64, 2048, 40, 1, 2, 1),
-+                   NAND_ECCREQ(4, 512),
-+                   SPINAND_INFO_OP_VARIANTS(&read_cache_variants_2gq5,
-+                                            &write_cache_variants,
-+                                            &update_cache_variants),
-+                   SPINAND_HAS_QE_BIT,
-                    SPINAND_ECCINFO(&gd5fxgqx_variant2_ooblayout,
-                                    gd5fxgq5xexxg_ecc_get_status)),
- };
diff --git a/target/linux/generic/backport-5.15/420-v5.19-05-mtd-spinand-gigadevice-add-support-for-GD5FxGM7xExxG.patch b/target/linux/generic/backport-5.15/420-v5.19-05-mtd-spinand-gigadevice-add-support-for-GD5FxGM7xExxG.patch
deleted file mode 100644 (file)
index 5e342a2..0000000
+++ /dev/null
@@ -1,91 +0,0 @@
-From 54647cd003c08b714474a5b599a147ec6a160486 Mon Sep 17 00:00:00 2001
-From: Chuanhong Guo <[email protected]>
-Date: Sun, 20 Mar 2022 18:00:01 +0800
-Subject: [PATCH 5/5] mtd: spinand: gigadevice: add support for GD5FxGM7xExxG
-
-Add support for:
- GD5F{1,2}GM7{U,R}ExxG
- GD5F4GM8{U,R}ExxG
-
-These are new 27nm counterparts for the GD5FxGQ4 chips from GigaDevice
-with 8b/512b on-die ECC capability.
-These chips (and currently supported GD5FxGQ5 chips) have QIO DTR
-instruction for reading page cache. It isn't added in this patch because
-I don't have a DTR spi controller for testing.
-
-Signed-off-by: Chuanhong Guo <[email protected]>
-Signed-off-by: Miquel Raynal <[email protected]>
-Link: https://lore.kernel.org/linux-mtd/[email protected]
----
- drivers/mtd/nand/spi/gigadevice.c | 60 +++++++++++++++++++++++++++++++
- 1 file changed, 60 insertions(+)
-
---- a/drivers/mtd/nand/spi/gigadevice.c
-+++ b/drivers/mtd/nand/spi/gigadevice.c
-@@ -443,6 +443,66 @@ static const struct spinand_info gigadev
-                    SPINAND_HAS_QE_BIT,
-                    SPINAND_ECCINFO(&gd5fxgqx_variant2_ooblayout,
-                                    gd5fxgq5xexxg_ecc_get_status)),
-+      SPINAND_INFO("GD5F1GM7UExxG",
-+                   SPINAND_ID(SPINAND_READID_METHOD_OPCODE_DUMMY, 0x91),
-+                   NAND_MEMORG(1, 2048, 128, 64, 1024, 20, 1, 1, 1),
-+                   NAND_ECCREQ(8, 512),
-+                   SPINAND_INFO_OP_VARIANTS(&read_cache_variants_1gq5,
-+                                            &write_cache_variants,
-+                                            &update_cache_variants),
-+                   SPINAND_HAS_QE_BIT,
-+                   SPINAND_ECCINFO(&gd5fxgqx_variant2_ooblayout,
-+                                   gd5fxgq4uexxg_ecc_get_status)),
-+      SPINAND_INFO("GD5F1GM7RExxG",
-+                   SPINAND_ID(SPINAND_READID_METHOD_OPCODE_DUMMY, 0x81),
-+                   NAND_MEMORG(1, 2048, 128, 64, 1024, 20, 1, 1, 1),
-+                   NAND_ECCREQ(8, 512),
-+                   SPINAND_INFO_OP_VARIANTS(&read_cache_variants_1gq5,
-+                                            &write_cache_variants,
-+                                            &update_cache_variants),
-+                   SPINAND_HAS_QE_BIT,
-+                   SPINAND_ECCINFO(&gd5fxgqx_variant2_ooblayout,
-+                                   gd5fxgq4uexxg_ecc_get_status)),
-+      SPINAND_INFO("GD5F2GM7UExxG",
-+                   SPINAND_ID(SPINAND_READID_METHOD_OPCODE_DUMMY, 0x92),
-+                   NAND_MEMORG(1, 2048, 128, 64, 2048, 40, 1, 1, 1),
-+                   NAND_ECCREQ(8, 512),
-+                   SPINAND_INFO_OP_VARIANTS(&read_cache_variants_1gq5,
-+                                            &write_cache_variants,
-+                                            &update_cache_variants),
-+                   SPINAND_HAS_QE_BIT,
-+                   SPINAND_ECCINFO(&gd5fxgqx_variant2_ooblayout,
-+                                   gd5fxgq4uexxg_ecc_get_status)),
-+      SPINAND_INFO("GD5F2GM7RExxG",
-+                   SPINAND_ID(SPINAND_READID_METHOD_OPCODE_DUMMY, 0x82),
-+                   NAND_MEMORG(1, 2048, 128, 64, 2048, 40, 1, 1, 1),
-+                   NAND_ECCREQ(8, 512),
-+                   SPINAND_INFO_OP_VARIANTS(&read_cache_variants_1gq5,
-+                                            &write_cache_variants,
-+                                            &update_cache_variants),
-+                   SPINAND_HAS_QE_BIT,
-+                   SPINAND_ECCINFO(&gd5fxgqx_variant2_ooblayout,
-+                                   gd5fxgq4uexxg_ecc_get_status)),
-+      SPINAND_INFO("GD5F4GM8UExxG",
-+                   SPINAND_ID(SPINAND_READID_METHOD_OPCODE_DUMMY, 0x95),
-+                   NAND_MEMORG(1, 2048, 128, 64, 4096, 80, 1, 1, 1),
-+                   NAND_ECCREQ(8, 512),
-+                   SPINAND_INFO_OP_VARIANTS(&read_cache_variants_1gq5,
-+                                            &write_cache_variants,
-+                                            &update_cache_variants),
-+                   SPINAND_HAS_QE_BIT,
-+                   SPINAND_ECCINFO(&gd5fxgqx_variant2_ooblayout,
-+                                   gd5fxgq4uexxg_ecc_get_status)),
-+      SPINAND_INFO("GD5F4GM8RExxG",
-+                   SPINAND_ID(SPINAND_READID_METHOD_OPCODE_DUMMY, 0x85),
-+                   NAND_MEMORG(1, 2048, 128, 64, 4096, 80, 1, 1, 1),
-+                   NAND_ECCREQ(8, 512),
-+                   SPINAND_INFO_OP_VARIANTS(&read_cache_variants_1gq5,
-+                                            &write_cache_variants,
-+                                            &update_cache_variants),
-+                   SPINAND_HAS_QE_BIT,
-+                   SPINAND_ECCINFO(&gd5fxgqx_variant2_ooblayout,
-+                                   gd5fxgq4uexxg_ecc_get_status)),
- };
- static const struct spinand_manufacturer_ops gigadevice_spinand_manuf_ops = {
diff --git a/target/linux/generic/backport-5.15/421-v6.2-mtd-parsers-add-TP-Link-SafeLoader-partitions-table-.patch b/target/linux/generic/backport-5.15/421-v6.2-mtd-parsers-add-TP-Link-SafeLoader-partitions-table-.patch
deleted file mode 100644 (file)
index 9f54336..0000000
+++ /dev/null
@@ -1,229 +0,0 @@
-From aec4d5f5ffd0f0092bd9dc21ea90e0bc237d4b74 Mon Sep 17 00:00:00 2001
-From: =?UTF-8?q?Rafa=C5=82=20Mi=C5=82ecki?= <[email protected]>
-Date: Sat, 15 Oct 2022 11:29:50 +0200
-Subject: [PATCH] mtd: parsers: add TP-Link SafeLoader partitions table parser
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-This parser deals with most TP-Link home routers. It reads info about
-partitions and registers them in the MTD subsystem.
-
-Example from TP-Link Archer C5 V2:
-
-spi-nor spi0.0: s25fl128s1 (16384 Kbytes)
-15 tplink-safeloader partitions found on MTD device spi0.0
-Creating 15 MTD partitions on "spi0.0":
-0x000000000000-0x000000040000 : "fs-uboot"
-0x000000040000-0x000000440000 : "os-image"
-0x000000440000-0x000000e40000 : "rootfs"
-0x000000e40000-0x000000e40200 : "default-mac"
-0x000000e40200-0x000000e40400 : "pin"
-0x000000e40400-0x000000e40600 : "product-info"
-0x000000e50000-0x000000e60000 : "partition-table"
-0x000000e60000-0x000000e60200 : "soft-version"
-0x000000e61000-0x000000e70000 : "support-list"
-0x000000e70000-0x000000e80000 : "profile"
-0x000000e80000-0x000000e90000 : "default-config"
-0x000000e90000-0x000000ee0000 : "user-config"
-0x000000ee0000-0x000000fe0000 : "log"
-0x000000fe0000-0x000000ff0000 : "radio_bk"
-0x000000ff0000-0x000001000000 : "radio"
-
-Signed-off-by: Rafał Miłecki <[email protected]>
-Signed-off-by: Miquel Raynal <[email protected]>
-Link: https://lore.kernel.org/linux-mtd/[email protected]
----
- drivers/mtd/parsers/Kconfig             |  15 +++
- drivers/mtd/parsers/Makefile            |   1 +
- drivers/mtd/parsers/tplink_safeloader.c | 150 ++++++++++++++++++++++++
- 3 files changed, 166 insertions(+)
- create mode 100644 drivers/mtd/parsers/tplink_safeloader.c
-
---- a/drivers/mtd/parsers/Kconfig
-+++ b/drivers/mtd/parsers/Kconfig
-@@ -113,6 +113,21 @@ config MTD_AFS_PARTS
-         for your particular device. It won't happen automatically. The
-         'physmap' map driver (CONFIG_MTD_PHYSMAP) does this, for example.
-+config MTD_PARSER_TPLINK_SAFELOADER
-+      tristate "TP-Link Safeloader partitions parser"
-+      depends on MTD && (ARCH_BCM_5301X || ATH79 || SOC_MT7620 || SOC_MT7621 || COMPILE_TEST)
-+      help
-+        TP-Link home routers use flash partitions to store various data. Info
-+        about flash space layout is stored in a partitions table using a
-+        custom ASCII-based format.
-+
-+        That format was first found in devices with SafeLoader bootloader and
-+        was named after it. Later it was adapted to CFE and U-Boot
-+        bootloaders.
-+
-+        This driver reads partitions table, parses it and creates MTD
-+        partitions.
-+
- config MTD_PARSER_TRX
-       tristate "Parser for TRX format partitions"
-       depends on MTD && (BCM47XX || ARCH_BCM_5301X || ARCH_MEDIATEK || RALINK || COMPILE_TEST)
---- a/drivers/mtd/parsers/Makefile
-+++ b/drivers/mtd/parsers/Makefile
-@@ -9,6 +9,7 @@ ofpart-$(CONFIG_MTD_OF_PARTS_BCM4908)  +=
- ofpart-$(CONFIG_MTD_OF_PARTS_LINKSYS_NS)+= ofpart_linksys_ns.o
- obj-$(CONFIG_MTD_PARSER_IMAGETAG)     += parser_imagetag.o
- obj-$(CONFIG_MTD_AFS_PARTS)           += afs.o
-+obj-$(CONFIG_MTD_PARSER_TPLINK_SAFELOADER)    += tplink_safeloader.o
- obj-$(CONFIG_MTD_PARSER_TRX)          += parser_trx.o
- obj-$(CONFIG_MTD_SERCOMM_PARTS)               += scpart.o
- obj-$(CONFIG_MTD_SHARPSL_PARTS)               += sharpslpart.o
---- /dev/null
-+++ b/drivers/mtd/parsers/tplink_safeloader.c
-@@ -0,0 +1,150 @@
-+// SPDX-License-Identifier: GPL-2.0-only
-+/*
-+ * Copyright © 2022 Rafał Miłecki <[email protected]>
-+ */
-+
-+#include <linux/kernel.h>
-+#include <linux/module.h>
-+#include <linux/mtd/mtd.h>
-+#include <linux/mtd/partitions.h>
-+#include <linux/of.h>
-+#include <linux/slab.h>
-+
-+#define TPLINK_SAFELOADER_DATA_OFFSET         4
-+#define TPLINK_SAFELOADER_MAX_PARTS           32
-+
-+struct safeloader_cmn_header {
-+      __be32 size;
-+      uint32_t unused;
-+} __packed;
-+
-+static void *mtd_parser_tplink_safeloader_read_table(struct mtd_info *mtd)
-+{
-+      struct safeloader_cmn_header hdr;
-+      struct device_node *np;
-+      size_t bytes_read;
-+      size_t offset;
-+      size_t size;
-+      char *buf;
-+      int err;
-+
-+      np = mtd_get_of_node(mtd);
-+      if (mtd_is_partition(mtd))
-+              of_node_get(np);
-+      else
-+              np = of_get_child_by_name(np, "partitions");
-+
-+      if (of_property_read_u32(np, "partitions-table-offset", (u32 *)&offset)) {
-+              pr_err("Failed to get partitions table offset\n");
-+              goto err_put;
-+      }
-+
-+      err = mtd_read(mtd, offset, sizeof(hdr), &bytes_read, (uint8_t *)&hdr);
-+      if (err && !mtd_is_bitflip(err)) {
-+              pr_err("Failed to read from %s at 0x%zx\n", mtd->name, offset);
-+              goto err_put;
-+      }
-+
-+      size = be32_to_cpu(hdr.size);
-+
-+      buf = kmalloc(size + 1, GFP_KERNEL);
-+      if (!buf)
-+              goto err_put;
-+
-+      err = mtd_read(mtd, offset + sizeof(hdr), size, &bytes_read, buf);
-+      if (err && !mtd_is_bitflip(err)) {
-+              pr_err("Failed to read from %s at 0x%zx\n", mtd->name, offset + sizeof(hdr));
-+              goto err_kfree;
-+      }
-+
-+      buf[size] = '\0';
-+
-+      of_node_put(np);
-+
-+      return buf;
-+
-+err_kfree:
-+      kfree(buf);
-+err_put:
-+      of_node_put(np);
-+      return NULL;
-+}
-+
-+static int mtd_parser_tplink_safeloader_parse(struct mtd_info *mtd,
-+                                            const struct mtd_partition **pparts,
-+                                            struct mtd_part_parser_data *data)
-+{
-+      struct mtd_partition *parts;
-+      char name[65];
-+      size_t offset;
-+      size_t bytes;
-+      char *buf;
-+      int idx;
-+      int err;
-+
-+      parts = kcalloc(TPLINK_SAFELOADER_MAX_PARTS, sizeof(*parts), GFP_KERNEL);
-+      if (!parts) {
-+              err = -ENOMEM;
-+              goto err_out;
-+      }
-+
-+      buf = mtd_parser_tplink_safeloader_read_table(mtd);
-+      if (!buf) {
-+              err = -ENOENT;
-+              goto err_out;
-+      }
-+
-+      for (idx = 0, offset = TPLINK_SAFELOADER_DATA_OFFSET;
-+           idx < TPLINK_SAFELOADER_MAX_PARTS &&
-+           sscanf(buf + offset, "partition %64s base 0x%llx size 0x%llx%zn\n",
-+                  name, &parts[idx].offset, &parts[idx].size, &bytes) == 3;
-+           idx++, offset += bytes + 1) {
-+              parts[idx].name = kstrdup(name, GFP_KERNEL);
-+              if (!parts[idx].name) {
-+                      err = -ENOMEM;
-+                      goto err_free;
-+              }
-+      }
-+
-+      if (idx == TPLINK_SAFELOADER_MAX_PARTS)
-+              pr_warn("Reached maximum number of partitions!\n");
-+
-+      kfree(buf);
-+
-+      *pparts = parts;
-+
-+      return idx;
-+
-+err_free:
-+      for (idx -= 1; idx >= 0; idx--)
-+              kfree(parts[idx].name);
-+err_out:
-+      return err;
-+};
-+
-+static void mtd_parser_tplink_safeloader_cleanup(const struct mtd_partition *pparts,
-+                                               int nr_parts)
-+{
-+      int i;
-+
-+      for (i = 0; i < nr_parts; i++)
-+              kfree(pparts[i].name);
-+
-+      kfree(pparts);
-+}
-+
-+static const struct of_device_id mtd_parser_tplink_safeloader_of_match_table[] = {
-+      { .compatible = "tplink,safeloader-partitions" },
-+      {},
-+};
-+MODULE_DEVICE_TABLE(of, mtd_parser_tplink_safeloader_of_match_table);
-+
-+static struct mtd_part_parser mtd_parser_tplink_safeloader = {
-+      .parse_fn = mtd_parser_tplink_safeloader_parse,
-+      .cleanup = mtd_parser_tplink_safeloader_cleanup,
-+      .name = "tplink-safeloader",
-+      .of_match_table = mtd_parser_tplink_safeloader_of_match_table,
-+};
-+module_mtd_part_parser(mtd_parser_tplink_safeloader);
-+
-+MODULE_LICENSE("GPL");
diff --git a/target/linux/generic/backport-5.15/422-v5.19-mtd-spi-nor-support-eon-en25qh256a.patch b/target/linux/generic/backport-5.15/422-v5.19-mtd-spi-nor-support-eon-en25qh256a.patch
deleted file mode 100644 (file)
index 2358352..0000000
+++ /dev/null
@@ -1,49 +0,0 @@
-From 6abef37d16d0c570ef5a149e63762fba2a30804b Mon Sep 17 00:00:00 2001
-From: "Leon M. George" <[email protected]>
-Date: Wed, 30 Mar 2022 16:16:56 +0200
-Subject: [PATCH] mtd: spi-nor: support eon en25qh256a variant
-
-The EN25QH256A variant of the EN25QH256 doesn't initialize correctly from SFDP
-alone and only accesses memory below 8m (addr_width is 4 but read_opcode takes
-only 3 bytes).
-
-Set SNOR_F_4B_OPCODES if the flash chip variant was detected using hwcaps.
-
-The fix submitted upstream uses the PARSE_SFDP initializer that is not
-available in the kernel used with Openwrt.
-
-Signed-off-by: Leon M. George <[email protected]>
----
- drivers/mtd/spi-nor/eon.c | 11 +++++++++++
- 1 file changed, 11 insertions(+)
-
---- a/drivers/mtd/spi-nor/eon.c
-+++ b/drivers/mtd/spi-nor/eon.c
-@@ -8,6 +8,16 @@
- #include "core.h"
-+static void en25qh256_post_sfdp_fixups(struct spi_nor *nor)
-+{
-+      if (nor->params->hwcaps.mask & SNOR_HWCAPS_READ_1_1_4)
-+              nor->flags |= SNOR_F_4B_OPCODES;
-+}
-+
-+static const struct spi_nor_fixups en25qh256_fixups = {
-+      .post_sfdp = en25qh256_post_sfdp_fixups,
-+};
-+
- static const struct flash_info eon_parts[] = {
-       /* EON -- en25xxx */
-       { "en25f32",    INFO(0x1c3116, 0, 64 * 1024,   64, SECT_4K) },
-@@ -23,7 +33,9 @@ static const struct flash_info eon_parts
-       { "en25qh64",   INFO(0x1c7017, 0, 64 * 1024,  128,
-                            SECT_4K | SPI_NOR_DUAL_READ) },
-       { "en25qh128",  INFO(0x1c7018, 0, 64 * 1024,  256, 0) },
--      { "en25qh256",  INFO(0x1c7019, 0, 64 * 1024,  512, 0) },
-+      { "en25qh256",  INFO(0x1c7019, 0, 64 * 1024,  512,
-+              SPI_NOR_DUAL_READ)
-+              .fixups = &en25qh256_fixups },
-       { "en25s64",    INFO(0x1c3817, 0, 64 * 1024,  128, SECT_4K) },
- };
diff --git a/target/linux/generic/backport-5.15/423-v6.1-0001-mtd-track-maximum-number-of-bitflips-for-each-read-r.patch b/target/linux/generic/backport-5.15/423-v6.1-0001-mtd-track-maximum-number-of-bitflips-for-each-read-r.patch
deleted file mode 100644 (file)
index c17dd5b..0000000
+++ /dev/null
@@ -1,73 +0,0 @@
-From e237285113963bd1dd2e925770aa8b3aa8a1894c Mon Sep 17 00:00:00 2001
-From: =?UTF-8?q?Micha=C5=82=20K=C4=99pie=C5=84?= <[email protected]>
-Date: Wed, 29 Jun 2022 14:57:34 +0200
-Subject: [PATCH 1/4] mtd: track maximum number of bitflips for each read
- request
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-mtd_read_oob() callers are currently oblivious to the details of ECC
-errors detected during the read operation - they only learn (through the
-return value) whether any corrected bitflips or uncorrectable errors
-occurred.  More detailed ECC information can be useful to user-space
-applications for making better-informed choices about moving data
-around.
-
-Extend struct mtd_oob_ops with a pointer to a newly-introduced struct
-mtd_req_stats and set its 'max_bitflips' field to the maximum number of
-bitflips found in a single ECC step during the read operation performed
-by mtd_read_oob().  This is a prerequisite for ultimately passing that
-value back to user space.
-
-Suggested-by: Boris Brezillon <[email protected]>
-Signed-off-by: Michał Kępień <[email protected]>
-Signed-off-by: Miquel Raynal <[email protected]>
-Link: https://lore.kernel.org/linux-mtd/[email protected]
----
- drivers/mtd/mtdcore.c   | 5 +++++
- include/linux/mtd/mtd.h | 5 +++++
- 2 files changed, 10 insertions(+)
-
---- a/drivers/mtd/mtdcore.c
-+++ b/drivers/mtd/mtdcore.c
-@@ -1678,6 +1678,9 @@ int mtd_read_oob(struct mtd_info *mtd, l
-       if (!master->_read_oob && (!master->_read || ops->oobbuf))
-               return -EOPNOTSUPP;
-+      if (ops->stats)
-+              memset(ops->stats, 0, sizeof(*ops->stats));
-+
-       if (mtd->flags & MTD_SLC_ON_MLC_EMULATION)
-               ret_code = mtd_io_emulated_slc(mtd, from, true, ops);
-       else
-@@ -1695,6 +1698,8 @@ int mtd_read_oob(struct mtd_info *mtd, l
-               return ret_code;
-       if (mtd->ecc_strength == 0)
-               return 0;       /* device lacks ecc */
-+      if (ops->stats)
-+              ops->stats->max_bitflips = ret_code;
-       return ret_code >= mtd->bitflip_threshold ? -EUCLEAN : 0;
- }
- EXPORT_SYMBOL_GPL(mtd_read_oob);
---- a/include/linux/mtd/mtd.h
-+++ b/include/linux/mtd/mtd.h
-@@ -40,6 +40,10 @@ struct mtd_erase_region_info {
-       unsigned long *lockmap;         /* If keeping bitmap of locks */
- };
-+struct mtd_req_stats {
-+      unsigned int max_bitflips;
-+};
-+
- /**
-  * struct mtd_oob_ops - oob operation operands
-  * @mode:     operation mode
-@@ -70,6 +74,7 @@ struct mtd_oob_ops {
-       uint32_t        ooboffs;
-       uint8_t         *datbuf;
-       uint8_t         *oobbuf;
-+      struct mtd_req_stats *stats;
- };
- #define MTD_MAX_OOBFREE_ENTRIES_LARGE 32
diff --git a/target/linux/generic/backport-5.15/423-v6.1-0002-mtd-always-initialize-stats-in-struct-mtd_oob_ops.patch b/target/linux/generic/backport-5.15/423-v6.1-0002-mtd-always-initialize-stats-in-struct-mtd_oob_ops.patch
deleted file mode 100644 (file)
index 1484624..0000000
+++ /dev/null
@@ -1,325 +0,0 @@
-From e97709c9d18903f5acd5fbe2985dd054da0432b1 Mon Sep 17 00:00:00 2001
-From: =?UTF-8?q?Micha=C5=82=20K=C4=99pie=C5=84?= <[email protected]>
-Date: Wed, 29 Jun 2022 14:57:35 +0200
-Subject: [PATCH 2/4] mtd: always initialize 'stats' in struct mtd_oob_ops
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-As the 'stats' field in struct mtd_oob_ops is used in conditional
-expressions, ensure it is always zero-initialized in all such structures
-to prevent random stack garbage from being interpreted as a pointer.
-
-Strictly speaking, this problem currently only needs to be fixed for
-struct mtd_oob_ops structures subsequently passed to mtd_read_oob().
-However, this commit goes a step further and makes all instances of
-struct mtd_oob_ops in the tree zero-initialized, in hope of preventing
-future problems, e.g. if struct mtd_req_stats gets extended with write
-statistics at some point.
-
-Signed-off-by: Michał Kępień <[email protected]>
-Signed-off-by: Miquel Raynal <[email protected]>
-Link: https://lore.kernel.org/linux-mtd/[email protected]
----
- drivers/mtd/inftlcore.c                 | 6 +++---
- drivers/mtd/mtdswap.c                   | 6 +++---
- drivers/mtd/nand/onenand/onenand_base.c | 4 ++--
- drivers/mtd/nand/onenand/onenand_bbt.c  | 2 +-
- drivers/mtd/nand/raw/nand_bbt.c         | 8 ++++----
- drivers/mtd/nand/raw/sm_common.c        | 2 +-
- drivers/mtd/nftlcore.c                  | 6 +++---
- drivers/mtd/sm_ftl.c                    | 4 ++--
- drivers/mtd/ssfdc.c                     | 2 +-
- drivers/mtd/tests/nandbiterrs.c         | 2 +-
- drivers/mtd/tests/oobtest.c             | 8 ++++----
- drivers/mtd/tests/readtest.c            | 2 +-
- fs/jffs2/wbuf.c                         | 6 +++---
- 13 files changed, 29 insertions(+), 29 deletions(-)
-
---- a/drivers/mtd/inftlcore.c
-+++ b/drivers/mtd/inftlcore.c
-@@ -136,7 +136,7 @@ static void inftl_remove_dev(struct mtd_
- int inftl_read_oob(struct mtd_info *mtd, loff_t offs, size_t len,
-                  size_t *retlen, uint8_t *buf)
- {
--      struct mtd_oob_ops ops;
-+      struct mtd_oob_ops ops = { };
-       int res;
-       ops.mode = MTD_OPS_PLACE_OOB;
-@@ -156,7 +156,7 @@ int inftl_read_oob(struct mtd_info *mtd,
- int inftl_write_oob(struct mtd_info *mtd, loff_t offs, size_t len,
-                   size_t *retlen, uint8_t *buf)
- {
--      struct mtd_oob_ops ops;
-+      struct mtd_oob_ops ops = { };
-       int res;
-       ops.mode = MTD_OPS_PLACE_OOB;
-@@ -176,7 +176,7 @@ int inftl_write_oob(struct mtd_info *mtd
- static int inftl_write(struct mtd_info *mtd, loff_t offs, size_t len,
-                      size_t *retlen, uint8_t *buf, uint8_t *oob)
- {
--      struct mtd_oob_ops ops;
-+      struct mtd_oob_ops ops = { };
-       int res;
-       ops.mode = MTD_OPS_PLACE_OOB;
---- a/drivers/mtd/mtdswap.c
-+++ b/drivers/mtd/mtdswap.c
-@@ -323,7 +323,7 @@ static int mtdswap_read_markers(struct m
-       struct mtdswap_oobdata *data, *data2;
-       int ret;
-       loff_t offset;
--      struct mtd_oob_ops ops;
-+      struct mtd_oob_ops ops = { };
-       offset = mtdswap_eb_offset(d, eb);
-@@ -370,7 +370,7 @@ static int mtdswap_write_marker(struct m
-       struct mtdswap_oobdata n;
-       int ret;
-       loff_t offset;
--      struct mtd_oob_ops ops;
-+      struct mtd_oob_ops ops = { };
-       ops.ooboffs = 0;
-       ops.oobbuf = (uint8_t *)&n;
-@@ -879,7 +879,7 @@ static unsigned int mtdswap_eblk_passes(
-       loff_t base, pos;
-       unsigned int *p1 = (unsigned int *)d->page_buf;
-       unsigned char *p2 = (unsigned char *)d->oob_buf;
--      struct mtd_oob_ops ops;
-+      struct mtd_oob_ops ops = { };
-       int ret;
-       ops.mode = MTD_OPS_AUTO_OOB;
---- a/drivers/mtd/nand/onenand/onenand_base.c
-+++ b/drivers/mtd/nand/onenand/onenand_base.c
-@@ -2935,7 +2935,7 @@ static int do_otp_write(struct mtd_info
-       struct onenand_chip *this = mtd->priv;
-       unsigned char *pbuf = buf;
-       int ret;
--      struct mtd_oob_ops ops;
-+      struct mtd_oob_ops ops = { };
-       /* Force buffer page aligned */
-       if (len < mtd->writesize) {
-@@ -2977,7 +2977,7 @@ static int do_otp_lock(struct mtd_info *
-               size_t *retlen, u_char *buf)
- {
-       struct onenand_chip *this = mtd->priv;
--      struct mtd_oob_ops ops;
-+      struct mtd_oob_ops ops = { };
-       int ret;
-       if (FLEXONENAND(this)) {
---- a/drivers/mtd/nand/onenand/onenand_bbt.c
-+++ b/drivers/mtd/nand/onenand/onenand_bbt.c
-@@ -61,7 +61,7 @@ static int create_bbt(struct mtd_info *m
-       int startblock;
-       loff_t from;
-       size_t readlen, ooblen;
--      struct mtd_oob_ops ops;
-+      struct mtd_oob_ops ops = { };
-       int rgn;
-       printk(KERN_INFO "Scanning device for bad blocks\n");
---- a/drivers/mtd/nand/raw/nand_bbt.c
-+++ b/drivers/mtd/nand/raw/nand_bbt.c
-@@ -313,7 +313,7 @@ static int scan_read_oob(struct nand_chi
-                        size_t len)
- {
-       struct mtd_info *mtd = nand_to_mtd(this);
--      struct mtd_oob_ops ops;
-+      struct mtd_oob_ops ops = { };
-       int res, ret = 0;
-       ops.mode = MTD_OPS_PLACE_OOB;
-@@ -354,7 +354,7 @@ static int scan_write_bbt(struct nand_ch
-                         uint8_t *buf, uint8_t *oob)
- {
-       struct mtd_info *mtd = nand_to_mtd(this);
--      struct mtd_oob_ops ops;
-+      struct mtd_oob_ops ops = { };
-       ops.mode = MTD_OPS_PLACE_OOB;
-       ops.ooboffs = 0;
-@@ -416,7 +416,7 @@ static int scan_block_fast(struct nand_c
- {
-       struct mtd_info *mtd = nand_to_mtd(this);
--      struct mtd_oob_ops ops;
-+      struct mtd_oob_ops ops = { };
-       int ret, page_offset;
-       ops.ooblen = mtd->oobsize;
-@@ -756,7 +756,7 @@ static int write_bbt(struct nand_chip *t
-       uint8_t rcode = td->reserved_block_code;
-       size_t retlen, len = 0;
-       loff_t to;
--      struct mtd_oob_ops ops;
-+      struct mtd_oob_ops ops = { };
-       ops.ooblen = mtd->oobsize;
-       ops.ooboffs = 0;
---- a/drivers/mtd/nand/raw/sm_common.c
-+++ b/drivers/mtd/nand/raw/sm_common.c
-@@ -99,7 +99,7 @@ static const struct mtd_ooblayout_ops oo
- static int sm_block_markbad(struct nand_chip *chip, loff_t ofs)
- {
-       struct mtd_info *mtd = nand_to_mtd(chip);
--      struct mtd_oob_ops ops;
-+      struct mtd_oob_ops ops = { };
-       struct sm_oob oob;
-       int ret;
---- a/drivers/mtd/nftlcore.c
-+++ b/drivers/mtd/nftlcore.c
-@@ -124,7 +124,7 @@ int nftl_read_oob(struct mtd_info *mtd,
-                 size_t *retlen, uint8_t *buf)
- {
-       loff_t mask = mtd->writesize - 1;
--      struct mtd_oob_ops ops;
-+      struct mtd_oob_ops ops = { };
-       int res;
-       ops.mode = MTD_OPS_PLACE_OOB;
-@@ -145,7 +145,7 @@ int nftl_write_oob(struct mtd_info *mtd,
-                  size_t *retlen, uint8_t *buf)
- {
-       loff_t mask = mtd->writesize - 1;
--      struct mtd_oob_ops ops;
-+      struct mtd_oob_ops ops = { };
-       int res;
-       ops.mode = MTD_OPS_PLACE_OOB;
-@@ -168,7 +168,7 @@ static int nftl_write(struct mtd_info *m
-                     size_t *retlen, uint8_t *buf, uint8_t *oob)
- {
-       loff_t mask = mtd->writesize - 1;
--      struct mtd_oob_ops ops;
-+      struct mtd_oob_ops ops = { };
-       int res;
-       ops.mode = MTD_OPS_PLACE_OOB;
---- a/drivers/mtd/sm_ftl.c
-+++ b/drivers/mtd/sm_ftl.c
-@@ -239,7 +239,7 @@ static int sm_read_sector(struct sm_ftl
-                         uint8_t *buffer, struct sm_oob *oob)
- {
-       struct mtd_info *mtd = ftl->trans->mtd;
--      struct mtd_oob_ops ops;
-+      struct mtd_oob_ops ops = { };
-       struct sm_oob tmp_oob;
-       int ret = -EIO;
-       int try = 0;
-@@ -323,7 +323,7 @@ static int sm_write_sector(struct sm_ftl
-                          int zone, int block, int boffset,
-                          uint8_t *buffer, struct sm_oob *oob)
- {
--      struct mtd_oob_ops ops;
-+      struct mtd_oob_ops ops = { };
-       struct mtd_info *mtd = ftl->trans->mtd;
-       int ret;
---- a/drivers/mtd/ssfdc.c
-+++ b/drivers/mtd/ssfdc.c
-@@ -163,7 +163,7 @@ static int read_physical_sector(struct m
- /* Read redundancy area (wrapper to MTD_READ_OOB */
- static int read_raw_oob(struct mtd_info *mtd, loff_t offs, uint8_t *buf)
- {
--      struct mtd_oob_ops ops;
-+      struct mtd_oob_ops ops = { };
-       int ret;
-       ops.mode = MTD_OPS_RAW;
---- a/drivers/mtd/tests/nandbiterrs.c
-+++ b/drivers/mtd/tests/nandbiterrs.c
-@@ -99,7 +99,7 @@ static int write_page(int log)
- static int rewrite_page(int log)
- {
-       int err = 0;
--      struct mtd_oob_ops ops;
-+      struct mtd_oob_ops ops = { };
-       if (log)
-               pr_info("rewrite page\n");
---- a/drivers/mtd/tests/oobtest.c
-+++ b/drivers/mtd/tests/oobtest.c
-@@ -56,7 +56,7 @@ static void do_vary_offset(void)
- static int write_eraseblock(int ebnum)
- {
-       int i;
--      struct mtd_oob_ops ops;
-+      struct mtd_oob_ops ops = { };
-       int err = 0;
-       loff_t addr = (loff_t)ebnum * mtd->erasesize;
-@@ -165,7 +165,7 @@ static size_t memffshow(loff_t addr, lof
- static int verify_eraseblock(int ebnum)
- {
-       int i;
--      struct mtd_oob_ops ops;
-+      struct mtd_oob_ops ops = { };
-       int err = 0;
-       loff_t addr = (loff_t)ebnum * mtd->erasesize;
-       size_t bitflips;
-@@ -260,7 +260,7 @@ static int verify_eraseblock(int ebnum)
- static int verify_eraseblock_in_one_go(int ebnum)
- {
--      struct mtd_oob_ops ops;
-+      struct mtd_oob_ops ops = { };
-       int err = 0;
-       loff_t addr = (loff_t)ebnum * mtd->erasesize;
-       size_t len = mtd->oobavail * pgcnt;
-@@ -338,7 +338,7 @@ static int __init mtd_oobtest_init(void)
-       int err = 0;
-       unsigned int i;
-       uint64_t tmp;
--      struct mtd_oob_ops ops;
-+      struct mtd_oob_ops ops = { };
-       loff_t addr = 0, addr0;
-       printk(KERN_INFO "\n");
---- a/drivers/mtd/tests/readtest.c
-+++ b/drivers/mtd/tests/readtest.c
-@@ -47,7 +47,7 @@ static int read_eraseblock_by_page(int e
-                               err = ret;
-               }
-               if (mtd->oobsize) {
--                      struct mtd_oob_ops ops;
-+                      struct mtd_oob_ops ops = { };
-                       ops.mode      = MTD_OPS_PLACE_OOB;
-                       ops.len       = 0;
---- a/fs/jffs2/wbuf.c
-+++ b/fs/jffs2/wbuf.c
-@@ -1035,7 +1035,7 @@ int jffs2_check_oob_empty(struct jffs2_s
- {
-       int i, ret;
-       int cmlen = min_t(int, c->oobavail, OOB_CM_SIZE);
--      struct mtd_oob_ops ops;
-+      struct mtd_oob_ops ops = { };
-       ops.mode = MTD_OPS_AUTO_OOB;
-       ops.ooblen = NR_OOB_SCAN_PAGES * c->oobavail;
-@@ -1076,7 +1076,7 @@ int jffs2_check_oob_empty(struct jffs2_s
- int jffs2_check_nand_cleanmarker(struct jffs2_sb_info *c,
-                                struct jffs2_eraseblock *jeb)
- {
--      struct mtd_oob_ops ops;
-+      struct mtd_oob_ops ops = { };
-       int ret, cmlen = min_t(int, c->oobavail, OOB_CM_SIZE);
-       ops.mode = MTD_OPS_AUTO_OOB;
-@@ -1101,7 +1101,7 @@ int jffs2_write_nand_cleanmarker(struct
-                                struct jffs2_eraseblock *jeb)
- {
-       int ret;
--      struct mtd_oob_ops ops;
-+      struct mtd_oob_ops ops = { };
-       int cmlen = min_t(int, c->oobavail, OOB_CM_SIZE);
-       ops.mode = MTD_OPS_AUTO_OOB;
diff --git a/target/linux/generic/backport-5.15/423-v6.1-0003-mtd-add-ECC-error-accounting-for-each-read-request.patch b/target/linux/generic/backport-5.15/423-v6.1-0003-mtd-add-ECC-error-accounting-for-each-read-request.patch
deleted file mode 100644 (file)
index f2f45eb..0000000
+++ /dev/null
@@ -1,172 +0,0 @@
-From 2ed18d818d1f7492172f8dd5904344c7d367e8ed Mon Sep 17 00:00:00 2001
-From: =?UTF-8?q?Micha=C5=82=20K=C4=99pie=C5=84?= <[email protected]>
-Date: Wed, 29 Jun 2022 14:57:36 +0200
-Subject: [PATCH 3/4] mtd: add ECC error accounting for each read request
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-Extend struct mtd_req_stats with two new fields holding the number of
-corrected bitflips and uncorrectable errors detected during a read
-operation.  This is a prerequisite for ultimately passing those counters
-to user space, where they can be useful to applications for making
-better-informed choices about moving data around.
-
-Unlike 'max_bitflips' (which is set - in a common code path - to the
-return value of a function called while the MTD device's mutex is held),
-these counters have to be maintained in each MTD driver which defines
-the '_read_oob' callback because the statistics need to be calculated
-while the MTD device's mutex is held.
-
-Suggested-by: Boris Brezillon <[email protected]>
-Signed-off-by: Michał Kępień <[email protected]>
-Signed-off-by: Miquel Raynal <[email protected]>
-Link: https://lore.kernel.org/linux-mtd/[email protected]
----
- drivers/mtd/devices/docg3.c             |  8 ++++++++
- drivers/mtd/nand/onenand/onenand_base.c | 12 ++++++++++++
- drivers/mtd/nand/raw/nand_base.c        | 10 ++++++++++
- drivers/mtd/nand/spi/core.c             | 10 ++++++++++
- include/linux/mtd/mtd.h                 |  2 ++
- 5 files changed, 42 insertions(+)
-
---- a/drivers/mtd/devices/docg3.c
-+++ b/drivers/mtd/devices/docg3.c
-@@ -871,6 +871,7 @@ static int doc_read_oob(struct mtd_info
-       u8 *buf = ops->datbuf;
-       size_t len, ooblen, nbdata, nboob;
-       u8 hwecc[DOC_ECC_BCH_SIZE], eccconf1;
-+      struct mtd_ecc_stats old_stats;
-       int max_bitflips = 0;
-       if (buf)
-@@ -895,6 +896,7 @@ static int doc_read_oob(struct mtd_info
-       ret = 0;
-       skip = from % DOC_LAYOUT_PAGE_SIZE;
-       mutex_lock(&docg3->cascade->lock);
-+      old_stats = mtd->ecc_stats;
-       while (ret >= 0 && (len > 0 || ooblen > 0)) {
-               calc_block_sector(from - skip, &block0, &block1, &page, &ofs,
-                       docg3->reliable);
-@@ -966,6 +968,12 @@ static int doc_read_oob(struct mtd_info
-       }
- out:
-+      if (ops->stats) {
-+              ops->stats->uncorrectable_errors +=
-+                      mtd->ecc_stats.failed - old_stats.failed;
-+              ops->stats->corrected_bitflips +=
-+                      mtd->ecc_stats.corrected - old_stats.corrected;
-+      }
-       mutex_unlock(&docg3->cascade->lock);
-       return ret;
- err_in_read:
---- a/drivers/mtd/nand/onenand/onenand_base.c
-+++ b/drivers/mtd/nand/onenand/onenand_base.c
-@@ -1440,6 +1440,7 @@ static int onenand_read_oob(struct mtd_i
-                           struct mtd_oob_ops *ops)
- {
-       struct onenand_chip *this = mtd->priv;
-+      struct mtd_ecc_stats old_stats;
-       int ret;
-       switch (ops->mode) {
-@@ -1453,12 +1454,23 @@ static int onenand_read_oob(struct mtd_i
-       }
-       onenand_get_device(mtd, FL_READING);
-+
-+      old_stats = mtd->ecc_stats;
-+
-       if (ops->datbuf)
-               ret = ONENAND_IS_4KB_PAGE(this) ?
-                       onenand_mlc_read_ops_nolock(mtd, from, ops) :
-                       onenand_read_ops_nolock(mtd, from, ops);
-       else
-               ret = onenand_read_oob_nolock(mtd, from, ops);
-+
-+      if (ops->stats) {
-+              ops->stats->uncorrectable_errors +=
-+                      mtd->ecc_stats.failed - old_stats.failed;
-+              ops->stats->corrected_bitflips +=
-+                      mtd->ecc_stats.corrected - old_stats.corrected;
-+      }
-+
-       onenand_release_device(mtd);
-       return ret;
---- a/drivers/mtd/nand/raw/nand_base.c
-+++ b/drivers/mtd/nand/raw/nand_base.c
-@@ -3815,6 +3815,7 @@ static int nand_read_oob(struct mtd_info
-                        struct mtd_oob_ops *ops)
- {
-       struct nand_chip *chip = mtd_to_nand(mtd);
-+      struct mtd_ecc_stats old_stats;
-       int ret;
-       ops->retlen = 0;
-@@ -3826,11 +3827,20 @@ static int nand_read_oob(struct mtd_info
-       nand_get_device(chip);
-+      old_stats = mtd->ecc_stats;
-+
-       if (!ops->datbuf)
-               ret = nand_do_read_oob(chip, from, ops);
-       else
-               ret = nand_do_read_ops(chip, from, ops);
-+      if (ops->stats) {
-+              ops->stats->uncorrectable_errors +=
-+                      mtd->ecc_stats.failed - old_stats.failed;
-+              ops->stats->corrected_bitflips +=
-+                      mtd->ecc_stats.corrected - old_stats.corrected;
-+      }
-+
-       nand_release_device(chip);
-       return ret;
- }
---- a/drivers/mtd/nand/spi/core.c
-+++ b/drivers/mtd/nand/spi/core.c
-@@ -629,6 +629,7 @@ static int spinand_mtd_read(struct mtd_i
- {
-       struct spinand_device *spinand = mtd_to_spinand(mtd);
-       struct nand_device *nand = mtd_to_nanddev(mtd);
-+      struct mtd_ecc_stats old_stats;
-       unsigned int max_bitflips = 0;
-       struct nand_io_iter iter;
-       bool disable_ecc = false;
-@@ -640,6 +641,8 @@ static int spinand_mtd_read(struct mtd_i
-       mutex_lock(&spinand->lock);
-+      old_stats = mtd->ecc_stats;
-+
-       nanddev_io_for_each_page(nand, NAND_PAGE_READ, from, ops, &iter) {
-               if (disable_ecc)
-                       iter.req.mode = MTD_OPS_RAW;
-@@ -662,6 +665,13 @@ static int spinand_mtd_read(struct mtd_i
-               ops->oobretlen += iter.req.ooblen;
-       }
-+      if (ops->stats) {
-+              ops->stats->uncorrectable_errors +=
-+                      mtd->ecc_stats.failed - old_stats.failed;
-+              ops->stats->corrected_bitflips +=
-+                      mtd->ecc_stats.corrected - old_stats.corrected;
-+      }
-+
-       mutex_unlock(&spinand->lock);
-       if (ecc_failed && !ret)
---- a/include/linux/mtd/mtd.h
-+++ b/include/linux/mtd/mtd.h
-@@ -41,6 +41,8 @@ struct mtd_erase_region_info {
- };
- struct mtd_req_stats {
-+      unsigned int uncorrectable_errors;
-+      unsigned int corrected_bitflips;
-       unsigned int max_bitflips;
- };
diff --git a/target/linux/generic/backport-5.15/423-v6.1-0004-mtdchar-add-MEMREAD-ioctl.patch b/target/linux/generic/backport-5.15/423-v6.1-0004-mtdchar-add-MEMREAD-ioctl.patch
deleted file mode 100644 (file)
index 182e4f6..0000000
+++ /dev/null
@@ -1,321 +0,0 @@
-From 2c9745d36e04ac27161acd78514f647b9b587ad4 Mon Sep 17 00:00:00 2001
-From: =?UTF-8?q?Micha=C5=82=20K=C4=99pie=C5=84?= <[email protected]>
-Date: Wed, 29 Jun 2022 14:57:37 +0200
-Subject: [PATCH 4/4] mtdchar: add MEMREAD ioctl
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-User-space applications making use of MTD devices via /dev/mtd*
-character devices currently have limited capabilities for reading data:
-
-  - only deprecated methods of accessing OOB layout information exist,
-
-  - there is no way to explicitly specify MTD operation mode to use; it
-    is auto-selected based on the MTD file mode (MTD_FILE_MODE_*) set
-    for the character device; in particular, this prevents using
-    MTD_OPS_AUTO_OOB for reads,
-
-  - all existing user-space interfaces which cause mtd_read() or
-    mtd_read_oob() to be called (via mtdchar_read() and
-    mtdchar_read_oob(), respectively) return success even when those
-    functions return -EUCLEAN or -EBADMSG; this renders user-space
-    applications using these interfaces unaware of any corrected
-    bitflips or uncorrectable ECC errors detected during reads.
-
-Note that the existing MEMWRITE ioctl allows the MTD operation mode to
-be explicitly set, allowing user-space applications to write page data
-and OOB data without requiring them to know anything about the OOB
-layout of the MTD device they are writing to (MTD_OPS_AUTO_OOB).  Also,
-the MEMWRITE ioctl does not mangle the return value of mtd_write_oob().
-
-Add a new ioctl, MEMREAD, which addresses the above issues.  It is
-intended to be a read-side counterpart of the existing MEMWRITE ioctl.
-Similarly to the latter, the read operation is performed in a loop which
-processes at most mtd->erasesize bytes in each iteration.  This is done
-to prevent unbounded memory allocations caused by calling kmalloc() with
-the 'size' argument taken directly from the struct mtd_read_req provided
-by user space.  However, the new ioctl is implemented so that the values
-it returns match those that would have been returned if just a single
-mtd_read_oob() call was issued to handle the entire read operation in
-one go.
-
-Note that while just returning -EUCLEAN or -EBADMSG to user space would
-already be a valid and useful indication of the ECC algorithm detecting
-errors during a read operation, that signal would not be granular enough
-to cover all use cases.  For example, knowing the maximum number of
-bitflips detected in a single ECC step during a read operation performed
-on a given page may be useful when dealing with an MTD partition whose
-ECC layout varies across pages (e.g. a partition consisting of a
-bootloader area using a "custom" ECC layout followed by data pages using
-a "standard" ECC layout).  To address that, include ECC statistics in
-the structure returned to user space by the new MEMREAD ioctl.
-
-Link: https://www.infradead.org/pipermail/linux-mtd/2016-April/067085.html
-
-Suggested-by: Boris Brezillon <[email protected]>
-Signed-off-by: Michał Kępień <[email protected]>
-Acked-by: Richard Weinberger <[email protected]>
-Signed-off-by: Miquel Raynal <[email protected]>
-Link: https://lore.kernel.org/linux-mtd/[email protected]
----
- drivers/mtd/mtdchar.c      | 139 +++++++++++++++++++++++++++++++++++++
- include/uapi/mtd/mtd-abi.h |  64 +++++++++++++++--
- 2 files changed, 198 insertions(+), 5 deletions(-)
-
---- a/drivers/mtd/mtdchar.c
-+++ b/drivers/mtd/mtdchar.c
-@@ -621,6 +621,137 @@ static int mtdchar_write_ioctl(struct mt
-       return ret;
- }
-+static int mtdchar_read_ioctl(struct mtd_info *mtd,
-+              struct mtd_read_req __user *argp)
-+{
-+      struct mtd_info *master = mtd_get_master(mtd);
-+      struct mtd_read_req req;
-+      void __user *usr_data, *usr_oob;
-+      uint8_t *datbuf = NULL, *oobbuf = NULL;
-+      size_t datbuf_len, oobbuf_len;
-+      size_t orig_len, orig_ooblen;
-+      int ret = 0;
-+
-+      if (copy_from_user(&req, argp, sizeof(req)))
-+              return -EFAULT;
-+
-+      orig_len = req.len;
-+      orig_ooblen = req.ooblen;
-+
-+      usr_data = (void __user *)(uintptr_t)req.usr_data;
-+      usr_oob = (void __user *)(uintptr_t)req.usr_oob;
-+
-+      if (!master->_read_oob)
-+              return -EOPNOTSUPP;
-+
-+      if (!usr_data)
-+              req.len = 0;
-+
-+      if (!usr_oob)
-+              req.ooblen = 0;
-+
-+      req.ecc_stats.uncorrectable_errors = 0;
-+      req.ecc_stats.corrected_bitflips = 0;
-+      req.ecc_stats.max_bitflips = 0;
-+
-+      req.len &= 0xffffffff;
-+      req.ooblen &= 0xffffffff;
-+
-+      if (req.start + req.len > mtd->size) {
-+              ret = -EINVAL;
-+              goto out;
-+      }
-+
-+      datbuf_len = min_t(size_t, req.len, mtd->erasesize);
-+      if (datbuf_len > 0) {
-+              datbuf = kvmalloc(datbuf_len, GFP_KERNEL);
-+              if (!datbuf) {
-+                      ret = -ENOMEM;
-+                      goto out;
-+              }
-+      }
-+
-+      oobbuf_len = min_t(size_t, req.ooblen, mtd->erasesize);
-+      if (oobbuf_len > 0) {
-+              oobbuf = kvmalloc(oobbuf_len, GFP_KERNEL);
-+              if (!oobbuf) {
-+                      ret = -ENOMEM;
-+                      goto out;
-+              }
-+      }
-+
-+      while (req.len > 0 || (!usr_data && req.ooblen > 0)) {
-+              struct mtd_req_stats stats;
-+              struct mtd_oob_ops ops = {
-+                      .mode = req.mode,
-+                      .len = min_t(size_t, req.len, datbuf_len),
-+                      .ooblen = min_t(size_t, req.ooblen, oobbuf_len),
-+                      .datbuf = datbuf,
-+                      .oobbuf = oobbuf,
-+                      .stats = &stats,
-+              };
-+
-+              /*
-+               * Shorten non-page-aligned, eraseblock-sized reads so that the
-+               * read ends on an eraseblock boundary.  This is necessary in
-+               * order to prevent OOB data for some pages from being
-+               * duplicated in the output of non-page-aligned reads requiring
-+               * multiple mtd_read_oob() calls to be completed.
-+               */
-+              if (ops.len == mtd->erasesize)
-+                      ops.len -= mtd_mod_by_ws(req.start + ops.len, mtd);
-+
-+              ret = mtd_read_oob(mtd, (loff_t)req.start, &ops);
-+
-+              req.ecc_stats.uncorrectable_errors +=
-+                      stats.uncorrectable_errors;
-+              req.ecc_stats.corrected_bitflips += stats.corrected_bitflips;
-+              req.ecc_stats.max_bitflips =
-+                      max(req.ecc_stats.max_bitflips, stats.max_bitflips);
-+
-+              if (ret && !mtd_is_bitflip_or_eccerr(ret))
-+                      break;
-+
-+              if (copy_to_user(usr_data, ops.datbuf, ops.retlen) ||
-+                  copy_to_user(usr_oob, ops.oobbuf, ops.oobretlen)) {
-+                      ret = -EFAULT;
-+                      break;
-+              }
-+
-+              req.start += ops.retlen;
-+              req.len -= ops.retlen;
-+              usr_data += ops.retlen;
-+
-+              req.ooblen -= ops.oobretlen;
-+              usr_oob += ops.oobretlen;
-+      }
-+
-+      /*
-+       * As multiple iterations of the above loop (and therefore multiple
-+       * mtd_read_oob() calls) may be necessary to complete the read request,
-+       * adjust the final return code to ensure it accounts for all detected
-+       * ECC errors.
-+       */
-+      if (!ret || mtd_is_bitflip(ret)) {
-+              if (req.ecc_stats.uncorrectable_errors > 0)
-+                      ret = -EBADMSG;
-+              else if (req.ecc_stats.corrected_bitflips > 0)
-+                      ret = -EUCLEAN;
-+      }
-+
-+out:
-+      req.len = orig_len - req.len;
-+      req.ooblen = orig_ooblen - req.ooblen;
-+
-+      if (copy_to_user(argp, &req, sizeof(req)))
-+              ret = -EFAULT;
-+
-+      kvfree(datbuf);
-+      kvfree(oobbuf);
-+
-+      return ret;
-+}
-+
- static int mtdchar_ioctl(struct file *file, u_int cmd, u_long arg)
- {
-       struct mtd_file_info *mfi = file->private_data;
-@@ -643,6 +774,7 @@ static int mtdchar_ioctl(struct file *fi
-       case MEMGETINFO:
-       case MEMREADOOB:
-       case MEMREADOOB64:
-+      case MEMREAD:
-       case MEMISLOCKED:
-       case MEMGETOOBSEL:
-       case MEMGETBADBLOCK:
-@@ -817,6 +949,13 @@ static int mtdchar_ioctl(struct file *fi
-               break;
-       }
-+      case MEMREAD:
-+      {
-+              ret = mtdchar_read_ioctl(mtd,
-+                    (struct mtd_read_req __user *)arg);
-+              break;
-+      }
-+
-       case MEMLOCK:
-       {
-               struct erase_info_user einfo;
---- a/include/uapi/mtd/mtd-abi.h
-+++ b/include/uapi/mtd/mtd-abi.h
-@@ -55,9 +55,9 @@ struct mtd_oob_buf64 {
-  * @MTD_OPS_RAW:      data are transferred as-is, with no error correction;
-  *                    this mode implies %MTD_OPS_PLACE_OOB
-  *
-- * These modes can be passed to ioctl(MEMWRITE) and are also used internally.
-- * See notes on "MTD file modes" for discussion on %MTD_OPS_RAW vs.
-- * %MTD_FILE_MODE_RAW.
-+ * These modes can be passed to ioctl(MEMWRITE) and ioctl(MEMREAD); they are
-+ * also used internally. See notes on "MTD file modes" for discussion on
-+ * %MTD_OPS_RAW vs. %MTD_FILE_MODE_RAW.
-  */
- enum {
-       MTD_OPS_PLACE_OOB = 0,
-@@ -91,6 +91,53 @@ struct mtd_write_req {
-       __u8 padding[7];
- };
-+/**
-+ * struct mtd_read_req_ecc_stats - ECC statistics for a read operation
-+ *
-+ * @uncorrectable_errors: the number of uncorrectable errors that happened
-+ *                      during the read operation
-+ * @corrected_bitflips: the number of bitflips corrected during the read
-+ *                    operation
-+ * @max_bitflips: the maximum number of bitflips detected in any single ECC
-+ *              step for the data read during the operation; this information
-+ *              can be used to decide whether the data stored in a specific
-+ *              region of the MTD device should be moved somewhere else to
-+ *              avoid data loss.
-+ */
-+struct mtd_read_req_ecc_stats {
-+      __u32 uncorrectable_errors;
-+      __u32 corrected_bitflips;
-+      __u32 max_bitflips;
-+};
-+
-+/**
-+ * struct mtd_read_req - data structure for requesting a read operation
-+ *
-+ * @start:    start address
-+ * @len:      length of data buffer (only lower 32 bits are used)
-+ * @ooblen:   length of OOB buffer (only lower 32 bits are used)
-+ * @usr_data: user-provided data buffer
-+ * @usr_oob:  user-provided OOB buffer
-+ * @mode:     MTD mode (see "MTD operation modes")
-+ * @padding:  reserved, must be set to 0
-+ * @ecc_stats:        ECC statistics for the read operation
-+ *
-+ * This structure supports ioctl(MEMREAD) operations, allowing data and/or OOB
-+ * reads in various modes. To read from OOB-only, set @usr_data == NULL, and to
-+ * read data-only, set @usr_oob == NULL. However, setting both @usr_data and
-+ * @usr_oob to NULL is not allowed.
-+ */
-+struct mtd_read_req {
-+      __u64 start;
-+      __u64 len;
-+      __u64 ooblen;
-+      __u64 usr_data;
-+      __u64 usr_oob;
-+      __u8 mode;
-+      __u8 padding[7];
-+      struct mtd_read_req_ecc_stats ecc_stats;
-+};
-+
- #define MTD_ABSENT            0
- #define MTD_RAM                       1
- #define MTD_ROM                       2
-@@ -207,6 +254,12 @@ struct otp_info {
- #define MEMWRITE              _IOWR('M', 24, struct mtd_write_req)
- /* Erase a given range of user data (must be in mode %MTD_FILE_MODE_OTP_USER) */
- #define OTPERASE              _IOW('M', 25, struct otp_info)
-+/*
-+ * Most generic read interface; can read in-band and/or out-of-band in various
-+ * modes (see "struct mtd_read_req"). This ioctl is not supported for flashes
-+ * without OOB, e.g., NOR flash.
-+ */
-+#define MEMREAD                       _IOWR('M', 26, struct mtd_read_req)
- /*
-  * Obsolete legacy interface. Keep it in order not to break userspace
-@@ -270,8 +323,9 @@ struct mtd_ecc_stats {
-  * Note: %MTD_FILE_MODE_RAW provides the same functionality as %MTD_OPS_RAW -
-  * raw access to the flash, without error correction or autoplacement schemes.
-  * Wherever possible, the MTD_OPS_* mode will override the MTD_FILE_MODE_* mode
-- * (e.g., when using ioctl(MEMWRITE)), but in some cases, the MTD_FILE_MODE is
-- * used out of necessity (e.g., `write()', ioctl(MEMWRITEOOB64)).
-+ * (e.g., when using ioctl(MEMWRITE) or ioctl(MEMREAD)), but in some cases, the
-+ * MTD_FILE_MODE is used out of necessity (e.g., `write()',
-+ * ioctl(MEMWRITEOOB64)).
-  */
- enum mtd_file_modes {
-       MTD_FILE_MODE_NORMAL = MTD_OTP_OFF,
diff --git a/target/linux/generic/backport-5.15/423-v6.3-mtd-spinand-macronix-use-scratch-buffer-for-DMA-oper.patch b/target/linux/generic/backport-5.15/423-v6.3-mtd-spinand-macronix-use-scratch-buffer-for-DMA-oper.patch
deleted file mode 100644 (file)
index 7dbc271..0000000
+++ /dev/null
@@ -1,35 +0,0 @@
-From ebed787a0becb9354f0a23620a5130cccd6c730c Mon Sep 17 00:00:00 2001
-From: Daniel Golle <[email protected]>
-Date: Thu, 19 Jan 2023 03:45:43 +0000
-Subject: [PATCH] mtd: spinand: macronix: use scratch buffer for DMA operation
-
-The mx35lf1ge4ab_get_eccsr() function uses an SPI DMA operation to
-read the eccsr, hence the buffer should not be on stack. Since commit
-380583227c0c7f ("spi: spi-mem: Add extra sanity checks on the op param")
-the kernel emmits a warning and blocks such operations.
-
-Use the scratch buffer to get eccsr instead of trying to directly read
-into a stack-allocated variable.
-
-Signed-off-by: Daniel Golle <[email protected]>
-Reviewed-by: Dhruva Gole <[email protected]>
-Signed-off-by: Miquel Raynal <[email protected]>
-Link: https://lore.kernel.org/linux-mtd/[email protected]
----
- drivers/mtd/nand/spi/macronix.c | 3 ++-
- 1 file changed, 2 insertions(+), 1 deletion(-)
-
---- a/drivers/mtd/nand/spi/macronix.c
-+++ b/drivers/mtd/nand/spi/macronix.c
-@@ -83,9 +83,10 @@ static int mx35lf1ge4ab_ecc_get_status(s
-                * in order to avoid forcing the wear-leveling layer to move
-                * data around if it's not necessary.
-                */
--              if (mx35lf1ge4ab_get_eccsr(spinand, &eccsr))
-+              if (mx35lf1ge4ab_get_eccsr(spinand, spinand->scratchbuf))
-                       return nanddev_get_ecc_conf(nand)->strength;
-+              eccsr = *spinand->scratchbuf;
-               if (WARN_ON(eccsr > nanddev_get_ecc_conf(nand)->strength ||
-                           !eccsr))
-                       return nanddev_get_ecc_conf(nand)->strength;
diff --git a/target/linux/generic/backport-5.15/424-v6.4-0004-mtd-core-prepare-mtd_otp_nvmem_add-to-handle-EPROBE_.patch b/target/linux/generic/backport-5.15/424-v6.4-0004-mtd-core-prepare-mtd_otp_nvmem_add-to-handle-EPROBE_.patch
deleted file mode 100644 (file)
index 001b556..0000000
+++ /dev/null
@@ -1,47 +0,0 @@
-From 281f7a6c1a33fffcde32001bacbb4f672140fbf9 Mon Sep 17 00:00:00 2001
-From: Michael Walle <[email protected]>
-Date: Wed, 8 Mar 2023 09:20:21 +0100
-Subject: [PATCH] mtd: core: prepare mtd_otp_nvmem_add() to handle
- -EPROBE_DEFER
-
-NVMEM soon will get the ability for nvmem layouts and these might
-not be ready when nvmem_register() is called and thus it might
-return -EPROBE_DEFER. Don't print the error message in this case.
-
-Signed-off-by: Michael Walle <[email protected]>
-Signed-off-by: Miquel Raynal <[email protected]>
-Link: https://lore.kernel.org/linux-mtd/[email protected]
----
- drivers/mtd/mtdcore.c | 7 +++----
- 1 file changed, 3 insertions(+), 4 deletions(-)
-
---- a/drivers/mtd/mtdcore.c
-+++ b/drivers/mtd/mtdcore.c
-@@ -962,8 +962,8 @@ static int mtd_otp_nvmem_add(struct mtd_
-                       nvmem = mtd_otp_nvmem_register(mtd, "user-otp", size,
-                                                      mtd_nvmem_user_otp_reg_read);
-                       if (IS_ERR(nvmem)) {
--                              dev_err(dev, "Failed to register OTP NVMEM device\n");
--                              return PTR_ERR(nvmem);
-+                              err = PTR_ERR(nvmem);
-+                              goto err;
-                       }
-                       mtd->otp_user_nvmem = nvmem;
-               }
-@@ -980,7 +980,6 @@ static int mtd_otp_nvmem_add(struct mtd_
-                       nvmem = mtd_otp_nvmem_register(mtd, "factory-otp", size,
-                                                      mtd_nvmem_fact_otp_reg_read);
-                       if (IS_ERR(nvmem)) {
--                              dev_err(dev, "Failed to register OTP NVMEM device\n");
-                               err = PTR_ERR(nvmem);
-                               goto err;
-                       }
-@@ -993,7 +992,7 @@ static int mtd_otp_nvmem_add(struct mtd_
- err:
-       if (mtd->otp_user_nvmem)
-               nvmem_unregister(mtd->otp_user_nvmem);
--      return err;
-+      return dev_err_probe(dev, err, "Failed to register OTP NVMEM device\n");
- }
- /**
diff --git a/target/linux/generic/backport-5.15/600-v5.18-page_pool-Add-allocation-stats.patch b/target/linux/generic/backport-5.15/600-v5.18-page_pool-Add-allocation-stats.patch
deleted file mode 100644 (file)
index dca1062..0000000
+++ /dev/null
@@ -1,165 +0,0 @@
-From 8610037e8106b48c79cfe0afb92b2b2466e51c3d Mon Sep 17 00:00:00 2001
-From: Joe Damato <[email protected]>
-Date: Tue, 1 Mar 2022 23:55:47 -0800
-Subject: [PATCH] page_pool: Add allocation stats
-
-Add per-pool statistics counters for the allocation path of a page pool.
-These stats are incremented in softirq context, so no locking or per-cpu
-variables are needed.
-
-This code is disabled by default and a kernel config option is provided for
-users who wish to enable them.
-
-The statistics added are:
-       - fast: successful fast path allocations
-       - slow: slow path order-0 allocations
-       - slow_high_order: slow path high order allocations
-       - empty: ptr ring is empty, so a slow path allocation was forced.
-       - refill: an allocation which triggered a refill of the cache
-       - waive: pages obtained from the ptr ring that cannot be added to
-         the cache due to a NUMA mismatch.
-
-Signed-off-by: Joe Damato <[email protected]>
-Acked-by: Jesper Dangaard Brouer <[email protected]>
-Reviewed-by: Ilias Apalodimas <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- include/net/page_pool.h | 18 ++++++++++++++++++
- net/Kconfig             | 13 +++++++++++++
- net/core/page_pool.c    | 24 ++++++++++++++++++++----
- 3 files changed, 51 insertions(+), 4 deletions(-)
-
---- a/include/net/page_pool.h
-+++ b/include/net/page_pool.h
-@@ -82,6 +82,19 @@ struct page_pool_params {
-       unsigned int    offset;  /* DMA addr offset */
- };
-+#ifdef CONFIG_PAGE_POOL_STATS
-+struct page_pool_alloc_stats {
-+      u64 fast; /* fast path allocations */
-+      u64 slow; /* slow-path order 0 allocations */
-+      u64 slow_high_order; /* slow-path high order allocations */
-+      u64 empty; /* failed refills due to empty ptr ring, forcing
-+                  * slow path allocation
-+                  */
-+      u64 refill; /* allocations via successful refill */
-+      u64 waive;  /* failed refills due to numa zone mismatch */
-+};
-+#endif
-+
- struct page_pool {
-       struct page_pool_params p;
-@@ -132,6 +145,11 @@ struct page_pool {
-       refcount_t user_cnt;
-       u64 destroy_cnt;
-+
-+#ifdef CONFIG_PAGE_POOL_STATS
-+      /* these stats are incremented while in softirq context */
-+      struct page_pool_alloc_stats alloc_stats;
-+#endif
- };
- struct page *page_pool_alloc_pages(struct page_pool *pool, gfp_t gfp);
---- a/net/Kconfig
-+++ b/net/Kconfig
-@@ -432,6 +432,19 @@ config NET_DEVLINK
- config PAGE_POOL
-       bool
-+config PAGE_POOL_STATS
-+      default n
-+      bool "Page pool stats"
-+      depends on PAGE_POOL
-+      help
-+        Enable page pool statistics to track page allocation and recycling
-+        in page pools. This option incurs additional CPU cost in allocation
-+        and recycle paths and additional memory cost to store the statistics.
-+        These statistics are only available if this option is enabled and if
-+        the driver using the page pool supports exporting this data.
-+
-+        If unsure, say N.
-+
- config FAILOVER
-       tristate "Generic failover module"
-       help
---- a/net/core/page_pool.c
-+++ b/net/core/page_pool.c
-@@ -49,6 +49,13 @@ static void page_pool_producer_unlock(st
-               spin_unlock_bh(&pool->ring.producer_lock);
- }
-+#ifdef CONFIG_PAGE_POOL_STATS
-+/* alloc_stat_inc is intended to be used in softirq context */
-+#define alloc_stat_inc(pool, __stat)  (pool->alloc_stats.__stat++)
-+#else
-+#define alloc_stat_inc(pool, __stat)
-+#endif
-+
- static int page_pool_init(struct page_pool *pool,
-                         const struct page_pool_params *params)
- {
-@@ -140,8 +147,10 @@ static struct page *page_pool_refill_all
-       int pref_nid; /* preferred NUMA node */
-       /* Quicker fallback, avoid locks when ring is empty */
--      if (__ptr_ring_empty(r))
-+      if (__ptr_ring_empty(r)) {
-+              alloc_stat_inc(pool, empty);
-               return NULL;
-+      }
-       /* Softirq guarantee CPU and thus NUMA node is stable. This,
-        * assumes CPU refilling driver RX-ring will also run RX-NAPI.
-@@ -171,14 +180,17 @@ static struct page *page_pool_refill_all
-                        * This limit stress on page buddy alloactor.
-                        */
-                       page_pool_return_page(pool, page);
-+                      alloc_stat_inc(pool, waive);
-                       page = NULL;
-                       break;
-               }
-       } while (pool->alloc.count < PP_ALLOC_CACHE_REFILL);
-       /* Return last page */
--      if (likely(pool->alloc.count > 0))
-+      if (likely(pool->alloc.count > 0)) {
-               page = pool->alloc.cache[--pool->alloc.count];
-+              alloc_stat_inc(pool, refill);
-+      }
-       spin_unlock(&r->consumer_lock);
-       return page;
-@@ -193,6 +205,7 @@ static struct page *__page_pool_get_cach
-       if (likely(pool->alloc.count)) {
-               /* Fast-path */
-               page = pool->alloc.cache[--pool->alloc.count];
-+              alloc_stat_inc(pool, fast);
-       } else {
-               page = page_pool_refill_alloc_cache(pool);
-       }
-@@ -264,6 +277,7 @@ static struct page *__page_pool_alloc_pa
-               return NULL;
-       }
-+      alloc_stat_inc(pool, slow_high_order);
-       page_pool_set_pp_info(pool, page);
-       /* Track how many pages are held 'in-flight' */
-@@ -318,10 +332,12 @@ static struct page *__page_pool_alloc_pa
-       }
-       /* Return last page */
--      if (likely(pool->alloc.count > 0))
-+      if (likely(pool->alloc.count > 0)) {
-               page = pool->alloc.cache[--pool->alloc.count];
--      else
-+              alloc_stat_inc(pool, slow);
-+      } else {
-               page = NULL;
-+      }
-       /* When page just alloc'ed is should/must have refcnt 1. */
-       return page;
diff --git a/target/linux/generic/backport-5.15/601-v5.18-page_pool-Add-recycle-stats.patch b/target/linux/generic/backport-5.15/601-v5.18-page_pool-Add-recycle-stats.patch
deleted file mode 100644 (file)
index b425b78..0000000
+++ /dev/null
@@ -1,140 +0,0 @@
-From ad6fa1e1ab1b8164f1ba296b1b4dc556a483bcad Mon Sep 17 00:00:00 2001
-From: Joe Damato <[email protected]>
-Date: Tue, 1 Mar 2022 23:55:48 -0800
-Subject: [PATCH 2/3] page_pool: Add recycle stats
-
-Add per-cpu stats tracking page pool recycling events:
-       - cached: recycling placed page in the page pool cache
-       - cache_full: page pool cache was full
-       - ring: page placed into the ptr ring
-       - ring_full: page released from page pool because the ptr ring was full
-       - released_refcnt: page released (and not recycled) because refcnt > 1
-
-Signed-off-by: Joe Damato <[email protected]>
-Acked-by: Jesper Dangaard Brouer <[email protected]>
-Reviewed-by: Ilias Apalodimas <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- include/net/page_pool.h | 16 ++++++++++++++++
- net/core/page_pool.c    | 30 ++++++++++++++++++++++++++++--
- 2 files changed, 44 insertions(+), 2 deletions(-)
-
---- a/include/net/page_pool.h
-+++ b/include/net/page_pool.h
-@@ -93,6 +93,18 @@ struct page_pool_alloc_stats {
-       u64 refill; /* allocations via successful refill */
-       u64 waive;  /* failed refills due to numa zone mismatch */
- };
-+
-+struct page_pool_recycle_stats {
-+      u64 cached;     /* recycling placed page in the cache. */
-+      u64 cache_full; /* cache was full */
-+      u64 ring;       /* recycling placed page back into ptr ring */
-+      u64 ring_full;  /* page was released from page-pool because
-+                       * PTR ring was full.
-+                       */
-+      u64 released_refcnt; /* page released because of elevated
-+                            * refcnt
-+                            */
-+};
- #endif
- struct page_pool {
-@@ -136,6 +148,10 @@ struct page_pool {
-        */
-       struct ptr_ring ring;
-+#ifdef CONFIG_PAGE_POOL_STATS
-+      /* recycle stats are per-cpu to avoid locking */
-+      struct page_pool_recycle_stats __percpu *recycle_stats;
-+#endif
-       atomic_t pages_state_release_cnt;
-       /* A page_pool is strictly tied to a single RX-queue being
---- a/net/core/page_pool.c
-+++ b/net/core/page_pool.c
-@@ -52,8 +52,15 @@ static void page_pool_producer_unlock(st
- #ifdef CONFIG_PAGE_POOL_STATS
- /* alloc_stat_inc is intended to be used in softirq context */
- #define alloc_stat_inc(pool, __stat)  (pool->alloc_stats.__stat++)
-+/* recycle_stat_inc is safe to use when preemption is possible. */
-+#define recycle_stat_inc(pool, __stat)                                                        \
-+      do {                                                                            \
-+              struct page_pool_recycle_stats __percpu *s = pool->recycle_stats;       \
-+              this_cpu_inc(s->__stat);                                                \
-+      } while (0)
- #else
- #define alloc_stat_inc(pool, __stat)
-+#define recycle_stat_inc(pool, __stat)
- #endif
- static int page_pool_init(struct page_pool *pool,
-@@ -103,6 +110,12 @@ static int page_pool_init(struct page_po
-           pool->p.flags & PP_FLAG_PAGE_FRAG)
-               return -EINVAL;
-+#ifdef CONFIG_PAGE_POOL_STATS
-+      pool->recycle_stats = alloc_percpu(struct page_pool_recycle_stats);
-+      if (!pool->recycle_stats)
-+              return -ENOMEM;
-+#endif
-+
-       if (ptr_ring_init(&pool->ring, ring_qsize, GFP_KERNEL) < 0)
-               return -ENOMEM;
-@@ -435,7 +448,12 @@ static bool page_pool_recycle_in_ring(st
-       else
-               ret = ptr_ring_produce_bh(&pool->ring, page);
--      return (ret == 0) ? true : false;
-+      if (!ret) {
-+              recycle_stat_inc(pool, ring);
-+              return true;
-+      }
-+
-+      return false;
- }
- /* Only allow direct recycling in special circumstances, into the
-@@ -446,11 +464,14 @@ static bool page_pool_recycle_in_ring(st
- static bool page_pool_recycle_in_cache(struct page *page,
-                                      struct page_pool *pool)
- {
--      if (unlikely(pool->alloc.count == PP_ALLOC_CACHE_SIZE))
-+      if (unlikely(pool->alloc.count == PP_ALLOC_CACHE_SIZE)) {
-+              recycle_stat_inc(pool, cache_full);
-               return false;
-+      }
-       /* Caller MUST have verified/know (page_ref_count(page) == 1) */
-       pool->alloc.cache[pool->alloc.count++] = page;
-+      recycle_stat_inc(pool, cached);
-       return true;
- }
-@@ -505,6 +526,7 @@ __page_pool_put_page(struct page_pool *p
-        * doing refcnt based recycle tricks, meaning another process
-        * will be invoking put_page.
-        */
-+      recycle_stat_inc(pool, released_refcnt);
-       /* Do not replace this with page_pool_return_page() */
-       page_pool_release_page(pool, page);
-       put_page(page);
-@@ -518,6 +540,7 @@ void page_pool_put_page(struct page_pool
-       page = __page_pool_put_page(pool, page, dma_sync_size, allow_direct);
-       if (page && !page_pool_recycle_in_ring(pool, page)) {
-               /* Cache full, fallback to free pages */
-+              recycle_stat_inc(pool, ring_full);
-               page_pool_return_page(pool, page);
-       }
- }
-@@ -665,6 +688,9 @@ static void page_pool_free(struct page_p
-       if (pool->p.flags & PP_FLAG_DMA_MAP)
-               put_device(pool->p.dev);
-+#ifdef CONFIG_PAGE_POOL_STATS
-+      free_percpu(pool->recycle_stats);
-+#endif
-       kfree(pool);
- }
diff --git a/target/linux/generic/backport-5.15/602-v5.18-page_pool-Add-function-to-batch-and-return-stats.patch b/target/linux/generic/backport-5.15/602-v5.18-page_pool-Add-function-to-batch-and-return-stats.patch
deleted file mode 100644 (file)
index e1a7635..0000000
+++ /dev/null
@@ -1,77 +0,0 @@
-From 6b95e3388b1ea0ca63500c5a6e39162dbf828433 Mon Sep 17 00:00:00 2001
-From: Joe Damato <[email protected]>
-Date: Tue, 1 Mar 2022 23:55:49 -0800
-Subject: [PATCH 3/3] page_pool: Add function to batch and return stats
-
-Adds a function page_pool_get_stats which can be used by drivers to obtain
-stats for a specified page_pool.
-
-Signed-off-by: Joe Damato <[email protected]>
-Acked-by: Jesper Dangaard Brouer <[email protected]>
-Reviewed-by: Ilias Apalodimas <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- include/net/page_pool.h | 17 +++++++++++++++++
- net/core/page_pool.c    | 25 +++++++++++++++++++++++++
- 2 files changed, 42 insertions(+)
-
---- a/include/net/page_pool.h
-+++ b/include/net/page_pool.h
-@@ -105,6 +105,23 @@ struct page_pool_recycle_stats {
-                             * refcnt
-                             */
- };
-+
-+/* This struct wraps the above stats structs so users of the
-+ * page_pool_get_stats API can pass a single argument when requesting the
-+ * stats for the page pool.
-+ */
-+struct page_pool_stats {
-+      struct page_pool_alloc_stats alloc_stats;
-+      struct page_pool_recycle_stats recycle_stats;
-+};
-+
-+/*
-+ * Drivers that wish to harvest page pool stats and report them to users
-+ * (perhaps via ethtool, debugfs, or another mechanism) can allocate a
-+ * struct page_pool_stats call page_pool_get_stats to get stats for the specified pool.
-+ */
-+bool page_pool_get_stats(struct page_pool *pool,
-+                       struct page_pool_stats *stats);
- #endif
- struct page_pool {
---- a/net/core/page_pool.c
-+++ b/net/core/page_pool.c
-@@ -58,6 +58,31 @@ static void page_pool_producer_unlock(st
-               struct page_pool_recycle_stats __percpu *s = pool->recycle_stats;       \
-               this_cpu_inc(s->__stat);                                                \
-       } while (0)
-+
-+bool page_pool_get_stats(struct page_pool *pool,
-+                       struct page_pool_stats *stats)
-+{
-+      int cpu = 0;
-+
-+      if (!stats)
-+              return false;
-+
-+      memcpy(&stats->alloc_stats, &pool->alloc_stats, sizeof(pool->alloc_stats));
-+
-+      for_each_possible_cpu(cpu) {
-+              const struct page_pool_recycle_stats *pcpu =
-+                      per_cpu_ptr(pool->recycle_stats, cpu);
-+
-+              stats->recycle_stats.cached += pcpu->cached;
-+              stats->recycle_stats.cache_full += pcpu->cache_full;
-+              stats->recycle_stats.ring += pcpu->ring;
-+              stats->recycle_stats.ring_full += pcpu->ring_full;
-+              stats->recycle_stats.released_refcnt += pcpu->released_refcnt;
-+      }
-+
-+      return true;
-+}
-+EXPORT_SYMBOL(page_pool_get_stats);
- #else
- #define alloc_stat_inc(pool, __stat)
- #define recycle_stat_inc(pool, __stat)
diff --git a/target/linux/generic/backport-5.15/603-v5.19-page_pool-Add-recycle-stats-to-page_pool_put_page_bu.patch b/target/linux/generic/backport-5.15/603-v5.19-page_pool-Add-recycle-stats-to-page_pool_put_page_bu.patch
deleted file mode 100644 (file)
index f438ef3..0000000
+++ /dev/null
@@ -1,55 +0,0 @@
-From 590032a4d2133ecc10d3078a8db1d85a4842f12c Mon Sep 17 00:00:00 2001
-From: Lorenzo Bianconi <[email protected]>
-Date: Mon, 11 Apr 2022 16:05:26 +0200
-Subject: [PATCH] page_pool: Add recycle stats to page_pool_put_page_bulk
-
-Add missing recycle stats to page_pool_put_page_bulk routine.
-
-Reviewed-by: Joe Damato <[email protected]>
-Signed-off-by: Lorenzo Bianconi <[email protected]>
-Reviewed-by: Ilias Apalodimas <[email protected]>
-Link: https://lore.kernel.org/r/3712178b51c007cfaed910ea80e68f00c916b1fa.1649685634.git.lorenzo@kernel.org
-Signed-off-by: Paolo Abeni <[email protected]>
----
- net/core/page_pool.c | 15 +++++++++++++--
- 1 file changed, 13 insertions(+), 2 deletions(-)
-
---- a/net/core/page_pool.c
-+++ b/net/core/page_pool.c
-@@ -59,6 +59,12 @@ static void page_pool_producer_unlock(st
-               this_cpu_inc(s->__stat);                                                \
-       } while (0)
-+#define recycle_stat_add(pool, __stat, val)                                           \
-+      do {                                                                            \
-+              struct page_pool_recycle_stats __percpu *s = pool->recycle_stats;       \
-+              this_cpu_add(s->__stat, val);                                           \
-+      } while (0)
-+
- bool page_pool_get_stats(struct page_pool *pool,
-                        struct page_pool_stats *stats)
- {
-@@ -86,6 +92,7 @@ EXPORT_SYMBOL(page_pool_get_stats);
- #else
- #define alloc_stat_inc(pool, __stat)
- #define recycle_stat_inc(pool, __stat)
-+#define recycle_stat_add(pool, __stat, val)
- #endif
- static int page_pool_init(struct page_pool *pool,
-@@ -593,9 +600,13 @@ void page_pool_put_page_bulk(struct page
-       /* Bulk producer into ptr_ring page_pool cache */
-       in_softirq = page_pool_producer_lock(pool);
-       for (i = 0; i < bulk_len; i++) {
--              if (__ptr_ring_produce(&pool->ring, data[i]))
--                      break; /* ring full */
-+              if (__ptr_ring_produce(&pool->ring, data[i])) {
-+                      /* ring full */
-+                      recycle_stat_inc(pool, ring_full);
-+                      break;
-+              }
-       }
-+      recycle_stat_add(pool, ring, i);
-       page_pool_producer_unlock(pool, in_softirq);
-       /* Hopefully all pages was return into ptr_ring */
diff --git a/target/linux/generic/backport-5.15/604-v5.19-net-page_pool-introduce-ethtool-stats.patch b/target/linux/generic/backport-5.15/604-v5.19-net-page_pool-introduce-ethtool-stats.patch
deleted file mode 100644 (file)
index 3ff136b..0000000
+++ /dev/null
@@ -1,147 +0,0 @@
-From f3c5264f452a5b0ac1de1f2f657efbabdea3c76a Mon Sep 17 00:00:00 2001
-From: Lorenzo Bianconi <[email protected]>
-Date: Tue, 12 Apr 2022 18:31:58 +0200
-Subject: [PATCH] net: page_pool: introduce ethtool stats
-
-Introduce page_pool APIs to report stats through ethtool and reduce
-duplicated code in each driver.
-
-Signed-off-by: Lorenzo Bianconi <[email protected]>
-Reviewed-by: Jakub Kicinski <[email protected]>
-Reviewed-by: Ilias Apalodimas <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- include/net/page_pool.h | 21 ++++++++++++++
- net/core/page_pool.c    | 63 ++++++++++++++++++++++++++++++++++++++++-
- 2 files changed, 83 insertions(+), 1 deletion(-)
-
---- a/include/net/page_pool.h
-+++ b/include/net/page_pool.h
-@@ -115,6 +115,10 @@ struct page_pool_stats {
-       struct page_pool_recycle_stats recycle_stats;
- };
-+int page_pool_ethtool_stats_get_count(void);
-+u8 *page_pool_ethtool_stats_get_strings(u8 *data);
-+u64 *page_pool_ethtool_stats_get(u64 *data, void *stats);
-+
- /*
-  * Drivers that wish to harvest page pool stats and report them to users
-  * (perhaps via ethtool, debugfs, or another mechanism) can allocate a
-@@ -122,6 +126,23 @@ struct page_pool_stats {
-  */
- bool page_pool_get_stats(struct page_pool *pool,
-                        struct page_pool_stats *stats);
-+#else
-+
-+static inline int page_pool_ethtool_stats_get_count(void)
-+{
-+      return 0;
-+}
-+
-+static inline u8 *page_pool_ethtool_stats_get_strings(u8 *data)
-+{
-+      return data;
-+}
-+
-+static inline u64 *page_pool_ethtool_stats_get(u64 *data, void *stats)
-+{
-+      return data;
-+}
-+
- #endif
- struct page_pool {
---- a/net/core/page_pool.c
-+++ b/net/core/page_pool.c
-@@ -18,6 +18,7 @@
- #include <linux/page-flags.h>
- #include <linux/mm.h> /* for __put_page() */
- #include <linux/poison.h>
-+#include <linux/ethtool.h>
- #include <trace/events/page_pool.h>
-@@ -65,6 +66,20 @@ static void page_pool_producer_unlock(st
-               this_cpu_add(s->__stat, val);                                           \
-       } while (0)
-+static const char pp_stats[][ETH_GSTRING_LEN] = {
-+      "rx_pp_alloc_fast",
-+      "rx_pp_alloc_slow",
-+      "rx_pp_alloc_slow_ho",
-+      "rx_pp_alloc_empty",
-+      "rx_pp_alloc_refill",
-+      "rx_pp_alloc_waive",
-+      "rx_pp_recycle_cached",
-+      "rx_pp_recycle_cache_full",
-+      "rx_pp_recycle_ring",
-+      "rx_pp_recycle_ring_full",
-+      "rx_pp_recycle_released_ref",
-+};
-+
- bool page_pool_get_stats(struct page_pool *pool,
-                        struct page_pool_stats *stats)
- {
-@@ -73,7 +88,13 @@ bool page_pool_get_stats(struct page_poo
-       if (!stats)
-               return false;
--      memcpy(&stats->alloc_stats, &pool->alloc_stats, sizeof(pool->alloc_stats));
-+      /* The caller is responsible to initialize stats. */
-+      stats->alloc_stats.fast += pool->alloc_stats.fast;
-+      stats->alloc_stats.slow += pool->alloc_stats.slow;
-+      stats->alloc_stats.slow_high_order += pool->alloc_stats.slow_high_order;
-+      stats->alloc_stats.empty += pool->alloc_stats.empty;
-+      stats->alloc_stats.refill += pool->alloc_stats.refill;
-+      stats->alloc_stats.waive += pool->alloc_stats.waive;
-       for_each_possible_cpu(cpu) {
-               const struct page_pool_recycle_stats *pcpu =
-@@ -89,6 +110,46 @@ bool page_pool_get_stats(struct page_poo
-       return true;
- }
- EXPORT_SYMBOL(page_pool_get_stats);
-+
-+u8 *page_pool_ethtool_stats_get_strings(u8 *data)
-+{
-+      int i;
-+
-+      for (i = 0; i < ARRAY_SIZE(pp_stats); i++) {
-+              memcpy(data, pp_stats[i], ETH_GSTRING_LEN);
-+              data += ETH_GSTRING_LEN;
-+      }
-+
-+      return data;
-+}
-+EXPORT_SYMBOL(page_pool_ethtool_stats_get_strings);
-+
-+int page_pool_ethtool_stats_get_count(void)
-+{
-+      return ARRAY_SIZE(pp_stats);
-+}
-+EXPORT_SYMBOL(page_pool_ethtool_stats_get_count);
-+
-+u64 *page_pool_ethtool_stats_get(u64 *data, void *stats)
-+{
-+      struct page_pool_stats *pool_stats = stats;
-+
-+      *data++ = pool_stats->alloc_stats.fast;
-+      *data++ = pool_stats->alloc_stats.slow;
-+      *data++ = pool_stats->alloc_stats.slow_high_order;
-+      *data++ = pool_stats->alloc_stats.empty;
-+      *data++ = pool_stats->alloc_stats.refill;
-+      *data++ = pool_stats->alloc_stats.waive;
-+      *data++ = pool_stats->recycle_stats.cached;
-+      *data++ = pool_stats->recycle_stats.cache_full;
-+      *data++ = pool_stats->recycle_stats.ring;
-+      *data++ = pool_stats->recycle_stats.ring_full;
-+      *data++ = pool_stats->recycle_stats.released_refcnt;
-+
-+      return data;
-+}
-+EXPORT_SYMBOL(page_pool_ethtool_stats_get);
-+
- #else
- #define alloc_stat_inc(pool, __stat)
- #define recycle_stat_inc(pool, __stat)
diff --git a/target/linux/generic/backport-5.15/605-v5.18-xdp-introduce-flags-field-in-xdp_buff-xdp_frame.patch b/target/linux/generic/backport-5.15/605-v5.18-xdp-introduce-flags-field-in-xdp_buff-xdp_frame.patch
deleted file mode 100644 (file)
index 4a91440..0000000
+++ /dev/null
@@ -1,99 +0,0 @@
-From 2e88d4ff03013937028f5397268b21e10cf68713 Mon Sep 17 00:00:00 2001
-From: Lorenzo Bianconi <[email protected]>
-Date: Fri, 21 Jan 2022 11:09:45 +0100
-Subject: [PATCH] xdp: introduce flags field in xdp_buff/xdp_frame
-
-Introduce flags field in xdp_frame and xdp_buffer data structures
-to define additional buffer features. At the moment the only
-supported buffer feature is frags bit (XDP_FLAGS_HAS_FRAGS).
-frags bit is used to specify if this is a linear buffer
-(XDP_FLAGS_HAS_FRAGS not set) or a frags frame (XDP_FLAGS_HAS_FRAGS
-set). In the latter case the driver is expected to initialize the
-skb_shared_info structure at the end of the first buffer to link together
-subsequent buffers belonging to the same frame.
-
-Acked-by: Toke Hoiland-Jorgensen <[email protected]>
-Acked-by: John Fastabend <[email protected]>
-Acked-by: Jesper Dangaard Brouer <[email protected]>
-Signed-off-by: Lorenzo Bianconi <[email protected]>
-Link: https://lore.kernel.org/r/e389f14f3a162c0a5bc6a2e1aa8dd01a90be117d.1642758637.git.lorenzo@kernel.org
-Signed-off-by: Alexei Starovoitov <[email protected]>
----
- include/net/xdp.h | 29 +++++++++++++++++++++++++++++
- 1 file changed, 29 insertions(+)
-
---- a/include/net/xdp.h
-+++ b/include/net/xdp.h
-@@ -66,6 +66,10 @@ struct xdp_txq_info {
-       struct net_device *dev;
- };
-+enum xdp_buff_flags {
-+      XDP_FLAGS_HAS_FRAGS     = BIT(0), /* non-linear xdp buff */
-+};
-+
- struct xdp_buff {
-       void *data;
-       void *data_end;
-@@ -74,13 +78,30 @@ struct xdp_buff {
-       struct xdp_rxq_info *rxq;
-       struct xdp_txq_info *txq;
-       u32 frame_sz; /* frame size to deduce data_hard_end/reserved tailroom*/
-+      u32 flags; /* supported values defined in xdp_buff_flags */
- };
-+static __always_inline bool xdp_buff_has_frags(struct xdp_buff *xdp)
-+{
-+      return !!(xdp->flags & XDP_FLAGS_HAS_FRAGS);
-+}
-+
-+static __always_inline void xdp_buff_set_frags_flag(struct xdp_buff *xdp)
-+{
-+      xdp->flags |= XDP_FLAGS_HAS_FRAGS;
-+}
-+
-+static __always_inline void xdp_buff_clear_frags_flag(struct xdp_buff *xdp)
-+{
-+      xdp->flags &= ~XDP_FLAGS_HAS_FRAGS;
-+}
-+
- static __always_inline void
- xdp_init_buff(struct xdp_buff *xdp, u32 frame_sz, struct xdp_rxq_info *rxq)
- {
-       xdp->frame_sz = frame_sz;
-       xdp->rxq = rxq;
-+      xdp->flags = 0;
- }
- static __always_inline void
-@@ -122,8 +143,14 @@ struct xdp_frame {
-        */
-       struct xdp_mem_info mem;
-       struct net_device *dev_rx; /* used by cpumap */
-+      u32 flags; /* supported values defined in xdp_buff_flags */
- };
-+static __always_inline bool xdp_frame_has_frags(struct xdp_frame *frame)
-+{
-+      return !!(frame->flags & XDP_FLAGS_HAS_FRAGS);
-+}
-+
- #define XDP_BULK_QUEUE_SIZE   16
- struct xdp_frame_bulk {
-       int count;
-@@ -180,6 +207,7 @@ void xdp_convert_frame_to_buff(struct xd
-       xdp->data_end = frame->data + frame->len;
-       xdp->data_meta = frame->data - frame->metasize;
-       xdp->frame_sz = frame->frame_sz;
-+      xdp->flags = frame->flags;
- }
- static inline
-@@ -206,6 +234,7 @@ int xdp_update_frame_from_buff(struct xd
-       xdp_frame->headroom = headroom - sizeof(*xdp_frame);
-       xdp_frame->metasize = metasize;
-       xdp_frame->frame_sz = xdp->frame_sz;
-+      xdp_frame->flags = xdp->flags;
-       return 0;
- }
diff --git a/target/linux/generic/backport-5.15/606-v5.18-xdp-add-frags-support-to-xdp_return_-buff-frame.patch b/target/linux/generic/backport-5.15/606-v5.18-xdp-add-frags-support-to-xdp_return_-buff-frame.patch
deleted file mode 100644 (file)
index e126b21..0000000
+++ /dev/null
@@ -1,137 +0,0 @@
-From 7c48cb0176c6d6d3b55029f7ff4ffa05faee6446 Mon Sep 17 00:00:00 2001
-From: Lorenzo Bianconi <[email protected]>
-Date: Fri, 21 Jan 2022 11:09:50 +0100
-Subject: [PATCH] xdp: add frags support to xdp_return_{buff/frame}
-
-Take into account if the received xdp_buff/xdp_frame is non-linear
-recycling/returning the frame memory to the allocator or into
-xdp_frame_bulk.
-
-Acked-by: Toke Hoiland-Jorgensen <[email protected]>
-Acked-by: John Fastabend <[email protected]>
-Signed-off-by: Lorenzo Bianconi <[email protected]>
-Link: https://lore.kernel.org/r/a961069febc868508ce1bdf5e53a343eb4e57cb2.1642758637.git.lorenzo@kernel.org
-Signed-off-by: Alexei Starovoitov <[email protected]>
----
- include/net/xdp.h | 18 ++++++++++++++--
- net/core/xdp.c    | 54 ++++++++++++++++++++++++++++++++++++++++++++++-
- 2 files changed, 69 insertions(+), 3 deletions(-)
-
---- a/include/net/xdp.h
-+++ b/include/net/xdp.h
-@@ -275,10 +275,24 @@ void __xdp_release_frame(void *data, str
- static inline void xdp_release_frame(struct xdp_frame *xdpf)
- {
-       struct xdp_mem_info *mem = &xdpf->mem;
-+      struct skb_shared_info *sinfo;
-+      int i;
-       /* Curr only page_pool needs this */
--      if (mem->type == MEM_TYPE_PAGE_POOL)
--              __xdp_release_frame(xdpf->data, mem);
-+      if (mem->type != MEM_TYPE_PAGE_POOL)
-+              return;
-+
-+      if (likely(!xdp_frame_has_frags(xdpf)))
-+              goto out;
-+
-+      sinfo = xdp_get_shared_info_from_frame(xdpf);
-+      for (i = 0; i < sinfo->nr_frags; i++) {
-+              struct page *page = skb_frag_page(&sinfo->frags[i]);
-+
-+              __xdp_release_frame(page_address(page), mem);
-+      }
-+out:
-+      __xdp_release_frame(xdpf->data, mem);
- }
- int xdp_rxq_info_reg(struct xdp_rxq_info *xdp_rxq,
---- a/net/core/xdp.c
-+++ b/net/core/xdp.c
-@@ -409,12 +409,38 @@ static void __xdp_return(void *data, str
- void xdp_return_frame(struct xdp_frame *xdpf)
- {
-+      struct skb_shared_info *sinfo;
-+      int i;
-+
-+      if (likely(!xdp_frame_has_frags(xdpf)))
-+              goto out;
-+
-+      sinfo = xdp_get_shared_info_from_frame(xdpf);
-+      for (i = 0; i < sinfo->nr_frags; i++) {
-+              struct page *page = skb_frag_page(&sinfo->frags[i]);
-+
-+              __xdp_return(page_address(page), &xdpf->mem, false, NULL);
-+      }
-+out:
-       __xdp_return(xdpf->data, &xdpf->mem, false, NULL);
- }
- EXPORT_SYMBOL_GPL(xdp_return_frame);
- void xdp_return_frame_rx_napi(struct xdp_frame *xdpf)
- {
-+      struct skb_shared_info *sinfo;
-+      int i;
-+
-+      if (likely(!xdp_frame_has_frags(xdpf)))
-+              goto out;
-+
-+      sinfo = xdp_get_shared_info_from_frame(xdpf);
-+      for (i = 0; i < sinfo->nr_frags; i++) {
-+              struct page *page = skb_frag_page(&sinfo->frags[i]);
-+
-+              __xdp_return(page_address(page), &xdpf->mem, true, NULL);
-+      }
-+out:
-       __xdp_return(xdpf->data, &xdpf->mem, true, NULL);
- }
- EXPORT_SYMBOL_GPL(xdp_return_frame_rx_napi);
-@@ -450,7 +476,7 @@ void xdp_return_frame_bulk(struct xdp_fr
-       struct xdp_mem_allocator *xa;
-       if (mem->type != MEM_TYPE_PAGE_POOL) {
--              __xdp_return(xdpf->data, &xdpf->mem, false, NULL);
-+              xdp_return_frame(xdpf);
-               return;
-       }
-@@ -469,12 +495,38 @@ void xdp_return_frame_bulk(struct xdp_fr
-               bq->xa = rhashtable_lookup(mem_id_ht, &mem->id, mem_id_rht_params);
-       }
-+      if (unlikely(xdp_frame_has_frags(xdpf))) {
-+              struct skb_shared_info *sinfo;
-+              int i;
-+
-+              sinfo = xdp_get_shared_info_from_frame(xdpf);
-+              for (i = 0; i < sinfo->nr_frags; i++) {
-+                      skb_frag_t *frag = &sinfo->frags[i];
-+
-+                      bq->q[bq->count++] = skb_frag_address(frag);
-+                      if (bq->count == XDP_BULK_QUEUE_SIZE)
-+                              xdp_flush_frame_bulk(bq);
-+              }
-+      }
-       bq->q[bq->count++] = xdpf->data;
- }
- EXPORT_SYMBOL_GPL(xdp_return_frame_bulk);
- void xdp_return_buff(struct xdp_buff *xdp)
- {
-+      struct skb_shared_info *sinfo;
-+      int i;
-+
-+      if (likely(!xdp_buff_has_frags(xdp)))
-+              goto out;
-+
-+      sinfo = xdp_get_shared_info_from_buff(xdp);
-+      for (i = 0; i < sinfo->nr_frags; i++) {
-+              struct page *page = skb_frag_page(&sinfo->frags[i]);
-+
-+              __xdp_return(page_address(page), &xdp->rxq->mem, true, xdp);
-+      }
-+out:
-       __xdp_return(xdp->data, &xdp->rxq->mem, true, xdp);
- }
diff --git a/target/linux/generic/backport-5.15/607-v5.18-net-skbuff-add-size-metadata-to-skb_shared_info-for-.patch b/target/linux/generic/backport-5.15/607-v5.18-net-skbuff-add-size-metadata-to-skb_shared_info-for-.patch
deleted file mode 100644 (file)
index 36f55d5..0000000
+++ /dev/null
@@ -1,31 +0,0 @@
-From d16697cb6261d4cc23422e6b1cb2759df8aa76d0 Mon Sep 17 00:00:00 2001
-From: Lorenzo Bianconi <[email protected]>
-Date: Fri, 21 Jan 2022 11:09:44 +0100
-Subject: [PATCH] net: skbuff: add size metadata to skb_shared_info for xdp
-
-Introduce xdp_frags_size field in skb_shared_info data structure
-to store xdp_buff/xdp_frame frame paged size (xdp_frags_size will
-be used in xdp frags support). In order to not increase
-skb_shared_info size we will use a hole due to skb_shared_info
-alignment.
-
-Acked-by: Toke Hoiland-Jorgensen <[email protected]>
-Acked-by: John Fastabend <[email protected]>
-Acked-by: Jesper Dangaard Brouer <[email protected]>
-Signed-off-by: Lorenzo Bianconi <[email protected]>
-Link: https://lore.kernel.org/r/8a849819a3e0a143d540f78a3a5add76e17e980d.1642758637.git.lorenzo@kernel.org
-Signed-off-by: Alexei Starovoitov <[email protected]>
----
- include/linux/skbuff.h | 1 +
- 1 file changed, 1 insertion(+)
-
---- a/include/linux/skbuff.h
-+++ b/include/linux/skbuff.h
-@@ -568,6 +568,7 @@ struct skb_shared_info {
-        * Warning : all fields before dataref are cleared in __alloc_skb()
-        */
-       atomic_t        dataref;
-+      unsigned int    xdp_frags_size;
-       /* Intermediate layers must ensure that destructor_arg
-        * remains valid until skb destructor */
diff --git a/target/linux/generic/backport-5.15/608-v5.18-net-veth-Account-total-xdp_frame-len-running-ndo_xdp.patch b/target/linux/generic/backport-5.15/608-v5.18-net-veth-Account-total-xdp_frame-len-running-ndo_xdp.patch
deleted file mode 100644 (file)
index 1ec260a..0000000
+++ /dev/null
@@ -1,65 +0,0 @@
-From 5142239a22219921a7863cf00c9ab853c00689d8 Mon Sep 17 00:00:00 2001
-From: Lorenzo Bianconi <[email protected]>
-Date: Fri, 11 Mar 2022 10:14:18 +0100
-Subject: [PATCH] net: veth: Account total xdp_frame len running ndo_xdp_xmit
-
-Even if this is a theoretical issue since it is not possible to perform
-XDP_REDIRECT on a non-linear xdp_frame, veth driver does not account
-paged area in ndo_xdp_xmit function pointer.
-Introduce xdp_get_frame_len utility routine to get the xdp_frame full
-length and account total frame size running XDP_REDIRECT of a
-non-linear xdp frame into a veth device.
-
-Signed-off-by: Lorenzo Bianconi <[email protected]>
-Signed-off-by: Daniel Borkmann <[email protected]>
-Acked-by: Toke Hoiland-Jorgensen <[email protected]>
-Acked-by: John Fastabend <[email protected]>
-Link: https://lore.kernel.org/bpf/54f9fd3bb65d190daf2c0bbae2f852ff16cfbaa0.1646989407.git.lorenzo@kernel.org
----
- drivers/net/veth.c |  4 ++--
- include/net/xdp.h  | 14 ++++++++++++++
- 2 files changed, 16 insertions(+), 2 deletions(-)
-
---- a/drivers/net/veth.c
-+++ b/drivers/net/veth.c
-@@ -503,7 +503,7 @@ static int veth_xdp_xmit(struct net_devi
-               struct xdp_frame *frame = frames[i];
-               void *ptr = veth_xdp_to_ptr(frame);
--              if (unlikely(frame->len > max_len ||
-+              if (unlikely(xdp_get_frame_len(frame) > max_len ||
-                            __ptr_ring_produce(&rq->xdp_ring, ptr)))
-                       break;
-               nxmit++;
-@@ -864,7 +864,7 @@ static int veth_xdp_rcv(struct veth_rq *
-                       /* ndo_xdp_xmit */
-                       struct xdp_frame *frame = veth_ptr_to_xdp(ptr);
--                      stats->xdp_bytes += frame->len;
-+                      stats->xdp_bytes += xdp_get_frame_len(frame);
-                       frame = veth_xdp_rcv_one(rq, frame, bq, stats);
-                       if (frame) {
-                               /* XDP_PASS */
---- a/include/net/xdp.h
-+++ b/include/net/xdp.h
-@@ -295,6 +295,20 @@ out:
-       __xdp_release_frame(xdpf->data, mem);
- }
-+static __always_inline unsigned int xdp_get_frame_len(struct xdp_frame *xdpf)
-+{
-+      struct skb_shared_info *sinfo;
-+      unsigned int len = xdpf->len;
-+
-+      if (likely(!xdp_frame_has_frags(xdpf)))
-+              goto out;
-+
-+      sinfo = xdp_get_shared_info_from_frame(xdpf);
-+      len += sinfo->xdp_frags_size;
-+out:
-+      return len;
-+}
-+
- int xdp_rxq_info_reg(struct xdp_rxq_info *xdp_rxq,
-                    struct net_device *dev, u32 queue_index, unsigned int napi_id);
- void xdp_rxq_info_unreg(struct xdp_rxq_info *xdp_rxq);
diff --git a/target/linux/generic/backport-5.15/609-v5.18-veth-Allow-jumbo-frames-in-xdp-mode.patch b/target/linux/generic/backport-5.15/609-v5.18-veth-Allow-jumbo-frames-in-xdp-mode.patch
deleted file mode 100644 (file)
index fd583e8..0000000
+++ /dev/null
@@ -1,40 +0,0 @@
-From 7cda76d858a4e71ac4a04066c093679a12e1312c Mon Sep 17 00:00:00 2001
-From: Lorenzo Bianconi <[email protected]>
-Date: Fri, 11 Mar 2022 10:14:20 +0100
-Subject: [PATCH] veth: Allow jumbo frames in xdp mode
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-Allow increasing the MTU over page boundaries on veth devices
-if the attached xdp program declares to support xdp fragments.
-
-Signed-off-by: Lorenzo Bianconi <[email protected]>
-Signed-off-by: Daniel Borkmann <[email protected]>
-Acked-by: Toke Høiland-Jørgensen <[email protected]>
-Acked-by: John Fastabend <[email protected]>
-Link: https://lore.kernel.org/bpf/d5dc039c3d4123426e7023a488c449181a7bc57f.1646989407.git.lorenzo@kernel.org
----
- drivers/net/veth.c | 11 ++++++++---
- 1 file changed, 8 insertions(+), 3 deletions(-)
-
---- a/drivers/net/veth.c
-+++ b/drivers/net/veth.c
-@@ -1455,9 +1455,14 @@ static int veth_xdp_set(struct net_devic
-                       goto err;
-               }
--              max_mtu = PAGE_SIZE - VETH_XDP_HEADROOM -
--                        peer->hard_header_len -
--                        SKB_DATA_ALIGN(sizeof(struct skb_shared_info));
-+              max_mtu = SKB_WITH_OVERHEAD(PAGE_SIZE - VETH_XDP_HEADROOM) -
-+                        peer->hard_header_len;
-+              /* Allow increasing the max_mtu if the program supports
-+               * XDP fragments.
-+               */
-+              //if (prog->aux->xdp_has_frags)
-+              max_mtu += PAGE_SIZE * MAX_SKB_FRAGS;
-+
-               if (peer->mtu > max_mtu) {
-                       NL_SET_ERR_MSG_MOD(extack, "Peer MTU is too large to set XDP");
-                       err = -ERANGE;
diff --git a/target/linux/generic/backport-5.15/611-v6.3-net-add-helper-eth_addr_add.patch b/target/linux/generic/backport-5.15/611-v6.3-net-add-helper-eth_addr_add.patch
deleted file mode 100644 (file)
index c5d5d2c..0000000
+++ /dev/null
@@ -1,41 +0,0 @@
-From 7390609b0121a1b982c5ecdfcd72dc328e5784ee Mon Sep 17 00:00:00 2001
-From: Michael Walle <[email protected]>
-Date: Mon, 6 Feb 2023 13:43:42 +0000
-Subject: [PATCH] net: add helper eth_addr_add()
-
-Add a helper to add an offset to a ethernet address. This comes in handy
-if you have a base ethernet address for multiple interfaces.
-
-Signed-off-by: Michael Walle <[email protected]>
-Reviewed-by: Andrew Lunn <[email protected]>
-Acked-by: Jakub Kicinski <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- include/linux/etherdevice.h | 14 ++++++++++++++
- 1 file changed, 14 insertions(+)
-
---- a/include/linux/etherdevice.h
-+++ b/include/linux/etherdevice.h
-@@ -478,6 +478,20 @@ static inline void eth_addr_inc(u8 *addr
- }
- /**
-+ * eth_addr_add() - Add (or subtract) an offset to/from the given MAC address.
-+ *
-+ * @offset: Offset to add.
-+ * @addr: Pointer to a six-byte array containing Ethernet address to increment.
-+ */
-+static inline void eth_addr_add(u8 *addr, long offset)
-+{
-+      u64 u = ether_addr_to_u64(addr);
-+
-+      u += offset;
-+      u64_to_ether_addr(u, addr);
-+}
-+
-+/**
-  * is_etherdev_addr - Tell if given Ethernet address belongs to the device.
-  * @dev: Pointer to a device structure
-  * @addr: Pointer to a six-byte array containing the Ethernet address
diff --git a/target/linux/generic/backport-5.15/700-v5.17-net-dsa-introduce-tagger-owned-storage-for-private.patch b/target/linux/generic/backport-5.15/700-v5.17-net-dsa-introduce-tagger-owned-storage-for-private.patch
deleted file mode 100644 (file)
index 8e5c718..0000000
+++ /dev/null
@@ -1,279 +0,0 @@
-From dc452a471dbae8aca8257c565174212620880093 Mon Sep 17 00:00:00 2001
-From: Vladimir Oltean <[email protected]>
-Date: Fri, 10 Dec 2021 01:34:37 +0200
-Subject: net: dsa: introduce tagger-owned storage for private and shared data
-
-Ansuel is working on register access over Ethernet for the qca8k switch
-family. This requires the qca8k tagging protocol driver to receive
-frames which aren't intended for the network stack, but instead for the
-qca8k switch driver itself.
-
-The dp->priv is currently the prevailing method for passing data back
-and forth between the tagging protocol driver and the switch driver.
-However, this method is riddled with caveats.
-
-The DSA design allows in principle for any switch driver to return any
-protocol it desires in ->get_tag_protocol(). The dsa_loop driver can be
-modified to do just that. But in the current design, the memory behind
-dp->priv has to be allocated by the switch driver, so if the tagging
-protocol is paired to an unexpected switch driver, we may end up in NULL
-pointer dereferences inside the kernel, or worse (a switch driver may
-allocate dp->priv according to the expectations of a different tagger).
-
-The latter possibility is even more plausible considering that DSA
-switches can dynamically change tagging protocols in certain cases
-(dsa <-> edsa, ocelot <-> ocelot-8021q), and the current design lends
-itself to mistakes that are all too easy to make.
-
-This patch proposes that the tagging protocol driver should manage its
-own memory, instead of relying on the switch driver to do so.
-After analyzing the different in-tree needs, it can be observed that the
-required tagger storage is per switch, therefore a ds->tagger_data
-pointer is introduced. In principle, per-port storage could also be
-introduced, although there is no need for it at the moment. Future
-changes will replace the current usage of dp->priv with ds->tagger_data.
-
-We define a "binding" event between the DSA switch tree and the tagging
-protocol. During this binding event, the tagging protocol's ->connect()
-method is called first, and this may allocate some memory for each
-switch of the tree. Then a cross-chip notifier is emitted for the
-switches within that tree, and they are given the opportunity to fix up
-the tagger's memory (for example, they might set up some function
-pointers that represent virtual methods for consuming packets).
-Because the memory is owned by the tagger, there exists a ->disconnect()
-method for the tagger (which is the place to free the resources), but
-there doesn't exist a ->disconnect() method for the switch driver.
-This is part of the design. The switch driver should make minimal use of
-the public part of the tagger data, and only after type-checking it
-using the supplied "proto" argument.
-
-In the code there are in fact two binding events, one is the initial
-event in dsa_switch_setup_tag_protocol(). At this stage, the cross chip
-notifier chains aren't initialized, so we call each switch's connect()
-method by hand. Then there is dsa_tree_bind_tag_proto() during
-dsa_tree_change_tag_proto(), and here we have an old protocol and a new
-one. We first connect to the new one before disconnecting from the old
-one, to simplify error handling a bit and to ensure we remain in a valid
-state at all times.
-
-Co-developed-by: Ansuel Smith <[email protected]>
-Signed-off-by: Ansuel Smith <[email protected]>
-Signed-off-by: Vladimir Oltean <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- include/net/dsa.h  | 12 +++++++++
- net/dsa/dsa2.c     | 73 +++++++++++++++++++++++++++++++++++++++++++++++++++---
- net/dsa/dsa_priv.h |  1 +
- net/dsa/switch.c   | 14 +++++++++++
- 4 files changed, 96 insertions(+), 4 deletions(-)
-
---- a/include/net/dsa.h
-+++ b/include/net/dsa.h
-@@ -80,12 +80,15 @@ enum dsa_tag_protocol {
- };
- struct dsa_switch;
-+struct dsa_switch_tree;
- struct dsa_device_ops {
-       struct sk_buff *(*xmit)(struct sk_buff *skb, struct net_device *dev);
-       struct sk_buff *(*rcv)(struct sk_buff *skb, struct net_device *dev);
-       void (*flow_dissect)(const struct sk_buff *skb, __be16 *proto,
-                            int *offset);
-+      int (*connect)(struct dsa_switch_tree *dst);
-+      void (*disconnect)(struct dsa_switch_tree *dst);
-       unsigned int needed_headroom;
-       unsigned int needed_tailroom;
-       const char *name;
-@@ -329,6 +332,8 @@ struct dsa_switch {
-        */
-       void *priv;
-+      void *tagger_data;
-+
-       /*
-        * Configuration data for this switch.
-        */
-@@ -612,6 +617,13 @@ struct dsa_switch_ops {
-                                                 enum dsa_tag_protocol mprot);
-       int     (*change_tag_protocol)(struct dsa_switch *ds, int port,
-                                      enum dsa_tag_protocol proto);
-+      /*
-+       * Method for switch drivers to connect to the tagging protocol driver
-+       * in current use. The switch driver can provide handlers for certain
-+       * types of packets for switch management.
-+       */
-+      int     (*connect_tag_protocol)(struct dsa_switch *ds,
-+                                      enum dsa_tag_protocol proto);
-       /* Optional switch-wide initialization and destruction methods */
-       int     (*setup)(struct dsa_switch *ds);
---- a/net/dsa/dsa2.c
-+++ b/net/dsa/dsa2.c
-@@ -230,8 +230,12 @@ static struct dsa_switch_tree *dsa_tree_
- static void dsa_tree_free(struct dsa_switch_tree *dst)
- {
--      if (dst->tag_ops)
-+      if (dst->tag_ops) {
-+              if (dst->tag_ops->disconnect)
-+                      dst->tag_ops->disconnect(dst);
-+
-               dsa_tag_driver_put(dst->tag_ops);
-+      }
-       list_del(&dst->list);
-       kfree(dst);
- }
-@@ -827,7 +831,7 @@ static int dsa_switch_setup_tag_protocol
-       int port, err;
-       if (tag_ops->proto == dst->default_proto)
--              return 0;
-+              goto connect;
-       for (port = 0; port < ds->num_ports; port++) {
-               if (!dsa_is_cpu_port(ds, port))
-@@ -843,6 +847,17 @@ static int dsa_switch_setup_tag_protocol
-               }
-       }
-+connect:
-+      if (ds->ops->connect_tag_protocol) {
-+              err = ds->ops->connect_tag_protocol(ds, tag_ops->proto);
-+              if (err) {
-+                      dev_err(ds->dev,
-+                              "Unable to connect to tag protocol \"%s\": %pe\n",
-+                              tag_ops->name, ERR_PTR(err));
-+                      return err;
-+              }
-+      }
-+
-       return 0;
- }
-@@ -1154,6 +1169,46 @@ static void dsa_tree_teardown(struct dsa
-       dst->setup = false;
- }
-+static int dsa_tree_bind_tag_proto(struct dsa_switch_tree *dst,
-+                                 const struct dsa_device_ops *tag_ops)
-+{
-+      const struct dsa_device_ops *old_tag_ops = dst->tag_ops;
-+      struct dsa_notifier_tag_proto_info info;
-+      int err;
-+
-+      dst->tag_ops = tag_ops;
-+
-+      /* Notify the new tagger about the connection to this tree */
-+      if (tag_ops->connect) {
-+              err = tag_ops->connect(dst);
-+              if (err)
-+                      goto out_revert;
-+      }
-+
-+      /* Notify the switches from this tree about the connection
-+       * to the new tagger
-+       */
-+      info.tag_ops = tag_ops;
-+      err = dsa_tree_notify(dst, DSA_NOTIFIER_TAG_PROTO_CONNECT, &info);
-+      if (err && err != -EOPNOTSUPP)
-+              goto out_disconnect;
-+
-+      /* Notify the old tagger about the disconnection from this tree */
-+      if (old_tag_ops->disconnect)
-+              old_tag_ops->disconnect(dst);
-+
-+      return 0;
-+
-+out_disconnect:
-+      /* Revert the new tagger's connection to this tree */
-+      if (tag_ops->disconnect)
-+              tag_ops->disconnect(dst);
-+out_revert:
-+      dst->tag_ops = old_tag_ops;
-+
-+      return err;
-+}
-+
- /* Since the dsa/tagging sysfs device attribute is per master, the assumption
-  * is that all DSA switches within a tree share the same tagger, otherwise
-  * they would have formed disjoint trees (different "dsa,member" values).
-@@ -1186,12 +1241,15 @@ int dsa_tree_change_tag_proto(struct dsa
-                       goto out_unlock;
-       }
-+      /* Notify the tag protocol change */
-       info.tag_ops = tag_ops;
-       err = dsa_tree_notify(dst, DSA_NOTIFIER_TAG_PROTO, &info);
-       if (err)
--              goto out_unwind_tagger;
-+              return err;
--      dst->tag_ops = tag_ops;
-+      err = dsa_tree_bind_tag_proto(dst, tag_ops);
-+      if (err)
-+              goto out_unwind_tagger;
-       rtnl_unlock();
-@@ -1279,6 +1337,7 @@ static int dsa_port_parse_cpu(struct dsa
-       struct dsa_switch *ds = dp->ds;
-       struct dsa_switch_tree *dst = ds->dst;
-       enum dsa_tag_protocol default_proto;
-+      int err;
-       /* Find out which protocol the switch would prefer. */
-       default_proto = dsa_get_tag_protocol(dp, master);
-@@ -1333,6 +1392,12 @@ static int dsa_port_parse_cpu(struct dsa
-                */
-               dsa_tag_driver_put(tag_ops);
-       } else {
-+              if (tag_ops->connect) {
-+                      err = tag_ops->connect(dst);
-+                      if (err)
-+                              return err;
-+              }
-+
-               dst->tag_ops = tag_ops;
-       }
---- a/net/dsa/dsa_priv.h
-+++ b/net/dsa/dsa_priv.h
-@@ -37,6 +37,7 @@ enum {
-       DSA_NOTIFIER_VLAN_DEL,
-       DSA_NOTIFIER_MTU,
-       DSA_NOTIFIER_TAG_PROTO,
-+      DSA_NOTIFIER_TAG_PROTO_CONNECT,
-       DSA_NOTIFIER_MRP_ADD,
-       DSA_NOTIFIER_MRP_DEL,
-       DSA_NOTIFIER_MRP_ADD_RING_ROLE,
---- a/net/dsa/switch.c
-+++ b/net/dsa/switch.c
-@@ -616,6 +616,17 @@ static int dsa_switch_change_tag_proto(s
-       return 0;
- }
-+static int dsa_switch_connect_tag_proto(struct dsa_switch *ds,
-+                                      struct dsa_notifier_tag_proto_info *info)
-+{
-+      const struct dsa_device_ops *tag_ops = info->tag_ops;
-+
-+      if (!ds->ops->connect_tag_protocol)
-+              return -EOPNOTSUPP;
-+
-+      return ds->ops->connect_tag_protocol(ds, tag_ops->proto);
-+}
-+
- static int dsa_switch_mrp_add(struct dsa_switch *ds,
-                             struct dsa_notifier_mrp_info *info)
- {
-@@ -735,6 +746,9 @@ static int dsa_switch_event(struct notif
-       case DSA_NOTIFIER_TAG_PROTO:
-               err = dsa_switch_change_tag_proto(ds, info);
-               break;
-+      case DSA_NOTIFIER_TAG_PROTO_CONNECT:
-+              err = dsa_switch_connect_tag_proto(ds, info);
-+              break;
-       case DSA_NOTIFIER_MRP_ADD:
-               err = dsa_switch_mrp_add(ds, info);
-               break;
diff --git a/target/linux/generic/backport-5.15/701-v5.17-dsa-make-tagging-protocols-connect-to-individual-switches.patch b/target/linux/generic/backport-5.15/701-v5.17-dsa-make-tagging-protocols-connect-to-individual-switches.patch
deleted file mode 100644 (file)
index 8c81ebc..0000000
+++ /dev/null
@@ -1,274 +0,0 @@
-From 7f2973149c22e7a6fee4c0c9fa6b8e4108e9c208 Mon Sep 17 00:00:00 2001
-From: Vladimir Oltean <[email protected]>
-Date: Tue, 14 Dec 2021 03:45:36 +0200
-Subject: net: dsa: make tagging protocols connect to individual switches from
- a tree
-
-On the NXP Bluebox 3 board which uses a multi-switch setup with sja1105,
-the mechanism through which the tagger connects to the switch tree is
-broken, due to improper DSA code design. At the time when tag_ops->connect()
-is called in dsa_port_parse_cpu(), DSA hasn't finished "touching" all
-the ports, so it doesn't know how large the tree is and how many ports
-it has. It has just seen the first CPU port by this time. As a result,
-this function will call the tagger's ->connect method too early, and the
-tagger will connect only to the first switch from the tree.
-
-This could be perhaps addressed a bit more simply by just moving the
-tag_ops->connect(dst) call a bit later (for example in dsa_tree_setup),
-but there is already a design inconsistency at present: on the switch
-side, the notification is on a per-switch basis, but on the tagger side,
-it is on a per-tree basis. Furthermore, the persistent storage itself is
-per switch (ds->tagger_data). And the tagger connect and disconnect
-procedures (at least the ones that exist currently) could see a fair bit
-of simplification if they didn't have to iterate through the switches of
-a tree.
-
-To fix the issue, this change transforms tag_ops->connect(dst) into
-tag_ops->connect(ds) and moves it somewhere where we already iterate
-over all switches of a tree. That is in dsa_switch_setup_tag_protocol(),
-which is a good placement because we already have there the connection
-call to the switch side of things.
-
-As for the dsa_tree_bind_tag_proto() method (called from the code path
-that changes the tag protocol), things are a bit more complicated
-because we receive the tree as argument, yet when we unwind on errors,
-it would be nice to not call tag_ops->disconnect(ds) where we didn't
-previously call tag_ops->connect(ds). We didn't have this problem before
-because the tag_ops connection operations passed the entire dst before,
-and this is more fine grained now. To solve the error rewind case using
-the new API, we have to create yet one more cross-chip notifier for
-disconnection, and stay connected with the old tag protocol to all the
-switches in the tree until we've succeeded to connect with the new one
-as well. So if something fails half way, the whole tree is still
-connected to the old tagger. But there may still be leaks if the tagger
-fails to connect to the 2nd out of 3 switches in a tree: somebody needs
-to tell the tagger to disconnect from the first switch. Nothing comes
-for free, and this was previously handled privately by the tagging
-protocol driver before, but now we need to emit a disconnect cross-chip
-notifier for that, because DSA has to take care of the unwind path. We
-assume that the tagging protocol has connected to a switch if it has set
-ds->tagger_data to something, otherwise we avoid calling its
-disconnection method in the error rewind path.
-
-The rest of the changes are in the tagging protocol drivers, and have to
-do with the replacement of dst with ds. The iteration is removed and the
-error unwind path is simplified, as mentioned above.
-
-Signed-off-by: Vladimir Oltean <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- include/net/dsa.h          |  5 ++--
- net/dsa/dsa2.c             | 44 +++++++++++++-----------------
- net/dsa/dsa_priv.h         |  1 +
- net/dsa/switch.c           | 52 ++++++++++++++++++++++++++++++++---
- net/dsa/tag_ocelot_8021q.c | 53 +++++++++++-------------------------
- net/dsa/tag_sja1105.c      | 67 ++++++++++++++++------------------------------
- 6 files changed, 109 insertions(+), 113 deletions(-)
-
---- a/include/net/dsa.h
-+++ b/include/net/dsa.h
-@@ -80,15 +80,14 @@ enum dsa_tag_protocol {
- };
- struct dsa_switch;
--struct dsa_switch_tree;
- struct dsa_device_ops {
-       struct sk_buff *(*xmit)(struct sk_buff *skb, struct net_device *dev);
-       struct sk_buff *(*rcv)(struct sk_buff *skb, struct net_device *dev);
-       void (*flow_dissect)(const struct sk_buff *skb, __be16 *proto,
-                            int *offset);
--      int (*connect)(struct dsa_switch_tree *dst);
--      void (*disconnect)(struct dsa_switch_tree *dst);
-+      int (*connect)(struct dsa_switch *ds);
-+      void (*disconnect)(struct dsa_switch *ds);
-       unsigned int needed_headroom;
-       unsigned int needed_tailroom;
-       const char *name;
---- a/net/dsa/dsa2.c
-+++ b/net/dsa/dsa2.c
-@@ -230,12 +230,8 @@ static struct dsa_switch_tree *dsa_tree_
- static void dsa_tree_free(struct dsa_switch_tree *dst)
- {
--      if (dst->tag_ops) {
--              if (dst->tag_ops->disconnect)
--                      dst->tag_ops->disconnect(dst);
--
-+      if (dst->tag_ops)
-               dsa_tag_driver_put(dst->tag_ops);
--      }
-       list_del(&dst->list);
-       kfree(dst);
- }
-@@ -848,17 +844,29 @@ static int dsa_switch_setup_tag_protocol
-       }
- connect:
-+      if (tag_ops->connect) {
-+              err = tag_ops->connect(ds);
-+              if (err)
-+                      return err;
-+      }
-+
-       if (ds->ops->connect_tag_protocol) {
-               err = ds->ops->connect_tag_protocol(ds, tag_ops->proto);
-               if (err) {
-                       dev_err(ds->dev,
-                               "Unable to connect to tag protocol \"%s\": %pe\n",
-                               tag_ops->name, ERR_PTR(err));
--                      return err;
-+                      goto disconnect;
-               }
-       }
-       return 0;
-+
-+disconnect:
-+      if (tag_ops->disconnect)
-+              tag_ops->disconnect(ds);
-+
-+      return err;
- }
- static int dsa_switch_setup(struct dsa_switch *ds)
-@@ -1178,13 +1186,6 @@ static int dsa_tree_bind_tag_proto(struc
-       dst->tag_ops = tag_ops;
--      /* Notify the new tagger about the connection to this tree */
--      if (tag_ops->connect) {
--              err = tag_ops->connect(dst);
--              if (err)
--                      goto out_revert;
--      }
--
-       /* Notify the switches from this tree about the connection
-        * to the new tagger
-        */
-@@ -1194,16 +1195,14 @@ static int dsa_tree_bind_tag_proto(struc
-               goto out_disconnect;
-       /* Notify the old tagger about the disconnection from this tree */
--      if (old_tag_ops->disconnect)
--              old_tag_ops->disconnect(dst);
-+      info.tag_ops = old_tag_ops;
-+      dsa_tree_notify(dst, DSA_NOTIFIER_TAG_PROTO_DISCONNECT, &info);
-       return 0;
- out_disconnect:
--      /* Revert the new tagger's connection to this tree */
--      if (tag_ops->disconnect)
--              tag_ops->disconnect(dst);
--out_revert:
-+      info.tag_ops = tag_ops;
-+      dsa_tree_notify(dst, DSA_NOTIFIER_TAG_PROTO_DISCONNECT, &info);
-       dst->tag_ops = old_tag_ops;
-       return err;
-@@ -1337,7 +1336,6 @@ static int dsa_port_parse_cpu(struct dsa
-       struct dsa_switch *ds = dp->ds;
-       struct dsa_switch_tree *dst = ds->dst;
-       enum dsa_tag_protocol default_proto;
--      int err;
-       /* Find out which protocol the switch would prefer. */
-       default_proto = dsa_get_tag_protocol(dp, master);
-@@ -1392,12 +1390,6 @@ static int dsa_port_parse_cpu(struct dsa
-                */
-               dsa_tag_driver_put(tag_ops);
-       } else {
--              if (tag_ops->connect) {
--                      err = tag_ops->connect(dst);
--                      if (err)
--                              return err;
--              }
--
-               dst->tag_ops = tag_ops;
-       }
---- a/net/dsa/dsa_priv.h
-+++ b/net/dsa/dsa_priv.h
-@@ -38,6 +38,7 @@ enum {
-       DSA_NOTIFIER_MTU,
-       DSA_NOTIFIER_TAG_PROTO,
-       DSA_NOTIFIER_TAG_PROTO_CONNECT,
-+      DSA_NOTIFIER_TAG_PROTO_DISCONNECT,
-       DSA_NOTIFIER_MRP_ADD,
-       DSA_NOTIFIER_MRP_DEL,
-       DSA_NOTIFIER_MRP_ADD_RING_ROLE,
---- a/net/dsa/switch.c
-+++ b/net/dsa/switch.c
-@@ -616,15 +616,58 @@ static int dsa_switch_change_tag_proto(s
-       return 0;
- }
--static int dsa_switch_connect_tag_proto(struct dsa_switch *ds,
--                                      struct dsa_notifier_tag_proto_info *info)
-+/* We use the same cross-chip notifiers to inform both the tagger side, as well
-+ * as the switch side, of connection and disconnection events.
-+ * Since ds->tagger_data is owned by the tagger, it isn't a hard error if the
-+ * switch side doesn't support connecting to this tagger, and therefore, the
-+ * fact that we don't disconnect the tagger side doesn't constitute a memory
-+ * leak: the tagger will still operate with persistent per-switch memory, just
-+ * with the switch side unconnected to it. What does constitute a hard error is
-+ * when the switch side supports connecting but fails.
-+ */
-+static int
-+dsa_switch_connect_tag_proto(struct dsa_switch *ds,
-+                           struct dsa_notifier_tag_proto_info *info)
- {
-       const struct dsa_device_ops *tag_ops = info->tag_ops;
-+      int err;
-+
-+      /* Notify the new tagger about the connection to this switch */
-+      if (tag_ops->connect) {
-+              err = tag_ops->connect(ds);
-+              if (err)
-+                      return err;
-+      }
-       if (!ds->ops->connect_tag_protocol)
-               return -EOPNOTSUPP;
--      return ds->ops->connect_tag_protocol(ds, tag_ops->proto);
-+      /* Notify the switch about the connection to the new tagger */
-+      err = ds->ops->connect_tag_protocol(ds, tag_ops->proto);
-+      if (err) {
-+              /* Revert the new tagger's connection to this tree */
-+              if (tag_ops->disconnect)
-+                      tag_ops->disconnect(ds);
-+              return err;
-+      }
-+
-+      return 0;
-+}
-+
-+static int
-+dsa_switch_disconnect_tag_proto(struct dsa_switch *ds,
-+                              struct dsa_notifier_tag_proto_info *info)
-+{
-+      const struct dsa_device_ops *tag_ops = info->tag_ops;
-+
-+      /* Notify the tagger about the disconnection from this switch */
-+      if (tag_ops->disconnect && ds->tagger_data)
-+              tag_ops->disconnect(ds);
-+
-+      /* No need to notify the switch, since it shouldn't have any
-+       * resources to tear down
-+       */
-+      return 0;
- }
- static int dsa_switch_mrp_add(struct dsa_switch *ds,
-@@ -749,6 +792,9 @@ static int dsa_switch_event(struct notif
-       case DSA_NOTIFIER_TAG_PROTO_CONNECT:
-               err = dsa_switch_connect_tag_proto(ds, info);
-               break;
-+      case DSA_NOTIFIER_TAG_PROTO_DISCONNECT:
-+              err = dsa_switch_disconnect_tag_proto(ds, info);
-+              break;
-       case DSA_NOTIFIER_MRP_ADD:
-               err = dsa_switch_mrp_add(ds, info);
-               break;
diff --git a/target/linux/generic/backport-5.15/702-v5.19-00-net-ethernet-mtk_eth_soc-add-support-for-coherent-DM.patch b/target/linux/generic/backport-5.15/702-v5.19-00-net-ethernet-mtk_eth_soc-add-support-for-coherent-DM.patch
deleted file mode 100644 (file)
index 2bace3b..0000000
+++ /dev/null
@@ -1,327 +0,0 @@
-From: Felix Fietkau <[email protected]>
-Date: Sat, 5 Feb 2022 17:59:07 +0100
-Subject: [PATCH] net: ethernet: mtk_eth_soc: add support for coherent
- DMA
-
-It improves performance by eliminating the need for a cache flush on rx and tx
-In preparation for supporting WED (Wireless Ethernet Dispatch), also add a
-function for disabling coherent DMA at runtime.
-
-Signed-off-by: Felix Fietkau <[email protected]>
----
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-@@ -9,6 +9,7 @@
- #include <linux/of_device.h>
- #include <linux/of_mdio.h>
- #include <linux/of_net.h>
-+#include <linux/of_address.h>
- #include <linux/mfd/syscon.h>
- #include <linux/regmap.h>
- #include <linux/clk.h>
-@@ -850,7 +851,7 @@ static int mtk_init_fq_dma(struct mtk_et
-       dma_addr_t dma_addr;
-       int i;
--      eth->scratch_ring = dma_alloc_coherent(eth->dev,
-+      eth->scratch_ring = dma_alloc_coherent(eth->dma_dev,
-                                              cnt * sizeof(struct mtk_tx_dma),
-                                              &eth->phy_scratch_ring,
-                                              GFP_ATOMIC);
-@@ -862,10 +863,10 @@ static int mtk_init_fq_dma(struct mtk_et
-       if (unlikely(!eth->scratch_head))
-               return -ENOMEM;
--      dma_addr = dma_map_single(eth->dev,
-+      dma_addr = dma_map_single(eth->dma_dev,
-                                 eth->scratch_head, cnt * MTK_QDMA_PAGE_SIZE,
-                                 DMA_FROM_DEVICE);
--      if (unlikely(dma_mapping_error(eth->dev, dma_addr)))
-+      if (unlikely(dma_mapping_error(eth->dma_dev, dma_addr)))
-               return -ENOMEM;
-       phy_ring_tail = eth->phy_scratch_ring +
-@@ -919,26 +920,26 @@ static void mtk_tx_unmap(struct mtk_eth
- {
-       if (MTK_HAS_CAPS(eth->soc->caps, MTK_QDMA)) {
-               if (tx_buf->flags & MTK_TX_FLAGS_SINGLE0) {
--                      dma_unmap_single(eth->dev,
-+                      dma_unmap_single(eth->dma_dev,
-                                        dma_unmap_addr(tx_buf, dma_addr0),
-                                        dma_unmap_len(tx_buf, dma_len0),
-                                        DMA_TO_DEVICE);
-               } else if (tx_buf->flags & MTK_TX_FLAGS_PAGE0) {
--                      dma_unmap_page(eth->dev,
-+                      dma_unmap_page(eth->dma_dev,
-                                      dma_unmap_addr(tx_buf, dma_addr0),
-                                      dma_unmap_len(tx_buf, dma_len0),
-                                      DMA_TO_DEVICE);
-               }
-       } else {
-               if (dma_unmap_len(tx_buf, dma_len0)) {
--                      dma_unmap_page(eth->dev,
-+                      dma_unmap_page(eth->dma_dev,
-                                      dma_unmap_addr(tx_buf, dma_addr0),
-                                      dma_unmap_len(tx_buf, dma_len0),
-                                      DMA_TO_DEVICE);
-               }
-               if (dma_unmap_len(tx_buf, dma_len1)) {
--                      dma_unmap_page(eth->dev,
-+                      dma_unmap_page(eth->dma_dev,
-                                      dma_unmap_addr(tx_buf, dma_addr1),
-                                      dma_unmap_len(tx_buf, dma_len1),
-                                      DMA_TO_DEVICE);
-@@ -1016,9 +1017,9 @@ static int mtk_tx_map(struct sk_buff *sk
-       if (skb_vlan_tag_present(skb))
-               txd4 |= TX_DMA_INS_VLAN | skb_vlan_tag_get(skb);
--      mapped_addr = dma_map_single(eth->dev, skb->data,
-+      mapped_addr = dma_map_single(eth->dma_dev, skb->data,
-                                    skb_headlen(skb), DMA_TO_DEVICE);
--      if (unlikely(dma_mapping_error(eth->dev, mapped_addr)))
-+      if (unlikely(dma_mapping_error(eth->dma_dev, mapped_addr)))
-               return -ENOMEM;
-       WRITE_ONCE(itxd->txd1, mapped_addr);
-@@ -1057,10 +1058,10 @@ static int mtk_tx_map(struct sk_buff *sk
-                       frag_map_size = min(frag_size, MTK_TX_DMA_BUF_LEN);
--                      mapped_addr = skb_frag_dma_map(eth->dev, frag, offset,
-+                      mapped_addr = skb_frag_dma_map(eth->dma_dev, frag, offset,
-                                                      frag_map_size,
-                                                      DMA_TO_DEVICE);
--                      if (unlikely(dma_mapping_error(eth->dev, mapped_addr)))
-+                      if (unlikely(dma_mapping_error(eth->dma_dev, mapped_addr)))
-                               goto err_dma;
-                       if (i == nr_frags - 1 &&
-@@ -1341,18 +1342,18 @@ static int mtk_poll_rx(struct napi_struc
-                       netdev->stats.rx_dropped++;
-                       goto release_desc;
-               }
--              dma_addr = dma_map_single(eth->dev,
-+              dma_addr = dma_map_single(eth->dma_dev,
-                                         new_data + NET_SKB_PAD +
-                                         eth->ip_align,
-                                         ring->buf_size,
-                                         DMA_FROM_DEVICE);
--              if (unlikely(dma_mapping_error(eth->dev, dma_addr))) {
-+              if (unlikely(dma_mapping_error(eth->dma_dev, dma_addr))) {
-                       skb_free_frag(new_data);
-                       netdev->stats.rx_dropped++;
-                       goto release_desc;
-               }
--              dma_unmap_single(eth->dev, trxd.rxd1,
-+              dma_unmap_single(eth->dma_dev, trxd.rxd1,
-                                ring->buf_size, DMA_FROM_DEVICE);
-               /* receive data */
-@@ -1625,7 +1626,7 @@ static int mtk_tx_alloc(struct mtk_eth *
-       if (!ring->buf)
-               goto no_tx_mem;
--      ring->dma = dma_alloc_coherent(eth->dev, MTK_DMA_SIZE * sz,
-+      ring->dma = dma_alloc_coherent(eth->dma_dev, MTK_DMA_SIZE * sz,
-                                      &ring->phys, GFP_ATOMIC);
-       if (!ring->dma)
-               goto no_tx_mem;
-@@ -1643,7 +1644,7 @@ static int mtk_tx_alloc(struct mtk_eth *
-        * descriptors in ring->dma_pdma.
-        */
-       if (!MTK_HAS_CAPS(eth->soc->caps, MTK_QDMA)) {
--              ring->dma_pdma = dma_alloc_coherent(eth->dev, MTK_DMA_SIZE * sz,
-+              ring->dma_pdma = dma_alloc_coherent(eth->dma_dev, MTK_DMA_SIZE * sz,
-                                                   &ring->phys_pdma,
-                                                   GFP_ATOMIC);
-               if (!ring->dma_pdma)
-@@ -1702,7 +1703,7 @@ static void mtk_tx_clean(struct mtk_eth
-       }
-       if (ring->dma) {
--              dma_free_coherent(eth->dev,
-+              dma_free_coherent(eth->dma_dev,
-                                 MTK_DMA_SIZE * sizeof(*ring->dma),
-                                 ring->dma,
-                                 ring->phys);
-@@ -1710,7 +1711,7 @@ static void mtk_tx_clean(struct mtk_eth
-       }
-       if (ring->dma_pdma) {
--              dma_free_coherent(eth->dev,
-+              dma_free_coherent(eth->dma_dev,
-                                 MTK_DMA_SIZE * sizeof(*ring->dma_pdma),
-                                 ring->dma_pdma,
-                                 ring->phys_pdma);
-@@ -1758,18 +1759,18 @@ static int mtk_rx_alloc(struct mtk_eth *
-                       return -ENOMEM;
-       }
--      ring->dma = dma_alloc_coherent(eth->dev,
-+      ring->dma = dma_alloc_coherent(eth->dma_dev,
-                                      rx_dma_size * sizeof(*ring->dma),
-                                      &ring->phys, GFP_ATOMIC);
-       if (!ring->dma)
-               return -ENOMEM;
-       for (i = 0; i < rx_dma_size; i++) {
--              dma_addr_t dma_addr = dma_map_single(eth->dev,
-+              dma_addr_t dma_addr = dma_map_single(eth->dma_dev,
-                               ring->data[i] + NET_SKB_PAD + eth->ip_align,
-                               ring->buf_size,
-                               DMA_FROM_DEVICE);
--              if (unlikely(dma_mapping_error(eth->dev, dma_addr)))
-+              if (unlikely(dma_mapping_error(eth->dma_dev, dma_addr)))
-                       return -ENOMEM;
-               ring->dma[i].rxd1 = (unsigned int)dma_addr;
-@@ -1805,7 +1806,7 @@ static void mtk_rx_clean(struct mtk_eth
-                               continue;
-                       if (!ring->dma[i].rxd1)
-                               continue;
--                      dma_unmap_single(eth->dev,
-+                      dma_unmap_single(eth->dma_dev,
-                                        ring->dma[i].rxd1,
-                                        ring->buf_size,
-                                        DMA_FROM_DEVICE);
-@@ -1816,7 +1817,7 @@ static void mtk_rx_clean(struct mtk_eth
-       }
-       if (ring->dma) {
--              dma_free_coherent(eth->dev,
-+              dma_free_coherent(eth->dma_dev,
-                                 ring->dma_size * sizeof(*ring->dma),
-                                 ring->dma,
-                                 ring->phys);
-@@ -2175,7 +2176,7 @@ static void mtk_dma_free(struct mtk_eth
-               if (eth->netdev[i])
-                       netdev_reset_queue(eth->netdev[i]);
-       if (eth->scratch_ring) {
--              dma_free_coherent(eth->dev,
-+              dma_free_coherent(eth->dma_dev,
-                                 MTK_DMA_SIZE * sizeof(struct mtk_tx_dma),
-                                 eth->scratch_ring,
-                                 eth->phy_scratch_ring);
-@@ -2527,6 +2528,8 @@ static void mtk_dim_tx(struct work_struc
- static int mtk_hw_init(struct mtk_eth *eth)
- {
-+      u32 dma_mask = ETHSYS_DMA_AG_MAP_PDMA | ETHSYS_DMA_AG_MAP_QDMA |
-+                     ETHSYS_DMA_AG_MAP_PPE;
-       int i, val, ret;
-       if (test_and_set_bit(MTK_HW_INIT, &eth->state))
-@@ -2539,6 +2542,10 @@ static int mtk_hw_init(struct mtk_eth *e
-       if (ret)
-               goto err_disable_pm;
-+      if (eth->ethsys)
-+              regmap_update_bits(eth->ethsys, ETHSYS_DMA_AG_MAP, dma_mask,
-+                                 of_dma_is_coherent(eth->dma_dev->of_node) * dma_mask);
-+
-       if (MTK_HAS_CAPS(eth->soc->caps, MTK_SOC_MT7628)) {
-               ret = device_reset(eth->dev);
-               if (ret) {
-@@ -3085,6 +3092,35 @@ free_netdev:
-       return err;
- }
-+void mtk_eth_set_dma_device(struct mtk_eth *eth, struct device *dma_dev)
-+{
-+      struct net_device *dev, *tmp;
-+      LIST_HEAD(dev_list);
-+      int i;
-+
-+      rtnl_lock();
-+
-+      for (i = 0; i < MTK_MAC_COUNT; i++) {
-+              dev = eth->netdev[i];
-+
-+              if (!dev || !(dev->flags & IFF_UP))
-+                      continue;
-+
-+              list_add_tail(&dev->close_list, &dev_list);
-+      }
-+
-+      dev_close_many(&dev_list, false);
-+
-+      eth->dma_dev = dma_dev;
-+
-+      list_for_each_entry_safe(dev, tmp, &dev_list, close_list) {
-+              list_del_init(&dev->close_list);
-+              dev_open(dev, NULL);
-+      }
-+
-+      rtnl_unlock();
-+}
-+
- static int mtk_probe(struct platform_device *pdev)
- {
-       struct device_node *mac_np;
-@@ -3098,6 +3134,7 @@ static int mtk_probe(struct platform_dev
-       eth->soc = of_device_get_match_data(&pdev->dev);
-       eth->dev = &pdev->dev;
-+      eth->dma_dev = &pdev->dev;
-       eth->base = devm_platform_ioremap_resource(pdev, 0);
-       if (IS_ERR(eth->base))
-               return PTR_ERR(eth->base);
-@@ -3146,6 +3183,16 @@ static int mtk_probe(struct platform_dev
-               }
-       }
-+      if (of_dma_is_coherent(pdev->dev.of_node)) {
-+              struct regmap *cci;
-+
-+              cci = syscon_regmap_lookup_by_phandle(pdev->dev.of_node,
-+                                                    "mediatek,cci-control");
-+              /* enable CPU/bus coherency */
-+              if (!IS_ERR(cci))
-+                      regmap_write(cci, 0, 3);
-+      }
-+
-       if (MTK_HAS_CAPS(eth->soc->caps, MTK_SGMII)) {
-               eth->sgmii = devm_kzalloc(eth->dev, sizeof(*eth->sgmii),
-                                         GFP_KERNEL);
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-@@ -463,6 +463,12 @@
- #define RSTCTRL_FE            BIT(6)
- #define RSTCTRL_PPE           BIT(31)
-+/* ethernet dma channel agent map */
-+#define ETHSYS_DMA_AG_MAP     0x408
-+#define ETHSYS_DMA_AG_MAP_PDMA        BIT(0)
-+#define ETHSYS_DMA_AG_MAP_QDMA        BIT(1)
-+#define ETHSYS_DMA_AG_MAP_PPE BIT(2)
-+
- /* SGMII subsystem config registers */
- /* Register to auto-negotiation restart */
- #define SGMSYS_PCS_CONTROL_1  0x0
-@@ -880,6 +886,7 @@ struct mtk_sgmii {
- /* struct mtk_eth -   This is the main datasructure for holding the state
-  *                    of the driver
-  * @dev:              The device pointer
-+ * @dev:              The device pointer used for dma mapping/alloc
-  * @base:             The mapped register i/o base
-  * @page_lock:                Make sure that register operations are atomic
-  * @tx_irq__lock:     Make sure that IRQ register operations are atomic
-@@ -923,6 +930,7 @@ struct mtk_sgmii {
- struct mtk_eth {
-       struct device                   *dev;
-+      struct device                   *dma_dev;
-       void __iomem                    *base;
-       spinlock_t                      page_lock;
-       spinlock_t                      tx_irq_lock;
-@@ -1021,6 +1029,7 @@ int mtk_gmac_rgmii_path_setup(struct mtk
- int mtk_eth_offload_init(struct mtk_eth *eth);
- int mtk_eth_setup_tc(struct net_device *dev, enum tc_setup_type type,
-                    void *type_data);
-+void mtk_eth_set_dma_device(struct mtk_eth *eth, struct device *dma_dev);
- #endif /* MTK_ETH_H */
diff --git a/target/linux/generic/backport-5.15/702-v5.19-02-net-ethernet-mtk_eth_soc-add-support-for-Wireless-Et.patch b/target/linux/generic/backport-5.15/702-v5.19-02-net-ethernet-mtk_eth_soc-add-support-for-Wireless-Et.patch
deleted file mode 100644 (file)
index 85dc9ad..0000000
+++ /dev/null
@@ -1,1679 +0,0 @@
-From: Felix Fietkau <[email protected]>
-Date: Sat, 5 Feb 2022 17:56:08 +0100
-Subject: [PATCH] net: ethernet: mtk_eth_soc: add support for Wireless
- Ethernet Dispatch (WED)
-
-The Wireless Ethernet Dispatch subsystem on the MT7622 SoC can be
-configured to intercept and handle access to the DMA queues and
-PCIe interrupts for a MT7615/MT7915 wireless card.
-It can manage the internal WDMA (Wireless DMA) controller, which allows
-ethernet packets to be passed from the packet switch engine (PSE) to the
-wireless card, bypassing the CPU entirely.
-This can be used to implement hardware flow offloading from ethernet to
-WLAN.
-
-Signed-off-by: Felix Fietkau <[email protected]>
----
- create mode 100644 drivers/net/ethernet/mediatek/mtk_wed.c
- create mode 100644 drivers/net/ethernet/mediatek/mtk_wed.h
- create mode 100644 drivers/net/ethernet/mediatek/mtk_wed_debugfs.c
- create mode 100644 drivers/net/ethernet/mediatek/mtk_wed_ops.c
- create mode 100644 drivers/net/ethernet/mediatek/mtk_wed_regs.h
- create mode 100644 include/linux/soc/mediatek/mtk_wed.h
-
---- a/drivers/net/ethernet/mediatek/Kconfig
-+++ b/drivers/net/ethernet/mediatek/Kconfig
-@@ -7,6 +7,10 @@ config NET_VENDOR_MEDIATEK
- if NET_VENDOR_MEDIATEK
-+config NET_MEDIATEK_SOC_WED
-+      depends on ARCH_MEDIATEK || COMPILE_TEST
-+      def_bool NET_MEDIATEK_SOC != n
-+
- config NET_MEDIATEK_SOC
-       tristate "MediaTek SoC Gigabit Ethernet support"
-       depends on NET_DSA || !NET_DSA
---- a/drivers/net/ethernet/mediatek/Makefile
-+++ b/drivers/net/ethernet/mediatek/Makefile
-@@ -5,4 +5,9 @@
- obj-$(CONFIG_NET_MEDIATEK_SOC) += mtk_eth.o
- mtk_eth-y := mtk_eth_soc.o mtk_sgmii.o mtk_eth_path.o mtk_ppe.o mtk_ppe_debugfs.o mtk_ppe_offload.o
-+mtk_eth-$(CONFIG_NET_MEDIATEK_SOC_WED) += mtk_wed.o
-+ifdef CONFIG_DEBUG_FS
-+mtk_eth-$(CONFIG_NET_MEDIATEK_SOC_WED) += mtk_wed_debugfs.o
-+endif
-+obj-$(CONFIG_NET_MEDIATEK_SOC_WED) += mtk_wed_ops.o
- obj-$(CONFIG_NET_MEDIATEK_STAR_EMAC) += mtk_star_emac.o
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-@@ -24,6 +24,7 @@
- #include <net/dsa.h>
- #include "mtk_eth_soc.h"
-+#include "mtk_wed.h"
- static int mtk_msg_level = -1;
- module_param_named(msg_level, mtk_msg_level, int, 0);
-@@ -3215,6 +3216,22 @@ static int mtk_probe(struct platform_dev
-               }
-       }
-+      for (i = 0;; i++) {
-+              struct device_node *np = of_parse_phandle(pdev->dev.of_node,
-+                                                        "mediatek,wed", i);
-+              static const u32 wdma_regs[] = {
-+                      MTK_WDMA0_BASE,
-+                      MTK_WDMA1_BASE
-+              };
-+              void __iomem *wdma;
-+
-+              if (!np || i >= ARRAY_SIZE(wdma_regs))
-+                      break;
-+
-+              wdma = eth->base + wdma_regs[i];
-+              mtk_wed_add_hw(np, eth, wdma, i);
-+      }
-+
-       for (i = 0; i < 3; i++) {
-               if (MTK_HAS_CAPS(eth->soc->caps, MTK_SHARED_INT) && i > 0)
-                       eth->irq[i] = eth->irq[0];
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-@@ -295,6 +295,9 @@
- #define MTK_GDM1_TX_GPCNT     0x2438
- #define MTK_STAT_OFFSET               0x40
-+#define MTK_WDMA0_BASE                0x2800
-+#define MTK_WDMA1_BASE                0x2c00
-+
- /* QDMA descriptor txd4 */
- #define TX_DMA_CHKSUM         (0x7 << 29)
- #define TX_DMA_TSO            BIT(28)
---- /dev/null
-+++ b/drivers/net/ethernet/mediatek/mtk_wed.c
-@@ -0,0 +1,875 @@
-+// SPDX-License-Identifier: GPL-2.0-only
-+/* Copyright (C) 2021 Felix Fietkau <[email protected]> */
-+
-+#include <linux/kernel.h>
-+#include <linux/slab.h>
-+#include <linux/module.h>
-+#include <linux/bitfield.h>
-+#include <linux/dma-mapping.h>
-+#include <linux/skbuff.h>
-+#include <linux/of_platform.h>
-+#include <linux/of_address.h>
-+#include <linux/mfd/syscon.h>
-+#include <linux/debugfs.h>
-+#include <linux/soc/mediatek/mtk_wed.h>
-+#include "mtk_eth_soc.h"
-+#include "mtk_wed_regs.h"
-+#include "mtk_wed.h"
-+#include "mtk_ppe.h"
-+
-+#define MTK_PCIE_BASE(n)              (0x1a143000 + (n) * 0x2000)
-+
-+#define MTK_WED_PKT_SIZE              1900
-+#define MTK_WED_BUF_SIZE              2048
-+#define MTK_WED_BUF_PER_PAGE          (PAGE_SIZE / 2048)
-+
-+#define MTK_WED_TX_RING_SIZE          2048
-+#define MTK_WED_WDMA_RING_SIZE                1024
-+
-+static struct mtk_wed_hw *hw_list[2];
-+static DEFINE_MUTEX(hw_lock);
-+
-+static void
-+wed_m32(struct mtk_wed_device *dev, u32 reg, u32 mask, u32 val)
-+{
-+      regmap_update_bits(dev->hw->regs, reg, mask | val, val);
-+}
-+
-+static void
-+wed_set(struct mtk_wed_device *dev, u32 reg, u32 mask)
-+{
-+      return wed_m32(dev, reg, 0, mask);
-+}
-+
-+static void
-+wed_clr(struct mtk_wed_device *dev, u32 reg, u32 mask)
-+{
-+      return wed_m32(dev, reg, mask, 0);
-+}
-+
-+static void
-+wdma_m32(struct mtk_wed_device *dev, u32 reg, u32 mask, u32 val)
-+{
-+      wdma_w32(dev, reg, (wdma_r32(dev, reg) & ~mask) | val);
-+}
-+
-+static void
-+wdma_set(struct mtk_wed_device *dev, u32 reg, u32 mask)
-+{
-+      wdma_m32(dev, reg, 0, mask);
-+}
-+
-+static u32
-+mtk_wed_read_reset(struct mtk_wed_device *dev)
-+{
-+      return wed_r32(dev, MTK_WED_RESET);
-+}
-+
-+static void
-+mtk_wed_reset(struct mtk_wed_device *dev, u32 mask)
-+{
-+      u32 status;
-+
-+      wed_w32(dev, MTK_WED_RESET, mask);
-+      if (readx_poll_timeout(mtk_wed_read_reset, dev, status,
-+                             !(status & mask), 0, 1000))
-+              WARN_ON_ONCE(1);
-+}
-+
-+static struct mtk_wed_hw *
-+mtk_wed_assign(struct mtk_wed_device *dev)
-+{
-+      struct mtk_wed_hw *hw;
-+
-+      hw = hw_list[pci_domain_nr(dev->wlan.pci_dev->bus)];
-+      if (!hw || hw->wed_dev)
-+              return NULL;
-+
-+      hw->wed_dev = dev;
-+      return hw;
-+}
-+
-+static int
-+mtk_wed_buffer_alloc(struct mtk_wed_device *dev)
-+{
-+      struct mtk_wdma_desc *desc;
-+      dma_addr_t desc_phys;
-+      void **page_list;
-+      int token = dev->wlan.token_start;
-+      int ring_size;
-+      int n_pages;
-+      int i, page_idx;
-+
-+      ring_size = dev->wlan.nbuf & ~(MTK_WED_BUF_PER_PAGE - 1);
-+      n_pages = ring_size / MTK_WED_BUF_PER_PAGE;
-+
-+      page_list = kcalloc(n_pages, sizeof(*page_list), GFP_KERNEL);
-+      if (!page_list)
-+              return -ENOMEM;
-+
-+      dev->buf_ring.size = ring_size;
-+      dev->buf_ring.pages = page_list;
-+
-+      desc = dma_alloc_coherent(dev->hw->dev, ring_size * sizeof(*desc),
-+                                &desc_phys, GFP_KERNEL);
-+      if (!desc)
-+              return -ENOMEM;
-+
-+      dev->buf_ring.desc = desc;
-+      dev->buf_ring.desc_phys = desc_phys;
-+
-+      for (i = 0, page_idx = 0; i < ring_size; i += MTK_WED_BUF_PER_PAGE) {
-+              dma_addr_t page_phys, buf_phys;
-+              struct page *page;
-+              void *buf;
-+              int s;
-+
-+              page = __dev_alloc_pages(GFP_KERNEL, 0);
-+              if (!page)
-+                      return -ENOMEM;
-+
-+              page_phys = dma_map_page(dev->hw->dev, page, 0, PAGE_SIZE,
-+                                       DMA_BIDIRECTIONAL);
-+              if (dma_mapping_error(dev->hw->dev, page_phys)) {
-+                      __free_page(page);
-+                      return -ENOMEM;
-+              }
-+
-+              page_list[page_idx++] = page;
-+              dma_sync_single_for_cpu(dev->hw->dev, page_phys, PAGE_SIZE,
-+                                      DMA_BIDIRECTIONAL);
-+
-+              buf = page_to_virt(page);
-+              buf_phys = page_phys;
-+
-+              for (s = 0; s < MTK_WED_BUF_PER_PAGE; s++) {
-+                      u32 txd_size;
-+
-+                      txd_size = dev->wlan.init_buf(buf, buf_phys, token++);
-+
-+                      desc->buf0 = buf_phys;
-+                      desc->buf1 = buf_phys + txd_size;
-+                      desc->ctrl = FIELD_PREP(MTK_WDMA_DESC_CTRL_LEN0,
-+                                              txd_size) |
-+                                   FIELD_PREP(MTK_WDMA_DESC_CTRL_LEN1,
-+                                              MTK_WED_BUF_SIZE - txd_size) |
-+                                   MTK_WDMA_DESC_CTRL_LAST_SEG1;
-+                      desc->info = 0;
-+                      desc++;
-+
-+                      buf += MTK_WED_BUF_SIZE;
-+                      buf_phys += MTK_WED_BUF_SIZE;
-+              }
-+
-+              dma_sync_single_for_device(dev->hw->dev, page_phys, PAGE_SIZE,
-+                                         DMA_BIDIRECTIONAL);
-+      }
-+
-+      return 0;
-+}
-+
-+static void
-+mtk_wed_free_buffer(struct mtk_wed_device *dev)
-+{
-+      struct mtk_wdma_desc *desc = dev->buf_ring.desc;
-+      void **page_list = dev->buf_ring.pages;
-+      int page_idx;
-+      int i;
-+
-+      if (!page_list)
-+              return;
-+
-+      if (!desc)
-+              goto free_pagelist;
-+
-+      for (i = 0, page_idx = 0; i < dev->buf_ring.size; i += MTK_WED_BUF_PER_PAGE) {
-+              void *page = page_list[page_idx++];
-+
-+              if (!page)
-+                      break;
-+
-+              dma_unmap_page(dev->hw->dev, desc[i].buf0,
-+                             PAGE_SIZE, DMA_BIDIRECTIONAL);
-+              __free_page(page);
-+      }
-+
-+      dma_free_coherent(dev->hw->dev, dev->buf_ring.size * sizeof(*desc),
-+                        desc, dev->buf_ring.desc_phys);
-+
-+free_pagelist:
-+      kfree(page_list);
-+}
-+
-+static void
-+mtk_wed_free_ring(struct mtk_wed_device *dev, struct mtk_wed_ring *ring)
-+{
-+      if (!ring->desc)
-+              return;
-+
-+      dma_free_coherent(dev->hw->dev, ring->size * sizeof(*ring->desc),
-+                        ring->desc, ring->desc_phys);
-+}
-+
-+static void
-+mtk_wed_free_tx_rings(struct mtk_wed_device *dev)
-+{
-+      int i;
-+
-+      for (i = 0; i < ARRAY_SIZE(dev->tx_ring); i++)
-+              mtk_wed_free_ring(dev, &dev->tx_ring[i]);
-+      for (i = 0; i < ARRAY_SIZE(dev->tx_wdma); i++)
-+              mtk_wed_free_ring(dev, &dev->tx_wdma[i]);
-+}
-+
-+static void
-+mtk_wed_set_ext_int(struct mtk_wed_device *dev, bool en)
-+{
-+      u32 mask = MTK_WED_EXT_INT_STATUS_ERROR_MASK;
-+
-+      if (!dev->hw->num_flows)
-+              mask &= ~MTK_WED_EXT_INT_STATUS_TKID_WO_PYLD;
-+
-+      wed_w32(dev, MTK_WED_EXT_INT_MASK, en ? mask : 0);
-+      wed_r32(dev, MTK_WED_EXT_INT_MASK);
-+}
-+
-+static void
-+mtk_wed_stop(struct mtk_wed_device *dev)
-+{
-+      regmap_write(dev->hw->mirror, dev->hw->index * 4, 0);
-+      mtk_wed_set_ext_int(dev, false);
-+
-+      wed_clr(dev, MTK_WED_CTRL,
-+              MTK_WED_CTRL_WDMA_INT_AGENT_EN |
-+              MTK_WED_CTRL_WPDMA_INT_AGENT_EN |
-+              MTK_WED_CTRL_WED_TX_BM_EN |
-+              MTK_WED_CTRL_WED_TX_FREE_AGENT_EN);
-+      wed_w32(dev, MTK_WED_WPDMA_INT_TRIGGER, 0);
-+      wed_w32(dev, MTK_WED_WDMA_INT_TRIGGER, 0);
-+      wdma_w32(dev, MTK_WDMA_INT_MASK, 0);
-+      wdma_w32(dev, MTK_WDMA_INT_GRP2, 0);
-+      wed_w32(dev, MTK_WED_WPDMA_INT_MASK, 0);
-+
-+      wed_clr(dev, MTK_WED_GLO_CFG,
-+              MTK_WED_GLO_CFG_TX_DMA_EN |
-+              MTK_WED_GLO_CFG_RX_DMA_EN);
-+      wed_clr(dev, MTK_WED_WPDMA_GLO_CFG,
-+              MTK_WED_WPDMA_GLO_CFG_TX_DRV_EN |
-+              MTK_WED_WPDMA_GLO_CFG_RX_DRV_EN);
-+      wed_clr(dev, MTK_WED_WDMA_GLO_CFG,
-+              MTK_WED_WDMA_GLO_CFG_RX_DRV_EN);
-+}
-+
-+static void
-+mtk_wed_detach(struct mtk_wed_device *dev)
-+{
-+      struct device_node *wlan_node = dev->wlan.pci_dev->dev.of_node;
-+      struct mtk_wed_hw *hw = dev->hw;
-+
-+      mutex_lock(&hw_lock);
-+
-+      mtk_wed_stop(dev);
-+
-+      wdma_w32(dev, MTK_WDMA_RESET_IDX, MTK_WDMA_RESET_IDX_RX);
-+      wdma_w32(dev, MTK_WDMA_RESET_IDX, 0);
-+
-+      mtk_wed_reset(dev, MTK_WED_RESET_WED);
-+
-+      mtk_wed_free_buffer(dev);
-+      mtk_wed_free_tx_rings(dev);
-+
-+      if (of_dma_is_coherent(wlan_node))
-+              regmap_update_bits(hw->hifsys, HIFSYS_DMA_AG_MAP,
-+                                 BIT(hw->index), BIT(hw->index));
-+
-+      if (!hw_list[!hw->index]->wed_dev &&
-+          hw->eth->dma_dev != hw->eth->dev)
-+              mtk_eth_set_dma_device(hw->eth, hw->eth->dev);
-+
-+      memset(dev, 0, sizeof(*dev));
-+      module_put(THIS_MODULE);
-+
-+      hw->wed_dev = NULL;
-+      mutex_unlock(&hw_lock);
-+}
-+
-+static void
-+mtk_wed_hw_init_early(struct mtk_wed_device *dev)
-+{
-+      u32 mask, set;
-+      u32 offset;
-+
-+      mtk_wed_stop(dev);
-+      mtk_wed_reset(dev, MTK_WED_RESET_WED);
-+
-+      mask = MTK_WED_WDMA_GLO_CFG_BT_SIZE |
-+             MTK_WED_WDMA_GLO_CFG_DYNAMIC_DMAD_RECYCLE |
-+             MTK_WED_WDMA_GLO_CFG_RX_DIS_FSM_AUTO_IDLE;
-+      set = FIELD_PREP(MTK_WED_WDMA_GLO_CFG_BT_SIZE, 2) |
-+            MTK_WED_WDMA_GLO_CFG_DYNAMIC_SKIP_DMAD_PREP |
-+            MTK_WED_WDMA_GLO_CFG_IDLE_DMAD_SUPPLY;
-+      wed_m32(dev, MTK_WED_WDMA_GLO_CFG, mask, set);
-+
-+      wdma_set(dev, MTK_WDMA_GLO_CFG, MTK_WDMA_GLO_CFG_RX_INFO_PRERES);
-+
-+      offset = dev->hw->index ? 0x04000400 : 0;
-+      wed_w32(dev, MTK_WED_WDMA_OFFSET0, 0x2a042a20 + offset);
-+      wed_w32(dev, MTK_WED_WDMA_OFFSET1, 0x29002800 + offset);
-+
-+      wed_w32(dev, MTK_WED_PCIE_CFG_BASE, MTK_PCIE_BASE(dev->hw->index));
-+      wed_w32(dev, MTK_WED_WPDMA_CFG_BASE, dev->wlan.wpdma_phys);
-+}
-+
-+static void
-+mtk_wed_hw_init(struct mtk_wed_device *dev)
-+{
-+      if (dev->init_done)
-+              return;
-+
-+      dev->init_done = true;
-+      mtk_wed_set_ext_int(dev, false);
-+      wed_w32(dev, MTK_WED_TX_BM_CTRL,
-+              MTK_WED_TX_BM_CTRL_PAUSE |
-+              FIELD_PREP(MTK_WED_TX_BM_CTRL_VLD_GRP_NUM,
-+                         dev->buf_ring.size / 128) |
-+              FIELD_PREP(MTK_WED_TX_BM_CTRL_RSV_GRP_NUM,
-+                         MTK_WED_TX_RING_SIZE / 256));
-+
-+      wed_w32(dev, MTK_WED_TX_BM_BASE, dev->buf_ring.desc_phys);
-+
-+      wed_w32(dev, MTK_WED_TX_BM_TKID,
-+              FIELD_PREP(MTK_WED_TX_BM_TKID_START,
-+                         dev->wlan.token_start) |
-+              FIELD_PREP(MTK_WED_TX_BM_TKID_END,
-+                         dev->wlan.token_start + dev->wlan.nbuf - 1));
-+
-+      wed_w32(dev, MTK_WED_TX_BM_BUF_LEN, MTK_WED_PKT_SIZE);
-+
-+      wed_w32(dev, MTK_WED_TX_BM_DYN_THR,
-+              FIELD_PREP(MTK_WED_TX_BM_DYN_THR_LO, 1) |
-+              MTK_WED_TX_BM_DYN_THR_HI);
-+
-+      mtk_wed_reset(dev, MTK_WED_RESET_TX_BM);
-+
-+      wed_set(dev, MTK_WED_CTRL,
-+              MTK_WED_CTRL_WED_TX_BM_EN |
-+              MTK_WED_CTRL_WED_TX_FREE_AGENT_EN);
-+
-+      wed_clr(dev, MTK_WED_TX_BM_CTRL, MTK_WED_TX_BM_CTRL_PAUSE);
-+}
-+
-+static void
-+mtk_wed_ring_reset(struct mtk_wdma_desc *desc, int size)
-+{
-+      int i;
-+
-+      for (i = 0; i < size; i++) {
-+              desc[i].buf0 = 0;
-+              desc[i].ctrl = cpu_to_le32(MTK_WDMA_DESC_CTRL_DMA_DONE);
-+              desc[i].buf1 = 0;
-+              desc[i].info = 0;
-+      }
-+}
-+
-+static u32
-+mtk_wed_check_busy(struct mtk_wed_device *dev)
-+{
-+      if (wed_r32(dev, MTK_WED_GLO_CFG) & MTK_WED_GLO_CFG_TX_DMA_BUSY)
-+              return true;
-+
-+      if (wed_r32(dev, MTK_WED_WPDMA_GLO_CFG) &
-+          MTK_WED_WPDMA_GLO_CFG_TX_DRV_BUSY)
-+              return true;
-+
-+      if (wed_r32(dev, MTK_WED_CTRL) & MTK_WED_CTRL_WDMA_INT_AGENT_BUSY)
-+              return true;
-+
-+      if (wed_r32(dev, MTK_WED_WDMA_GLO_CFG) &
-+          MTK_WED_WDMA_GLO_CFG_RX_DRV_BUSY)
-+              return true;
-+
-+      if (wdma_r32(dev, MTK_WDMA_GLO_CFG) &
-+          MTK_WED_WDMA_GLO_CFG_RX_DRV_BUSY)
-+              return true;
-+
-+      if (wed_r32(dev, MTK_WED_CTRL) &
-+          (MTK_WED_CTRL_WED_TX_BM_BUSY | MTK_WED_CTRL_WED_TX_FREE_AGENT_BUSY))
-+              return true;
-+
-+      return false;
-+}
-+
-+static int
-+mtk_wed_poll_busy(struct mtk_wed_device *dev)
-+{
-+      int sleep = 15000;
-+      int timeout = 100 * sleep;
-+      u32 val;
-+
-+      return read_poll_timeout(mtk_wed_check_busy, val, !val, sleep,
-+                               timeout, false, dev);
-+}
-+
-+static void
-+mtk_wed_reset_dma(struct mtk_wed_device *dev)
-+{
-+      bool busy = false;
-+      u32 val;
-+      int i;
-+
-+      for (i = 0; i < ARRAY_SIZE(dev->tx_ring); i++) {
-+              struct mtk_wdma_desc *desc = dev->tx_ring[i].desc;
-+
-+              if (!desc)
-+                      continue;
-+
-+              mtk_wed_ring_reset(desc, MTK_WED_TX_RING_SIZE);
-+      }
-+
-+      if (mtk_wed_poll_busy(dev))
-+              busy = mtk_wed_check_busy(dev);
-+
-+      if (busy) {
-+              mtk_wed_reset(dev, MTK_WED_RESET_WED_TX_DMA);
-+      } else {
-+              wed_w32(dev, MTK_WED_RESET_IDX,
-+                      MTK_WED_RESET_IDX_TX |
-+                      MTK_WED_RESET_IDX_RX);
-+              wed_w32(dev, MTK_WED_RESET_IDX, 0);
-+      }
-+
-+      wdma_w32(dev, MTK_WDMA_RESET_IDX, MTK_WDMA_RESET_IDX_RX);
-+      wdma_w32(dev, MTK_WDMA_RESET_IDX, 0);
-+
-+      if (busy) {
-+              mtk_wed_reset(dev, MTK_WED_RESET_WDMA_INT_AGENT);
-+              mtk_wed_reset(dev, MTK_WED_RESET_WDMA_RX_DRV);
-+      } else {
-+              wed_w32(dev, MTK_WED_WDMA_RESET_IDX,
-+                      MTK_WED_WDMA_RESET_IDX_RX | MTK_WED_WDMA_RESET_IDX_DRV);
-+              wed_w32(dev, MTK_WED_WDMA_RESET_IDX, 0);
-+
-+              wed_set(dev, MTK_WED_WDMA_GLO_CFG,
-+                      MTK_WED_WDMA_GLO_CFG_RST_INIT_COMPLETE);
-+
-+              wed_clr(dev, MTK_WED_WDMA_GLO_CFG,
-+                      MTK_WED_WDMA_GLO_CFG_RST_INIT_COMPLETE);
-+      }
-+
-+      for (i = 0; i < 100; i++) {
-+              val = wed_r32(dev, MTK_WED_TX_BM_INTF);
-+              if (FIELD_GET(MTK_WED_TX_BM_INTF_TKFIFO_FDEP, val) == 0x40)
-+                      break;
-+      }
-+
-+      mtk_wed_reset(dev, MTK_WED_RESET_TX_FREE_AGENT);
-+      mtk_wed_reset(dev, MTK_WED_RESET_TX_BM);
-+
-+      if (busy) {
-+              mtk_wed_reset(dev, MTK_WED_RESET_WPDMA_INT_AGENT);
-+              mtk_wed_reset(dev, MTK_WED_RESET_WPDMA_TX_DRV);
-+              mtk_wed_reset(dev, MTK_WED_RESET_WPDMA_RX_DRV);
-+      } else {
-+              wed_w32(dev, MTK_WED_WPDMA_RESET_IDX,
-+                      MTK_WED_WPDMA_RESET_IDX_TX |
-+                      MTK_WED_WPDMA_RESET_IDX_RX);
-+              wed_w32(dev, MTK_WED_WPDMA_RESET_IDX, 0);
-+      }
-+
-+}
-+
-+static int
-+mtk_wed_ring_alloc(struct mtk_wed_device *dev, struct mtk_wed_ring *ring,
-+                 int size)
-+{
-+      ring->desc = dma_alloc_coherent(dev->hw->dev,
-+                                      size * sizeof(*ring->desc),
-+                                      &ring->desc_phys, GFP_KERNEL);
-+      if (!ring->desc)
-+              return -ENOMEM;
-+
-+      ring->size = size;
-+      mtk_wed_ring_reset(ring->desc, size);
-+
-+      return 0;
-+}
-+
-+static int
-+mtk_wed_wdma_ring_setup(struct mtk_wed_device *dev, int idx, int size)
-+{
-+      struct mtk_wed_ring *wdma = &dev->tx_wdma[idx];
-+
-+      if (mtk_wed_ring_alloc(dev, wdma, MTK_WED_WDMA_RING_SIZE))
-+              return -ENOMEM;
-+
-+      wdma_w32(dev, MTK_WDMA_RING_RX(idx) + MTK_WED_RING_OFS_BASE,
-+               wdma->desc_phys);
-+      wdma_w32(dev, MTK_WDMA_RING_RX(idx) + MTK_WED_RING_OFS_COUNT,
-+               size);
-+      wdma_w32(dev, MTK_WDMA_RING_RX(idx) + MTK_WED_RING_OFS_CPU_IDX, 0);
-+
-+      wed_w32(dev, MTK_WED_WDMA_RING_RX(idx) + MTK_WED_RING_OFS_BASE,
-+              wdma->desc_phys);
-+      wed_w32(dev, MTK_WED_WDMA_RING_RX(idx) + MTK_WED_RING_OFS_COUNT,
-+              size);
-+
-+      return 0;
-+}
-+
-+static void
-+mtk_wed_start(struct mtk_wed_device *dev, u32 irq_mask)
-+{
-+      u32 wdma_mask;
-+      u32 val;
-+      int i;
-+
-+      for (i = 0; i < ARRAY_SIZE(dev->tx_wdma); i++)
-+              if (!dev->tx_wdma[i].desc)
-+                      mtk_wed_wdma_ring_setup(dev, i, 16);
-+
-+      wdma_mask = FIELD_PREP(MTK_WDMA_INT_MASK_RX_DONE, GENMASK(1, 0));
-+
-+      mtk_wed_hw_init(dev);
-+
-+      wed_set(dev, MTK_WED_CTRL,
-+              MTK_WED_CTRL_WDMA_INT_AGENT_EN |
-+              MTK_WED_CTRL_WPDMA_INT_AGENT_EN |
-+              MTK_WED_CTRL_WED_TX_BM_EN |
-+              MTK_WED_CTRL_WED_TX_FREE_AGENT_EN);
-+
-+      wed_w32(dev, MTK_WED_PCIE_INT_TRIGGER, MTK_WED_PCIE_INT_TRIGGER_STATUS);
-+
-+      wed_w32(dev, MTK_WED_WPDMA_INT_TRIGGER,
-+              MTK_WED_WPDMA_INT_TRIGGER_RX_DONE |
-+              MTK_WED_WPDMA_INT_TRIGGER_TX_DONE);
-+
-+      wed_set(dev, MTK_WED_WPDMA_INT_CTRL,
-+              MTK_WED_WPDMA_INT_CTRL_SUBRT_ADV);
-+
-+      wed_w32(dev, MTK_WED_WDMA_INT_TRIGGER, wdma_mask);
-+      wed_clr(dev, MTK_WED_WDMA_INT_CTRL, wdma_mask);
-+
-+      wdma_w32(dev, MTK_WDMA_INT_MASK, wdma_mask);
-+      wdma_w32(dev, MTK_WDMA_INT_GRP2, wdma_mask);
-+
-+      wed_w32(dev, MTK_WED_WPDMA_INT_MASK, irq_mask);
-+      wed_w32(dev, MTK_WED_INT_MASK, irq_mask);
-+
-+      wed_set(dev, MTK_WED_GLO_CFG,
-+              MTK_WED_GLO_CFG_TX_DMA_EN |
-+              MTK_WED_GLO_CFG_RX_DMA_EN);
-+      wed_set(dev, MTK_WED_WPDMA_GLO_CFG,
-+              MTK_WED_WPDMA_GLO_CFG_TX_DRV_EN |
-+              MTK_WED_WPDMA_GLO_CFG_RX_DRV_EN);
-+      wed_set(dev, MTK_WED_WDMA_GLO_CFG,
-+              MTK_WED_WDMA_GLO_CFG_RX_DRV_EN);
-+
-+      mtk_wed_set_ext_int(dev, true);
-+      val = dev->wlan.wpdma_phys |
-+            MTK_PCIE_MIRROR_MAP_EN |
-+            FIELD_PREP(MTK_PCIE_MIRROR_MAP_WED_ID, dev->hw->index);
-+
-+      if (dev->hw->index)
-+              val |= BIT(1);
-+      val |= BIT(0);
-+      regmap_write(dev->hw->mirror, dev->hw->index * 4, val);
-+
-+      dev->running = true;
-+}
-+
-+static int
-+mtk_wed_attach(struct mtk_wed_device *dev)
-+      __releases(RCU)
-+{
-+      struct mtk_wed_hw *hw;
-+      int ret = 0;
-+
-+      RCU_LOCKDEP_WARN(!rcu_read_lock_held(),
-+                       "mtk_wed_attach without holding the RCU read lock");
-+
-+      if (pci_domain_nr(dev->wlan.pci_dev->bus) > 1 ||
-+          !try_module_get(THIS_MODULE))
-+              ret = -ENODEV;
-+
-+      rcu_read_unlock();
-+
-+      if (ret)
-+              return ret;
-+
-+      mutex_lock(&hw_lock);
-+
-+      hw = mtk_wed_assign(dev);
-+      if (!hw) {
-+              module_put(THIS_MODULE);
-+              ret = -ENODEV;
-+              goto out;
-+      }
-+
-+      dev_info(&dev->wlan.pci_dev->dev, "attaching wed device %d\n", hw->index);
-+
-+      dev->hw = hw;
-+      dev->dev = hw->dev;
-+      dev->irq = hw->irq;
-+      dev->wdma_idx = hw->index;
-+
-+      if (hw->eth->dma_dev == hw->eth->dev &&
-+          of_dma_is_coherent(hw->eth->dev->of_node))
-+              mtk_eth_set_dma_device(hw->eth, hw->dev);
-+
-+      ret = mtk_wed_buffer_alloc(dev);
-+      if (ret) {
-+              mtk_wed_detach(dev);
-+              goto out;
-+      }
-+
-+      mtk_wed_hw_init_early(dev);
-+      regmap_update_bits(hw->hifsys, HIFSYS_DMA_AG_MAP, BIT(hw->index), 0);
-+
-+out:
-+      mutex_unlock(&hw_lock);
-+
-+      return ret;
-+}
-+
-+static int
-+mtk_wed_tx_ring_setup(struct mtk_wed_device *dev, int idx, void __iomem *regs)
-+{
-+      struct mtk_wed_ring *ring = &dev->tx_ring[idx];
-+
-+      /*
-+       * Tx ring redirection:
-+       * Instead of configuring the WLAN PDMA TX ring directly, the WLAN
-+       * driver allocated DMA ring gets configured into WED MTK_WED_RING_TX(n)
-+       * registers.
-+       *
-+       * WED driver posts its own DMA ring as WLAN PDMA TX and configures it
-+       * into MTK_WED_WPDMA_RING_TX(n) registers.
-+       * It gets filled with packets picked up from WED TX ring and from
-+       * WDMA RX.
-+       */
-+
-+      BUG_ON(idx > ARRAY_SIZE(dev->tx_ring));
-+
-+      if (mtk_wed_ring_alloc(dev, ring, MTK_WED_TX_RING_SIZE))
-+              return -ENOMEM;
-+
-+      if (mtk_wed_wdma_ring_setup(dev, idx, MTK_WED_WDMA_RING_SIZE))
-+              return -ENOMEM;
-+
-+      ring->reg_base = MTK_WED_RING_TX(idx);
-+      ring->wpdma = regs;
-+
-+      /* WED -> WPDMA */
-+      wpdma_tx_w32(dev, idx, MTK_WED_RING_OFS_BASE, ring->desc_phys);
-+      wpdma_tx_w32(dev, idx, MTK_WED_RING_OFS_COUNT, MTK_WED_TX_RING_SIZE);
-+      wpdma_tx_w32(dev, idx, MTK_WED_RING_OFS_CPU_IDX, 0);
-+
-+      wed_w32(dev, MTK_WED_WPDMA_RING_TX(idx) + MTK_WED_RING_OFS_BASE,
-+              ring->desc_phys);
-+      wed_w32(dev, MTK_WED_WPDMA_RING_TX(idx) + MTK_WED_RING_OFS_COUNT,
-+              MTK_WED_TX_RING_SIZE);
-+      wed_w32(dev, MTK_WED_WPDMA_RING_TX(idx) + MTK_WED_RING_OFS_CPU_IDX, 0);
-+
-+      return 0;
-+}
-+
-+static int
-+mtk_wed_txfree_ring_setup(struct mtk_wed_device *dev, void __iomem *regs)
-+{
-+      struct mtk_wed_ring *ring = &dev->txfree_ring;
-+      int i;
-+
-+      /*
-+       * For txfree event handling, the same DMA ring is shared between WED
-+       * and WLAN. The WLAN driver accesses the ring index registers through
-+       * WED
-+       */
-+      ring->reg_base = MTK_WED_RING_RX(1);
-+      ring->wpdma = regs;
-+
-+      for (i = 0; i < 12; i += 4) {
-+              u32 val = readl(regs + i);
-+
-+              wed_w32(dev, MTK_WED_RING_RX(1) + i, val);
-+              wed_w32(dev, MTK_WED_WPDMA_RING_RX(1) + i, val);
-+      }
-+
-+      return 0;
-+}
-+
-+static u32
-+mtk_wed_irq_get(struct mtk_wed_device *dev, u32 mask)
-+{
-+      u32 val;
-+
-+      val = wed_r32(dev, MTK_WED_EXT_INT_STATUS);
-+      wed_w32(dev, MTK_WED_EXT_INT_STATUS, val);
-+      val &= MTK_WED_EXT_INT_STATUS_ERROR_MASK;
-+      if (!dev->hw->num_flows)
-+              val &= ~MTK_WED_EXT_INT_STATUS_TKID_WO_PYLD;
-+      if (val && net_ratelimit())
-+              pr_err("mtk_wed%d: error status=%08x\n", dev->hw->index, val);
-+
-+      val = wed_r32(dev, MTK_WED_INT_STATUS);
-+      val &= mask;
-+      wed_w32(dev, MTK_WED_INT_STATUS, val); /* ACK */
-+
-+      return val;
-+}
-+
-+static void
-+mtk_wed_irq_set_mask(struct mtk_wed_device *dev, u32 mask)
-+{
-+      if (!dev->running)
-+              return;
-+
-+      mtk_wed_set_ext_int(dev, !!mask);
-+      wed_w32(dev, MTK_WED_INT_MASK, mask);
-+}
-+
-+int mtk_wed_flow_add(int index)
-+{
-+      struct mtk_wed_hw *hw = hw_list[index];
-+      int ret;
-+
-+      if (!hw || !hw->wed_dev)
-+              return -ENODEV;
-+
-+      if (hw->num_flows) {
-+              hw->num_flows++;
-+              return 0;
-+      }
-+
-+      mutex_lock(&hw_lock);
-+      if (!hw->wed_dev) {
-+              ret = -ENODEV;
-+              goto out;
-+      }
-+
-+      ret = hw->wed_dev->wlan.offload_enable(hw->wed_dev);
-+      if (!ret)
-+              hw->num_flows++;
-+      mtk_wed_set_ext_int(hw->wed_dev, true);
-+
-+out:
-+      mutex_unlock(&hw_lock);
-+
-+      return ret;
-+}
-+
-+void mtk_wed_flow_remove(int index)
-+{
-+      struct mtk_wed_hw *hw = hw_list[index];
-+
-+      if (!hw)
-+              return;
-+
-+      if (--hw->num_flows)
-+              return;
-+
-+      mutex_lock(&hw_lock);
-+      if (!hw->wed_dev)
-+              goto out;
-+
-+      hw->wed_dev->wlan.offload_disable(hw->wed_dev);
-+      mtk_wed_set_ext_int(hw->wed_dev, true);
-+
-+out:
-+      mutex_unlock(&hw_lock);
-+}
-+
-+void mtk_wed_add_hw(struct device_node *np, struct mtk_eth *eth,
-+                  void __iomem *wdma, int index)
-+{
-+      static const struct mtk_wed_ops wed_ops = {
-+              .attach = mtk_wed_attach,
-+              .tx_ring_setup = mtk_wed_tx_ring_setup,
-+              .txfree_ring_setup = mtk_wed_txfree_ring_setup,
-+              .start = mtk_wed_start,
-+              .stop = mtk_wed_stop,
-+              .reset_dma = mtk_wed_reset_dma,
-+              .reg_read = wed_r32,
-+              .reg_write = wed_w32,
-+              .irq_get = mtk_wed_irq_get,
-+              .irq_set_mask = mtk_wed_irq_set_mask,
-+              .detach = mtk_wed_detach,
-+      };
-+      struct device_node *eth_np = eth->dev->of_node;
-+      struct platform_device *pdev;
-+      struct mtk_wed_hw *hw;
-+      struct regmap *regs;
-+      int irq;
-+
-+      if (!np)
-+              return;
-+
-+      pdev = of_find_device_by_node(np);
-+      if (!pdev)
-+              return;
-+
-+      get_device(&pdev->dev);
-+      irq = platform_get_irq(pdev, 0);
-+      if (irq < 0)
-+              return;
-+
-+      regs = syscon_regmap_lookup_by_phandle(np, NULL);
-+      if (!regs)
-+              return;
-+
-+      rcu_assign_pointer(mtk_soc_wed_ops, &wed_ops);
-+
-+      mutex_lock(&hw_lock);
-+
-+      if (WARN_ON(hw_list[index]))
-+              goto unlock;
-+
-+      hw = kzalloc(sizeof(*hw), GFP_KERNEL);
-+      hw->node = np;
-+      hw->regs = regs;
-+      hw->eth = eth;
-+      hw->dev = &pdev->dev;
-+      hw->wdma = wdma;
-+      hw->index = index;
-+      hw->irq = irq;
-+      hw->mirror = syscon_regmap_lookup_by_phandle(eth_np,
-+                                                   "mediatek,pcie-mirror");
-+      hw->hifsys = syscon_regmap_lookup_by_phandle(eth_np,
-+                                                   "mediatek,hifsys");
-+      if (IS_ERR(hw->mirror) || IS_ERR(hw->hifsys)) {
-+              kfree(hw);
-+              goto unlock;
-+      }
-+
-+      if (!index) {
-+              regmap_write(hw->mirror, 0, 0);
-+              regmap_write(hw->mirror, 4, 0);
-+      }
-+      mtk_wed_hw_add_debugfs(hw);
-+
-+      hw_list[index] = hw;
-+
-+unlock:
-+      mutex_unlock(&hw_lock);
-+}
-+
-+void mtk_wed_exit(void)
-+{
-+      int i;
-+
-+      rcu_assign_pointer(mtk_soc_wed_ops, NULL);
-+
-+      synchronize_rcu();
-+
-+      for (i = 0; i < ARRAY_SIZE(hw_list); i++) {
-+              struct mtk_wed_hw *hw;
-+
-+              hw = hw_list[i];
-+              if (!hw)
-+                      continue;
-+
-+              hw_list[i] = NULL;
-+              debugfs_remove(hw->debugfs_dir);
-+              put_device(hw->dev);
-+              kfree(hw);
-+      }
-+}
---- /dev/null
-+++ b/drivers/net/ethernet/mediatek/mtk_wed.h
-@@ -0,0 +1,128 @@
-+// SPDX-License-Identifier: GPL-2.0-only
-+/* Copyright (C) 2021 Felix Fietkau <[email protected]> */
-+
-+#ifndef __MTK_WED_PRIV_H
-+#define __MTK_WED_PRIV_H
-+
-+#include <linux/soc/mediatek/mtk_wed.h>
-+#include <linux/debugfs.h>
-+#include <linux/regmap.h>
-+
-+struct mtk_eth;
-+
-+struct mtk_wed_hw {
-+      struct device_node *node;
-+      struct mtk_eth *eth;
-+      struct regmap *regs;
-+      struct regmap *hifsys;
-+      struct device *dev;
-+      void __iomem *wdma;
-+      struct regmap *mirror;
-+      struct dentry *debugfs_dir;
-+      struct mtk_wed_device *wed_dev;
-+      u32 debugfs_reg;
-+      u32 num_flows;
-+      char dirname[5];
-+      int irq;
-+      int index;
-+};
-+
-+
-+#ifdef CONFIG_NET_MEDIATEK_SOC_WED
-+static inline void
-+wed_w32(struct mtk_wed_device *dev, u32 reg, u32 val)
-+{
-+      regmap_write(dev->hw->regs, reg, val);
-+}
-+
-+static inline u32
-+wed_r32(struct mtk_wed_device *dev, u32 reg)
-+{
-+      unsigned int val;
-+
-+      regmap_read(dev->hw->regs, reg, &val);
-+
-+      return val;
-+}
-+
-+static inline void
-+wdma_w32(struct mtk_wed_device *dev, u32 reg, u32 val)
-+{
-+      writel(val, dev->hw->wdma + reg);
-+}
-+
-+static inline u32
-+wdma_r32(struct mtk_wed_device *dev, u32 reg)
-+{
-+      return readl(dev->hw->wdma + reg);
-+}
-+
-+static inline u32
-+wpdma_tx_r32(struct mtk_wed_device *dev, int ring, u32 reg)
-+{
-+      if (!dev->tx_ring[ring].wpdma)
-+              return 0;
-+
-+      return readl(dev->tx_ring[ring].wpdma + reg);
-+}
-+
-+static inline void
-+wpdma_tx_w32(struct mtk_wed_device *dev, int ring, u32 reg, u32 val)
-+{
-+      if (!dev->tx_ring[ring].wpdma)
-+              return;
-+
-+      writel(val, dev->tx_ring[ring].wpdma + reg);
-+}
-+
-+static inline u32
-+wpdma_txfree_r32(struct mtk_wed_device *dev, u32 reg)
-+{
-+      if (!dev->txfree_ring.wpdma)
-+              return 0;
-+
-+      return readl(dev->txfree_ring.wpdma + reg);
-+}
-+
-+static inline void
-+wpdma_txfree_w32(struct mtk_wed_device *dev, u32 reg, u32 val)
-+{
-+      if (!dev->txfree_ring.wpdma)
-+              return;
-+
-+      writel(val, dev->txfree_ring.wpdma + reg);
-+}
-+
-+void mtk_wed_add_hw(struct device_node *np, struct mtk_eth *eth,
-+                  void __iomem *wdma, int index);
-+void mtk_wed_exit(void);
-+int mtk_wed_flow_add(int index);
-+void mtk_wed_flow_remove(int index);
-+#else
-+static inline void
-+mtk_wed_add_hw(struct device_node *np, struct mtk_eth *eth,
-+             void __iomem *wdma, int index)
-+{
-+}
-+static inline void
-+mtk_wed_exit(void)
-+{
-+}
-+static inline int mtk_wed_flow_add(int index)
-+{
-+      return -EINVAL;
-+}
-+static inline void mtk_wed_flow_remove(int index)
-+{
-+}
-+#endif
-+
-+#ifdef CONFIG_DEBUG_FS
-+void mtk_wed_hw_add_debugfs(struct mtk_wed_hw *hw);
-+#else
-+static inline void mtk_wed_hw_add_debugfs(struct mtk_wed_hw *hw)
-+{
-+}
-+#endif
-+
-+#endif
---- /dev/null
-+++ b/drivers/net/ethernet/mediatek/mtk_wed_debugfs.c
-@@ -0,0 +1,175 @@
-+// SPDX-License-Identifier: GPL-2.0-only
-+/* Copyright (C) 2021 Felix Fietkau <[email protected]> */
-+
-+#include <linux/seq_file.h>
-+#include "mtk_wed.h"
-+#include "mtk_wed_regs.h"
-+
-+struct reg_dump {
-+      const char *name;
-+      u16 offset;
-+      u8 type;
-+      u8 base;
-+};
-+
-+enum {
-+      DUMP_TYPE_STRING,
-+      DUMP_TYPE_WED,
-+      DUMP_TYPE_WDMA,
-+      DUMP_TYPE_WPDMA_TX,
-+      DUMP_TYPE_WPDMA_TXFREE,
-+};
-+
-+#define DUMP_STR(_str) { _str, 0, DUMP_TYPE_STRING }
-+#define DUMP_REG(_reg, ...) { #_reg, MTK_##_reg, __VA_ARGS__ }
-+#define DUMP_RING(_prefix, _base, ...)                                \
-+      { _prefix " BASE", _base, __VA_ARGS__ },                \
-+      { _prefix " CNT",  _base + 0x4, __VA_ARGS__ },  \
-+      { _prefix " CIDX", _base + 0x8, __VA_ARGS__ },  \
-+      { _prefix " DIDX", _base + 0xc, __VA_ARGS__ }
-+
-+#define DUMP_WED(_reg) DUMP_REG(_reg, DUMP_TYPE_WED)
-+#define DUMP_WED_RING(_base) DUMP_RING(#_base, MTK_##_base, DUMP_TYPE_WED)
-+
-+#define DUMP_WDMA(_reg) DUMP_REG(_reg, DUMP_TYPE_WDMA)
-+#define DUMP_WDMA_RING(_base) DUMP_RING(#_base, MTK_##_base, DUMP_TYPE_WDMA)
-+
-+#define DUMP_WPDMA_TX_RING(_n) DUMP_RING("WPDMA_TX" #_n, 0, DUMP_TYPE_WPDMA_TX, _n)
-+#define DUMP_WPDMA_TXFREE_RING DUMP_RING("WPDMA_RX1", 0, DUMP_TYPE_WPDMA_TXFREE)
-+
-+static void
-+print_reg_val(struct seq_file *s, const char *name, u32 val)
-+{
-+      seq_printf(s, "%-32s %08x\n", name, val);
-+}
-+
-+static void
-+dump_wed_regs(struct seq_file *s, struct mtk_wed_device *dev,
-+            const struct reg_dump *regs, int n_regs)
-+{
-+      const struct reg_dump *cur;
-+      u32 val;
-+
-+      for (cur = regs; cur < &regs[n_regs]; cur++) {
-+              switch (cur->type) {
-+              case DUMP_TYPE_STRING:
-+                      seq_printf(s, "%s======== %s:\n",
-+                                 cur > regs ? "\n" : "",
-+                                 cur->name);
-+                      continue;
-+              case DUMP_TYPE_WED:
-+                      val = wed_r32(dev, cur->offset);
-+                      break;
-+              case DUMP_TYPE_WDMA:
-+                      val = wdma_r32(dev, cur->offset);
-+                      break;
-+              case DUMP_TYPE_WPDMA_TX:
-+                      val = wpdma_tx_r32(dev, cur->base, cur->offset);
-+                      break;
-+              case DUMP_TYPE_WPDMA_TXFREE:
-+                      val = wpdma_txfree_r32(dev, cur->offset);
-+                      break;
-+              }
-+              print_reg_val(s, cur->name, val);
-+      }
-+}
-+
-+
-+static int
-+wed_txinfo_show(struct seq_file *s, void *data)
-+{
-+      static const struct reg_dump regs[] = {
-+              DUMP_STR("WED TX"),
-+              DUMP_WED(WED_TX_MIB(0)),
-+              DUMP_WED_RING(WED_RING_TX(0)),
-+
-+              DUMP_WED(WED_TX_MIB(1)),
-+              DUMP_WED_RING(WED_RING_TX(1)),
-+
-+              DUMP_STR("WPDMA TX"),
-+              DUMP_WED(WED_WPDMA_TX_MIB(0)),
-+              DUMP_WED_RING(WED_WPDMA_RING_TX(0)),
-+              DUMP_WED(WED_WPDMA_TX_COHERENT_MIB(0)),
-+
-+              DUMP_WED(WED_WPDMA_TX_MIB(1)),
-+              DUMP_WED_RING(WED_WPDMA_RING_TX(1)),
-+              DUMP_WED(WED_WPDMA_TX_COHERENT_MIB(1)),
-+
-+              DUMP_STR("WPDMA TX"),
-+              DUMP_WPDMA_TX_RING(0),
-+              DUMP_WPDMA_TX_RING(1),
-+
-+              DUMP_STR("WED WDMA RX"),
-+              DUMP_WED(WED_WDMA_RX_MIB(0)),
-+              DUMP_WED_RING(WED_WDMA_RING_RX(0)),
-+              DUMP_WED(WED_WDMA_RX_THRES(0)),
-+              DUMP_WED(WED_WDMA_RX_RECYCLE_MIB(0)),
-+              DUMP_WED(WED_WDMA_RX_PROCESSED_MIB(0)),
-+
-+              DUMP_WED(WED_WDMA_RX_MIB(1)),
-+              DUMP_WED_RING(WED_WDMA_RING_RX(1)),
-+              DUMP_WED(WED_WDMA_RX_THRES(1)),
-+              DUMP_WED(WED_WDMA_RX_RECYCLE_MIB(1)),
-+              DUMP_WED(WED_WDMA_RX_PROCESSED_MIB(1)),
-+
-+              DUMP_STR("WDMA RX"),
-+              DUMP_WDMA(WDMA_GLO_CFG),
-+              DUMP_WDMA_RING(WDMA_RING_RX(0)),
-+              DUMP_WDMA_RING(WDMA_RING_RX(1)),
-+      };
-+      struct mtk_wed_hw *hw = s->private;
-+      struct mtk_wed_device *dev = hw->wed_dev;
-+
-+      if (!dev)
-+              return 0;
-+
-+      dump_wed_regs(s, dev, regs, ARRAY_SIZE(regs));
-+
-+      return 0;
-+}
-+DEFINE_SHOW_ATTRIBUTE(wed_txinfo);
-+
-+
-+static int
-+mtk_wed_reg_set(void *data, u64 val)
-+{
-+      struct mtk_wed_hw *hw = data;
-+
-+      regmap_write(hw->regs, hw->debugfs_reg, val);
-+
-+      return 0;
-+}
-+
-+static int
-+mtk_wed_reg_get(void *data, u64 *val)
-+{
-+      struct mtk_wed_hw *hw = data;
-+      unsigned int regval;
-+      int ret;
-+
-+      ret = regmap_read(hw->regs, hw->debugfs_reg, &regval);
-+      if (ret)
-+              return ret;
-+
-+      *val = regval;
-+
-+      return 0;
-+}
-+
-+DEFINE_DEBUGFS_ATTRIBUTE(fops_regval, mtk_wed_reg_get, mtk_wed_reg_set,
-+             "0x%08llx\n");
-+
-+void mtk_wed_hw_add_debugfs(struct mtk_wed_hw *hw)
-+{
-+      struct dentry *dir;
-+
-+      snprintf(hw->dirname, sizeof(hw->dirname), "wed%d", hw->index);
-+      dir = debugfs_create_dir(hw->dirname, NULL);
-+      if (!dir)
-+              return;
-+
-+      hw->debugfs_dir = dir;
-+      debugfs_create_u32("regidx", 0600, dir, &hw->debugfs_reg);
-+      debugfs_create_file_unsafe("regval", 0600, dir, hw, &fops_regval);
-+      debugfs_create_file_unsafe("txinfo", 0400, dir, hw, &wed_txinfo_fops);
-+}
---- /dev/null
-+++ b/drivers/net/ethernet/mediatek/mtk_wed_ops.c
-@@ -0,0 +1,8 @@
-+// SPDX-License-Identifier: GPL-2.0-only
-+/* Copyright (C) 2020 Felix Fietkau <[email protected]> */
-+
-+#include <linux/kernel.h>
-+#include <linux/soc/mediatek/mtk_wed.h>
-+
-+const struct mtk_wed_ops __rcu *mtk_soc_wed_ops;
-+EXPORT_SYMBOL_GPL(mtk_soc_wed_ops);
---- /dev/null
-+++ b/drivers/net/ethernet/mediatek/mtk_wed_regs.h
-@@ -0,0 +1,251 @@
-+// SPDX-License-Identifier: GPL-2.0-only
-+/* Copyright (C) 2020 Felix Fietkau <[email protected]> */
-+
-+#ifndef __MTK_WED_REGS_H
-+#define __MTK_WED_REGS_H
-+
-+#define MTK_WDMA_DESC_CTRL_LEN1                       GENMASK(14, 0)
-+#define MTK_WDMA_DESC_CTRL_LAST_SEG1          BIT(15)
-+#define MTK_WDMA_DESC_CTRL_BURST              BIT(16)
-+#define MTK_WDMA_DESC_CTRL_LEN0                       GENMASK(29, 16)
-+#define MTK_WDMA_DESC_CTRL_LAST_SEG0          BIT(30)
-+#define MTK_WDMA_DESC_CTRL_DMA_DONE           BIT(31)
-+
-+struct mtk_wdma_desc {
-+      __le32 buf0;
-+      __le32 ctrl;
-+      __le32 buf1;
-+      __le32 info;
-+} __packed __aligned(4);
-+
-+#define MTK_WED_RESET                                 0x008
-+#define MTK_WED_RESET_TX_BM                           BIT(0)
-+#define MTK_WED_RESET_TX_FREE_AGENT                   BIT(4)
-+#define MTK_WED_RESET_WPDMA_TX_DRV                    BIT(8)
-+#define MTK_WED_RESET_WPDMA_RX_DRV                    BIT(9)
-+#define MTK_WED_RESET_WPDMA_INT_AGENT                 BIT(11)
-+#define MTK_WED_RESET_WED_TX_DMA                      BIT(12)
-+#define MTK_WED_RESET_WDMA_RX_DRV                     BIT(17)
-+#define MTK_WED_RESET_WDMA_INT_AGENT                  BIT(19)
-+#define MTK_WED_RESET_WED                             BIT(31)
-+
-+#define MTK_WED_CTRL                                  0x00c
-+#define MTK_WED_CTRL_WPDMA_INT_AGENT_EN                       BIT(0)
-+#define MTK_WED_CTRL_WPDMA_INT_AGENT_BUSY             BIT(1)
-+#define MTK_WED_CTRL_WDMA_INT_AGENT_EN                        BIT(2)
-+#define MTK_WED_CTRL_WDMA_INT_AGENT_BUSY              BIT(3)
-+#define MTK_WED_CTRL_WED_TX_BM_EN                     BIT(8)
-+#define MTK_WED_CTRL_WED_TX_BM_BUSY                   BIT(9)
-+#define MTK_WED_CTRL_WED_TX_FREE_AGENT_EN             BIT(10)
-+#define MTK_WED_CTRL_WED_TX_FREE_AGENT_BUSY           BIT(11)
-+#define MTK_WED_CTRL_RESERVE_EN                               BIT(12)
-+#define MTK_WED_CTRL_RESERVE_BUSY                     BIT(13)
-+#define MTK_WED_CTRL_FINAL_DIDX_READ                  BIT(24)
-+#define MTK_WED_CTRL_MIB_READ_CLEAR                   BIT(28)
-+
-+#define MTK_WED_EXT_INT_STATUS                                0x020
-+#define MTK_WED_EXT_INT_STATUS_TF_LEN_ERR             BIT(0)
-+#define MTK_WED_EXT_INT_STATUS_TKID_WO_PYLD           BIT(1)
-+#define MTK_WED_EXT_INT_STATUS_TKID_TITO_INVALID      BIT(4)
-+#define MTK_WED_EXT_INT_STATUS_TX_FBUF_LO_TH          BIT(8)
-+#define MTK_WED_EXT_INT_STATUS_TX_FBUF_HI_TH          BIT(9)
-+#define MTK_WED_EXT_INT_STATUS_RX_FBUF_LO_TH          BIT(12)
-+#define MTK_WED_EXT_INT_STATUS_RX_FBUF_HI_TH          BIT(13)
-+#define MTK_WED_EXT_INT_STATUS_RX_DRV_R_RESP_ERR      BIT(16)
-+#define MTK_WED_EXT_INT_STATUS_RX_DRV_W_RESP_ERR      BIT(17)
-+#define MTK_WED_EXT_INT_STATUS_RX_DRV_COHERENT                BIT(18)
-+#define MTK_WED_EXT_INT_STATUS_RX_DRV_INIT_WDMA_EN    BIT(19)
-+#define MTK_WED_EXT_INT_STATUS_RX_DRV_BM_DMAD_COHERENT        BIT(20)
-+#define MTK_WED_EXT_INT_STATUS_TX_DRV_R_RESP_ERR      BIT(21)
-+#define MTK_WED_EXT_INT_STATUS_TX_DRV_W_RESP_ERR      BIT(22)
-+#define MTK_WED_EXT_INT_STATUS_RX_DRV_DMA_RECYCLE     BIT(24)
-+#define MTK_WED_EXT_INT_STATUS_ERROR_MASK             (MTK_WED_EXT_INT_STATUS_TF_LEN_ERR | \
-+                                                       MTK_WED_EXT_INT_STATUS_TKID_WO_PYLD | \
-+                                                       MTK_WED_EXT_INT_STATUS_TKID_TITO_INVALID | \
-+                                                       MTK_WED_EXT_INT_STATUS_RX_DRV_R_RESP_ERR | \
-+                                                       MTK_WED_EXT_INT_STATUS_RX_DRV_W_RESP_ERR | \
-+                                                       MTK_WED_EXT_INT_STATUS_RX_DRV_INIT_WDMA_EN | \
-+                                                       MTK_WED_EXT_INT_STATUS_TX_DRV_R_RESP_ERR | \
-+                                                       MTK_WED_EXT_INT_STATUS_TX_DRV_W_RESP_ERR)
-+
-+#define MTK_WED_EXT_INT_MASK                          0x028
-+
-+#define MTK_WED_STATUS                                        0x060
-+#define MTK_WED_STATUS_TX                             GENMASK(15, 8)
-+
-+#define MTK_WED_TX_BM_CTRL                            0x080
-+#define MTK_WED_TX_BM_CTRL_VLD_GRP_NUM                        GENMASK(6, 0)
-+#define MTK_WED_TX_BM_CTRL_RSV_GRP_NUM                        GENMASK(22, 16)
-+#define MTK_WED_TX_BM_CTRL_PAUSE                      BIT(28)
-+
-+#define MTK_WED_TX_BM_BASE                            0x084
-+
-+#define MTK_WED_TX_BM_TKID                            0x088
-+#define MTK_WED_TX_BM_TKID_START                      GENMASK(15, 0)
-+#define MTK_WED_TX_BM_TKID_END                                GENMASK(31, 16)
-+
-+#define MTK_WED_TX_BM_BUF_LEN                         0x08c
-+
-+#define MTK_WED_TX_BM_INTF                            0x09c
-+#define MTK_WED_TX_BM_INTF_TKID                               GENMASK(15, 0)
-+#define MTK_WED_TX_BM_INTF_TKFIFO_FDEP                        GENMASK(23, 16)
-+#define MTK_WED_TX_BM_INTF_TKID_VALID                 BIT(28)
-+#define MTK_WED_TX_BM_INTF_TKID_READ                  BIT(29)
-+
-+#define MTK_WED_TX_BM_DYN_THR                         0x0a0
-+#define MTK_WED_TX_BM_DYN_THR_LO                      GENMASK(6, 0)
-+#define MTK_WED_TX_BM_DYN_THR_HI                      GENMASK(22, 16)
-+
-+#define MTK_WED_INT_STATUS                            0x200
-+#define MTK_WED_INT_MASK                              0x204
-+
-+#define MTK_WED_GLO_CFG                                       0x208
-+#define MTK_WED_GLO_CFG_TX_DMA_EN                     BIT(0)
-+#define MTK_WED_GLO_CFG_TX_DMA_BUSY                   BIT(1)
-+#define MTK_WED_GLO_CFG_RX_DMA_EN                     BIT(2)
-+#define MTK_WED_GLO_CFG_RX_DMA_BUSY                   BIT(3)
-+#define MTK_WED_GLO_CFG_RX_BT_SIZE                    GENMASK(5, 4)
-+#define MTK_WED_GLO_CFG_TX_WB_DDONE                   BIT(6)
-+#define MTK_WED_GLO_CFG_BIG_ENDIAN                    BIT(7)
-+#define MTK_WED_GLO_CFG_DIS_BT_SIZE_ALIGN             BIT(8)
-+#define MTK_WED_GLO_CFG_TX_BT_SIZE_LO                 BIT(9)
-+#define MTK_WED_GLO_CFG_MULTI_DMA_EN                  GENMASK(11, 10)
-+#define MTK_WED_GLO_CFG_FIFO_LITTLE_ENDIAN            BIT(12)
-+#define MTK_WED_GLO_CFG_MI_DEPTH_RD                   GENMASK(21, 13)
-+#define MTK_WED_GLO_CFG_TX_BT_SIZE_HI                 GENMASK(23, 22)
-+#define MTK_WED_GLO_CFG_SW_RESET                      BIT(24)
-+#define MTK_WED_GLO_CFG_FIRST_TOKEN_ONLY              BIT(26)
-+#define MTK_WED_GLO_CFG_OMIT_RX_INFO                  BIT(27)
-+#define MTK_WED_GLO_CFG_OMIT_TX_INFO                  BIT(28)
-+#define MTK_WED_GLO_CFG_BYTE_SWAP                     BIT(29)
-+#define MTK_WED_GLO_CFG_RX_2B_OFFSET                  BIT(31)
-+
-+#define MTK_WED_RESET_IDX                             0x20c
-+#define MTK_WED_RESET_IDX_TX                          GENMASK(3, 0)
-+#define MTK_WED_RESET_IDX_RX                          GENMASK(17, 16)
-+
-+#define MTK_WED_TX_MIB(_n)                            (0x2a0 + (_n) * 4)
-+
-+#define MTK_WED_RING_TX(_n)                           (0x300 + (_n) * 0x10)
-+
-+#define MTK_WED_RING_RX(_n)                           (0x400 + (_n) * 0x10)
-+
-+#define MTK_WED_WPDMA_INT_TRIGGER                     0x504
-+#define MTK_WED_WPDMA_INT_TRIGGER_RX_DONE             BIT(1)
-+#define MTK_WED_WPDMA_INT_TRIGGER_TX_DONE             GENMASK(5, 4)
-+
-+#define MTK_WED_WPDMA_GLO_CFG                         0x508
-+#define MTK_WED_WPDMA_GLO_CFG_TX_DRV_EN                       BIT(0)
-+#define MTK_WED_WPDMA_GLO_CFG_TX_DRV_BUSY             BIT(1)
-+#define MTK_WED_WPDMA_GLO_CFG_RX_DRV_EN                       BIT(2)
-+#define MTK_WED_WPDMA_GLO_CFG_RX_DRV_BUSY             BIT(3)
-+#define MTK_WED_WPDMA_GLO_CFG_RX_BT_SIZE              GENMASK(5, 4)
-+#define MTK_WED_WPDMA_GLO_CFG_TX_WB_DDONE             BIT(6)
-+#define MTK_WED_WPDMA_GLO_CFG_BIG_ENDIAN              BIT(7)
-+#define MTK_WED_WPDMA_GLO_CFG_DIS_BT_SIZE_ALIGN               BIT(8)
-+#define MTK_WED_WPDMA_GLO_CFG_TX_BT_SIZE_LO           BIT(9)
-+#define MTK_WED_WPDMA_GLO_CFG_MULTI_DMA_EN            GENMASK(11, 10)
-+#define MTK_WED_WPDMA_GLO_CFG_FIFO_LITTLE_ENDIAN      BIT(12)
-+#define MTK_WED_WPDMA_GLO_CFG_MI_DEPTH_RD             GENMASK(21, 13)
-+#define MTK_WED_WPDMA_GLO_CFG_TX_BT_SIZE_HI           GENMASK(23, 22)
-+#define MTK_WED_WPDMA_GLO_CFG_SW_RESET                        BIT(24)
-+#define MTK_WED_WPDMA_GLO_CFG_FIRST_TOKEN_ONLY                BIT(26)
-+#define MTK_WED_WPDMA_GLO_CFG_OMIT_RX_INFO            BIT(27)
-+#define MTK_WED_WPDMA_GLO_CFG_OMIT_TX_INFO            BIT(28)
-+#define MTK_WED_WPDMA_GLO_CFG_BYTE_SWAP                       BIT(29)
-+#define MTK_WED_WPDMA_GLO_CFG_RX_2B_OFFSET            BIT(31)
-+
-+#define MTK_WED_WPDMA_RESET_IDX                               0x50c
-+#define MTK_WED_WPDMA_RESET_IDX_TX                    GENMASK(3, 0)
-+#define MTK_WED_WPDMA_RESET_IDX_RX                    GENMASK(17, 16)
-+
-+#define MTK_WED_WPDMA_INT_CTRL                                0x520
-+#define MTK_WED_WPDMA_INT_CTRL_SUBRT_ADV              BIT(21)
-+
-+#define MTK_WED_WPDMA_INT_MASK                                0x524
-+
-+#define MTK_WED_PCIE_CFG_BASE                         0x560
-+
-+#define MTK_WED_PCIE_INT_TRIGGER                      0x570
-+#define MTK_WED_PCIE_INT_TRIGGER_STATUS                       BIT(16)
-+
-+#define MTK_WED_WPDMA_CFG_BASE                                0x580
-+
-+#define MTK_WED_WPDMA_TX_MIB(_n)                      (0x5a0 + (_n) * 4)
-+#define MTK_WED_WPDMA_TX_COHERENT_MIB(_n)             (0x5d0 + (_n) * 4)
-+
-+#define MTK_WED_WPDMA_RING_TX(_n)                     (0x600 + (_n) * 0x10)
-+#define MTK_WED_WPDMA_RING_RX(_n)                     (0x700 + (_n) * 0x10)
-+#define MTK_WED_WDMA_RING_RX(_n)                      (0x900 + (_n) * 0x10)
-+#define MTK_WED_WDMA_RX_THRES(_n)                     (0x940 + (_n) * 0x4)
-+
-+#define MTK_WED_WDMA_GLO_CFG                          0xa04
-+#define MTK_WED_WDMA_GLO_CFG_TX_DRV_EN                        BIT(0)
-+#define MTK_WED_WDMA_GLO_CFG_RX_DRV_EN                        BIT(2)
-+#define MTK_WED_WDMA_GLO_CFG_RX_DRV_BUSY              BIT(3)
-+#define MTK_WED_WDMA_GLO_CFG_BT_SIZE                  GENMASK(5, 4)
-+#define MTK_WED_WDMA_GLO_CFG_TX_WB_DDONE              BIT(6)
-+#define MTK_WED_WDMA_GLO_CFG_RX_DIS_FSM_AUTO_IDLE     BIT(13)
-+#define MTK_WED_WDMA_GLO_CFG_WCOMPLETE_SEL            BIT(16)
-+#define MTK_WED_WDMA_GLO_CFG_INIT_PHASE_RXDMA_BYPASS  BIT(17)
-+#define MTK_WED_WDMA_GLO_CFG_INIT_PHASE_BYPASS                BIT(18)
-+#define MTK_WED_WDMA_GLO_CFG_FSM_RETURN_IDLE          BIT(19)
-+#define MTK_WED_WDMA_GLO_CFG_WAIT_COHERENT            BIT(20)
-+#define MTK_WED_WDMA_GLO_CFG_AXI_W_AFTER_AW           BIT(21)
-+#define MTK_WED_WDMA_GLO_CFG_IDLE_DMAD_SUPPLY_SINGLE_W        BIT(22)
-+#define MTK_WED_WDMA_GLO_CFG_IDLE_DMAD_SUPPLY         BIT(23)
-+#define MTK_WED_WDMA_GLO_CFG_DYNAMIC_SKIP_DMAD_PREP   BIT(24)
-+#define MTK_WED_WDMA_GLO_CFG_DYNAMIC_DMAD_RECYCLE     BIT(25)
-+#define MTK_WED_WDMA_GLO_CFG_RST_INIT_COMPLETE                BIT(26)
-+#define MTK_WED_WDMA_GLO_CFG_RXDRV_CLKGATE_BYPASS     BIT(30)
-+
-+#define MTK_WED_WDMA_RESET_IDX                                0xa08
-+#define MTK_WED_WDMA_RESET_IDX_RX                     GENMASK(17, 16)
-+#define MTK_WED_WDMA_RESET_IDX_DRV                    GENMASK(25, 24)
-+
-+#define MTK_WED_WDMA_INT_TRIGGER                      0xa28
-+#define MTK_WED_WDMA_INT_TRIGGER_RX_DONE              GENMASK(17, 16)
-+
-+#define MTK_WED_WDMA_INT_CTRL                         0xa2c
-+#define MTK_WED_WDMA_INT_CTRL_POLL_SRC_SEL            GENMASK(17, 16)
-+
-+#define MTK_WED_WDMA_OFFSET0                          0xaa4
-+#define MTK_WED_WDMA_OFFSET1                          0xaa8
-+
-+#define MTK_WED_WDMA_RX_MIB(_n)                               (0xae0 + (_n) * 4)
-+#define MTK_WED_WDMA_RX_RECYCLE_MIB(_n)                       (0xae8 + (_n) * 4)
-+#define MTK_WED_WDMA_RX_PROCESSED_MIB(_n)             (0xaf0 + (_n) * 4)
-+
-+#define MTK_WED_RING_OFS_BASE                         0x00
-+#define MTK_WED_RING_OFS_COUNT                                0x04
-+#define MTK_WED_RING_OFS_CPU_IDX                      0x08
-+#define MTK_WED_RING_OFS_DMA_IDX                      0x0c
-+
-+#define MTK_WDMA_RING_RX(_n)                          (0x100 + (_n) * 0x10)
-+
-+#define MTK_WDMA_GLO_CFG                              0x204
-+#define MTK_WDMA_GLO_CFG_RX_INFO_PRERES                       GENMASK(28, 26)
-+
-+#define MTK_WDMA_RESET_IDX                            0x208
-+#define MTK_WDMA_RESET_IDX_TX                         GENMASK(3, 0)
-+#define MTK_WDMA_RESET_IDX_RX                         GENMASK(17, 16)
-+
-+#define MTK_WDMA_INT_MASK                             0x228
-+#define MTK_WDMA_INT_MASK_TX_DONE                     GENMASK(3, 0)
-+#define MTK_WDMA_INT_MASK_RX_DONE                     GENMASK(17, 16)
-+#define MTK_WDMA_INT_MASK_TX_DELAY                    BIT(28)
-+#define MTK_WDMA_INT_MASK_TX_COHERENT                 BIT(29)
-+#define MTK_WDMA_INT_MASK_RX_DELAY                    BIT(30)
-+#define MTK_WDMA_INT_MASK_RX_COHERENT                 BIT(31)
-+
-+#define MTK_WDMA_INT_GRP1                             0x250
-+#define MTK_WDMA_INT_GRP2                             0x254
-+
-+#define MTK_PCIE_MIRROR_MAP(n)                                ((n) ? 0x4 : 0x0)
-+#define MTK_PCIE_MIRROR_MAP_EN                                BIT(0)
-+#define MTK_PCIE_MIRROR_MAP_WED_ID                    BIT(1)
-+
-+/* DMA channel mapping */
-+#define HIFSYS_DMA_AG_MAP                             0x008
-+
-+#endif
---- /dev/null
-+++ b/include/linux/soc/mediatek/mtk_wed.h
-@@ -0,0 +1,131 @@
-+#ifndef __MTK_WED_H
-+#define __MTK_WED_H
-+
-+#include <linux/kernel.h>
-+#include <linux/rcupdate.h>
-+#include <linux/regmap.h>
-+#include <linux/pci.h>
-+
-+#define MTK_WED_TX_QUEUES             2
-+
-+struct mtk_wed_hw;
-+struct mtk_wdma_desc;
-+
-+struct mtk_wed_ring {
-+      struct mtk_wdma_desc *desc;
-+      dma_addr_t desc_phys;
-+      int size;
-+
-+      u32 reg_base;
-+      void __iomem *wpdma;
-+};
-+
-+struct mtk_wed_device {
-+#ifdef CONFIG_NET_MEDIATEK_SOC_WED
-+      const struct mtk_wed_ops *ops;
-+      struct device *dev;
-+      struct mtk_wed_hw *hw;
-+      bool init_done, running;
-+      int wdma_idx;
-+      int irq;
-+
-+      struct mtk_wed_ring tx_ring[MTK_WED_TX_QUEUES];
-+      struct mtk_wed_ring txfree_ring;
-+      struct mtk_wed_ring tx_wdma[MTK_WED_TX_QUEUES];
-+
-+      struct {
-+              int size;
-+              void **pages;
-+              struct mtk_wdma_desc *desc;
-+              dma_addr_t desc_phys;
-+      } buf_ring;
-+
-+      /* filled by driver: */
-+      struct {
-+              struct pci_dev *pci_dev;
-+
-+              u32 wpdma_phys;
-+
-+              u16 token_start;
-+              unsigned int nbuf;
-+
-+              u32 (*init_buf)(void *ptr, dma_addr_t phys, int token_id);
-+              int (*offload_enable)(struct mtk_wed_device *wed);
-+              void (*offload_disable)(struct mtk_wed_device *wed);
-+      } wlan;
-+#endif
-+};
-+
-+struct mtk_wed_ops {
-+      int (*attach)(struct mtk_wed_device *dev);
-+      int (*tx_ring_setup)(struct mtk_wed_device *dev, int ring,
-+                           void __iomem *regs);
-+      int (*txfree_ring_setup)(struct mtk_wed_device *dev,
-+                               void __iomem *regs);
-+      void (*detach)(struct mtk_wed_device *dev);
-+
-+      void (*stop)(struct mtk_wed_device *dev);
-+      void (*start)(struct mtk_wed_device *dev, u32 irq_mask);
-+      void (*reset_dma)(struct mtk_wed_device *dev);
-+
-+      u32 (*reg_read)(struct mtk_wed_device *dev, u32 reg);
-+      void (*reg_write)(struct mtk_wed_device *dev, u32 reg, u32 val);
-+
-+      u32 (*irq_get)(struct mtk_wed_device *dev, u32 mask);
-+      void (*irq_set_mask)(struct mtk_wed_device *dev, u32 mask);
-+};
-+
-+extern const struct mtk_wed_ops __rcu *mtk_soc_wed_ops;
-+
-+static inline int
-+mtk_wed_device_attach(struct mtk_wed_device *dev)
-+{
-+      int ret = -ENODEV;
-+
-+#ifdef CONFIG_NET_MEDIATEK_SOC_WED
-+      rcu_read_lock();
-+      dev->ops = rcu_dereference(mtk_soc_wed_ops);
-+      if (dev->ops)
-+              ret = dev->ops->attach(dev);
-+      else
-+              rcu_read_unlock();
-+
-+      if (ret)
-+              dev->ops = NULL;
-+#endif
-+
-+      return ret;
-+}
-+
-+#ifdef CONFIG_NET_MEDIATEK_SOC_WED
-+#define mtk_wed_device_active(_dev) !!(_dev)->ops
-+#define mtk_wed_device_detach(_dev) (_dev)->ops->detach(_dev)
-+#define mtk_wed_device_start(_dev, _mask) (_dev)->ops->start(_dev, _mask)
-+#define mtk_wed_device_tx_ring_setup(_dev, _ring, _regs) \
-+      (_dev)->ops->tx_ring_setup(_dev, _ring, _regs)
-+#define mtk_wed_device_txfree_ring_setup(_dev, _regs) \
-+      (_dev)->ops->txfree_ring_setup(_dev, _regs)
-+#define mtk_wed_device_reg_read(_dev, _reg) \
-+      (_dev)->ops->reg_read(_dev, _reg)
-+#define mtk_wed_device_reg_write(_dev, _reg, _val) \
-+      (_dev)->ops->reg_write(_dev, _reg, _val)
-+#define mtk_wed_device_irq_get(_dev, _mask) \
-+      (_dev)->ops->irq_get(_dev, _mask)
-+#define mtk_wed_device_irq_set_mask(_dev, _mask) \
-+      (_dev)->ops->irq_set_mask(_dev, _mask)
-+#else
-+static inline bool mtk_wed_device_active(struct mtk_wed_device *dev)
-+{
-+      return false;
-+}
-+#define mtk_wed_device_detach(_dev) do {} while (0)
-+#define mtk_wed_device_start(_dev, _mask) do {} while (0)
-+#define mtk_wed_device_tx_ring_setup(_dev, _ring, _regs) -ENODEV
-+#define mtk_wed_device_txfree_ring_setup(_dev, _ring, _regs) -ENODEV
-+#define mtk_wed_device_reg_read(_dev, _reg) 0
-+#define mtk_wed_device_reg_write(_dev, _reg, _val) do {} while (0)
-+#define mtk_wed_device_irq_get(_dev, _mask) 0
-+#define mtk_wed_device_irq_set_mask(_dev, _mask) do {} while (0)
-+#endif
-+
-+#endif
diff --git a/target/linux/generic/backport-5.15/702-v5.19-03-net-ethernet-mtk_eth_soc-implement-flow-offloading-t.patch b/target/linux/generic/backport-5.15/702-v5.19-03-net-ethernet-mtk_eth_soc-implement-flow-offloading-t.patch
deleted file mode 100644 (file)
index 69113c2..0000000
+++ /dev/null
@@ -1,269 +0,0 @@
-From: Felix Fietkau <[email protected]>
-Date: Sat, 5 Feb 2022 18:29:22 +0100
-Subject: [PATCH] net: ethernet: mtk_eth_soc: implement flow offloading
- to WED devices
-
-This allows hardware flow offloading from Ethernet to WLAN on MT7622 SoC
-
-Co-developed-by: Lorenzo Bianconi <[email protected]>
-Signed-off-by: Lorenzo Bianconi <[email protected]>
-Signed-off-by: Felix Fietkau <[email protected]>
----
-
---- a/drivers/net/ethernet/mediatek/mtk_ppe.c
-+++ b/drivers/net/ethernet/mediatek/mtk_ppe.c
-@@ -329,6 +329,24 @@ int mtk_foe_entry_set_pppoe(struct mtk_f
-       return 0;
- }
-+int mtk_foe_entry_set_wdma(struct mtk_foe_entry *entry, int wdma_idx, int txq,
-+                         int bss, int wcid)
-+{
-+      struct mtk_foe_mac_info *l2 = mtk_foe_entry_l2(entry);
-+      u32 *ib2 = mtk_foe_entry_ib2(entry);
-+
-+      *ib2 &= ~MTK_FOE_IB2_PORT_MG;
-+      *ib2 |= MTK_FOE_IB2_WDMA_WINFO;
-+      if (wdma_idx)
-+              *ib2 |= MTK_FOE_IB2_WDMA_DEVIDX;
-+
-+      l2->vlan2 = FIELD_PREP(MTK_FOE_VLAN2_WINFO_BSS, bss) |
-+                  FIELD_PREP(MTK_FOE_VLAN2_WINFO_WCID, wcid) |
-+                  FIELD_PREP(MTK_FOE_VLAN2_WINFO_RING, txq);
-+
-+      return 0;
-+}
-+
- static inline bool mtk_foe_entry_usable(struct mtk_foe_entry *entry)
- {
-       return !(entry->ib1 & MTK_FOE_IB1_STATIC) &&
---- a/drivers/net/ethernet/mediatek/mtk_ppe.h
-+++ b/drivers/net/ethernet/mediatek/mtk_ppe.h
-@@ -48,9 +48,9 @@ enum {
- #define MTK_FOE_IB2_DEST_PORT         GENMASK(7, 5)
- #define MTK_FOE_IB2_MULTICAST         BIT(8)
--#define MTK_FOE_IB2_WHNAT_QID2                GENMASK(13, 12)
--#define MTK_FOE_IB2_WHNAT_DEVIDX      BIT(16)
--#define MTK_FOE_IB2_WHNAT_NAT         BIT(17)
-+#define MTK_FOE_IB2_WDMA_QID2         GENMASK(13, 12)
-+#define MTK_FOE_IB2_WDMA_DEVIDX               BIT(16)
-+#define MTK_FOE_IB2_WDMA_WINFO                BIT(17)
- #define MTK_FOE_IB2_PORT_MG           GENMASK(17, 12)
-@@ -58,9 +58,9 @@ enum {
- #define MTK_FOE_IB2_DSCP              GENMASK(31, 24)
--#define MTK_FOE_VLAN2_WHNAT_BSS               GEMMASK(5, 0)
--#define MTK_FOE_VLAN2_WHNAT_WCID      GENMASK(13, 6)
--#define MTK_FOE_VLAN2_WHNAT_RING      GENMASK(15, 14)
-+#define MTK_FOE_VLAN2_WINFO_BSS               GENMASK(5, 0)
-+#define MTK_FOE_VLAN2_WINFO_WCID      GENMASK(13, 6)
-+#define MTK_FOE_VLAN2_WINFO_RING      GENMASK(15, 14)
- enum {
-       MTK_FOE_STATE_INVALID,
-@@ -281,6 +281,8 @@ int mtk_foe_entry_set_ipv6_tuple(struct
- int mtk_foe_entry_set_dsa(struct mtk_foe_entry *entry, int port);
- int mtk_foe_entry_set_vlan(struct mtk_foe_entry *entry, int vid);
- int mtk_foe_entry_set_pppoe(struct mtk_foe_entry *entry, int sid);
-+int mtk_foe_entry_set_wdma(struct mtk_foe_entry *entry, int wdma_idx, int txq,
-+                         int bss, int wcid);
- int mtk_foe_entry_commit(struct mtk_ppe *ppe, struct mtk_foe_entry *entry,
-                        u16 timestamp);
- int mtk_ppe_debugfs_init(struct mtk_ppe *ppe);
---- a/drivers/net/ethernet/mediatek/mtk_ppe_offload.c
-+++ b/drivers/net/ethernet/mediatek/mtk_ppe_offload.c
-@@ -10,6 +10,7 @@
- #include <net/pkt_cls.h>
- #include <net/dsa.h>
- #include "mtk_eth_soc.h"
-+#include "mtk_wed.h"
- struct mtk_flow_data {
-       struct ethhdr eth;
-@@ -39,6 +40,7 @@ struct mtk_flow_entry {
-       struct rhash_head node;
-       unsigned long cookie;
-       u16 hash;
-+      s8 wed_index;
- };
- static const struct rhashtable_params mtk_flow_ht_params = {
-@@ -80,6 +82,35 @@ mtk_flow_offload_mangle_eth(const struct
-       memcpy(dest, src, act->mangle.mask ? 2 : 4);
- }
-+static int
-+mtk_flow_get_wdma_info(struct net_device *dev, const u8 *addr, struct mtk_wdma_info *info)
-+{
-+      struct net_device_path_ctx ctx = {
-+              .dev = dev,
-+              .daddr = addr,
-+      };
-+      struct net_device_path path = {};
-+
-+      if (!IS_ENABLED(CONFIG_NET_MEDIATEK_SOC_WED))
-+              return -1;
-+
-+      if (!dev->netdev_ops->ndo_fill_forward_path)
-+              return -1;
-+
-+      if (dev->netdev_ops->ndo_fill_forward_path(&ctx, &path))
-+              return -1;
-+
-+      if (path.type != DEV_PATH_MTK_WDMA)
-+              return -1;
-+
-+      info->wdma_idx = path.mtk_wdma.wdma_idx;
-+      info->queue = path.mtk_wdma.queue;
-+      info->bss = path.mtk_wdma.bss;
-+      info->wcid = path.mtk_wdma.wcid;
-+
-+      return 0;
-+}
-+
- static int
- mtk_flow_mangle_ports(const struct flow_action_entry *act,
-@@ -149,10 +180,20 @@ mtk_flow_get_dsa_port(struct net_device
- static int
- mtk_flow_set_output_device(struct mtk_eth *eth, struct mtk_foe_entry *foe,
--                         struct net_device *dev)
-+                         struct net_device *dev, const u8 *dest_mac,
-+                         int *wed_index)
- {
-+      struct mtk_wdma_info info = {};
-       int pse_port, dsa_port;
-+      if (mtk_flow_get_wdma_info(dev, dest_mac, &info) == 0) {
-+              mtk_foe_entry_set_wdma(foe, info.wdma_idx, info.queue, info.bss,
-+                                     info.wcid);
-+              pse_port = 3;
-+              *wed_index = info.wdma_idx;
-+              goto out;
-+      }
-+
-       dsa_port = mtk_flow_get_dsa_port(&dev);
-       if (dsa_port >= 0)
-               mtk_foe_entry_set_dsa(foe, dsa_port);
-@@ -164,6 +205,7 @@ mtk_flow_set_output_device(struct mtk_et
-       else
-               return -EOPNOTSUPP;
-+out:
-       mtk_foe_entry_set_pse_port(foe, pse_port);
-       return 0;
-@@ -179,6 +221,7 @@ mtk_flow_offload_replace(struct mtk_eth
-       struct net_device *odev = NULL;
-       struct mtk_flow_entry *entry;
-       int offload_type = 0;
-+      int wed_index = -1;
-       u16 addr_type = 0;
-       u32 timestamp;
-       u8 l4proto = 0;
-@@ -326,10 +369,14 @@ mtk_flow_offload_replace(struct mtk_eth
-       if (data.pppoe.num == 1)
-               mtk_foe_entry_set_pppoe(&foe, data.pppoe.sid);
--      err = mtk_flow_set_output_device(eth, &foe, odev);
-+      err = mtk_flow_set_output_device(eth, &foe, odev, data.eth.h_dest,
-+                                       &wed_index);
-       if (err)
-               return err;
-+      if (wed_index >= 0 && (err = mtk_wed_flow_add(wed_index)) < 0)
-+              return err;
-+
-       entry = kzalloc(sizeof(*entry), GFP_KERNEL);
-       if (!entry)
-               return -ENOMEM;
-@@ -343,6 +390,7 @@ mtk_flow_offload_replace(struct mtk_eth
-       }
-       entry->hash = hash;
-+      entry->wed_index = wed_index;
-       err = rhashtable_insert_fast(&eth->flow_table, &entry->node,
-                                    mtk_flow_ht_params);
-       if (err < 0)
-@@ -353,6 +401,8 @@ clear_flow:
-       mtk_foe_entry_clear(&eth->ppe, hash);
- free:
-       kfree(entry);
-+      if (wed_index >= 0)
-+          mtk_wed_flow_remove(wed_index);
-       return err;
- }
-@@ -369,6 +419,8 @@ mtk_flow_offload_destroy(struct mtk_eth
-       mtk_foe_entry_clear(&eth->ppe, entry->hash);
-       rhashtable_remove_fast(&eth->flow_table, &entry->node,
-                              mtk_flow_ht_params);
-+      if (entry->wed_index >= 0)
-+              mtk_wed_flow_remove(entry->wed_index);
-       kfree(entry);
-       return 0;
---- a/drivers/net/ethernet/mediatek/mtk_wed.h
-+++ b/drivers/net/ethernet/mediatek/mtk_wed.h
-@@ -7,6 +7,7 @@
- #include <linux/soc/mediatek/mtk_wed.h>
- #include <linux/debugfs.h>
- #include <linux/regmap.h>
-+#include <linux/netdevice.h>
- struct mtk_eth;
-@@ -27,6 +28,12 @@ struct mtk_wed_hw {
-       int index;
- };
-+struct mtk_wdma_info {
-+      u8 wdma_idx;
-+      u8 queue;
-+      u16 wcid;
-+      u8 bss;
-+};
- #ifdef CONFIG_NET_MEDIATEK_SOC_WED
- static inline void
---- a/include/linux/netdevice.h
-+++ b/include/linux/netdevice.h
-@@ -875,6 +875,7 @@ enum net_device_path_type {
-       DEV_PATH_BRIDGE,
-       DEV_PATH_PPPOE,
-       DEV_PATH_DSA,
-+      DEV_PATH_MTK_WDMA,
- };
- struct net_device_path {
-@@ -900,6 +901,12 @@ struct net_device_path {
-                       int port;
-                       u16 proto;
-               } dsa;
-+              struct {
-+                      u8 wdma_idx;
-+                      u8 queue;
-+                      u16 wcid;
-+                      u8 bss;
-+              } mtk_wdma;
-       };
- };
---- a/net/core/dev.c
-+++ b/net/core/dev.c
-@@ -769,6 +769,10 @@ int dev_fill_forward_path(const struct n
-               if (WARN_ON_ONCE(last_dev == ctx.dev))
-                       return -1;
-       }
-+
-+      if (!ctx.dev)
-+              return ret;
-+
-       path = dev_fwd_path(stack);
-       if (!path)
-               return -1;
diff --git a/target/linux/generic/backport-5.15/702-v5.19-05-net-ethernet-mtk_eth_soc-add-ipv6-flow-offload-suppo.patch b/target/linux/generic/backport-5.15/702-v5.19-05-net-ethernet-mtk_eth_soc-add-ipv6-flow-offload-suppo.patch
deleted file mode 100644 (file)
index 9adb067..0000000
+++ /dev/null
@@ -1,79 +0,0 @@
-From: David Bentham <[email protected]>
-Date: Mon, 21 Feb 2022 15:36:16 +0100
-Subject: [PATCH] net: ethernet: mtk_eth_soc: add ipv6 flow offload
- support
-
-Add the missing IPv6 flow offloading support for routing only.
-Hardware flow offloading is done by the packet processing engine (PPE)
-of the Ethernet MAC and as it doesn't support mangling of IPv6 packets,
-IPv6 NAT cannot be supported.
-
-Signed-off-by: David Bentham <[email protected]>
-Signed-off-by: Felix Fietkau <[email protected]>
----
-
---- a/drivers/net/ethernet/mediatek/mtk_ppe_offload.c
-+++ b/drivers/net/ethernet/mediatek/mtk_ppe_offload.c
-@@ -6,6 +6,7 @@
- #include <linux/if_ether.h>
- #include <linux/rhashtable.h>
- #include <linux/ip.h>
-+#include <linux/ipv6.h>
- #include <net/flow_offload.h>
- #include <net/pkt_cls.h>
- #include <net/dsa.h>
-@@ -20,6 +21,11 @@ struct mtk_flow_data {
-                       __be32 src_addr;
-                       __be32 dst_addr;
-               } v4;
-+
-+              struct {
-+                      struct in6_addr src_addr;
-+                      struct in6_addr dst_addr;
-+              } v6;
-       };
-       __be16 src_port;
-@@ -65,6 +71,14 @@ mtk_flow_set_ipv4_addr(struct mtk_foe_en
-                                           data->v4.dst_addr, data->dst_port);
- }
-+static int
-+mtk_flow_set_ipv6_addr(struct mtk_foe_entry *foe, struct mtk_flow_data *data)
-+{
-+      return mtk_foe_entry_set_ipv6_tuple(foe,
-+                                          data->v6.src_addr.s6_addr32, data->src_port,
-+                                          data->v6.dst_addr.s6_addr32, data->dst_port);
-+}
-+
- static void
- mtk_flow_offload_mangle_eth(const struct flow_action_entry *act, void *eth)
- {
-@@ -296,6 +310,9 @@ mtk_flow_offload_replace(struct mtk_eth
-       case FLOW_DISSECTOR_KEY_IPV4_ADDRS:
-               offload_type = MTK_PPE_PKT_TYPE_IPV4_HNAPT;
-               break;
-+      case FLOW_DISSECTOR_KEY_IPV6_ADDRS:
-+              offload_type = MTK_PPE_PKT_TYPE_IPV6_ROUTE_5T;
-+              break;
-       default:
-               return -EOPNOTSUPP;
-       }
-@@ -331,6 +348,17 @@ mtk_flow_offload_replace(struct mtk_eth
-               mtk_flow_set_ipv4_addr(&foe, &data, false);
-       }
-+      if (addr_type == FLOW_DISSECTOR_KEY_IPV6_ADDRS) {
-+              struct flow_match_ipv6_addrs addrs;
-+
-+              flow_rule_match_ipv6_addrs(rule, &addrs);
-+
-+              data.v6.src_addr = addrs.key->src;
-+              data.v6.dst_addr = addrs.key->dst;
-+
-+              mtk_flow_set_ipv6_addr(&foe, &data);
-+      }
-+
-       flow_action_for_each(i, act, &rule->action) {
-               if (act->id != FLOW_ACTION_MANGLE)
-                       continue;
diff --git a/target/linux/generic/backport-5.15/702-v5.19-06-net-ethernet-mtk_eth_soc-support-TC_SETUP_BLOCK-for-.patch b/target/linux/generic/backport-5.15/702-v5.19-06-net-ethernet-mtk_eth_soc-support-TC_SETUP_BLOCK-for-.patch
deleted file mode 100644 (file)
index 1950d81..0000000
+++ /dev/null
@@ -1,29 +0,0 @@
-From: Felix Fietkau <[email protected]>
-Date: Mon, 21 Feb 2022 15:37:21 +0100
-Subject: [PATCH] net: ethernet: mtk_eth_soc: support TC_SETUP_BLOCK for
- PPE offload
-
-This allows offload entries to be created from user space
-
-Signed-off-by: Felix Fietkau <[email protected]>
----
-
---- a/drivers/net/ethernet/mediatek/mtk_ppe_offload.c
-+++ b/drivers/net/ethernet/mediatek/mtk_ppe_offload.c
-@@ -564,10 +564,13 @@ mtk_eth_setup_tc_block(struct net_device
- int mtk_eth_setup_tc(struct net_device *dev, enum tc_setup_type type,
-                    void *type_data)
- {
--      if (type == TC_SETUP_FT)
-+      switch (type) {
-+      case TC_SETUP_BLOCK:
-+      case TC_SETUP_FT:
-               return mtk_eth_setup_tc_block(dev, type_data);
--
--      return -EOPNOTSUPP;
-+      default:
-+              return -EOPNOTSUPP;
-+      }
- }
- int mtk_eth_offload_init(struct mtk_eth *eth)
diff --git a/target/linux/generic/backport-5.15/702-v5.19-07-net-ethernet-mtk_eth_soc-allocate-struct-mtk_ppe-sep.patch b/target/linux/generic/backport-5.15/702-v5.19-07-net-ethernet-mtk_eth_soc-allocate-struct-mtk_ppe-sep.patch
deleted file mode 100644 (file)
index 488a799..0000000
+++ /dev/null
@@ -1,159 +0,0 @@
-From: Felix Fietkau <[email protected]>
-Date: Mon, 21 Feb 2022 15:38:20 +0100
-Subject: [PATCH] net: ethernet: mtk_eth_soc: allocate struct mtk_ppe
- separately
-
-Preparation for adding more data to it, which will increase its size.
-
-Signed-off-by: Felix Fietkau <[email protected]>
----
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-@@ -2348,7 +2348,7 @@ static int mtk_open(struct net_device *d
-                       return err;
-               }
--              if (eth->soc->offload_version && mtk_ppe_start(&eth->ppe) == 0)
-+              if (eth->soc->offload_version && mtk_ppe_start(eth->ppe) == 0)
-                       gdm_config = MTK_GDMA_TO_PPE;
-               mtk_gdm_config(eth, gdm_config);
-@@ -2422,7 +2422,7 @@ static int mtk_stop(struct net_device *d
-       mtk_dma_free(eth);
-       if (eth->soc->offload_version)
--              mtk_ppe_stop(&eth->ppe);
-+              mtk_ppe_stop(eth->ppe);
-       return 0;
- }
-@@ -3307,10 +3307,11 @@ static int mtk_probe(struct platform_dev
-       }
-       if (eth->soc->offload_version) {
--              err = mtk_ppe_init(&eth->ppe, eth->dev,
--                                 eth->base + MTK_ETH_PPE_BASE, 2);
--              if (err)
-+              eth->ppe = mtk_ppe_init(eth->dev, eth->base + MTK_ETH_PPE_BASE, 2);
-+              if (!eth->ppe) {
-+                      err = -ENOMEM;
-                       goto err_free_dev;
-+              }
-               err = mtk_eth_offload_init(eth);
-               if (err)
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-@@ -983,7 +983,7 @@ struct mtk_eth {
-       u32                             rx_dma_l4_valid;
-       int                             ip_align;
--      struct mtk_ppe                  ppe;
-+      struct mtk_ppe                  *ppe;
-       struct rhashtable               flow_table;
- };
---- a/drivers/net/ethernet/mediatek/mtk_ppe.c
-+++ b/drivers/net/ethernet/mediatek/mtk_ppe.c
-@@ -384,10 +384,15 @@ int mtk_foe_entry_commit(struct mtk_ppe
-       return hash;
- }
--int mtk_ppe_init(struct mtk_ppe *ppe, struct device *dev, void __iomem *base,
-+struct mtk_ppe *mtk_ppe_init(struct device *dev, void __iomem *base,
-                int version)
- {
-       struct mtk_foe_entry *foe;
-+      struct mtk_ppe *ppe;
-+
-+      ppe = devm_kzalloc(dev, sizeof(*ppe), GFP_KERNEL);
-+      if (!ppe)
-+              return NULL;
-       /* need to allocate a separate device, since it PPE DMA access is
-        * not coherent.
-@@ -399,13 +404,13 @@ int mtk_ppe_init(struct mtk_ppe *ppe, st
-       foe = dmam_alloc_coherent(ppe->dev, MTK_PPE_ENTRIES * sizeof(*foe),
-                                 &ppe->foe_phys, GFP_KERNEL);
-       if (!foe)
--              return -ENOMEM;
-+              return NULL;
-       ppe->foe_table = foe;
-       mtk_ppe_debugfs_init(ppe);
--      return 0;
-+      return ppe;
- }
- static void mtk_ppe_init_foe_table(struct mtk_ppe *ppe)
---- a/drivers/net/ethernet/mediatek/mtk_ppe.h
-+++ b/drivers/net/ethernet/mediatek/mtk_ppe.h
-@@ -246,8 +246,7 @@ struct mtk_ppe {
-       void *acct_table;
- };
--int mtk_ppe_init(struct mtk_ppe *ppe, struct device *dev, void __iomem *base,
--               int version);
-+struct mtk_ppe *mtk_ppe_init(struct device *dev, void __iomem *base, int version);
- int mtk_ppe_start(struct mtk_ppe *ppe);
- int mtk_ppe_stop(struct mtk_ppe *ppe);
---- a/drivers/net/ethernet/mediatek/mtk_ppe_offload.c
-+++ b/drivers/net/ethernet/mediatek/mtk_ppe_offload.c
-@@ -411,7 +411,7 @@ mtk_flow_offload_replace(struct mtk_eth
-       entry->cookie = f->cookie;
-       timestamp = mtk_eth_timestamp(eth);
--      hash = mtk_foe_entry_commit(&eth->ppe, &foe, timestamp);
-+      hash = mtk_foe_entry_commit(eth->ppe, &foe, timestamp);
-       if (hash < 0) {
-               err = hash;
-               goto free;
-@@ -426,7 +426,7 @@ mtk_flow_offload_replace(struct mtk_eth
-       return 0;
- clear_flow:
--      mtk_foe_entry_clear(&eth->ppe, hash);
-+      mtk_foe_entry_clear(eth->ppe, hash);
- free:
-       kfree(entry);
-       if (wed_index >= 0)
-@@ -444,7 +444,7 @@ mtk_flow_offload_destroy(struct mtk_eth
-       if (!entry)
-               return -ENOENT;
--      mtk_foe_entry_clear(&eth->ppe, entry->hash);
-+      mtk_foe_entry_clear(eth->ppe, entry->hash);
-       rhashtable_remove_fast(&eth->flow_table, &entry->node,
-                              mtk_flow_ht_params);
-       if (entry->wed_index >= 0)
-@@ -466,7 +466,7 @@ mtk_flow_offload_stats(struct mtk_eth *e
-       if (!entry)
-               return -ENOENT;
--      timestamp = mtk_foe_entry_timestamp(&eth->ppe, entry->hash);
-+      timestamp = mtk_foe_entry_timestamp(eth->ppe, entry->hash);
-       if (timestamp < 0)
-               return -ETIMEDOUT;
-@@ -522,7 +522,7 @@ mtk_eth_setup_tc_block(struct net_device
-       struct flow_block_cb *block_cb;
-       flow_setup_cb_t *cb;
--      if (!eth->ppe.foe_table)
-+      if (!eth->ppe || !eth->ppe->foe_table)
-               return -EOPNOTSUPP;
-       if (f->binder_type != FLOW_BLOCK_BINDER_TYPE_CLSACT_INGRESS)
-@@ -575,7 +575,7 @@ int mtk_eth_setup_tc(struct net_device *
- int mtk_eth_offload_init(struct mtk_eth *eth)
- {
--      if (!eth->ppe.foe_table)
-+      if (!eth->ppe || !eth->ppe->foe_table)
-               return 0;
-       return rhashtable_init(&eth->flow_table, &mtk_flow_ht_params);
diff --git a/target/linux/generic/backport-5.15/702-v5.19-08-net-ethernet-mtk_eth_soc-rework-hardware-flow-table-.patch b/target/linux/generic/backport-5.15/702-v5.19-08-net-ethernet-mtk_eth_soc-rework-hardware-flow-table-.patch
deleted file mode 100644 (file)
index 182c6af..0000000
+++ /dev/null
@@ -1,424 +0,0 @@
-From: Felix Fietkau <[email protected]>
-Date: Mon, 21 Feb 2022 15:39:18 +0100
-Subject: [PATCH] net: ethernet: mtk_eth_soc: rework hardware flow table
- management
-
-The hardware was designed to handle flow detection and creation of flow entries
-by itself, relying on the software primarily for filling in egress routing
-information.
-When there is a hash collision between multiple flows, this allows the hardware
-to maintain the entry for the most active flow.
-Additionally, the hardware only keeps offloading active for entries with at
-least 30 packets per second.
-
-With this rework, the code no longer creates a hardware entries directly.
-Instead, the hardware entry is only created when the PPE reports a matching
-unbound flow with the minimum target rate.
-In order to reduce CPU overhead, looking for flows belonging to a hash entry
-is rate limited to once every 100ms.
-
-This rework is also used as preparation for emulating bridge offload by
-managing L4 offload entries on demand.
-
-Signed-off-by: Felix Fietkau <[email protected]>
----
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-@@ -21,6 +21,7 @@
- #include <linux/pinctrl/devinfo.h>
- #include <linux/phylink.h>
- #include <linux/jhash.h>
-+#include <linux/bitfield.h>
- #include <net/dsa.h>
- #include "mtk_eth_soc.h"
-@@ -1303,7 +1304,7 @@ static int mtk_poll_rx(struct napi_struc
-               struct net_device *netdev;
-               unsigned int pktlen;
-               dma_addr_t dma_addr;
--              u32 hash;
-+              u32 hash, reason;
-               int mac;
-               ring = mtk_get_rx_ring(eth);
-@@ -1382,6 +1383,11 @@ static int mtk_poll_rx(struct napi_struc
-                       skb_set_hash(skb, hash, PKT_HASH_TYPE_L4);
-               }
-+              reason = FIELD_GET(MTK_RXD4_PPE_CPU_REASON, trxd.rxd4);
-+              if (reason == MTK_PPE_CPU_REASON_HIT_UNBIND_RATE_REACHED)
-+                      mtk_ppe_check_skb(eth->ppe, skb,
-+                                        trxd.rxd4 & MTK_RXD4_FOE_ENTRY);
-+
-               if (netdev->features & NETIF_F_HW_VLAN_CTAG_RX &&
-                   (trxd.rxd2 & RX_DMA_VTAG))
-                       __vlan_hwaccel_put_tag(skb, htons(ETH_P_8021Q),
-@@ -3307,7 +3313,7 @@ static int mtk_probe(struct platform_dev
-       }
-       if (eth->soc->offload_version) {
--              eth->ppe = mtk_ppe_init(eth->dev, eth->base + MTK_ETH_PPE_BASE, 2);
-+              eth->ppe = mtk_ppe_init(eth, eth->base + MTK_ETH_PPE_BASE, 2);
-               if (!eth->ppe) {
-                       err = -ENOMEM;
-                       goto err_free_dev;
---- a/drivers/net/ethernet/mediatek/mtk_ppe.c
-+++ b/drivers/net/ethernet/mediatek/mtk_ppe.c
-@@ -6,9 +6,12 @@
- #include <linux/iopoll.h>
- #include <linux/etherdevice.h>
- #include <linux/platform_device.h>
-+#include "mtk_eth_soc.h"
- #include "mtk_ppe.h"
- #include "mtk_ppe_regs.h"
-+static DEFINE_SPINLOCK(ppe_lock);
-+
- static void ppe_w32(struct mtk_ppe *ppe, u32 reg, u32 val)
- {
-       writel(val, ppe->base + reg);
-@@ -41,6 +44,11 @@ static u32 ppe_clear(struct mtk_ppe *ppe
-       return ppe_m32(ppe, reg, val, 0);
- }
-+static u32 mtk_eth_timestamp(struct mtk_eth *eth)
-+{
-+      return mtk_r32(eth, 0x0010) & MTK_FOE_IB1_BIND_TIMESTAMP;
-+}
-+
- static int mtk_ppe_wait_busy(struct mtk_ppe *ppe)
- {
-       int ret;
-@@ -353,26 +361,59 @@ static inline bool mtk_foe_entry_usable(
-              FIELD_GET(MTK_FOE_IB1_STATE, entry->ib1) != MTK_FOE_STATE_BIND;
- }
--int mtk_foe_entry_commit(struct mtk_ppe *ppe, struct mtk_foe_entry *entry,
--                       u16 timestamp)
-+static bool
-+mtk_flow_entry_match(struct mtk_flow_entry *entry, struct mtk_foe_entry *data)
-+{
-+      int type, len;
-+
-+      if ((data->ib1 ^ entry->data.ib1) & MTK_FOE_IB1_UDP)
-+              return false;
-+
-+      type = FIELD_GET(MTK_FOE_IB1_PACKET_TYPE, entry->data.ib1);
-+      if (type > MTK_PPE_PKT_TYPE_IPV4_DSLITE)
-+              len = offsetof(struct mtk_foe_entry, ipv6._rsv);
-+      else
-+              len = offsetof(struct mtk_foe_entry, ipv4.ib2);
-+
-+      return !memcmp(&entry->data.data, &data->data, len - 4);
-+}
-+
-+static void
-+mtk_flow_entry_update(struct mtk_ppe *ppe, struct mtk_flow_entry *entry)
- {
-       struct mtk_foe_entry *hwe;
--      u32 hash;
-+      struct mtk_foe_entry foe;
-+      spin_lock_bh(&ppe_lock);
-+      if (entry->hash == 0xffff)
-+              goto out;
-+
-+      hwe = &ppe->foe_table[entry->hash];
-+      memcpy(&foe, hwe, sizeof(foe));
-+      if (!mtk_flow_entry_match(entry, &foe)) {
-+              entry->hash = 0xffff;
-+              goto out;
-+      }
-+
-+      entry->data.ib1 = foe.ib1;
-+
-+out:
-+      spin_unlock_bh(&ppe_lock);
-+}
-+
-+static void
-+__mtk_foe_entry_commit(struct mtk_ppe *ppe, struct mtk_foe_entry *entry,
-+                     u16 hash)
-+{
-+      struct mtk_foe_entry *hwe;
-+      u16 timestamp;
-+
-+      timestamp = mtk_eth_timestamp(ppe->eth);
-       timestamp &= MTK_FOE_IB1_BIND_TIMESTAMP;
-       entry->ib1 &= ~MTK_FOE_IB1_BIND_TIMESTAMP;
-       entry->ib1 |= FIELD_PREP(MTK_FOE_IB1_BIND_TIMESTAMP, timestamp);
--      hash = mtk_ppe_hash_entry(entry);
-       hwe = &ppe->foe_table[hash];
--      if (!mtk_foe_entry_usable(hwe)) {
--              hwe++;
--              hash++;
--
--              if (!mtk_foe_entry_usable(hwe))
--                      return -ENOSPC;
--      }
--
-       memcpy(&hwe->data, &entry->data, sizeof(hwe->data));
-       wmb();
-       hwe->ib1 = entry->ib1;
-@@ -380,13 +421,77 @@ int mtk_foe_entry_commit(struct mtk_ppe
-       dma_wmb();
-       mtk_ppe_cache_clear(ppe);
-+}
--      return hash;
-+void mtk_foe_entry_clear(struct mtk_ppe *ppe, struct mtk_flow_entry *entry)
-+{
-+      spin_lock_bh(&ppe_lock);
-+      hlist_del_init(&entry->list);
-+      if (entry->hash != 0xffff) {
-+              ppe->foe_table[entry->hash].ib1 &= ~MTK_FOE_IB1_STATE;
-+              ppe->foe_table[entry->hash].ib1 |= FIELD_PREP(MTK_FOE_IB1_STATE,
-+                                                            MTK_FOE_STATE_BIND);
-+              dma_wmb();
-+      }
-+      entry->hash = 0xffff;
-+      spin_unlock_bh(&ppe_lock);
-+}
-+
-+int mtk_foe_entry_commit(struct mtk_ppe *ppe, struct mtk_flow_entry *entry)
-+{
-+      u32 hash = mtk_ppe_hash_entry(&entry->data);
-+
-+      entry->hash = 0xffff;
-+      spin_lock_bh(&ppe_lock);
-+      hlist_add_head(&entry->list, &ppe->foe_flow[hash / 2]);
-+      spin_unlock_bh(&ppe_lock);
-+
-+      return 0;
-+}
-+
-+void __mtk_ppe_check_skb(struct mtk_ppe *ppe, struct sk_buff *skb, u16 hash)
-+{
-+      struct hlist_head *head = &ppe->foe_flow[hash / 2];
-+      struct mtk_flow_entry *entry;
-+      struct mtk_foe_entry *hwe = &ppe->foe_table[hash];
-+      bool found = false;
-+
-+      if (hlist_empty(head))
-+              return;
-+
-+      spin_lock_bh(&ppe_lock);
-+      hlist_for_each_entry(entry, head, list) {
-+              if (found || !mtk_flow_entry_match(entry, hwe)) {
-+                      if (entry->hash != 0xffff)
-+                              entry->hash = 0xffff;
-+                      continue;
-+              }
-+
-+              entry->hash = hash;
-+              __mtk_foe_entry_commit(ppe, &entry->data, hash);
-+              found = true;
-+      }
-+      spin_unlock_bh(&ppe_lock);
-+}
-+
-+int mtk_foe_entry_idle_time(struct mtk_ppe *ppe, struct mtk_flow_entry *entry)
-+{
-+      u16 now = mtk_eth_timestamp(ppe->eth) & MTK_FOE_IB1_BIND_TIMESTAMP;
-+      u16 timestamp;
-+
-+      mtk_flow_entry_update(ppe, entry);
-+      timestamp = entry->data.ib1 & MTK_FOE_IB1_BIND_TIMESTAMP;
-+
-+      if (timestamp > now)
-+              return MTK_FOE_IB1_BIND_TIMESTAMP + 1 - timestamp + now;
-+      else
-+              return now - timestamp;
- }
--struct mtk_ppe *mtk_ppe_init(struct device *dev, void __iomem *base,
-+struct mtk_ppe *mtk_ppe_init(struct mtk_eth *eth, void __iomem *base,
-                int version)
- {
-+      struct device *dev = eth->dev;
-       struct mtk_foe_entry *foe;
-       struct mtk_ppe *ppe;
-@@ -398,6 +503,7 @@ struct mtk_ppe *mtk_ppe_init(struct devi
-        * not coherent.
-        */
-       ppe->base = base;
-+      ppe->eth = eth;
-       ppe->dev = dev;
-       ppe->version = version;
---- a/drivers/net/ethernet/mediatek/mtk_ppe.h
-+++ b/drivers/net/ethernet/mediatek/mtk_ppe.h
-@@ -235,7 +235,17 @@ enum {
-       MTK_PPE_CPU_REASON_INVALID                      = 0x1f,
- };
-+struct mtk_flow_entry {
-+      struct rhash_head node;
-+      struct hlist_node list;
-+      unsigned long cookie;
-+      struct mtk_foe_entry data;
-+      u16 hash;
-+      s8 wed_index;
-+};
-+
- struct mtk_ppe {
-+      struct mtk_eth *eth;
-       struct device *dev;
-       void __iomem *base;
-       int version;
-@@ -243,18 +253,33 @@ struct mtk_ppe {
-       struct mtk_foe_entry *foe_table;
-       dma_addr_t foe_phys;
-+      u16 foe_check_time[MTK_PPE_ENTRIES];
-+      struct hlist_head foe_flow[MTK_PPE_ENTRIES / 2];
-+
-       void *acct_table;
- };
--struct mtk_ppe *mtk_ppe_init(struct device *dev, void __iomem *base, int version);
-+struct mtk_ppe *mtk_ppe_init(struct mtk_eth *eth, void __iomem *base, int version);
- int mtk_ppe_start(struct mtk_ppe *ppe);
- int mtk_ppe_stop(struct mtk_ppe *ppe);
-+void __mtk_ppe_check_skb(struct mtk_ppe *ppe, struct sk_buff *skb, u16 hash);
-+
- static inline void
--mtk_foe_entry_clear(struct mtk_ppe *ppe, u16 hash)
-+mtk_ppe_check_skb(struct mtk_ppe *ppe, struct sk_buff *skb, u16 hash)
- {
--      ppe->foe_table[hash].ib1 = 0;
--      dma_wmb();
-+      u16 now, diff;
-+
-+      if (!ppe)
-+              return;
-+
-+      now = (u16)jiffies;
-+      diff = now - ppe->foe_check_time[hash];
-+      if (diff < HZ / 10)
-+              return;
-+
-+      ppe->foe_check_time[hash] = now;
-+      __mtk_ppe_check_skb(ppe, skb, hash);
- }
- static inline int
-@@ -282,8 +307,9 @@ int mtk_foe_entry_set_vlan(struct mtk_fo
- int mtk_foe_entry_set_pppoe(struct mtk_foe_entry *entry, int sid);
- int mtk_foe_entry_set_wdma(struct mtk_foe_entry *entry, int wdma_idx, int txq,
-                          int bss, int wcid);
--int mtk_foe_entry_commit(struct mtk_ppe *ppe, struct mtk_foe_entry *entry,
--                       u16 timestamp);
-+int mtk_foe_entry_commit(struct mtk_ppe *ppe, struct mtk_flow_entry *entry);
-+void mtk_foe_entry_clear(struct mtk_ppe *ppe, struct mtk_flow_entry *entry);
-+int mtk_foe_entry_idle_time(struct mtk_ppe *ppe, struct mtk_flow_entry *entry);
- int mtk_ppe_debugfs_init(struct mtk_ppe *ppe);
- #endif
---- a/drivers/net/ethernet/mediatek/mtk_ppe_offload.c
-+++ b/drivers/net/ethernet/mediatek/mtk_ppe_offload.c
-@@ -42,13 +42,6 @@ struct mtk_flow_data {
-       } pppoe;
- };
--struct mtk_flow_entry {
--      struct rhash_head node;
--      unsigned long cookie;
--      u16 hash;
--      s8 wed_index;
--};
--
- static const struct rhashtable_params mtk_flow_ht_params = {
-       .head_offset = offsetof(struct mtk_flow_entry, node),
-       .key_offset = offsetof(struct mtk_flow_entry, cookie),
-@@ -56,12 +49,6 @@ static const struct rhashtable_params mt
-       .automatic_shrinking = true,
- };
--static u32
--mtk_eth_timestamp(struct mtk_eth *eth)
--{
--      return mtk_r32(eth, 0x0010) & MTK_FOE_IB1_BIND_TIMESTAMP;
--}
--
- static int
- mtk_flow_set_ipv4_addr(struct mtk_foe_entry *foe, struct mtk_flow_data *data,
-                      bool egress)
-@@ -237,10 +224,8 @@ mtk_flow_offload_replace(struct mtk_eth
-       int offload_type = 0;
-       int wed_index = -1;
-       u16 addr_type = 0;
--      u32 timestamp;
-       u8 l4proto = 0;
-       int err = 0;
--      int hash;
-       int i;
-       if (rhashtable_lookup(&eth->flow_table, &f->cookie, mtk_flow_ht_params))
-@@ -410,23 +395,21 @@ mtk_flow_offload_replace(struct mtk_eth
-               return -ENOMEM;
-       entry->cookie = f->cookie;
--      timestamp = mtk_eth_timestamp(eth);
--      hash = mtk_foe_entry_commit(eth->ppe, &foe, timestamp);
--      if (hash < 0) {
--              err = hash;
-+      memcpy(&entry->data, &foe, sizeof(entry->data));
-+      entry->wed_index = wed_index;
-+
-+      if (mtk_foe_entry_commit(eth->ppe, entry) < 0)
-               goto free;
--      }
--      entry->hash = hash;
--      entry->wed_index = wed_index;
-       err = rhashtable_insert_fast(&eth->flow_table, &entry->node,
-                                    mtk_flow_ht_params);
-       if (err < 0)
--              goto clear_flow;
-+              goto clear;
-       return 0;
--clear_flow:
--      mtk_foe_entry_clear(eth->ppe, hash);
-+
-+clear:
-+      mtk_foe_entry_clear(eth->ppe, entry);
- free:
-       kfree(entry);
-       if (wed_index >= 0)
-@@ -444,7 +427,7 @@ mtk_flow_offload_destroy(struct mtk_eth
-       if (!entry)
-               return -ENOENT;
--      mtk_foe_entry_clear(eth->ppe, entry->hash);
-+      mtk_foe_entry_clear(eth->ppe, entry);
-       rhashtable_remove_fast(&eth->flow_table, &entry->node,
-                              mtk_flow_ht_params);
-       if (entry->wed_index >= 0)
-@@ -458,7 +441,6 @@ static int
- mtk_flow_offload_stats(struct mtk_eth *eth, struct flow_cls_offload *f)
- {
-       struct mtk_flow_entry *entry;
--      int timestamp;
-       u32 idle;
-       entry = rhashtable_lookup(&eth->flow_table, &f->cookie,
-@@ -466,11 +448,7 @@ mtk_flow_offload_stats(struct mtk_eth *e
-       if (!entry)
-               return -ENOENT;
--      timestamp = mtk_foe_entry_timestamp(eth->ppe, entry->hash);
--      if (timestamp < 0)
--              return -ETIMEDOUT;
--
--      idle = mtk_eth_timestamp(eth) - timestamp;
-+      idle = mtk_foe_entry_idle_time(eth->ppe, entry);
-       f->stats.lastused = jiffies - idle * HZ;
-       return 0;
diff --git a/target/linux/generic/backport-5.15/702-v5.19-09-net-ethernet-mtk_eth_soc-remove-bridge-flow-offload-.patch b/target/linux/generic/backport-5.15/702-v5.19-09-net-ethernet-mtk_eth_soc-remove-bridge-flow-offload-.patch
deleted file mode 100644 (file)
index 2ff0b34..0000000
+++ /dev/null
@@ -1,44 +0,0 @@
-From: Felix Fietkau <[email protected]>
-Date: Mon, 21 Feb 2022 15:55:19 +0100
-Subject: [PATCH] net: ethernet: mtk_eth_soc: remove bridge flow offload
- type entry support
-
-According to MediaTek, this feature is not supported in current hardware
-
-Signed-off-by: Felix Fietkau <[email protected]>
----
-
---- a/drivers/net/ethernet/mediatek/mtk_ppe.c
-+++ b/drivers/net/ethernet/mediatek/mtk_ppe.c
-@@ -84,13 +84,6 @@ static u32 mtk_ppe_hash_entry(struct mtk
-       u32 hash;
-       switch (FIELD_GET(MTK_FOE_IB1_PACKET_TYPE, e->ib1)) {
--              case MTK_PPE_PKT_TYPE_BRIDGE:
--                      hv1 = e->bridge.src_mac_lo;
--                      hv1 ^= ((e->bridge.src_mac_hi & 0xffff) << 16);
--                      hv2 = e->bridge.src_mac_hi >> 16;
--                      hv2 ^= e->bridge.dest_mac_lo;
--                      hv3 = e->bridge.dest_mac_hi;
--                      break;
-               case MTK_PPE_PKT_TYPE_IPV4_ROUTE:
-               case MTK_PPE_PKT_TYPE_IPV4_HNAPT:
-                       hv1 = e->ipv4.orig.ports;
-@@ -572,7 +565,6 @@ int mtk_ppe_start(struct mtk_ppe *ppe)
-             MTK_PPE_FLOW_CFG_IP4_NAT |
-             MTK_PPE_FLOW_CFG_IP4_NAPT |
-             MTK_PPE_FLOW_CFG_IP4_DSLITE |
--            MTK_PPE_FLOW_CFG_L2_BRIDGE |
-             MTK_PPE_FLOW_CFG_IP4_NAT_FRAG;
-       ppe_w32(ppe, MTK_PPE_FLOW_CFG, val);
---- a/drivers/net/ethernet/mediatek/mtk_ppe_debugfs.c
-+++ b/drivers/net/ethernet/mediatek/mtk_ppe_debugfs.c
-@@ -32,7 +32,6 @@ static const char *mtk_foe_pkt_type_str(
-       static const char * const type_str[] = {
-               [MTK_PPE_PKT_TYPE_IPV4_HNAPT] = "IPv4 5T",
-               [MTK_PPE_PKT_TYPE_IPV4_ROUTE] = "IPv4 3T",
--              [MTK_PPE_PKT_TYPE_BRIDGE] = "L2",
-               [MTK_PPE_PKT_TYPE_IPV4_DSLITE] = "DS-LITE",
-               [MTK_PPE_PKT_TYPE_IPV6_ROUTE_3T] = "IPv6 3T",
-               [MTK_PPE_PKT_TYPE_IPV6_ROUTE_5T] = "IPv6 5T",
diff --git a/target/linux/generic/backport-5.15/702-v5.19-10-net-ethernet-mtk_eth_soc-support-creating-mac-addres.patch b/target/linux/generic/backport-5.15/702-v5.19-10-net-ethernet-mtk_eth_soc-support-creating-mac-addres.patch
deleted file mode 100644 (file)
index 209c65e..0000000
+++ /dev/null
@@ -1,553 +0,0 @@
-From: Felix Fietkau <[email protected]>
-Date: Wed, 23 Feb 2022 10:56:34 +0100
-Subject: [PATCH] net: ethernet: mtk_eth_soc: support creating mac
- address based offload entries
-
-This will be used to implement a limited form of bridge offloading.
-Since the hardware does not support flow table entries with just source
-and destination MAC address, the driver has to emulate it.
-
-The hardware automatically creates entries entries for incoming flows, even
-when they are bridged instead of routed, and reports when packets for these
-flows have reached the minimum PPS rate for offloading.
-
-After this happens, we look up the L2 flow offload entry based on the MAC
-header and fill in the output routing information in the flow table.
-The dynamically created per-flow entries are automatically removed when
-either the hardware flowtable entry expires, is replaced, or if the offload
-rule they belong to is removed
-
-Signed-off-by: Felix Fietkau <[email protected]>
----
-
---- a/drivers/net/ethernet/mediatek/mtk_ppe.c
-+++ b/drivers/net/ethernet/mediatek/mtk_ppe.c
-@@ -6,12 +6,22 @@
- #include <linux/iopoll.h>
- #include <linux/etherdevice.h>
- #include <linux/platform_device.h>
-+#include <linux/if_ether.h>
-+#include <linux/if_vlan.h>
-+#include <net/dsa.h>
- #include "mtk_eth_soc.h"
- #include "mtk_ppe.h"
- #include "mtk_ppe_regs.h"
- static DEFINE_SPINLOCK(ppe_lock);
-+static const struct rhashtable_params mtk_flow_l2_ht_params = {
-+      .head_offset = offsetof(struct mtk_flow_entry, l2_node),
-+      .key_offset = offsetof(struct mtk_flow_entry, data.bridge),
-+      .key_len = offsetof(struct mtk_foe_bridge, key_end),
-+      .automatic_shrinking = true,
-+};
-+
- static void ppe_w32(struct mtk_ppe *ppe, u32 reg, u32 val)
- {
-       writel(val, ppe->base + reg);
-@@ -123,6 +133,9 @@ mtk_foe_entry_l2(struct mtk_foe_entry *e
- {
-       int type = FIELD_GET(MTK_FOE_IB1_PACKET_TYPE, entry->ib1);
-+      if (type == MTK_PPE_PKT_TYPE_BRIDGE)
-+              return &entry->bridge.l2;
-+
-       if (type >= MTK_PPE_PKT_TYPE_IPV4_DSLITE)
-               return &entry->ipv6.l2;
-@@ -134,6 +147,9 @@ mtk_foe_entry_ib2(struct mtk_foe_entry *
- {
-       int type = FIELD_GET(MTK_FOE_IB1_PACKET_TYPE, entry->ib1);
-+      if (type == MTK_PPE_PKT_TYPE_BRIDGE)
-+              return &entry->bridge.ib2;
-+
-       if (type >= MTK_PPE_PKT_TYPE_IPV4_DSLITE)
-               return &entry->ipv6.ib2;
-@@ -168,7 +184,12 @@ int mtk_foe_entry_prepare(struct mtk_foe
-       if (type == MTK_PPE_PKT_TYPE_IPV6_ROUTE_3T)
-               entry->ipv6.ports = ports_pad;
--      if (type >= MTK_PPE_PKT_TYPE_IPV4_DSLITE) {
-+      if (type == MTK_PPE_PKT_TYPE_BRIDGE) {
-+              ether_addr_copy(entry->bridge.src_mac, src_mac);
-+              ether_addr_copy(entry->bridge.dest_mac, dest_mac);
-+              entry->bridge.ib2 = val;
-+              l2 = &entry->bridge.l2;
-+      } else if (type >= MTK_PPE_PKT_TYPE_IPV4_DSLITE) {
-               entry->ipv6.ib2 = val;
-               l2 = &entry->ipv6.l2;
-       } else {
-@@ -372,12 +393,96 @@ mtk_flow_entry_match(struct mtk_flow_ent
- }
- static void
-+__mtk_foe_entry_clear(struct mtk_ppe *ppe, struct mtk_flow_entry *entry)
-+{
-+      struct hlist_head *head;
-+      struct hlist_node *tmp;
-+
-+      if (entry->type == MTK_FLOW_TYPE_L2) {
-+              rhashtable_remove_fast(&ppe->l2_flows, &entry->l2_node,
-+                                     mtk_flow_l2_ht_params);
-+
-+              head = &entry->l2_flows;
-+              hlist_for_each_entry_safe(entry, tmp, head, l2_data.list)
-+                      __mtk_foe_entry_clear(ppe, entry);
-+              return;
-+      }
-+
-+      hlist_del_init(&entry->list);
-+      if (entry->hash != 0xffff) {
-+              ppe->foe_table[entry->hash].ib1 &= ~MTK_FOE_IB1_STATE;
-+              ppe->foe_table[entry->hash].ib1 |= FIELD_PREP(MTK_FOE_IB1_STATE,
-+                                                            MTK_FOE_STATE_BIND);
-+              dma_wmb();
-+      }
-+      entry->hash = 0xffff;
-+
-+      if (entry->type != MTK_FLOW_TYPE_L2_SUBFLOW)
-+              return;
-+
-+      hlist_del_init(&entry->l2_data.list);
-+      kfree(entry);
-+}
-+
-+static int __mtk_foe_entry_idle_time(struct mtk_ppe *ppe, u32 ib1)
-+{
-+      u16 timestamp;
-+      u16 now;
-+
-+      now = mtk_eth_timestamp(ppe->eth) & MTK_FOE_IB1_BIND_TIMESTAMP;
-+      timestamp = ib1 & MTK_FOE_IB1_BIND_TIMESTAMP;
-+
-+      if (timestamp > now)
-+              return MTK_FOE_IB1_BIND_TIMESTAMP + 1 - timestamp + now;
-+      else
-+              return now - timestamp;
-+}
-+
-+static void
-+mtk_flow_entry_update_l2(struct mtk_ppe *ppe, struct mtk_flow_entry *entry)
-+{
-+      struct mtk_flow_entry *cur;
-+      struct mtk_foe_entry *hwe;
-+      struct hlist_node *tmp;
-+      int idle;
-+
-+      idle = __mtk_foe_entry_idle_time(ppe, entry->data.ib1);
-+      hlist_for_each_entry_safe(cur, tmp, &entry->l2_flows, l2_data.list) {
-+              int cur_idle;
-+              u32 ib1;
-+
-+              hwe = &ppe->foe_table[cur->hash];
-+              ib1 = READ_ONCE(hwe->ib1);
-+
-+              if (FIELD_GET(MTK_FOE_IB1_STATE, ib1) != MTK_FOE_STATE_BIND) {
-+                      cur->hash = 0xffff;
-+                      __mtk_foe_entry_clear(ppe, cur);
-+                      continue;
-+              }
-+
-+              cur_idle = __mtk_foe_entry_idle_time(ppe, ib1);
-+              if (cur_idle >= idle)
-+                      continue;
-+
-+              idle = cur_idle;
-+              entry->data.ib1 &= ~MTK_FOE_IB1_BIND_TIMESTAMP;
-+              entry->data.ib1 |= hwe->ib1 & MTK_FOE_IB1_BIND_TIMESTAMP;
-+      }
-+}
-+
-+static void
- mtk_flow_entry_update(struct mtk_ppe *ppe, struct mtk_flow_entry *entry)
- {
-       struct mtk_foe_entry *hwe;
-       struct mtk_foe_entry foe;
-       spin_lock_bh(&ppe_lock);
-+
-+      if (entry->type == MTK_FLOW_TYPE_L2) {
-+              mtk_flow_entry_update_l2(ppe, entry);
-+              goto out;
-+      }
-+
-       if (entry->hash == 0xffff)
-               goto out;
-@@ -419,21 +524,28 @@ __mtk_foe_entry_commit(struct mtk_ppe *p
- void mtk_foe_entry_clear(struct mtk_ppe *ppe, struct mtk_flow_entry *entry)
- {
-       spin_lock_bh(&ppe_lock);
--      hlist_del_init(&entry->list);
--      if (entry->hash != 0xffff) {
--              ppe->foe_table[entry->hash].ib1 &= ~MTK_FOE_IB1_STATE;
--              ppe->foe_table[entry->hash].ib1 |= FIELD_PREP(MTK_FOE_IB1_STATE,
--                                                            MTK_FOE_STATE_BIND);
--              dma_wmb();
--      }
--      entry->hash = 0xffff;
-+      __mtk_foe_entry_clear(ppe, entry);
-       spin_unlock_bh(&ppe_lock);
- }
-+static int
-+mtk_foe_entry_commit_l2(struct mtk_ppe *ppe, struct mtk_flow_entry *entry)
-+{
-+      entry->type = MTK_FLOW_TYPE_L2;
-+
-+      return rhashtable_insert_fast(&ppe->l2_flows, &entry->l2_node,
-+                                    mtk_flow_l2_ht_params);
-+}
-+
- int mtk_foe_entry_commit(struct mtk_ppe *ppe, struct mtk_flow_entry *entry)
- {
--      u32 hash = mtk_ppe_hash_entry(&entry->data);
-+      int type = FIELD_GET(MTK_FOE_IB1_PACKET_TYPE, entry->data.ib1);
-+      u32 hash;
-+
-+      if (type == MTK_PPE_PKT_TYPE_BRIDGE)
-+              return mtk_foe_entry_commit_l2(ppe, entry);
-+      hash = mtk_ppe_hash_entry(&entry->data);
-       entry->hash = 0xffff;
-       spin_lock_bh(&ppe_lock);
-       hlist_add_head(&entry->list, &ppe->foe_flow[hash / 2]);
-@@ -442,18 +554,72 @@ int mtk_foe_entry_commit(struct mtk_ppe
-       return 0;
- }
-+static void
-+mtk_foe_entry_commit_subflow(struct mtk_ppe *ppe, struct mtk_flow_entry *entry,
-+                           u16 hash)
-+{
-+      struct mtk_flow_entry *flow_info;
-+      struct mtk_foe_entry foe, *hwe;
-+      struct mtk_foe_mac_info *l2;
-+      u32 ib1_mask = MTK_FOE_IB1_PACKET_TYPE | MTK_FOE_IB1_UDP;
-+      int type;
-+
-+      flow_info = kzalloc(offsetof(struct mtk_flow_entry, l2_data.end),
-+                          GFP_ATOMIC);
-+      if (!flow_info)
-+              return;
-+
-+      flow_info->l2_data.base_flow = entry;
-+      flow_info->type = MTK_FLOW_TYPE_L2_SUBFLOW;
-+      flow_info->hash = hash;
-+      hlist_add_head(&flow_info->list, &ppe->foe_flow[hash / 2]);
-+      hlist_add_head(&flow_info->l2_data.list, &entry->l2_flows);
-+
-+      hwe = &ppe->foe_table[hash];
-+      memcpy(&foe, hwe, sizeof(foe));
-+      foe.ib1 &= ib1_mask;
-+      foe.ib1 |= entry->data.ib1 & ~ib1_mask;
-+
-+      l2 = mtk_foe_entry_l2(&foe);
-+      memcpy(l2, &entry->data.bridge.l2, sizeof(*l2));
-+
-+      type = FIELD_GET(MTK_FOE_IB1_PACKET_TYPE, foe.ib1);
-+      if (type == MTK_PPE_PKT_TYPE_IPV4_HNAPT)
-+              memcpy(&foe.ipv4.new, &foe.ipv4.orig, sizeof(foe.ipv4.new));
-+      else if (type >= MTK_PPE_PKT_TYPE_IPV6_ROUTE_3T && l2->etype == ETH_P_IP)
-+              l2->etype = ETH_P_IPV6;
-+
-+      *mtk_foe_entry_ib2(&foe) = entry->data.bridge.ib2;
-+
-+      __mtk_foe_entry_commit(ppe, &foe, hash);
-+}
-+
- void __mtk_ppe_check_skb(struct mtk_ppe *ppe, struct sk_buff *skb, u16 hash)
- {
-       struct hlist_head *head = &ppe->foe_flow[hash / 2];
--      struct mtk_flow_entry *entry;
-       struct mtk_foe_entry *hwe = &ppe->foe_table[hash];
-+      struct mtk_flow_entry *entry;
-+      struct mtk_foe_bridge key = {};
-+      struct ethhdr *eh;
-       bool found = false;
--
--      if (hlist_empty(head))
--              return;
-+      u8 *tag;
-       spin_lock_bh(&ppe_lock);
-+
-+      if (FIELD_GET(MTK_FOE_IB1_STATE, hwe->ib1) == MTK_FOE_STATE_BIND)
-+              goto out;
-+
-       hlist_for_each_entry(entry, head, list) {
-+              if (entry->type == MTK_FLOW_TYPE_L2_SUBFLOW) {
-+                      if (unlikely(FIELD_GET(MTK_FOE_IB1_STATE, hwe->ib1) ==
-+                                   MTK_FOE_STATE_BIND))
-+                              continue;
-+
-+                      entry->hash = 0xffff;
-+                      __mtk_foe_entry_clear(ppe, entry);
-+                      continue;
-+              }
-+
-               if (found || !mtk_flow_entry_match(entry, hwe)) {
-                       if (entry->hash != 0xffff)
-                               entry->hash = 0xffff;
-@@ -464,21 +630,50 @@ void __mtk_ppe_check_skb(struct mtk_ppe
-               __mtk_foe_entry_commit(ppe, &entry->data, hash);
-               found = true;
-       }
-+
-+      if (found)
-+              goto out;
-+
-+      eh = eth_hdr(skb);
-+      ether_addr_copy(key.dest_mac, eh->h_dest);
-+      ether_addr_copy(key.src_mac, eh->h_source);
-+      tag = skb->data - 2;
-+      key.vlan = 0;
-+      switch (skb->protocol) {
-+#if IS_ENABLED(CONFIG_NET_DSA)
-+      case htons(ETH_P_XDSA):
-+              if (!netdev_uses_dsa(skb->dev) ||
-+                  skb->dev->dsa_ptr->tag_ops->proto != DSA_TAG_PROTO_MTK)
-+                      goto out;
-+
-+              tag += 4;
-+              if (get_unaligned_be16(tag) != ETH_P_8021Q)
-+                      break;
-+
-+              fallthrough;
-+#endif
-+      case htons(ETH_P_8021Q):
-+              key.vlan = get_unaligned_be16(tag + 2) & VLAN_VID_MASK;
-+              break;
-+      default:
-+              break;
-+      }
-+
-+      entry = rhashtable_lookup_fast(&ppe->l2_flows, &key, mtk_flow_l2_ht_params);
-+      if (!entry)
-+              goto out;
-+
-+      mtk_foe_entry_commit_subflow(ppe, entry, hash);
-+
-+out:
-       spin_unlock_bh(&ppe_lock);
- }
- int mtk_foe_entry_idle_time(struct mtk_ppe *ppe, struct mtk_flow_entry *entry)
- {
--      u16 now = mtk_eth_timestamp(ppe->eth) & MTK_FOE_IB1_BIND_TIMESTAMP;
--      u16 timestamp;
--
-       mtk_flow_entry_update(ppe, entry);
--      timestamp = entry->data.ib1 & MTK_FOE_IB1_BIND_TIMESTAMP;
--      if (timestamp > now)
--              return MTK_FOE_IB1_BIND_TIMESTAMP + 1 - timestamp + now;
--      else
--              return now - timestamp;
-+      return __mtk_foe_entry_idle_time(ppe, entry->data.ib1);
- }
- struct mtk_ppe *mtk_ppe_init(struct mtk_eth *eth, void __iomem *base,
-@@ -492,6 +687,8 @@ struct mtk_ppe *mtk_ppe_init(struct mtk_
-       if (!ppe)
-               return NULL;
-+      rhashtable_init(&ppe->l2_flows, &mtk_flow_l2_ht_params);
-+
-       /* need to allocate a separate device, since it PPE DMA access is
-        * not coherent.
-        */
---- a/drivers/net/ethernet/mediatek/mtk_ppe.h
-+++ b/drivers/net/ethernet/mediatek/mtk_ppe.h
-@@ -6,6 +6,7 @@
- #include <linux/kernel.h>
- #include <linux/bitfield.h>
-+#include <linux/rhashtable.h>
- #define MTK_ETH_PPE_BASE              0xc00
-@@ -84,19 +85,16 @@ struct mtk_foe_mac_info {
-       u16 src_mac_lo;
- };
-+/* software-only entry type */
- struct mtk_foe_bridge {
--      u32 dest_mac_hi;
--
--      u16 src_mac_lo;
--      u16 dest_mac_lo;
-+      u8 dest_mac[ETH_ALEN];
-+      u8 src_mac[ETH_ALEN];
-+      u16 vlan;
--      u32 src_mac_hi;
-+      struct {} key_end;
-       u32 ib2;
--      u32 _rsv[5];
--
--      u32 udf_tsid;
-       struct mtk_foe_mac_info l2;
- };
-@@ -235,13 +233,33 @@ enum {
-       MTK_PPE_CPU_REASON_INVALID                      = 0x1f,
- };
-+enum {
-+      MTK_FLOW_TYPE_L4,
-+      MTK_FLOW_TYPE_L2,
-+      MTK_FLOW_TYPE_L2_SUBFLOW,
-+};
-+
- struct mtk_flow_entry {
-+      union {
-+              struct hlist_node list;
-+              struct {
-+                      struct rhash_head l2_node;
-+                      struct hlist_head l2_flows;
-+              };
-+      };
-+      u8 type;
-+      s8 wed_index;
-+      u16 hash;
-+      union {
-+              struct mtk_foe_entry data;
-+              struct {
-+                      struct mtk_flow_entry *base_flow;
-+                      struct hlist_node list;
-+                      struct {} end;
-+              } l2_data;
-+      };
-       struct rhash_head node;
--      struct hlist_node list;
-       unsigned long cookie;
--      struct mtk_foe_entry data;
--      u16 hash;
--      s8 wed_index;
- };
- struct mtk_ppe {
-@@ -256,6 +274,8 @@ struct mtk_ppe {
-       u16 foe_check_time[MTK_PPE_ENTRIES];
-       struct hlist_head foe_flow[MTK_PPE_ENTRIES / 2];
-+      struct rhashtable l2_flows;
-+
-       void *acct_table;
- };
---- a/drivers/net/ethernet/mediatek/mtk_ppe_offload.c
-+++ b/drivers/net/ethernet/mediatek/mtk_ppe_offload.c
-@@ -31,6 +31,8 @@ struct mtk_flow_data {
-       __be16 src_port;
-       __be16 dst_port;
-+      u16 vlan_in;
-+
-       struct {
-               u16 id;
-               __be16 proto;
-@@ -257,9 +259,45 @@ mtk_flow_offload_replace(struct mtk_eth
-               return -EOPNOTSUPP;
-       }
-+      switch (addr_type) {
-+      case 0:
-+              offload_type = MTK_PPE_PKT_TYPE_BRIDGE;
-+              if (flow_rule_match_key(rule, FLOW_DISSECTOR_KEY_ETH_ADDRS)) {
-+                      struct flow_match_eth_addrs match;
-+
-+                      flow_rule_match_eth_addrs(rule, &match);
-+                      memcpy(data.eth.h_dest, match.key->dst, ETH_ALEN);
-+                      memcpy(data.eth.h_source, match.key->src, ETH_ALEN);
-+              } else {
-+                      return -EOPNOTSUPP;
-+              }
-+
-+              if (flow_rule_match_key(rule, FLOW_DISSECTOR_KEY_VLAN)) {
-+                      struct flow_match_vlan match;
-+
-+                      flow_rule_match_vlan(rule, &match);
-+
-+                      if (match.key->vlan_tpid != cpu_to_be16(ETH_P_8021Q))
-+                              return -EOPNOTSUPP;
-+
-+                      data.vlan_in = match.key->vlan_id;
-+              }
-+              break;
-+      case FLOW_DISSECTOR_KEY_IPV4_ADDRS:
-+              offload_type = MTK_PPE_PKT_TYPE_IPV4_HNAPT;
-+              break;
-+      case FLOW_DISSECTOR_KEY_IPV6_ADDRS:
-+              offload_type = MTK_PPE_PKT_TYPE_IPV6_ROUTE_5T;
-+              break;
-+      default:
-+              return -EOPNOTSUPP;
-+      }
-+
-       flow_action_for_each(i, act, &rule->action) {
-               switch (act->id) {
-               case FLOW_ACTION_MANGLE:
-+                      if (offload_type == MTK_PPE_PKT_TYPE_BRIDGE)
-+                              return -EOPNOTSUPP;
-                       if (act->mangle.htype == FLOW_ACT_MANGLE_HDR_TYPE_ETH)
-                               mtk_flow_offload_mangle_eth(act, &data.eth);
-                       break;
-@@ -291,17 +329,6 @@ mtk_flow_offload_replace(struct mtk_eth
-               }
-       }
--      switch (addr_type) {
--      case FLOW_DISSECTOR_KEY_IPV4_ADDRS:
--              offload_type = MTK_PPE_PKT_TYPE_IPV4_HNAPT;
--              break;
--      case FLOW_DISSECTOR_KEY_IPV6_ADDRS:
--              offload_type = MTK_PPE_PKT_TYPE_IPV6_ROUTE_5T;
--              break;
--      default:
--              return -EOPNOTSUPP;
--      }
--
-       if (!is_valid_ether_addr(data.eth.h_source) ||
-           !is_valid_ether_addr(data.eth.h_dest))
-               return -EINVAL;
-@@ -315,10 +342,13 @@ mtk_flow_offload_replace(struct mtk_eth
-       if (flow_rule_match_key(rule, FLOW_DISSECTOR_KEY_PORTS)) {
-               struct flow_match_ports ports;
-+              if (offload_type == MTK_PPE_PKT_TYPE_BRIDGE)
-+                      return -EOPNOTSUPP;
-+
-               flow_rule_match_ports(rule, &ports);
-               data.src_port = ports.key->src;
-               data.dst_port = ports.key->dst;
--      } else {
-+      } else if (offload_type != MTK_PPE_PKT_TYPE_BRIDGE) {
-               return -EOPNOTSUPP;
-       }
-@@ -348,6 +378,9 @@ mtk_flow_offload_replace(struct mtk_eth
-               if (act->id != FLOW_ACTION_MANGLE)
-                       continue;
-+              if (offload_type == MTK_PPE_PKT_TYPE_BRIDGE)
-+                      return -EOPNOTSUPP;
-+
-               switch (act->mangle.htype) {
-               case FLOW_ACT_MANGLE_HDR_TYPE_TCP:
-               case FLOW_ACT_MANGLE_HDR_TYPE_UDP:
-@@ -373,6 +406,9 @@ mtk_flow_offload_replace(struct mtk_eth
-                       return err;
-       }
-+      if (offload_type == MTK_PPE_PKT_TYPE_BRIDGE)
-+              foe.bridge.vlan = data.vlan_in;
-+
-       if (data.vlan.num == 1) {
-               if (data.vlan.proto != htons(ETH_P_8021Q))
-                       return -EOPNOTSUPP;
diff --git a/target/linux/generic/backport-5.15/702-v5.19-11-net-ethernet-mtk_eth_soc-wed-fix-sparse-endian-warni.patch b/target/linux/generic/backport-5.15/702-v5.19-11-net-ethernet-mtk_eth_soc-wed-fix-sparse-endian-warni.patch
deleted file mode 100644 (file)
index 8f3dfe8..0000000
+++ /dev/null
@@ -1,56 +0,0 @@
-From: Felix Fietkau <[email protected]>
-Date: Fri, 8 Apr 2022 10:59:45 +0200
-Subject: [PATCH] net: ethernet: mtk_eth_soc/wed: fix sparse endian warnings
-
-Descriptor fields are little-endian
-
-Fixes: 804775dfc288 ("net: ethernet: mtk_eth_soc: add support for Wireless Ethernet Dispatch (WED)")
-Reported-by: kernel test robot <[email protected]>
-Signed-off-by: Felix Fietkau <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
-
---- a/drivers/net/ethernet/mediatek/mtk_wed.c
-+++ b/drivers/net/ethernet/mediatek/mtk_wed.c
-@@ -144,16 +144,17 @@ mtk_wed_buffer_alloc(struct mtk_wed_devi
-               for (s = 0; s < MTK_WED_BUF_PER_PAGE; s++) {
-                       u32 txd_size;
-+                      u32 ctrl;
-                       txd_size = dev->wlan.init_buf(buf, buf_phys, token++);
--                      desc->buf0 = buf_phys;
--                      desc->buf1 = buf_phys + txd_size;
--                      desc->ctrl = FIELD_PREP(MTK_WDMA_DESC_CTRL_LEN0,
--                                              txd_size) |
--                                   FIELD_PREP(MTK_WDMA_DESC_CTRL_LEN1,
--                                              MTK_WED_BUF_SIZE - txd_size) |
--                                   MTK_WDMA_DESC_CTRL_LAST_SEG1;
-+                      desc->buf0 = cpu_to_le32(buf_phys);
-+                      desc->buf1 = cpu_to_le32(buf_phys + txd_size);
-+                      ctrl = FIELD_PREP(MTK_WDMA_DESC_CTRL_LEN0, txd_size) |
-+                             FIELD_PREP(MTK_WDMA_DESC_CTRL_LEN1,
-+                                        MTK_WED_BUF_SIZE - txd_size) |
-+                             MTK_WDMA_DESC_CTRL_LAST_SEG1;
-+                      desc->ctrl = cpu_to_le32(ctrl);
-                       desc->info = 0;
-                       desc++;
-@@ -184,12 +185,14 @@ mtk_wed_free_buffer(struct mtk_wed_devic
-       for (i = 0, page_idx = 0; i < dev->buf_ring.size; i += MTK_WED_BUF_PER_PAGE) {
-               void *page = page_list[page_idx++];
-+              dma_addr_t buf_addr;
-               if (!page)
-                       break;
--              dma_unmap_page(dev->hw->dev, desc[i].buf0,
--                             PAGE_SIZE, DMA_BIDIRECTIONAL);
-+              buf_addr = le32_to_cpu(desc[i].buf0);
-+              dma_unmap_page(dev->hw->dev, buf_addr, PAGE_SIZE,
-+                             DMA_BIDIRECTIONAL);
-               __free_page(page);
-       }
diff --git a/target/linux/generic/backport-5.15/702-v5.19-12-net-ethernet-mtk_eth_soc-fix-return-value-check-in-m.patch b/target/linux/generic/backport-5.15/702-v5.19-12-net-ethernet-mtk_eth_soc-fix-return-value-check-in-m.patch
deleted file mode 100644 (file)
index 4ec8fe7..0000000
+++ /dev/null
@@ -1,25 +0,0 @@
-From: Yang Yingliang <[email protected]>
-Date: Fri, 8 Apr 2022 11:22:46 +0800
-Subject: [PATCH] net: ethernet: mtk_eth_soc: fix return value check in
- mtk_wed_add_hw()
-
-If syscon_regmap_lookup_by_phandle() fails, it never return NULL pointer,
-change the check to IS_ERR().
-
-Fixes: 804775dfc288 ("net: ethernet: mtk_eth_soc: add support for Wireless Ethernet Dispatch (WED)")
-Reported-by: Hulk Robot <[email protected]>
-Signed-off-by: Yang Yingliang <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
-
---- a/drivers/net/ethernet/mediatek/mtk_wed.c
-+++ b/drivers/net/ethernet/mediatek/mtk_wed.c
-@@ -816,7 +816,7 @@ void mtk_wed_add_hw(struct device_node *
-               return;
-       regs = syscon_regmap_lookup_by_phandle(np, NULL);
--      if (!regs)
-+      if (IS_ERR(regs))
-               return;
-       rcu_assign_pointer(mtk_soc_wed_ops, &wed_ops);
diff --git a/target/linux/generic/backport-5.15/702-v5.19-13-net-ethernet-mtk_eth_soc-use-standard-property-for-c.patch b/target/linux/generic/backport-5.15/702-v5.19-13-net-ethernet-mtk_eth_soc-use-standard-property-for-c.patch
deleted file mode 100644 (file)
index 22125a4..0000000
+++ /dev/null
@@ -1,35 +0,0 @@
-From: Lorenzo Bianconi <[email protected]>
-Date: Mon, 11 Apr 2022 12:13:25 +0200
-Subject: [PATCH] net: ethernet: mtk_eth_soc: use standard property for
- cci-control-port
-
-Rely on standard cci-control-port property to identify CCI port
-reference.
-Update mt7622 dts binding.
-
-Signed-off-by: Lorenzo Bianconi <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
-
---- a/arch/arm64/boot/dts/mediatek/mt7622.dtsi
-+++ b/arch/arm64/boot/dts/mediatek/mt7622.dtsi
-@@ -957,7 +957,7 @@
-               power-domains = <&scpsys MT7622_POWER_DOMAIN_ETHSYS>;
-               mediatek,ethsys = <&ethsys>;
-               mediatek,sgmiisys = <&sgmiisys>;
--              mediatek,cci-control = <&cci_control2>;
-+              cci-control-port = <&cci_control2>;
-               mediatek,wed = <&wed0>, <&wed1>;
-               mediatek,pcie-mirror = <&pcie_mirror>;
-               mediatek,hifsys = <&hifsys>;
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-@@ -3194,7 +3194,7 @@ static int mtk_probe(struct platform_dev
-               struct regmap *cci;
-               cci = syscon_regmap_lookup_by_phandle(pdev->dev.of_node,
--                                                    "mediatek,cci-control");
-+                                                    "cci-control-port");
-               /* enable CPU/bus coherency */
-               if (!IS_ERR(cci))
-                       regmap_write(cci, 0, 3);
diff --git a/target/linux/generic/backport-5.15/702-v5.19-14-net-ethernet-mtk_eth_soc-use-after-free-in-__mtk_ppe.patch b/target/linux/generic/backport-5.15/702-v5.19-14-net-ethernet-mtk_eth_soc-use-after-free-in-__mtk_ppe.patch
deleted file mode 100644 (file)
index 656b3a1..0000000
+++ /dev/null
@@ -1,33 +0,0 @@
-From: Dan Carpenter <[email protected]>
-Date: Tue, 12 Apr 2022 12:24:19 +0300
-Subject: [PATCH] net: ethernet: mtk_eth_soc: use after free in
- __mtk_ppe_check_skb()
-
-The __mtk_foe_entry_clear() function frees "entry" so we have to use
-the _safe() version of hlist_for_each_entry() to prevent a use after
-free.
-
-Fixes: 33fc42de3327 ("net: ethernet: mtk_eth_soc: support creating mac address based offload entries")
-Signed-off-by: Dan Carpenter <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
-
---- a/drivers/net/ethernet/mediatek/mtk_ppe.c
-+++ b/drivers/net/ethernet/mediatek/mtk_ppe.c
-@@ -600,6 +600,7 @@ void __mtk_ppe_check_skb(struct mtk_ppe
-       struct mtk_foe_entry *hwe = &ppe->foe_table[hash];
-       struct mtk_flow_entry *entry;
-       struct mtk_foe_bridge key = {};
-+      struct hlist_node *n;
-       struct ethhdr *eh;
-       bool found = false;
-       u8 *tag;
-@@ -609,7 +610,7 @@ void __mtk_ppe_check_skb(struct mtk_ppe
-       if (FIELD_GET(MTK_FOE_IB1_STATE, hwe->ib1) == MTK_FOE_STATE_BIND)
-               goto out;
--      hlist_for_each_entry(entry, head, list) {
-+      hlist_for_each_entry_safe(entry, n, head, list) {
-               if (entry->type == MTK_FLOW_TYPE_L2_SUBFLOW) {
-                       if (unlikely(FIELD_GET(MTK_FOE_IB1_STATE, hwe->ib1) ==
-                                    MTK_FOE_STATE_BIND))
diff --git a/target/linux/generic/backport-5.15/702-v5.19-15-net-ethernet-mtk_eth_soc-add-check-for-allocation-fa.patch b/target/linux/generic/backport-5.15/702-v5.19-15-net-ethernet-mtk_eth_soc-add-check-for-allocation-fa.patch
deleted file mode 100644 (file)
index 714163c..0000000
+++ /dev/null
@@ -1,22 +0,0 @@
-From: Dan Carpenter <[email protected]>
-Date: Thu, 21 Apr 2022 18:49:02 +0300
-Subject: [PATCH] net: ethernet: mtk_eth_soc: add check for allocation failure
-
-Check if the kzalloc() failed.
-
-Fixes: 804775dfc288 ("net: ethernet: mtk_eth_soc: add support for Wireless Ethernet Dispatch (WED)")
-Signed-off-by: Dan Carpenter <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
-
---- a/drivers/net/ethernet/mediatek/mtk_wed.c
-+++ b/drivers/net/ethernet/mediatek/mtk_wed.c
-@@ -827,6 +827,8 @@ void mtk_wed_add_hw(struct device_node *
-               goto unlock;
-       hw = kzalloc(sizeof(*hw), GFP_KERNEL);
-+      if (!hw)
-+              goto unlock;
-       hw->node = np;
-       hw->regs = regs;
-       hw->eth = eth;
diff --git a/target/linux/generic/backport-5.15/702-v5.19-16-eth-mtk_eth_soc-silence-the-GCC-12-array-bounds-warn.patch b/target/linux/generic/backport-5.15/702-v5.19-16-eth-mtk_eth_soc-silence-the-GCC-12-array-bounds-warn.patch
deleted file mode 100644 (file)
index aa98745..0000000
+++ /dev/null
@@ -1,26 +0,0 @@
-From: Jakub Kicinski <[email protected]>
-Date: Fri, 20 May 2022 12:56:03 -0700
-Subject: [PATCH] eth: mtk_eth_soc: silence the GCC 12 array-bounds warning
-
-GCC 12 gets upset because in mtk_foe_entry_commit_subflow()
-this driver allocates a partial structure. The writes are
-within bounds.
-
-Silence these warnings for now, our build bot runs GCC 12
-so we won't allow any new instances.
-
-Signed-off-by: Jakub Kicinski <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
-
---- a/drivers/net/ethernet/mediatek/Makefile
-+++ b/drivers/net/ethernet/mediatek/Makefile
-@@ -11,3 +11,8 @@ mtk_eth-$(CONFIG_NET_MEDIATEK_SOC_WED) +
- endif
- obj-$(CONFIG_NET_MEDIATEK_SOC_WED) += mtk_wed_ops.o
- obj-$(CONFIG_NET_MEDIATEK_STAR_EMAC) += mtk_star_emac.o
-+
-+# FIXME: temporarily silence -Warray-bounds on non W=1+ builds
-+ifndef KBUILD_EXTRA_WARN
-+CFLAGS_mtk_ppe.o += -Wno-array-bounds
-+endif
diff --git a/target/linux/generic/backport-5.15/702-v5.19-17-net-ethernet-mtk_eth_soc-rely-on-GFP_KERNEL-for-dma_.patch b/target/linux/generic/backport-5.15/702-v5.19-17-net-ethernet-mtk_eth_soc-rely-on-GFP_KERNEL-for-dma_.patch
deleted file mode 100644 (file)
index 268b372..0000000
+++ /dev/null
@@ -1,52 +0,0 @@
-From: Lorenzo Bianconi <[email protected]>
-Date: Fri, 20 May 2022 20:11:26 +0200
-Subject: [PATCH] net: ethernet: mtk_eth_soc: rely on GFP_KERNEL for
- dma_alloc_coherent whenever possible
-
-Rely on GFP_KERNEL for dma descriptors mappings in mtk_tx_alloc(),
-mtk_rx_alloc() and mtk_init_fq_dma() since they are run in non-irq
-context.
-
-Signed-off-by: Lorenzo Bianconi <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-@@ -856,7 +856,7 @@ static int mtk_init_fq_dma(struct mtk_et
-       eth->scratch_ring = dma_alloc_coherent(eth->dma_dev,
-                                              cnt * sizeof(struct mtk_tx_dma),
-                                              &eth->phy_scratch_ring,
--                                             GFP_ATOMIC);
-+                                             GFP_KERNEL);
-       if (unlikely(!eth->scratch_ring))
-               return -ENOMEM;
-@@ -1634,7 +1634,7 @@ static int mtk_tx_alloc(struct mtk_eth *
-               goto no_tx_mem;
-       ring->dma = dma_alloc_coherent(eth->dma_dev, MTK_DMA_SIZE * sz,
--                                     &ring->phys, GFP_ATOMIC);
-+                                     &ring->phys, GFP_KERNEL);
-       if (!ring->dma)
-               goto no_tx_mem;
-@@ -1652,8 +1652,7 @@ static int mtk_tx_alloc(struct mtk_eth *
-        */
-       if (!MTK_HAS_CAPS(eth->soc->caps, MTK_QDMA)) {
-               ring->dma_pdma = dma_alloc_coherent(eth->dma_dev, MTK_DMA_SIZE * sz,
--                                                  &ring->phys_pdma,
--                                                  GFP_ATOMIC);
-+                                                  &ring->phys_pdma, GFP_KERNEL);
-               if (!ring->dma_pdma)
-                       goto no_tx_mem;
-@@ -1768,7 +1767,7 @@ static int mtk_rx_alloc(struct mtk_eth *
-       ring->dma = dma_alloc_coherent(eth->dma_dev,
-                                      rx_dma_size * sizeof(*ring->dma),
--                                     &ring->phys, GFP_ATOMIC);
-+                                     &ring->phys, GFP_KERNEL);
-       if (!ring->dma)
-               return -ENOMEM;
diff --git a/target/linux/generic/backport-5.15/702-v5.19-18-net-ethernet-mtk_eth_soc-move-tx-dma-desc-configurat.patch b/target/linux/generic/backport-5.15/702-v5.19-18-net-ethernet-mtk_eth_soc-move-tx-dma-desc-configurat.patch
deleted file mode 100644 (file)
index dc85786..0000000
+++ /dev/null
@@ -1,206 +0,0 @@
-From: Lorenzo Bianconi <[email protected]>
-Date: Fri, 20 May 2022 20:11:27 +0200
-Subject: [PATCH] net: ethernet: mtk_eth_soc: move tx dma desc configuration in
- mtk_tx_set_dma_desc
-
-Move tx dma descriptor configuration in mtk_tx_set_dma_desc routine.
-This is a preliminary patch to introduce mt7986 ethernet support since
-it relies on a different tx dma descriptor layout.
-
-Tested-by: Sam Shih <[email protected]>
-Signed-off-by: Lorenzo Bianconi <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-@@ -982,18 +982,51 @@ static void setup_tx_buf(struct mtk_eth
-       }
- }
-+static void mtk_tx_set_dma_desc(struct net_device *dev, struct mtk_tx_dma *desc,
-+                              struct mtk_tx_dma_desc_info *info)
-+{
-+      struct mtk_mac *mac = netdev_priv(dev);
-+      u32 data;
-+
-+      WRITE_ONCE(desc->txd1, info->addr);
-+
-+      data = TX_DMA_SWC | TX_DMA_PLEN0(info->size);
-+      if (info->last)
-+              data |= TX_DMA_LS0;
-+      WRITE_ONCE(desc->txd3, data);
-+
-+      data = (mac->id + 1) << TX_DMA_FPORT_SHIFT; /* forward port */
-+      if (info->first) {
-+              if (info->gso)
-+                      data |= TX_DMA_TSO;
-+              /* tx checksum offload */
-+              if (info->csum)
-+                      data |= TX_DMA_CHKSUM;
-+              /* vlan header offload */
-+              if (info->vlan)
-+                      data |= TX_DMA_INS_VLAN | info->vlan_tci;
-+      }
-+      WRITE_ONCE(desc->txd4, data);
-+}
-+
- static int mtk_tx_map(struct sk_buff *skb, struct net_device *dev,
-                     int tx_num, struct mtk_tx_ring *ring, bool gso)
- {
-+      struct mtk_tx_dma_desc_info txd_info = {
-+              .size = skb_headlen(skb),
-+              .gso = gso,
-+              .csum = skb->ip_summed == CHECKSUM_PARTIAL,
-+              .vlan = skb_vlan_tag_present(skb),
-+              .vlan_tci = skb_vlan_tag_get(skb),
-+              .first = true,
-+              .last = !skb_is_nonlinear(skb),
-+      };
-       struct mtk_mac *mac = netdev_priv(dev);
-       struct mtk_eth *eth = mac->hw;
-       struct mtk_tx_dma *itxd, *txd;
-       struct mtk_tx_dma *itxd_pdma, *txd_pdma;
-       struct mtk_tx_buf *itx_buf, *tx_buf;
--      dma_addr_t mapped_addr;
--      unsigned int nr_frags;
-       int i, n_desc = 1;
--      u32 txd4 = 0, fport;
-       int k = 0;
-       itxd = ring->next_free;
-@@ -1001,49 +1034,32 @@ static int mtk_tx_map(struct sk_buff *sk
-       if (itxd == ring->last_free)
-               return -ENOMEM;
--      /* set the forward port */
--      fport = (mac->id + 1) << TX_DMA_FPORT_SHIFT;
--      txd4 |= fport;
--
-       itx_buf = mtk_desc_to_tx_buf(ring, itxd);
-       memset(itx_buf, 0, sizeof(*itx_buf));
--      if (gso)
--              txd4 |= TX_DMA_TSO;
--
--      /* TX Checksum offload */
--      if (skb->ip_summed == CHECKSUM_PARTIAL)
--              txd4 |= TX_DMA_CHKSUM;
--
--      /* VLAN header offload */
--      if (skb_vlan_tag_present(skb))
--              txd4 |= TX_DMA_INS_VLAN | skb_vlan_tag_get(skb);
--
--      mapped_addr = dma_map_single(eth->dma_dev, skb->data,
--                                   skb_headlen(skb), DMA_TO_DEVICE);
--      if (unlikely(dma_mapping_error(eth->dma_dev, mapped_addr)))
-+      txd_info.addr = dma_map_single(eth->dma_dev, skb->data, txd_info.size,
-+                                     DMA_TO_DEVICE);
-+      if (unlikely(dma_mapping_error(eth->dma_dev, txd_info.addr)))
-               return -ENOMEM;
--      WRITE_ONCE(itxd->txd1, mapped_addr);
-+      mtk_tx_set_dma_desc(dev, itxd, &txd_info);
-+
-       itx_buf->flags |= MTK_TX_FLAGS_SINGLE0;
-       itx_buf->flags |= (!mac->id) ? MTK_TX_FLAGS_FPORT0 :
-                         MTK_TX_FLAGS_FPORT1;
--      setup_tx_buf(eth, itx_buf, itxd_pdma, mapped_addr, skb_headlen(skb),
-+      setup_tx_buf(eth, itx_buf, itxd_pdma, txd_info.addr, txd_info.size,
-                    k++);
-       /* TX SG offload */
-       txd = itxd;
-       txd_pdma = qdma_to_pdma(ring, txd);
--      nr_frags = skb_shinfo(skb)->nr_frags;
--      for (i = 0; i < nr_frags; i++) {
-+      for (i = 0; i < skb_shinfo(skb)->nr_frags; i++) {
-               skb_frag_t *frag = &skb_shinfo(skb)->frags[i];
-               unsigned int offset = 0;
-               int frag_size = skb_frag_size(frag);
-               while (frag_size) {
--                      bool last_frag = false;
--                      unsigned int frag_map_size;
-                       bool new_desc = true;
-                       if (MTK_HAS_CAPS(eth->soc->caps, MTK_QDMA) ||
-@@ -1058,23 +1074,17 @@ static int mtk_tx_map(struct sk_buff *sk
-                               new_desc = false;
-                       }
--
--                      frag_map_size = min(frag_size, MTK_TX_DMA_BUF_LEN);
--                      mapped_addr = skb_frag_dma_map(eth->dma_dev, frag, offset,
--                                                     frag_map_size,
--                                                     DMA_TO_DEVICE);
--                      if (unlikely(dma_mapping_error(eth->dma_dev, mapped_addr)))
-+                      memset(&txd_info, 0, sizeof(struct mtk_tx_dma_desc_info));
-+                      txd_info.size = min(frag_size, MTK_TX_DMA_BUF_LEN);
-+                      txd_info.last = i == skb_shinfo(skb)->nr_frags - 1 &&
-+                                      !(frag_size - txd_info.size);
-+                      txd_info.addr = skb_frag_dma_map(eth->dma_dev, frag,
-+                                                       offset, txd_info.size,
-+                                                       DMA_TO_DEVICE);
-+                      if (unlikely(dma_mapping_error(eth->dma_dev, txd_info.addr)))
-                               goto err_dma;
--                      if (i == nr_frags - 1 &&
--                          (frag_size - frag_map_size) == 0)
--                              last_frag = true;
--
--                      WRITE_ONCE(txd->txd1, mapped_addr);
--                      WRITE_ONCE(txd->txd3, (TX_DMA_SWC |
--                                             TX_DMA_PLEN0(frag_map_size) |
--                                             last_frag * TX_DMA_LS0));
--                      WRITE_ONCE(txd->txd4, fport);
-+                      mtk_tx_set_dma_desc(dev, txd, &txd_info);
-                       tx_buf = mtk_desc_to_tx_buf(ring, txd);
-                       if (new_desc)
-@@ -1084,20 +1094,17 @@ static int mtk_tx_map(struct sk_buff *sk
-                       tx_buf->flags |= (!mac->id) ? MTK_TX_FLAGS_FPORT0 :
-                                        MTK_TX_FLAGS_FPORT1;
--                      setup_tx_buf(eth, tx_buf, txd_pdma, mapped_addr,
--                                   frag_map_size, k++);
-+                      setup_tx_buf(eth, tx_buf, txd_pdma, txd_info.addr,
-+                                   txd_info.size, k++);
--                      frag_size -= frag_map_size;
--                      offset += frag_map_size;
-+                      frag_size -= txd_info.size;
-+                      offset += txd_info.size;
-               }
-       }
-       /* store skb to cleanup */
-       itx_buf->skb = skb;
--      WRITE_ONCE(itxd->txd4, txd4);
--      WRITE_ONCE(itxd->txd3, (TX_DMA_SWC | TX_DMA_PLEN0(skb_headlen(skb)) |
--                              (!nr_frags * TX_DMA_LS0)));
-       if (!MTK_HAS_CAPS(eth->soc->caps, MTK_QDMA)) {
-               if (k & 0x1)
-                       txd_pdma->txd2 |= TX_DMA_LS0;
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-@@ -843,6 +843,17 @@ enum mkt_eth_capabilities {
-                     MTK_MUX_U3_GMAC2_TO_QPHY | \
-                     MTK_MUX_GMAC12_TO_GEPHY_SGMII | MTK_QDMA)
-+struct mtk_tx_dma_desc_info {
-+      dma_addr_t      addr;
-+      u32             size;
-+      u16             vlan_tci;
-+      u8              gso:1;
-+      u8              csum:1;
-+      u8              vlan:1;
-+      u8              first:1;
-+      u8              last:1;
-+};
-+
- /* struct mtk_eth_data -      This is the structure holding all differences
-  *                            among various plaforms
-  * @ana_rgc3:                   The offset for register ANA_RGC3 related to
diff --git a/target/linux/generic/backport-5.15/702-v5.19-19-net-ethernet-mtk_eth_soc-add-txd_size-to-mtk_soc_dat.patch b/target/linux/generic/backport-5.15/702-v5.19-19-net-ethernet-mtk_eth_soc-add-txd_size-to-mtk_soc_dat.patch
deleted file mode 100644 (file)
index 7e05181..0000000
+++ /dev/null
@@ -1,167 +0,0 @@
-From: Lorenzo Bianconi <[email protected]>
-Date: Fri, 20 May 2022 20:11:28 +0200
-Subject: [PATCH] net: ethernet: mtk_eth_soc: add txd_size to mtk_soc_data
-
-In order to remove mtk_tx_dma size dependency, introduce txd_size in
-mtk_soc_data data structure. Rely on txd_size in mtk_init_fq_dma() and
-mtk_dma_free() routines.
-This is a preliminary patch to add mt7986 ethernet support.
-
-Tested-by: Sam Shih <[email protected]>
-Signed-off-by: Lorenzo Bianconi <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-@@ -848,20 +848,20 @@ static void *mtk_max_lro_buf_alloc(gfp_t
- /* the qdma core needs scratch memory to be setup */
- static int mtk_init_fq_dma(struct mtk_eth *eth)
- {
-+      const struct mtk_soc_data *soc = eth->soc;
-       dma_addr_t phy_ring_tail;
-       int cnt = MTK_DMA_SIZE;
-       dma_addr_t dma_addr;
-       int i;
-       eth->scratch_ring = dma_alloc_coherent(eth->dma_dev,
--                                             cnt * sizeof(struct mtk_tx_dma),
-+                                             cnt * soc->txrx.txd_size,
-                                              &eth->phy_scratch_ring,
-                                              GFP_KERNEL);
-       if (unlikely(!eth->scratch_ring))
-               return -ENOMEM;
--      eth->scratch_head = kcalloc(cnt, MTK_QDMA_PAGE_SIZE,
--                                  GFP_KERNEL);
-+      eth->scratch_head = kcalloc(cnt, MTK_QDMA_PAGE_SIZE, GFP_KERNEL);
-       if (unlikely(!eth->scratch_head))
-               return -ENOMEM;
-@@ -871,16 +871,19 @@ static int mtk_init_fq_dma(struct mtk_et
-       if (unlikely(dma_mapping_error(eth->dma_dev, dma_addr)))
-               return -ENOMEM;
--      phy_ring_tail = eth->phy_scratch_ring +
--                      (sizeof(struct mtk_tx_dma) * (cnt - 1));
-+      phy_ring_tail = eth->phy_scratch_ring + soc->txrx.txd_size * (cnt - 1);
-       for (i = 0; i < cnt; i++) {
--              eth->scratch_ring[i].txd1 =
--                                      (dma_addr + (i * MTK_QDMA_PAGE_SIZE));
-+              struct mtk_tx_dma *txd;
-+
-+              txd = (void *)eth->scratch_ring + i * soc->txrx.txd_size;
-+              txd->txd1 = dma_addr + i * MTK_QDMA_PAGE_SIZE;
-               if (i < cnt - 1)
--                      eth->scratch_ring[i].txd2 = (eth->phy_scratch_ring +
--                              ((i + 1) * sizeof(struct mtk_tx_dma)));
--              eth->scratch_ring[i].txd3 = TX_DMA_SDL(MTK_QDMA_PAGE_SIZE);
-+                      txd->txd2 = eth->phy_scratch_ring +
-+                                  (i + 1) * soc->txrx.txd_size;
-+
-+              txd->txd3 = TX_DMA_PLEN0(MTK_QDMA_PAGE_SIZE);
-+              txd->txd4 = 0;
-       }
-       mtk_w32(eth, eth->phy_scratch_ring, MTK_QDMA_FQ_HEAD);
-@@ -2183,6 +2186,7 @@ static int mtk_dma_init(struct mtk_eth *
- static void mtk_dma_free(struct mtk_eth *eth)
- {
-+      const struct mtk_soc_data *soc = eth->soc;
-       int i;
-       for (i = 0; i < MTK_MAC_COUNT; i++)
-@@ -2190,9 +2194,8 @@ static void mtk_dma_free(struct mtk_eth
-                       netdev_reset_queue(eth->netdev[i]);
-       if (eth->scratch_ring) {
-               dma_free_coherent(eth->dma_dev,
--                                MTK_DMA_SIZE * sizeof(struct mtk_tx_dma),
--                                eth->scratch_ring,
--                                eth->phy_scratch_ring);
-+                                MTK_DMA_SIZE * soc->txrx.txd_size,
-+                                eth->scratch_ring, eth->phy_scratch_ring);
-               eth->scratch_ring = NULL;
-               eth->phy_scratch_ring = 0;
-       }
-@@ -3397,6 +3400,9 @@ static const struct mtk_soc_data mt2701_
-       .hw_features = MTK_HW_FEATURES,
-       .required_clks = MT7623_CLKS_BITMAP,
-       .required_pctl = true,
-+      .txrx = {
-+              .txd_size = sizeof(struct mtk_tx_dma),
-+      },
- };
- static const struct mtk_soc_data mt7621_data = {
-@@ -3405,6 +3411,9 @@ static const struct mtk_soc_data mt7621_
-       .required_clks = MT7621_CLKS_BITMAP,
-       .required_pctl = false,
-       .offload_version = 2,
-+      .txrx = {
-+              .txd_size = sizeof(struct mtk_tx_dma),
-+      },
- };
- static const struct mtk_soc_data mt7622_data = {
-@@ -3414,6 +3423,9 @@ static const struct mtk_soc_data mt7622_
-       .required_clks = MT7622_CLKS_BITMAP,
-       .required_pctl = false,
-       .offload_version = 2,
-+      .txrx = {
-+              .txd_size = sizeof(struct mtk_tx_dma),
-+      },
- };
- static const struct mtk_soc_data mt7623_data = {
-@@ -3422,6 +3434,9 @@ static const struct mtk_soc_data mt7623_
-       .required_clks = MT7623_CLKS_BITMAP,
-       .required_pctl = true,
-       .offload_version = 2,
-+      .txrx = {
-+              .txd_size = sizeof(struct mtk_tx_dma),
-+      },
- };
- static const struct mtk_soc_data mt7629_data = {
-@@ -3430,6 +3445,9 @@ static const struct mtk_soc_data mt7629_
-       .hw_features = MTK_HW_FEATURES,
-       .required_clks = MT7629_CLKS_BITMAP,
-       .required_pctl = false,
-+      .txrx = {
-+              .txd_size = sizeof(struct mtk_tx_dma),
-+      },
- };
- static const struct mtk_soc_data rt5350_data = {
-@@ -3437,6 +3455,9 @@ static const struct mtk_soc_data rt5350_
-       .hw_features = MTK_HW_FEATURES_MT7628,
-       .required_clks = MT7628_CLKS_BITMAP,
-       .required_pctl = false,
-+      .txrx = {
-+              .txd_size = sizeof(struct mtk_tx_dma),
-+      },
- };
- const struct of_device_id of_mtk_match[] = {
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-@@ -864,6 +864,7 @@ struct mtk_tx_dma_desc_info {
-  *                            the target SoC
-  * @required_pctl             A bool value to show whether the SoC requires
-  *                            the extra setup for those pins used by GMAC.
-+ * @txd_size                  Tx DMA descriptor size.
-  */
- struct mtk_soc_data {
-       u32             ana_rgc3;
-@@ -872,6 +873,9 @@ struct mtk_soc_data {
-       bool            required_pctl;
-       u8              offload_version;
-       netdev_features_t hw_features;
-+      struct {
-+              u32     txd_size;
-+      } txrx;
- };
- /* currently no SoC has more than 2 macs */
diff --git a/target/linux/generic/backport-5.15/702-v5.19-20-net-ethernet-mtk_eth_soc-rely-on-txd_size-in-mtk_tx_.patch b/target/linux/generic/backport-5.15/702-v5.19-20-net-ethernet-mtk_eth_soc-rely-on-txd_size-in-mtk_tx_.patch
deleted file mode 100644 (file)
index 0547d78..0000000
+++ /dev/null
@@ -1,78 +0,0 @@
-From: Lorenzo Bianconi <[email protected]>
-Date: Fri, 20 May 2022 20:11:29 +0200
-Subject: [PATCH] net: ethernet: mtk_eth_soc: rely on txd_size in
- mtk_tx_alloc/mtk_tx_clean
-
-This is a preliminary patch to add mt7986 ethernet support.
-
-Tested-by: Sam Shih <[email protected]>
-Signed-off-by: Lorenzo Bianconi <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-@@ -1635,8 +1635,10 @@ static int mtk_napi_rx(struct napi_struc
- static int mtk_tx_alloc(struct mtk_eth *eth)
- {
-+      const struct mtk_soc_data *soc = eth->soc;
-       struct mtk_tx_ring *ring = &eth->tx_ring;
--      int i, sz = sizeof(*ring->dma);
-+      int i, sz = soc->txrx.txd_size;
-+      struct mtk_tx_dma *txd;
-       ring->buf = kcalloc(MTK_DMA_SIZE, sizeof(*ring->buf),
-                              GFP_KERNEL);
-@@ -1652,8 +1654,10 @@ static int mtk_tx_alloc(struct mtk_eth *
-               int next = (i + 1) % MTK_DMA_SIZE;
-               u32 next_ptr = ring->phys + next * sz;
--              ring->dma[i].txd2 = next_ptr;
--              ring->dma[i].txd3 = TX_DMA_LS0 | TX_DMA_OWNER_CPU;
-+              txd = (void *)ring->dma + i * sz;
-+              txd->txd2 = next_ptr;
-+              txd->txd3 = TX_DMA_LS0 | TX_DMA_OWNER_CPU;
-+              txd->txd4 = 0;
-       }
-       /* On MT7688 (PDMA only) this driver uses the ring->dma structs
-@@ -1675,7 +1679,7 @@ static int mtk_tx_alloc(struct mtk_eth *
-       ring->dma_size = MTK_DMA_SIZE;
-       atomic_set(&ring->free_count, MTK_DMA_SIZE - 2);
-       ring->next_free = &ring->dma[0];
--      ring->last_free = &ring->dma[MTK_DMA_SIZE - 1];
-+      ring->last_free = (void *)txd;
-       ring->last_free_ptr = (u32)(ring->phys + ((MTK_DMA_SIZE - 1) * sz));
-       ring->thresh = MAX_SKB_FRAGS;
-@@ -1708,6 +1712,7 @@ no_tx_mem:
- static void mtk_tx_clean(struct mtk_eth *eth)
- {
-+      const struct mtk_soc_data *soc = eth->soc;
-       struct mtk_tx_ring *ring = &eth->tx_ring;
-       int i;
-@@ -1720,17 +1725,15 @@ static void mtk_tx_clean(struct mtk_eth
-       if (ring->dma) {
-               dma_free_coherent(eth->dma_dev,
--                                MTK_DMA_SIZE * sizeof(*ring->dma),
--                                ring->dma,
--                                ring->phys);
-+                                MTK_DMA_SIZE * soc->txrx.txd_size,
-+                                ring->dma, ring->phys);
-               ring->dma = NULL;
-       }
-       if (ring->dma_pdma) {
-               dma_free_coherent(eth->dma_dev,
--                                MTK_DMA_SIZE * sizeof(*ring->dma_pdma),
--                                ring->dma_pdma,
--                                ring->phys_pdma);
-+                                MTK_DMA_SIZE * soc->txrx.txd_size,
-+                                ring->dma_pdma, ring->phys_pdma);
-               ring->dma_pdma = NULL;
-       }
- }
diff --git a/target/linux/generic/backport-5.15/702-v5.19-21-net-ethernet-mtk_eth_soc-rely-on-txd_size-in-mtk_des.patch b/target/linux/generic/backport-5.15/702-v5.19-21-net-ethernet-mtk_eth_soc-rely-on-txd_size-in-mtk_des.patch
deleted file mode 100644 (file)
index b76d69c..0000000
+++ /dev/null
@@ -1,109 +0,0 @@
-From: Lorenzo Bianconi <[email protected]>
-Date: Fri, 20 May 2022 20:11:30 +0200
-Subject: [PATCH] net: ethernet: mtk_eth_soc: rely on txd_size in
- mtk_desc_to_tx_buf
-
-This is a preliminary patch to add mt7986 ethernet support.
-
-Tested-by: Sam Shih <[email protected]>
-Signed-off-by: Lorenzo Bianconi <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-@@ -901,10 +901,11 @@ static inline void *mtk_qdma_phys_to_vir
-       return ret + (desc - ring->phys);
- }
--static inline struct mtk_tx_buf *mtk_desc_to_tx_buf(struct mtk_tx_ring *ring,
--                                                  struct mtk_tx_dma *txd)
-+static struct mtk_tx_buf *mtk_desc_to_tx_buf(struct mtk_tx_ring *ring,
-+                                           struct mtk_tx_dma *txd,
-+                                           u32 txd_size)
- {
--      int idx = txd - ring->dma;
-+      int idx = ((void *)txd - (void *)ring->dma) / txd_size;
-       return &ring->buf[idx];
- }
-@@ -1026,6 +1027,7 @@ static int mtk_tx_map(struct sk_buff *sk
-       };
-       struct mtk_mac *mac = netdev_priv(dev);
-       struct mtk_eth *eth = mac->hw;
-+      const struct mtk_soc_data *soc = eth->soc;
-       struct mtk_tx_dma *itxd, *txd;
-       struct mtk_tx_dma *itxd_pdma, *txd_pdma;
-       struct mtk_tx_buf *itx_buf, *tx_buf;
-@@ -1037,7 +1039,7 @@ static int mtk_tx_map(struct sk_buff *sk
-       if (itxd == ring->last_free)
-               return -ENOMEM;
--      itx_buf = mtk_desc_to_tx_buf(ring, itxd);
-+      itx_buf = mtk_desc_to_tx_buf(ring, itxd, soc->txrx.txd_size);
-       memset(itx_buf, 0, sizeof(*itx_buf));
-       txd_info.addr = dma_map_single(eth->dma_dev, skb->data, txd_info.size,
-@@ -1065,7 +1067,7 @@ static int mtk_tx_map(struct sk_buff *sk
-               while (frag_size) {
-                       bool new_desc = true;
--                      if (MTK_HAS_CAPS(eth->soc->caps, MTK_QDMA) ||
-+                      if (MTK_HAS_CAPS(soc->caps, MTK_QDMA) ||
-                           (i & 0x1)) {
-                               txd = mtk_qdma_phys_to_virt(ring, txd->txd2);
-                               txd_pdma = qdma_to_pdma(ring, txd);
-@@ -1089,7 +1091,8 @@ static int mtk_tx_map(struct sk_buff *sk
-                       mtk_tx_set_dma_desc(dev, txd, &txd_info);
--                      tx_buf = mtk_desc_to_tx_buf(ring, txd);
-+                      tx_buf = mtk_desc_to_tx_buf(ring, txd,
-+                                                  soc->txrx.txd_size);
-                       if (new_desc)
-                               memset(tx_buf, 0, sizeof(*tx_buf));
-                       tx_buf->skb = (struct sk_buff *)MTK_DMA_DUMMY_DESC;
-@@ -1108,7 +1111,7 @@ static int mtk_tx_map(struct sk_buff *sk
-       /* store skb to cleanup */
-       itx_buf->skb = skb;
--      if (!MTK_HAS_CAPS(eth->soc->caps, MTK_QDMA)) {
-+      if (!MTK_HAS_CAPS(soc->caps, MTK_QDMA)) {
-               if (k & 0x1)
-                       txd_pdma->txd2 |= TX_DMA_LS0;
-               else
-@@ -1126,7 +1129,7 @@ static int mtk_tx_map(struct sk_buff *sk
-        */
-       wmb();
--      if (MTK_HAS_CAPS(eth->soc->caps, MTK_QDMA)) {
-+      if (MTK_HAS_CAPS(soc->caps, MTK_QDMA)) {
-               if (netif_xmit_stopped(netdev_get_tx_queue(dev, 0)) ||
-                   !netdev_xmit_more())
-                       mtk_w32(eth, txd->txd2, MTK_QTX_CTX_PTR);
-@@ -1140,13 +1143,13 @@ static int mtk_tx_map(struct sk_buff *sk
- err_dma:
-       do {
--              tx_buf = mtk_desc_to_tx_buf(ring, itxd);
-+              tx_buf = mtk_desc_to_tx_buf(ring, itxd, soc->txrx.txd_size);
-               /* unmap dma */
-               mtk_tx_unmap(eth, tx_buf, false);
-               itxd->txd3 = TX_DMA_LS0 | TX_DMA_OWNER_CPU;
--              if (!MTK_HAS_CAPS(eth->soc->caps, MTK_QDMA))
-+              if (!MTK_HAS_CAPS(soc->caps, MTK_QDMA))
-                       itxd_pdma->txd2 = TX_DMA_DESP2_DEF;
-               itxd = mtk_qdma_phys_to_virt(ring, itxd->txd2);
-@@ -1460,7 +1463,8 @@ static int mtk_poll_tx_qdma(struct mtk_e
-               if ((desc->txd3 & TX_DMA_OWNER_CPU) == 0)
-                       break;
--              tx_buf = mtk_desc_to_tx_buf(ring, desc);
-+              tx_buf = mtk_desc_to_tx_buf(ring, desc,
-+                                          eth->soc->txrx.txd_size);
-               if (tx_buf->flags & MTK_TX_FLAGS_FPORT1)
-                       mac = 1;
diff --git a/target/linux/generic/backport-5.15/702-v5.19-22-net-ethernet-mtk_eth_soc-rely-on-txd_size-in-txd_to_.patch b/target/linux/generic/backport-5.15/702-v5.19-22-net-ethernet-mtk_eth_soc-rely-on-txd_size-in-txd_to_.patch
deleted file mode 100644 (file)
index 99ee2c5..0000000
+++ /dev/null
@@ -1,39 +0,0 @@
-From: Lorenzo Bianconi <[email protected]>
-Date: Fri, 20 May 2022 20:11:31 +0200
-Subject: [PATCH] net: ethernet: mtk_eth_soc: rely on txd_size in txd_to_idx
-
-This is a preliminary patch to add mt7986 ethernet support.
-
-Tested-by: Sam Shih <[email protected]>
-Signed-off-by: Lorenzo Bianconi <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-@@ -916,9 +916,10 @@ static struct mtk_tx_dma *qdma_to_pdma(s
-       return ring->dma_pdma - ring->dma + dma;
- }
--static int txd_to_idx(struct mtk_tx_ring *ring, struct mtk_tx_dma *dma)
-+static int txd_to_idx(struct mtk_tx_ring *ring, struct mtk_tx_dma *dma,
-+                    u32 txd_size)
- {
--      return ((void *)dma - (void *)ring->dma) / sizeof(*dma);
-+      return ((void *)dma - (void *)ring->dma) / txd_size;
- }
- static void mtk_tx_unmap(struct mtk_eth *eth, struct mtk_tx_buf *tx_buf,
-@@ -1134,8 +1135,10 @@ static int mtk_tx_map(struct sk_buff *sk
-                   !netdev_xmit_more())
-                       mtk_w32(eth, txd->txd2, MTK_QTX_CTX_PTR);
-       } else {
--              int next_idx = NEXT_DESP_IDX(txd_to_idx(ring, txd),
--                                           ring->dma_size);
-+              int next_idx;
-+
-+              next_idx = NEXT_DESP_IDX(txd_to_idx(ring, txd, soc->txrx.txd_size),
-+                                       ring->dma_size);
-               mtk_w32(eth, next_idx, MT7628_TX_CTX_IDX0);
-       }
diff --git a/target/linux/generic/backport-5.15/702-v5.19-23-net-ethernet-mtk_eth_soc-add-rxd_size-to-mtk_soc_dat.patch b/target/linux/generic/backport-5.15/702-v5.19-23-net-ethernet-mtk_eth_soc-add-rxd_size-to-mtk_soc_dat.patch
deleted file mode 100644 (file)
index 27bf69b..0000000
+++ /dev/null
@@ -1,102 +0,0 @@
-From: Lorenzo Bianconi <[email protected]>
-Date: Fri, 20 May 2022 20:11:32 +0200
-Subject: [PATCH] net: ethernet: mtk_eth_soc: add rxd_size to mtk_soc_data
-
-Similar to tx counterpart, introduce rxd_size in mtk_soc_data data
-structure.
-This is a preliminary patch to add mt7986 ethernet support.
-
-Tested-by: Sam Shih <[email protected]>
-Signed-off-by: Lorenzo Bianconi <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-@@ -1786,7 +1786,7 @@ static int mtk_rx_alloc(struct mtk_eth *
-       }
-       ring->dma = dma_alloc_coherent(eth->dma_dev,
--                                     rx_dma_size * sizeof(*ring->dma),
-+                                     rx_dma_size * eth->soc->txrx.rxd_size,
-                                      &ring->phys, GFP_KERNEL);
-       if (!ring->dma)
-               return -ENOMEM;
-@@ -1844,9 +1844,8 @@ static void mtk_rx_clean(struct mtk_eth
-       if (ring->dma) {
-               dma_free_coherent(eth->dma_dev,
--                                ring->dma_size * sizeof(*ring->dma),
--                                ring->dma,
--                                ring->phys);
-+                                ring->dma_size * eth->soc->txrx.rxd_size,
-+                                ring->dma, ring->phys);
-               ring->dma = NULL;
-       }
- }
-@@ -3412,6 +3411,7 @@ static const struct mtk_soc_data mt2701_
-       .required_pctl = true,
-       .txrx = {
-               .txd_size = sizeof(struct mtk_tx_dma),
-+              .rxd_size = sizeof(struct mtk_rx_dma),
-       },
- };
-@@ -3423,6 +3423,7 @@ static const struct mtk_soc_data mt7621_
-       .offload_version = 2,
-       .txrx = {
-               .txd_size = sizeof(struct mtk_tx_dma),
-+              .rxd_size = sizeof(struct mtk_rx_dma),
-       },
- };
-@@ -3435,6 +3436,7 @@ static const struct mtk_soc_data mt7622_
-       .offload_version = 2,
-       .txrx = {
-               .txd_size = sizeof(struct mtk_tx_dma),
-+              .rxd_size = sizeof(struct mtk_rx_dma),
-       },
- };
-@@ -3446,6 +3448,7 @@ static const struct mtk_soc_data mt7623_
-       .offload_version = 2,
-       .txrx = {
-               .txd_size = sizeof(struct mtk_tx_dma),
-+              .rxd_size = sizeof(struct mtk_rx_dma),
-       },
- };
-@@ -3457,6 +3460,7 @@ static const struct mtk_soc_data mt7629_
-       .required_pctl = false,
-       .txrx = {
-               .txd_size = sizeof(struct mtk_tx_dma),
-+              .rxd_size = sizeof(struct mtk_rx_dma),
-       },
- };
-@@ -3467,6 +3471,7 @@ static const struct mtk_soc_data rt5350_
-       .required_pctl = false,
-       .txrx = {
-               .txd_size = sizeof(struct mtk_tx_dma),
-+              .rxd_size = sizeof(struct mtk_rx_dma),
-       },
- };
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-@@ -865,6 +865,7 @@ struct mtk_tx_dma_desc_info {
-  * @required_pctl             A bool value to show whether the SoC requires
-  *                            the extra setup for those pins used by GMAC.
-  * @txd_size                  Tx DMA descriptor size.
-+ * @rxd_size                  Rx DMA descriptor size.
-  */
- struct mtk_soc_data {
-       u32             ana_rgc3;
-@@ -875,6 +876,7 @@ struct mtk_soc_data {
-       netdev_features_t hw_features;
-       struct {
-               u32     txd_size;
-+              u32     rxd_size;
-       } txrx;
- };
diff --git a/target/linux/generic/backport-5.15/702-v5.19-24-net-ethernet-mtk_eth_soc-rely-on-txd_size-field-in-m.patch b/target/linux/generic/backport-5.15/702-v5.19-24-net-ethernet-mtk_eth_soc-rely-on-txd_size-field-in-m.patch
deleted file mode 100644 (file)
index 393faf6..0000000
+++ /dev/null
@@ -1,46 +0,0 @@
-From: Lorenzo Bianconi <[email protected]>
-Date: Fri, 20 May 2022 20:11:33 +0200
-Subject: [PATCH] net: ethernet: mtk_eth_soc: rely on txd_size field in
- mtk_poll_tx/mtk_poll_rx
-
-This is a preliminary to ad mt7986 ethernet support.
-
-Tested-by: Sam Shih <[email protected]>
-Signed-off-by: Lorenzo Bianconi <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-@@ -1275,9 +1275,12 @@ static struct mtk_rx_ring *mtk_get_rx_ri
-               return &eth->rx_ring[0];
-       for (i = 0; i < MTK_MAX_RX_RING_NUM; i++) {
-+              struct mtk_rx_dma *rxd;
-+
-               ring = &eth->rx_ring[i];
-               idx = NEXT_DESP_IDX(ring->calc_idx, ring->dma_size);
--              if (ring->dma[idx].rxd2 & RX_DMA_DONE) {
-+              rxd = (void *)ring->dma + idx * eth->soc->txrx.rxd_size;
-+              if (rxd->rxd2 & RX_DMA_DONE) {
-                       ring->calc_idx_update = true;
-                       return ring;
-               }
-@@ -1328,7 +1331,7 @@ static int mtk_poll_rx(struct napi_struc
-                       goto rx_done;
-               idx = NEXT_DESP_IDX(ring->calc_idx, ring->dma_size);
--              rxd = &ring->dma[idx];
-+              rxd = (void *)ring->dma + idx * eth->soc->txrx.rxd_size;
-               data = ring->data[idx];
-               if (!mtk_rx_get_desc(&trxd, rxd))
-@@ -1520,7 +1523,7 @@ static int mtk_poll_tx_pdma(struct mtk_e
-               mtk_tx_unmap(eth, tx_buf, true);
--              desc = &ring->dma[cpu];
-+              desc = (void *)ring->dma + cpu * eth->soc->txrx.txd_size;
-               ring->last_free = desc;
-               atomic_inc(&ring->free_count);
diff --git a/target/linux/generic/backport-5.15/702-v5.19-25-net-ethernet-mtk_eth_soc-rely-on-rxd_size-field-in-m.patch b/target/linux/generic/backport-5.15/702-v5.19-25-net-ethernet-mtk_eth_soc-rely-on-rxd_size-field-in-m.patch
deleted file mode 100644 (file)
index fdfa8b9..0000000
+++ /dev/null
@@ -1,68 +0,0 @@
-From: Lorenzo Bianconi <[email protected]>
-Date: Fri, 20 May 2022 20:11:34 +0200
-Subject: [PATCH] net: ethernet: mtk_eth_soc: rely on rxd_size field in
- mtk_rx_alloc/mtk_rx_clean
-
-Remove mtk_rx_dma structure layout dependency in mtk_rx_alloc/mtk_rx_clean.
-Initialize to 0 rxd3 and rxd4 in mtk_rx_alloc.
-This is a preliminary patch to add mt7986 ethernet support.
-
-Tested-by: Sam Shih <[email protected]>
-Signed-off-by: Lorenzo Bianconi <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-@@ -1795,18 +1795,25 @@ static int mtk_rx_alloc(struct mtk_eth *
-               return -ENOMEM;
-       for (i = 0; i < rx_dma_size; i++) {
-+              struct mtk_rx_dma *rxd;
-+
-               dma_addr_t dma_addr = dma_map_single(eth->dma_dev,
-                               ring->data[i] + NET_SKB_PAD + eth->ip_align,
-                               ring->buf_size,
-                               DMA_FROM_DEVICE);
-               if (unlikely(dma_mapping_error(eth->dma_dev, dma_addr)))
-                       return -ENOMEM;
--              ring->dma[i].rxd1 = (unsigned int)dma_addr;
-+
-+              rxd = (void *)ring->dma + i * eth->soc->txrx.rxd_size;
-+              rxd->rxd1 = (unsigned int)dma_addr;
-               if (MTK_HAS_CAPS(eth->soc->caps, MTK_SOC_MT7628))
--                      ring->dma[i].rxd2 = RX_DMA_LSO;
-+                      rxd->rxd2 = RX_DMA_LSO;
-               else
--                      ring->dma[i].rxd2 = RX_DMA_PLEN0(ring->buf_size);
-+                      rxd->rxd2 = RX_DMA_PLEN0(ring->buf_size);
-+
-+              rxd->rxd3 = 0;
-+              rxd->rxd4 = 0;
-       }
-       ring->dma_size = rx_dma_size;
-       ring->calc_idx_update = false;
-@@ -1831,14 +1838,17 @@ static void mtk_rx_clean(struct mtk_eth
-       if (ring->data && ring->dma) {
-               for (i = 0; i < ring->dma_size; i++) {
-+                      struct mtk_rx_dma *rxd;
-+
-                       if (!ring->data[i])
-                               continue;
--                      if (!ring->dma[i].rxd1)
-+
-+                      rxd = (void *)ring->dma + i * eth->soc->txrx.rxd_size;
-+                      if (!rxd->rxd1)
-                               continue;
--                      dma_unmap_single(eth->dma_dev,
--                                       ring->dma[i].rxd1,
--                                       ring->buf_size,
--                                       DMA_FROM_DEVICE);
-+
-+                      dma_unmap_single(eth->dma_dev, rxd->rxd1,
-+                                       ring->buf_size, DMA_FROM_DEVICE);
-                       skb_free_frag(ring->data[i]);
-               }
-               kfree(ring->data);
diff --git a/target/linux/generic/backport-5.15/702-v5.19-26-net-ethernet-mtk_eth_soc-introduce-device-register-m.patch b/target/linux/generic/backport-5.15/702-v5.19-26-net-ethernet-mtk_eth_soc-introduce-device-register-m.patch
deleted file mode 100644 (file)
index c4c337a..0000000
+++ /dev/null
@@ -1,814 +0,0 @@
-From: Lorenzo Bianconi <[email protected]>
-Date: Fri, 20 May 2022 20:11:35 +0200
-Subject: [PATCH] net: ethernet: mtk_eth_soc: introduce device register map
-
-Introduce reg_map structure to add the capability to support different
-register definitions. Move register definitions in mtk_regmap structure.
-This is a preliminary patch to introduce mt7986 ethernet support.
-
-Tested-by: Sam Shih <[email protected]>
-Signed-off-by: Lorenzo Bianconi <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-@@ -34,6 +34,59 @@ MODULE_PARM_DESC(msg_level, "Message lev
- #define MTK_ETHTOOL_STAT(x) { #x, \
-                             offsetof(struct mtk_hw_stats, x) / sizeof(u64) }
-+static const struct mtk_reg_map mtk_reg_map = {
-+      .tx_irq_mask            = 0x1a1c,
-+      .tx_irq_status          = 0x1a18,
-+      .pdma = {
-+              .rx_ptr         = 0x0900,
-+              .rx_cnt_cfg     = 0x0904,
-+              .pcrx_ptr       = 0x0908,
-+              .glo_cfg        = 0x0a04,
-+              .rst_idx        = 0x0a08,
-+              .delay_irq      = 0x0a0c,
-+              .irq_status     = 0x0a20,
-+              .irq_mask       = 0x0a28,
-+              .int_grp        = 0x0a50,
-+      },
-+      .qdma = {
-+              .qtx_cfg        = 0x1800,
-+              .rx_ptr         = 0x1900,
-+              .rx_cnt_cfg     = 0x1904,
-+              .qcrx_ptr       = 0x1908,
-+              .glo_cfg        = 0x1a04,
-+              .rst_idx        = 0x1a08,
-+              .delay_irq      = 0x1a0c,
-+              .fc_th          = 0x1a10,
-+              .int_grp        = 0x1a20,
-+              .hred           = 0x1a44,
-+              .ctx_ptr        = 0x1b00,
-+              .dtx_ptr        = 0x1b04,
-+              .crx_ptr        = 0x1b10,
-+              .drx_ptr        = 0x1b14,
-+              .fq_head        = 0x1b20,
-+              .fq_tail        = 0x1b24,
-+              .fq_count       = 0x1b28,
-+              .fq_blen        = 0x1b2c,
-+      },
-+      .gdm1_cnt               = 0x2400,
-+};
-+
-+static const struct mtk_reg_map mt7628_reg_map = {
-+      .tx_irq_mask            = 0x0a28,
-+      .tx_irq_status          = 0x0a20,
-+      .pdma = {
-+              .rx_ptr         = 0x0900,
-+              .rx_cnt_cfg     = 0x0904,
-+              .pcrx_ptr       = 0x0908,
-+              .glo_cfg        = 0x0a04,
-+              .rst_idx        = 0x0a08,
-+              .delay_irq      = 0x0a0c,
-+              .irq_status     = 0x0a20,
-+              .irq_mask       = 0x0a28,
-+              .int_grp        = 0x0a50,
-+      },
-+};
-+
- /* strings used by ethtool */
- static const struct mtk_ethtool_stats {
-       char str[ETH_GSTRING_LEN];
-@@ -629,8 +682,8 @@ static inline void mtk_tx_irq_disable(st
-       u32 val;
-       spin_lock_irqsave(&eth->tx_irq_lock, flags);
--      val = mtk_r32(eth, eth->tx_int_mask_reg);
--      mtk_w32(eth, val & ~mask, eth->tx_int_mask_reg);
-+      val = mtk_r32(eth, eth->soc->reg_map->tx_irq_mask);
-+      mtk_w32(eth, val & ~mask, eth->soc->reg_map->tx_irq_mask);
-       spin_unlock_irqrestore(&eth->tx_irq_lock, flags);
- }
-@@ -640,8 +693,8 @@ static inline void mtk_tx_irq_enable(str
-       u32 val;
-       spin_lock_irqsave(&eth->tx_irq_lock, flags);
--      val = mtk_r32(eth, eth->tx_int_mask_reg);
--      mtk_w32(eth, val | mask, eth->tx_int_mask_reg);
-+      val = mtk_r32(eth, eth->soc->reg_map->tx_irq_mask);
-+      mtk_w32(eth, val | mask, eth->soc->reg_map->tx_irq_mask);
-       spin_unlock_irqrestore(&eth->tx_irq_lock, flags);
- }
-@@ -651,8 +704,8 @@ static inline void mtk_rx_irq_disable(st
-       u32 val;
-       spin_lock_irqsave(&eth->rx_irq_lock, flags);
--      val = mtk_r32(eth, MTK_PDMA_INT_MASK);
--      mtk_w32(eth, val & ~mask, MTK_PDMA_INT_MASK);
-+      val = mtk_r32(eth, eth->soc->reg_map->pdma.irq_mask);
-+      mtk_w32(eth, val & ~mask, eth->soc->reg_map->pdma.irq_mask);
-       spin_unlock_irqrestore(&eth->rx_irq_lock, flags);
- }
-@@ -662,8 +715,8 @@ static inline void mtk_rx_irq_enable(str
-       u32 val;
-       spin_lock_irqsave(&eth->rx_irq_lock, flags);
--      val = mtk_r32(eth, MTK_PDMA_INT_MASK);
--      mtk_w32(eth, val | mask, MTK_PDMA_INT_MASK);
-+      val = mtk_r32(eth, eth->soc->reg_map->pdma.irq_mask);
-+      mtk_w32(eth, val | mask, eth->soc->reg_map->pdma.irq_mask);
-       spin_unlock_irqrestore(&eth->rx_irq_lock, flags);
- }
-@@ -714,39 +767,39 @@ void mtk_stats_update_mac(struct mtk_mac
-               hw_stats->rx_checksum_errors +=
-                       mtk_r32(mac->hw, MT7628_SDM_CS_ERR);
-       } else {
-+              const struct mtk_reg_map *reg_map = eth->soc->reg_map;
-               unsigned int offs = hw_stats->reg_offset;
-               u64 stats;
--              hw_stats->rx_bytes += mtk_r32(mac->hw,
--                                            MTK_GDM1_RX_GBCNT_L + offs);
--              stats = mtk_r32(mac->hw, MTK_GDM1_RX_GBCNT_H + offs);
-+              hw_stats->rx_bytes += mtk_r32(mac->hw, reg_map->gdm1_cnt + offs);
-+              stats = mtk_r32(mac->hw, reg_map->gdm1_cnt + 0x4 + offs);
-               if (stats)
-                       hw_stats->rx_bytes += (stats << 32);
-               hw_stats->rx_packets +=
--                      mtk_r32(mac->hw, MTK_GDM1_RX_GPCNT + offs);
-+                      mtk_r32(mac->hw, reg_map->gdm1_cnt + 0x8 + offs);
-               hw_stats->rx_overflow +=
--                      mtk_r32(mac->hw, MTK_GDM1_RX_OERCNT + offs);
-+                      mtk_r32(mac->hw, reg_map->gdm1_cnt + 0x10 + offs);
-               hw_stats->rx_fcs_errors +=
--                      mtk_r32(mac->hw, MTK_GDM1_RX_FERCNT + offs);
-+                      mtk_r32(mac->hw, reg_map->gdm1_cnt + 0x14 + offs);
-               hw_stats->rx_short_errors +=
--                      mtk_r32(mac->hw, MTK_GDM1_RX_SERCNT + offs);
-+                      mtk_r32(mac->hw, reg_map->gdm1_cnt + 0x18 + offs);
-               hw_stats->rx_long_errors +=
--                      mtk_r32(mac->hw, MTK_GDM1_RX_LENCNT + offs);
-+                      mtk_r32(mac->hw, reg_map->gdm1_cnt + 0x1c + offs);
-               hw_stats->rx_checksum_errors +=
--                      mtk_r32(mac->hw, MTK_GDM1_RX_CERCNT + offs);
-+                      mtk_r32(mac->hw, reg_map->gdm1_cnt + 0x20 + offs);
-               hw_stats->rx_flow_control_packets +=
--                      mtk_r32(mac->hw, MTK_GDM1_RX_FCCNT + offs);
-+                      mtk_r32(mac->hw, reg_map->gdm1_cnt + 0x24 + offs);
-               hw_stats->tx_skip +=
--                      mtk_r32(mac->hw, MTK_GDM1_TX_SKIPCNT + offs);
-+                      mtk_r32(mac->hw, reg_map->gdm1_cnt + 0x28 + offs);
-               hw_stats->tx_collisions +=
--                      mtk_r32(mac->hw, MTK_GDM1_TX_COLCNT + offs);
-+                      mtk_r32(mac->hw, reg_map->gdm1_cnt + 0x2c + offs);
-               hw_stats->tx_bytes +=
--                      mtk_r32(mac->hw, MTK_GDM1_TX_GBCNT_L + offs);
--              stats =  mtk_r32(mac->hw, MTK_GDM1_TX_GBCNT_H + offs);
-+                      mtk_r32(mac->hw, reg_map->gdm1_cnt + 0x30 + offs);
-+              stats =  mtk_r32(mac->hw, reg_map->gdm1_cnt + 0x34 + offs);
-               if (stats)
-                       hw_stats->tx_bytes += (stats << 32);
-               hw_stats->tx_packets +=
--                      mtk_r32(mac->hw, MTK_GDM1_TX_GPCNT + offs);
-+                      mtk_r32(mac->hw, reg_map->gdm1_cnt + 0x38 + offs);
-       }
-       u64_stats_update_end(&hw_stats->syncp);
-@@ -886,10 +939,10 @@ static int mtk_init_fq_dma(struct mtk_et
-               txd->txd4 = 0;
-       }
--      mtk_w32(eth, eth->phy_scratch_ring, MTK_QDMA_FQ_HEAD);
--      mtk_w32(eth, phy_ring_tail, MTK_QDMA_FQ_TAIL);
--      mtk_w32(eth, (cnt << 16) | cnt, MTK_QDMA_FQ_CNT);
--      mtk_w32(eth, MTK_QDMA_PAGE_SIZE << 16, MTK_QDMA_FQ_BLEN);
-+      mtk_w32(eth, eth->phy_scratch_ring, soc->reg_map->qdma.fq_head);
-+      mtk_w32(eth, phy_ring_tail, soc->reg_map->qdma.fq_tail);
-+      mtk_w32(eth, (cnt << 16) | cnt, soc->reg_map->qdma.fq_count);
-+      mtk_w32(eth, MTK_QDMA_PAGE_SIZE << 16, soc->reg_map->qdma.fq_blen);
-       return 0;
- }
-@@ -1133,7 +1186,7 @@ static int mtk_tx_map(struct sk_buff *sk
-       if (MTK_HAS_CAPS(soc->caps, MTK_QDMA)) {
-               if (netif_xmit_stopped(netdev_get_tx_queue(dev, 0)) ||
-                   !netdev_xmit_more())
--                      mtk_w32(eth, txd->txd2, MTK_QTX_CTX_PTR);
-+                      mtk_w32(eth, txd->txd2, soc->reg_map->qdma.ctx_ptr);
-       } else {
-               int next_idx;
-@@ -1450,6 +1503,7 @@ rx_done:
- static int mtk_poll_tx_qdma(struct mtk_eth *eth, int budget,
-                           unsigned int *done, unsigned int *bytes)
- {
-+      const struct mtk_reg_map *reg_map = eth->soc->reg_map;
-       struct mtk_tx_ring *ring = &eth->tx_ring;
-       struct mtk_tx_dma *desc;
-       struct sk_buff *skb;
-@@ -1457,7 +1511,7 @@ static int mtk_poll_tx_qdma(struct mtk_e
-       u32 cpu, dma;
-       cpu = ring->last_free_ptr;
--      dma = mtk_r32(eth, MTK_QTX_DRX_PTR);
-+      dma = mtk_r32(eth, reg_map->qdma.drx_ptr);
-       desc = mtk_qdma_phys_to_virt(ring, cpu);
-@@ -1492,7 +1546,7 @@ static int mtk_poll_tx_qdma(struct mtk_e
-       }
-       ring->last_free_ptr = cpu;
--      mtk_w32(eth, cpu, MTK_QTX_CRX_PTR);
-+      mtk_w32(eth, cpu, reg_map->qdma.crx_ptr);
-       return budget;
- }
-@@ -1585,24 +1639,25 @@ static void mtk_handle_status_irq(struct
- static int mtk_napi_tx(struct napi_struct *napi, int budget)
- {
-       struct mtk_eth *eth = container_of(napi, struct mtk_eth, tx_napi);
-+      const struct mtk_reg_map *reg_map = eth->soc->reg_map;
-       int tx_done = 0;
-       if (MTK_HAS_CAPS(eth->soc->caps, MTK_QDMA))
-               mtk_handle_status_irq(eth);
--      mtk_w32(eth, MTK_TX_DONE_INT, eth->tx_int_status_reg);
-+      mtk_w32(eth, MTK_TX_DONE_INT, reg_map->tx_irq_status);
-       tx_done = mtk_poll_tx(eth, budget);
-       if (unlikely(netif_msg_intr(eth))) {
-               dev_info(eth->dev,
-                        "done tx %d, intr 0x%08x/0x%x\n", tx_done,
--                       mtk_r32(eth, eth->tx_int_status_reg),
--                       mtk_r32(eth, eth->tx_int_mask_reg));
-+                       mtk_r32(eth, reg_map->tx_irq_status),
-+                       mtk_r32(eth, reg_map->tx_irq_mask));
-       }
-       if (tx_done == budget)
-               return budget;
--      if (mtk_r32(eth, eth->tx_int_status_reg) & MTK_TX_DONE_INT)
-+      if (mtk_r32(eth, reg_map->tx_irq_status) & MTK_TX_DONE_INT)
-               return budget;
-       if (napi_complete_done(napi, tx_done))
-@@ -1614,6 +1669,7 @@ static int mtk_napi_tx(struct napi_struc
- static int mtk_napi_rx(struct napi_struct *napi, int budget)
- {
-       struct mtk_eth *eth = container_of(napi, struct mtk_eth, rx_napi);
-+      const struct mtk_reg_map *reg_map = eth->soc->reg_map;
-       int rx_done_total = 0;
-       mtk_handle_status_irq(eth);
-@@ -1621,21 +1677,21 @@ static int mtk_napi_rx(struct napi_struc
-       do {
-               int rx_done;
--              mtk_w32(eth, MTK_RX_DONE_INT, MTK_PDMA_INT_STATUS);
-+              mtk_w32(eth, MTK_RX_DONE_INT, reg_map->pdma.irq_status);
-               rx_done = mtk_poll_rx(napi, budget - rx_done_total, eth);
-               rx_done_total += rx_done;
-               if (unlikely(netif_msg_intr(eth))) {
-                       dev_info(eth->dev,
-                                "done rx %d, intr 0x%08x/0x%x\n", rx_done,
--                               mtk_r32(eth, MTK_PDMA_INT_STATUS),
--                               mtk_r32(eth, MTK_PDMA_INT_MASK));
-+                               mtk_r32(eth, reg_map->pdma.irq_status),
-+                               mtk_r32(eth, reg_map->pdma.irq_mask));
-               }
-               if (rx_done_total == budget)
-                       return budget;
--      } while (mtk_r32(eth, MTK_PDMA_INT_STATUS) & MTK_RX_DONE_INT);
-+      } while (mtk_r32(eth, reg_map->pdma.irq_status) & MTK_RX_DONE_INT);
-       if (napi_complete_done(napi, rx_done_total))
-               mtk_rx_irq_enable(eth, MTK_RX_DONE_INT);
-@@ -1698,20 +1754,20 @@ static int mtk_tx_alloc(struct mtk_eth *
-        */
-       wmb();
--      if (MTK_HAS_CAPS(eth->soc->caps, MTK_QDMA)) {
--              mtk_w32(eth, ring->phys, MTK_QTX_CTX_PTR);
--              mtk_w32(eth, ring->phys, MTK_QTX_DTX_PTR);
-+      if (MTK_HAS_CAPS(soc->caps, MTK_QDMA)) {
-+              mtk_w32(eth, ring->phys, soc->reg_map->qdma.ctx_ptr);
-+              mtk_w32(eth, ring->phys, soc->reg_map->qdma.dtx_ptr);
-               mtk_w32(eth,
-                       ring->phys + ((MTK_DMA_SIZE - 1) * sz),
--                      MTK_QTX_CRX_PTR);
--              mtk_w32(eth, ring->last_free_ptr, MTK_QTX_DRX_PTR);
-+                      soc->reg_map->qdma.crx_ptr);
-+              mtk_w32(eth, ring->last_free_ptr, soc->reg_map->qdma.drx_ptr);
-               mtk_w32(eth, (QDMA_RES_THRES << 8) | QDMA_RES_THRES,
--                      MTK_QTX_CFG(0));
-+                      soc->reg_map->qdma.qtx_cfg);
-       } else {
-               mtk_w32(eth, ring->phys_pdma, MT7628_TX_BASE_PTR0);
-               mtk_w32(eth, MTK_DMA_SIZE, MT7628_TX_MAX_CNT0);
-               mtk_w32(eth, 0, MT7628_TX_CTX_IDX0);
--              mtk_w32(eth, MT7628_PST_DTX_IDX0, MTK_PDMA_RST_IDX);
-+              mtk_w32(eth, MT7628_PST_DTX_IDX0, soc->reg_map->pdma.rst_idx);
-       }
-       return 0;
-@@ -1750,6 +1806,7 @@ static void mtk_tx_clean(struct mtk_eth
- static int mtk_rx_alloc(struct mtk_eth *eth, int ring_no, int rx_flag)
- {
-+      const struct mtk_reg_map *reg_map = eth->soc->reg_map;
-       struct mtk_rx_ring *ring;
-       int rx_data_len, rx_dma_size;
-       int i;
-@@ -1818,16 +1875,18 @@ static int mtk_rx_alloc(struct mtk_eth *
-       ring->dma_size = rx_dma_size;
-       ring->calc_idx_update = false;
-       ring->calc_idx = rx_dma_size - 1;
--      ring->crx_idx_reg = MTK_PRX_CRX_IDX_CFG(ring_no);
-+      ring->crx_idx_reg = reg_map->pdma.pcrx_ptr + ring_no * MTK_QRX_OFFSET;
-       /* make sure that all changes to the dma ring are flushed before we
-        * continue
-        */
-       wmb();
--      mtk_w32(eth, ring->phys, MTK_PRX_BASE_PTR_CFG(ring_no) + offset);
--      mtk_w32(eth, rx_dma_size, MTK_PRX_MAX_CNT_CFG(ring_no) + offset);
-+      mtk_w32(eth, ring->phys,
-+              reg_map->pdma.rx_ptr + ring_no * MTK_QRX_OFFSET + offset);
-+      mtk_w32(eth, rx_dma_size,
-+              reg_map->pdma.rx_cnt_cfg + ring_no * MTK_QRX_OFFSET + offset);
-       mtk_w32(eth, ring->calc_idx, ring->crx_idx_reg + offset);
--      mtk_w32(eth, MTK_PST_DRX_IDX_CFG(ring_no), MTK_PDMA_RST_IDX + offset);
-+      mtk_w32(eth, MTK_PST_DRX_IDX_CFG(ring_no), reg_map->pdma.rst_idx + offset);
-       return 0;
- }
-@@ -2139,9 +2198,9 @@ static int mtk_dma_busy_wait(struct mtk_
-       u32 val;
-       if (MTK_HAS_CAPS(eth->soc->caps, MTK_QDMA))
--              reg = MTK_QDMA_GLO_CFG;
-+              reg = eth->soc->reg_map->qdma.glo_cfg;
-       else
--              reg = MTK_PDMA_GLO_CFG;
-+              reg = eth->soc->reg_map->pdma.glo_cfg;
-       ret = readx_poll_timeout_atomic(__raw_readl, eth->base + reg, val,
-                                       !(val & (MTK_RX_DMA_BUSY | MTK_TX_DMA_BUSY)),
-@@ -2199,8 +2258,8 @@ static int mtk_dma_init(struct mtk_eth *
-                * automatically
-                */
-               mtk_w32(eth, FC_THRES_DROP_MODE | FC_THRES_DROP_EN |
--                      FC_THRES_MIN, MTK_QDMA_FC_THRES);
--              mtk_w32(eth, 0x0, MTK_QDMA_HRED2);
-+                      FC_THRES_MIN, eth->soc->reg_map->qdma.fc_th);
-+              mtk_w32(eth, 0x0, eth->soc->reg_map->qdma.hred);
-       }
-       return 0;
-@@ -2274,13 +2333,14 @@ static irqreturn_t mtk_handle_irq_tx(int
- static irqreturn_t mtk_handle_irq(int irq, void *_eth)
- {
-       struct mtk_eth *eth = _eth;
-+      const struct mtk_reg_map *reg_map = eth->soc->reg_map;
--      if (mtk_r32(eth, MTK_PDMA_INT_MASK) & MTK_RX_DONE_INT) {
--              if (mtk_r32(eth, MTK_PDMA_INT_STATUS) & MTK_RX_DONE_INT)
-+      if (mtk_r32(eth, reg_map->pdma.irq_mask) & MTK_RX_DONE_INT) {
-+              if (mtk_r32(eth, reg_map->pdma.irq_status) & MTK_RX_DONE_INT)
-                       mtk_handle_irq_rx(irq, _eth);
-       }
--      if (mtk_r32(eth, eth->tx_int_mask_reg) & MTK_TX_DONE_INT) {
--              if (mtk_r32(eth, eth->tx_int_status_reg) & MTK_TX_DONE_INT)
-+      if (mtk_r32(eth, reg_map->tx_irq_mask) & MTK_TX_DONE_INT) {
-+              if (mtk_r32(eth, reg_map->tx_irq_status) & MTK_TX_DONE_INT)
-                       mtk_handle_irq_tx(irq, _eth);
-       }
-@@ -2304,6 +2364,7 @@ static void mtk_poll_controller(struct n
- static int mtk_start_dma(struct mtk_eth *eth)
- {
-       u32 rx_2b_offset = (NET_IP_ALIGN == 2) ? MTK_RX_2B_OFFSET : 0;
-+      const struct mtk_reg_map *reg_map = eth->soc->reg_map;
-       int err;
-       err = mtk_dma_init(eth);
-@@ -2318,16 +2379,15 @@ static int mtk_start_dma(struct mtk_eth
-                       MTK_TX_BT_32DWORDS | MTK_NDP_CO_PRO |
-                       MTK_RX_DMA_EN | MTK_RX_2B_OFFSET |
-                       MTK_RX_BT_32DWORDS,
--                      MTK_QDMA_GLO_CFG);
--
-+                      reg_map->qdma.glo_cfg);
-               mtk_w32(eth,
-                       MTK_RX_DMA_EN | rx_2b_offset |
-                       MTK_RX_BT_32DWORDS | MTK_MULTI_EN,
--                      MTK_PDMA_GLO_CFG);
-+                      reg_map->pdma.glo_cfg);
-       } else {
-               mtk_w32(eth, MTK_TX_WB_DDONE | MTK_TX_DMA_EN | MTK_RX_DMA_EN |
-                       MTK_MULTI_EN | MTK_PDMA_SIZE_8DWORDS,
--                      MTK_PDMA_GLO_CFG);
-+                      reg_map->pdma.glo_cfg);
-       }
-       return 0;
-@@ -2453,8 +2513,8 @@ static int mtk_stop(struct net_device *d
-       cancel_work_sync(&eth->tx_dim.work);
-       if (MTK_HAS_CAPS(eth->soc->caps, MTK_QDMA))
--              mtk_stop_dma(eth, MTK_QDMA_GLO_CFG);
--      mtk_stop_dma(eth, MTK_PDMA_GLO_CFG);
-+              mtk_stop_dma(eth, eth->soc->reg_map->qdma.glo_cfg);
-+      mtk_stop_dma(eth, eth->soc->reg_map->pdma.glo_cfg);
-       mtk_dma_free(eth);
-@@ -2508,6 +2568,7 @@ static void mtk_dim_rx(struct work_struc
- {
-       struct dim *dim = container_of(work, struct dim, work);
-       struct mtk_eth *eth = container_of(dim, struct mtk_eth, rx_dim);
-+      const struct mtk_reg_map *reg_map = eth->soc->reg_map;
-       struct dim_cq_moder cur_profile;
-       u32 val, cur;
-@@ -2515,7 +2576,7 @@ static void mtk_dim_rx(struct work_struc
-                                               dim->profile_ix);
-       spin_lock_bh(&eth->dim_lock);
--      val = mtk_r32(eth, MTK_PDMA_DELAY_INT);
-+      val = mtk_r32(eth, reg_map->pdma.delay_irq);
-       val &= MTK_PDMA_DELAY_TX_MASK;
-       val |= MTK_PDMA_DELAY_RX_EN;
-@@ -2525,9 +2586,9 @@ static void mtk_dim_rx(struct work_struc
-       cur = min_t(u32, cur_profile.pkts, MTK_PDMA_DELAY_PINT_MASK);
-       val |= cur << MTK_PDMA_DELAY_RX_PINT_SHIFT;
--      mtk_w32(eth, val, MTK_PDMA_DELAY_INT);
-+      mtk_w32(eth, val, reg_map->pdma.delay_irq);
-       if (MTK_HAS_CAPS(eth->soc->caps, MTK_QDMA))
--              mtk_w32(eth, val, MTK_QDMA_DELAY_INT);
-+              mtk_w32(eth, val, reg_map->qdma.delay_irq);
-       spin_unlock_bh(&eth->dim_lock);
-@@ -2538,6 +2599,7 @@ static void mtk_dim_tx(struct work_struc
- {
-       struct dim *dim = container_of(work, struct dim, work);
-       struct mtk_eth *eth = container_of(dim, struct mtk_eth, tx_dim);
-+      const struct mtk_reg_map *reg_map = eth->soc->reg_map;
-       struct dim_cq_moder cur_profile;
-       u32 val, cur;
-@@ -2545,7 +2607,7 @@ static void mtk_dim_tx(struct work_struc
-                                               dim->profile_ix);
-       spin_lock_bh(&eth->dim_lock);
--      val = mtk_r32(eth, MTK_PDMA_DELAY_INT);
-+      val = mtk_r32(eth, reg_map->pdma.delay_irq);
-       val &= MTK_PDMA_DELAY_RX_MASK;
-       val |= MTK_PDMA_DELAY_TX_EN;
-@@ -2555,9 +2617,9 @@ static void mtk_dim_tx(struct work_struc
-       cur = min_t(u32, cur_profile.pkts, MTK_PDMA_DELAY_PINT_MASK);
-       val |= cur << MTK_PDMA_DELAY_TX_PINT_SHIFT;
--      mtk_w32(eth, val, MTK_PDMA_DELAY_INT);
-+      mtk_w32(eth, val, reg_map->pdma.delay_irq);
-       if (MTK_HAS_CAPS(eth->soc->caps, MTK_QDMA))
--              mtk_w32(eth, val, MTK_QDMA_DELAY_INT);
-+              mtk_w32(eth, val, reg_map->qdma.delay_irq);
-       spin_unlock_bh(&eth->dim_lock);
-@@ -2568,6 +2630,7 @@ static int mtk_hw_init(struct mtk_eth *e
- {
-       u32 dma_mask = ETHSYS_DMA_AG_MAP_PDMA | ETHSYS_DMA_AG_MAP_QDMA |
-                      ETHSYS_DMA_AG_MAP_PPE;
-+      const struct mtk_reg_map *reg_map = eth->soc->reg_map;
-       int i, val, ret;
-       if (test_and_set_bit(MTK_HW_INIT, &eth->state))
-@@ -2642,10 +2705,10 @@ static int mtk_hw_init(struct mtk_eth *e
-       mtk_rx_irq_disable(eth, ~0);
-       /* FE int grouping */
--      mtk_w32(eth, MTK_TX_DONE_INT, MTK_PDMA_INT_GRP1);
--      mtk_w32(eth, MTK_RX_DONE_INT, MTK_PDMA_INT_GRP2);
--      mtk_w32(eth, MTK_TX_DONE_INT, MTK_QDMA_INT_GRP1);
--      mtk_w32(eth, MTK_RX_DONE_INT, MTK_QDMA_INT_GRP2);
-+      mtk_w32(eth, MTK_TX_DONE_INT, reg_map->pdma.int_grp);
-+      mtk_w32(eth, MTK_RX_DONE_INT, reg_map->pdma.int_grp + 4);
-+      mtk_w32(eth, MTK_TX_DONE_INT, reg_map->qdma.int_grp);
-+      mtk_w32(eth, MTK_RX_DONE_INT, reg_map->qdma.int_grp + 4);
-       mtk_w32(eth, 0x21021000, MTK_FE_INT_GRP);
-       return 0;
-@@ -3177,14 +3240,6 @@ static int mtk_probe(struct platform_dev
-       if (IS_ERR(eth->base))
-               return PTR_ERR(eth->base);
--      if (MTK_HAS_CAPS(eth->soc->caps, MTK_QDMA)) {
--              eth->tx_int_mask_reg = MTK_QDMA_INT_MASK;
--              eth->tx_int_status_reg = MTK_QDMA_INT_STATUS;
--      } else {
--              eth->tx_int_mask_reg = MTK_PDMA_INT_MASK;
--              eth->tx_int_status_reg = MTK_PDMA_INT_STATUS;
--      }
--
-       if (MTK_HAS_CAPS(eth->soc->caps, MTK_SOC_MT7628)) {
-               eth->rx_dma_l4_valid = RX_DMA_L4_VALID_PDMA;
-               eth->ip_align = NET_IP_ALIGN;
-@@ -3418,6 +3473,7 @@ static int mtk_remove(struct platform_de
- }
- static const struct mtk_soc_data mt2701_data = {
-+      .reg_map = &mtk_reg_map,
-       .caps = MT7623_CAPS | MTK_HWLRO,
-       .hw_features = MTK_HW_FEATURES,
-       .required_clks = MT7623_CLKS_BITMAP,
-@@ -3429,6 +3485,7 @@ static const struct mtk_soc_data mt2701_
- };
- static const struct mtk_soc_data mt7621_data = {
-+      .reg_map = &mtk_reg_map,
-       .caps = MT7621_CAPS,
-       .hw_features = MTK_HW_FEATURES,
-       .required_clks = MT7621_CLKS_BITMAP,
-@@ -3441,6 +3498,7 @@ static const struct mtk_soc_data mt7621_
- };
- static const struct mtk_soc_data mt7622_data = {
-+      .reg_map = &mtk_reg_map,
-       .ana_rgc3 = 0x2028,
-       .caps = MT7622_CAPS | MTK_HWLRO,
-       .hw_features = MTK_HW_FEATURES,
-@@ -3454,6 +3512,7 @@ static const struct mtk_soc_data mt7622_
- };
- static const struct mtk_soc_data mt7623_data = {
-+      .reg_map = &mtk_reg_map,
-       .caps = MT7623_CAPS | MTK_HWLRO,
-       .hw_features = MTK_HW_FEATURES,
-       .required_clks = MT7623_CLKS_BITMAP,
-@@ -3466,6 +3525,7 @@ static const struct mtk_soc_data mt7623_
- };
- static const struct mtk_soc_data mt7629_data = {
-+      .reg_map = &mtk_reg_map,
-       .ana_rgc3 = 0x128,
-       .caps = MT7629_CAPS | MTK_HWLRO,
-       .hw_features = MTK_HW_FEATURES,
-@@ -3478,6 +3538,7 @@ static const struct mtk_soc_data mt7629_
- };
- static const struct mtk_soc_data rt5350_data = {
-+      .reg_map = &mt7628_reg_map,
-       .caps = MT7628_CAPS,
-       .hw_features = MTK_HW_FEATURES_MT7628,
-       .required_clks = MT7628_CLKS_BITMAP,
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-@@ -48,6 +48,8 @@
- #define MTK_HW_FEATURES_MT7628        (NETIF_F_SG | NETIF_F_RXCSUM)
- #define NEXT_DESP_IDX(X, Y)   (((X) + 1) & ((Y) - 1))
-+#define MTK_QRX_OFFSET                0x10
-+
- #define MTK_MAX_RX_RING_NUM   4
- #define MTK_HW_LRO_DMA_SIZE   8
-@@ -100,18 +102,6 @@
- /* Unicast Filter MAC Address Register - High */
- #define MTK_GDMA_MAC_ADRH(x)  (0x50C + (x * 0x1000))
--/* PDMA RX Base Pointer Register */
--#define MTK_PRX_BASE_PTR0     0x900
--#define MTK_PRX_BASE_PTR_CFG(x)       (MTK_PRX_BASE_PTR0 + (x * 0x10))
--
--/* PDMA RX Maximum Count Register */
--#define MTK_PRX_MAX_CNT0      0x904
--#define MTK_PRX_MAX_CNT_CFG(x)        (MTK_PRX_MAX_CNT0 + (x * 0x10))
--
--/* PDMA RX CPU Pointer Register */
--#define MTK_PRX_CRX_IDX0      0x908
--#define MTK_PRX_CRX_IDX_CFG(x)        (MTK_PRX_CRX_IDX0 + (x * 0x10))
--
- /* PDMA HW LRO Control Registers */
- #define MTK_PDMA_LRO_CTRL_DW0 0x980
- #define MTK_LRO_EN                    BIT(0)
-@@ -126,18 +116,19 @@
- #define MTK_ADMA_MODE         BIT(15)
- #define MTK_LRO_MIN_RXD_SDL   (MTK_HW_LRO_SDL_REMAIN_ROOM << 16)
--/* PDMA Global Configuration Register */
--#define MTK_PDMA_GLO_CFG      0xa04
-+#define MTK_RX_DMA_LRO_EN     BIT(8)
- #define MTK_MULTI_EN          BIT(10)
- #define MTK_PDMA_SIZE_8DWORDS (1 << 4)
-+/* PDMA Global Configuration Register */
-+#define MTK_PDMA_LRO_SDL      0x3000
-+#define MTK_RX_CFG_SDL_OFFSET 16
-+
- /* PDMA Reset Index Register */
--#define MTK_PDMA_RST_IDX      0xa08
- #define MTK_PST_DRX_IDX0      BIT(16)
- #define MTK_PST_DRX_IDX_CFG(x)        (MTK_PST_DRX_IDX0 << (x))
- /* PDMA Delay Interrupt Register */
--#define MTK_PDMA_DELAY_INT            0xa0c
- #define MTK_PDMA_DELAY_RX_MASK                GENMASK(15, 0)
- #define MTK_PDMA_DELAY_RX_EN          BIT(15)
- #define MTK_PDMA_DELAY_RX_PINT_SHIFT  8
-@@ -151,19 +142,9 @@
- #define MTK_PDMA_DELAY_PINT_MASK      0x7f
- #define MTK_PDMA_DELAY_PTIME_MASK     0xff
--/* PDMA Interrupt Status Register */
--#define MTK_PDMA_INT_STATUS   0xa20
--
--/* PDMA Interrupt Mask Register */
--#define MTK_PDMA_INT_MASK     0xa28
--
- /* PDMA HW LRO Alter Flow Delta Register */
- #define MTK_PDMA_LRO_ALT_SCORE_DELTA  0xa4c
--/* PDMA Interrupt grouping registers */
--#define MTK_PDMA_INT_GRP1     0xa50
--#define MTK_PDMA_INT_GRP2     0xa54
--
- /* PDMA HW LRO IP Setting Registers */
- #define MTK_LRO_RX_RING0_DIP_DW0      0xb04
- #define MTK_LRO_DIP_DW0_CFG(x)                (MTK_LRO_RX_RING0_DIP_DW0 + (x * 0x40))
-@@ -185,26 +166,9 @@
- #define MTK_RING_MAX_AGG_CNT_H                ((MTK_HW_LRO_MAX_AGG_CNT >> 6) & 0x3)
- /* QDMA TX Queue Configuration Registers */
--#define MTK_QTX_CFG(x)                (0x1800 + (x * 0x10))
- #define QDMA_RES_THRES                4
--/* QDMA TX Queue Scheduler Registers */
--#define MTK_QTX_SCH(x)                (0x1804 + (x * 0x10))
--
--/* QDMA RX Base Pointer Register */
--#define MTK_QRX_BASE_PTR0     0x1900
--
--/* QDMA RX Maximum Count Register */
--#define MTK_QRX_MAX_CNT0      0x1904
--
--/* QDMA RX CPU Pointer Register */
--#define MTK_QRX_CRX_IDX0      0x1908
--
--/* QDMA RX DMA Pointer Register */
--#define MTK_QRX_DRX_IDX0      0x190C
--
- /* QDMA Global Configuration Register */
--#define MTK_QDMA_GLO_CFG      0x1A04
- #define MTK_RX_2B_OFFSET      BIT(31)
- #define MTK_RX_BT_32DWORDS    (3 << 11)
- #define MTK_NDP_CO_PRO                BIT(10)
-@@ -216,20 +180,12 @@
- #define MTK_TX_DMA_EN         BIT(0)
- #define MTK_DMA_BUSY_TIMEOUT_US       1000000
--/* QDMA Reset Index Register */
--#define MTK_QDMA_RST_IDX      0x1A08
--
--/* QDMA Delay Interrupt Register */
--#define MTK_QDMA_DELAY_INT    0x1A0C
--
- /* QDMA Flow Control Register */
--#define MTK_QDMA_FC_THRES     0x1A10
- #define FC_THRES_DROP_MODE    BIT(20)
- #define FC_THRES_DROP_EN      (7 << 16)
- #define FC_THRES_MIN          0x4444
- /* QDMA Interrupt Status Register */
--#define MTK_QDMA_INT_STATUS   0x1A18
- #define MTK_RX_DONE_DLY               BIT(30)
- #define MTK_TX_DONE_DLY               BIT(28)
- #define MTK_RX_DONE_INT3      BIT(19)
-@@ -244,55 +200,8 @@
- #define MTK_TX_DONE_INT               MTK_TX_DONE_DLY
- /* QDMA Interrupt grouping registers */
--#define MTK_QDMA_INT_GRP1     0x1a20
--#define MTK_QDMA_INT_GRP2     0x1a24
- #define MTK_RLS_DONE_INT      BIT(0)
--/* QDMA Interrupt Status Register */
--#define MTK_QDMA_INT_MASK     0x1A1C
--
--/* QDMA Interrupt Mask Register */
--#define MTK_QDMA_HRED2                0x1A44
--
--/* QDMA TX Forward CPU Pointer Register */
--#define MTK_QTX_CTX_PTR               0x1B00
--
--/* QDMA TX Forward DMA Pointer Register */
--#define MTK_QTX_DTX_PTR               0x1B04
--
--/* QDMA TX Release CPU Pointer Register */
--#define MTK_QTX_CRX_PTR               0x1B10
--
--/* QDMA TX Release DMA Pointer Register */
--#define MTK_QTX_DRX_PTR               0x1B14
--
--/* QDMA FQ Head Pointer Register */
--#define MTK_QDMA_FQ_HEAD      0x1B20
--
--/* QDMA FQ Head Pointer Register */
--#define MTK_QDMA_FQ_TAIL      0x1B24
--
--/* QDMA FQ Free Page Counter Register */
--#define MTK_QDMA_FQ_CNT               0x1B28
--
--/* QDMA FQ Free Page Buffer Length Register */
--#define MTK_QDMA_FQ_BLEN      0x1B2C
--
--/* GMA1 counter / statics register */
--#define MTK_GDM1_RX_GBCNT_L   0x2400
--#define MTK_GDM1_RX_GBCNT_H   0x2404
--#define MTK_GDM1_RX_GPCNT     0x2408
--#define MTK_GDM1_RX_OERCNT    0x2410
--#define MTK_GDM1_RX_FERCNT    0x2414
--#define MTK_GDM1_RX_SERCNT    0x2418
--#define MTK_GDM1_RX_LENCNT    0x241c
--#define MTK_GDM1_RX_CERCNT    0x2420
--#define MTK_GDM1_RX_FCCNT     0x2424
--#define MTK_GDM1_TX_SKIPCNT   0x2428
--#define MTK_GDM1_TX_COLCNT    0x242c
--#define MTK_GDM1_TX_GBCNT_L   0x2430
--#define MTK_GDM1_TX_GBCNT_H   0x2434
--#define MTK_GDM1_TX_GPCNT     0x2438
- #define MTK_STAT_OFFSET               0x40
- #define MTK_WDMA0_BASE                0x2800
-@@ -854,8 +763,46 @@ struct mtk_tx_dma_desc_info {
-       u8              last:1;
- };
-+struct mtk_reg_map {
-+      u32     tx_irq_mask;
-+      u32     tx_irq_status;
-+      struct {
-+              u32     rx_ptr;         /* rx base pointer */
-+              u32     rx_cnt_cfg;     /* rx max count configuration */
-+              u32     pcrx_ptr;       /* rx cpu pointer */
-+              u32     glo_cfg;        /* global configuration */
-+              u32     rst_idx;        /* reset index */
-+              u32     delay_irq;      /* delay interrupt */
-+              u32     irq_status;     /* interrupt status */
-+              u32     irq_mask;       /* interrupt mask */
-+              u32     int_grp;
-+      } pdma;
-+      struct {
-+              u32     qtx_cfg;        /* tx queue configuration */
-+              u32     rx_ptr;         /* rx base pointer */
-+              u32     rx_cnt_cfg;     /* rx max count configuration */
-+              u32     qcrx_ptr;       /* rx cpu pointer */
-+              u32     glo_cfg;        /* global configuration */
-+              u32     rst_idx;        /* reset index */
-+              u32     delay_irq;      /* delay interrupt */
-+              u32     fc_th;          /* flow control */
-+              u32     int_grp;
-+              u32     hred;           /* interrupt mask */
-+              u32     ctx_ptr;        /* tx acquire cpu pointer */
-+              u32     dtx_ptr;        /* tx acquire dma pointer */
-+              u32     crx_ptr;        /* tx release cpu pointer */
-+              u32     drx_ptr;        /* tx release dma pointer */
-+              u32     fq_head;        /* fq head pointer */
-+              u32     fq_tail;        /* fq tail pointer */
-+              u32     fq_count;       /* fq free page count */
-+              u32     fq_blen;        /* fq free page buffer length */
-+      } qdma;
-+      u32     gdm1_cnt;
-+};
-+
- /* struct mtk_eth_data -      This is the structure holding all differences
-  *                            among various plaforms
-+ * @reg_map                   Soc register map.
-  * @ana_rgc3:                   The offset for register ANA_RGC3 related to
-  *                            sgmiisys syscon
-  * @caps                      Flags shown the extra capability for the SoC
-@@ -868,6 +815,7 @@ struct mtk_tx_dma_desc_info {
-  * @rxd_size                  Rx DMA descriptor size.
-  */
- struct mtk_soc_data {
-+      const struct mtk_reg_map *reg_map;
-       u32             ana_rgc3;
-       u32             caps;
-       u32             required_clks;
-@@ -995,8 +943,6 @@ struct mtk_eth {
-       u32                             tx_bytes;
-       struct dim                      tx_dim;
--      u32                             tx_int_mask_reg;
--      u32                             tx_int_status_reg;
-       u32                             rx_dma_l4_valid;
-       int                             ip_align;
diff --git a/target/linux/generic/backport-5.15/702-v5.19-27-net-ethernet-mtk_eth_soc-introduce-MTK_NETSYS_V2-sup.patch b/target/linux/generic/backport-5.15/702-v5.19-27-net-ethernet-mtk_eth_soc-introduce-MTK_NETSYS_V2-sup.patch
deleted file mode 100644 (file)
index d55ab77..0000000
+++ /dev/null
@@ -1,917 +0,0 @@
-From: Lorenzo Bianconi <[email protected]>
-Date: Fri, 20 May 2022 20:11:36 +0200
-Subject: [PATCH] net: ethernet: mtk_eth_soc: introduce MTK_NETSYS_V2 support
-
-Introduce MTK_NETSYS_V2 support. MTK_NETSYS_V2 defines 32B TX/RX DMA
-descriptors.
-This is a preliminary patch to add mt7986 ethernet support.
-
-Tested-by: Sam Shih <[email protected]>
-Signed-off-by: Lorenzo Bianconi <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-@@ -873,8 +873,8 @@ static inline int mtk_max_buf_size(int f
-       return buf_size;
- }
--static inline bool mtk_rx_get_desc(struct mtk_rx_dma *rxd,
--                                 struct mtk_rx_dma *dma_rxd)
-+static bool mtk_rx_get_desc(struct mtk_eth *eth, struct mtk_rx_dma_v2 *rxd,
-+                          struct mtk_rx_dma_v2 *dma_rxd)
- {
-       rxd->rxd2 = READ_ONCE(dma_rxd->rxd2);
-       if (!(rxd->rxd2 & RX_DMA_DONE))
-@@ -883,6 +883,10 @@ static inline bool mtk_rx_get_desc(struc
-       rxd->rxd1 = READ_ONCE(dma_rxd->rxd1);
-       rxd->rxd3 = READ_ONCE(dma_rxd->rxd3);
-       rxd->rxd4 = READ_ONCE(dma_rxd->rxd4);
-+      if (MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2)) {
-+              rxd->rxd5 = READ_ONCE(dma_rxd->rxd5);
-+              rxd->rxd6 = READ_ONCE(dma_rxd->rxd6);
-+      }
-       return true;
- }
-@@ -927,7 +931,7 @@ static int mtk_init_fq_dma(struct mtk_et
-       phy_ring_tail = eth->phy_scratch_ring + soc->txrx.txd_size * (cnt - 1);
-       for (i = 0; i < cnt; i++) {
--              struct mtk_tx_dma *txd;
-+              struct mtk_tx_dma_v2 *txd;
-               txd = (void *)eth->scratch_ring + i * soc->txrx.txd_size;
-               txd->txd1 = dma_addr + i * MTK_QDMA_PAGE_SIZE;
-@@ -937,6 +941,12 @@ static int mtk_init_fq_dma(struct mtk_et
-               txd->txd3 = TX_DMA_PLEN0(MTK_QDMA_PAGE_SIZE);
-               txd->txd4 = 0;
-+              if (MTK_HAS_CAPS(soc->caps, MTK_NETSYS_V2)) {
-+                      txd->txd5 = 0;
-+                      txd->txd6 = 0;
-+                      txd->txd7 = 0;
-+                      txd->txd8 = 0;
-+              }
-       }
-       mtk_w32(eth, eth->phy_scratch_ring, soc->reg_map->qdma.fq_head);
-@@ -1040,10 +1050,12 @@ static void setup_tx_buf(struct mtk_eth
-       }
- }
--static void mtk_tx_set_dma_desc(struct net_device *dev, struct mtk_tx_dma *desc,
--                              struct mtk_tx_dma_desc_info *info)
-+static void mtk_tx_set_dma_desc_v1(struct net_device *dev, void *txd,
-+                                 struct mtk_tx_dma_desc_info *info)
- {
-       struct mtk_mac *mac = netdev_priv(dev);
-+      struct mtk_eth *eth = mac->hw;
-+      struct mtk_tx_dma *desc = txd;
-       u32 data;
-       WRITE_ONCE(desc->txd1, info->addr);
-@@ -1067,6 +1079,59 @@ static void mtk_tx_set_dma_desc(struct n
-       WRITE_ONCE(desc->txd4, data);
- }
-+static void mtk_tx_set_dma_desc_v2(struct net_device *dev, void *txd,
-+                                 struct mtk_tx_dma_desc_info *info)
-+{
-+      struct mtk_mac *mac = netdev_priv(dev);
-+      struct mtk_tx_dma_v2 *desc = txd;
-+      struct mtk_eth *eth = mac->hw;
-+      u32 data;
-+
-+      WRITE_ONCE(desc->txd1, info->addr);
-+
-+      data = TX_DMA_PLEN0(info->size);
-+      if (info->last)
-+              data |= TX_DMA_LS0;
-+      WRITE_ONCE(desc->txd3, data);
-+
-+      if (!info->qid && mac->id)
-+              info->qid = MTK_QDMA_GMAC2_QID;
-+
-+      data = (mac->id + 1) << TX_DMA_FPORT_SHIFT_V2; /* forward port */
-+      data |= TX_DMA_SWC_V2 | QID_BITS_V2(info->qid);
-+      WRITE_ONCE(desc->txd4, data);
-+
-+      data = 0;
-+      if (info->first) {
-+              if (info->gso)
-+                      data |= TX_DMA_TSO_V2;
-+              /* tx checksum offload */
-+              if (info->csum)
-+                      data |= TX_DMA_CHKSUM_V2;
-+      }
-+      WRITE_ONCE(desc->txd5, data);
-+
-+      data = 0;
-+      if (info->first && info->vlan)
-+              data |= TX_DMA_INS_VLAN_V2 | info->vlan_tci;
-+      WRITE_ONCE(desc->txd6, data);
-+
-+      WRITE_ONCE(desc->txd7, 0);
-+      WRITE_ONCE(desc->txd8, 0);
-+}
-+
-+static void mtk_tx_set_dma_desc(struct net_device *dev, void *txd,
-+                              struct mtk_tx_dma_desc_info *info)
-+{
-+      struct mtk_mac *mac = netdev_priv(dev);
-+      struct mtk_eth *eth = mac->hw;
-+
-+      if (MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2))
-+              mtk_tx_set_dma_desc_v2(dev, txd, info);
-+      else
-+              mtk_tx_set_dma_desc_v1(dev, txd, info);
-+}
-+
- static int mtk_tx_map(struct sk_buff *skb, struct net_device *dev,
-                     int tx_num, struct mtk_tx_ring *ring, bool gso)
- {
-@@ -1075,6 +1140,7 @@ static int mtk_tx_map(struct sk_buff *sk
-               .gso = gso,
-               .csum = skb->ip_summed == CHECKSUM_PARTIAL,
-               .vlan = skb_vlan_tag_present(skb),
-+              .qid = skb->mark & MTK_QDMA_TX_MASK,
-               .vlan_tci = skb_vlan_tag_get(skb),
-               .first = true,
-               .last = !skb_is_nonlinear(skb),
-@@ -1134,7 +1200,9 @@ static int mtk_tx_map(struct sk_buff *sk
-                       }
-                       memset(&txd_info, 0, sizeof(struct mtk_tx_dma_desc_info));
--                      txd_info.size = min(frag_size, MTK_TX_DMA_BUF_LEN);
-+                      txd_info.size = min_t(unsigned int, frag_size,
-+                                            soc->txrx.dma_max_len);
-+                      txd_info.qid = skb->mark & MTK_QDMA_TX_MASK;
-                       txd_info.last = i == skb_shinfo(skb)->nr_frags - 1 &&
-                                       !(frag_size - txd_info.size);
-                       txd_info.addr = skb_frag_dma_map(eth->dma_dev, frag,
-@@ -1215,17 +1283,16 @@ err_dma:
-       return -ENOMEM;
- }
--static inline int mtk_cal_txd_req(struct sk_buff *skb)
-+static int mtk_cal_txd_req(struct mtk_eth *eth, struct sk_buff *skb)
- {
--      int i, nfrags;
-+      int i, nfrags = 1;
-       skb_frag_t *frag;
--      nfrags = 1;
-       if (skb_is_gso(skb)) {
-               for (i = 0; i < skb_shinfo(skb)->nr_frags; i++) {
-                       frag = &skb_shinfo(skb)->frags[i];
-                       nfrags += DIV_ROUND_UP(skb_frag_size(frag),
--                                              MTK_TX_DMA_BUF_LEN);
-+                                             eth->soc->txrx.dma_max_len);
-               }
-       } else {
-               nfrags += skb_shinfo(skb)->nr_frags;
-@@ -1277,7 +1344,7 @@ static netdev_tx_t mtk_start_xmit(struct
-       if (unlikely(test_bit(MTK_RESETTING, &eth->state)))
-               goto drop;
--      tx_num = mtk_cal_txd_req(skb);
-+      tx_num = mtk_cal_txd_req(eth, skb);
-       if (unlikely(atomic_read(&ring->free_count) <= tx_num)) {
-               netif_stop_queue(dev);
-               netif_err(eth, tx_queued, dev,
-@@ -1369,7 +1436,7 @@ static int mtk_poll_rx(struct napi_struc
-       int idx;
-       struct sk_buff *skb;
-       u8 *data, *new_data;
--      struct mtk_rx_dma *rxd, trxd;
-+      struct mtk_rx_dma_v2 *rxd, trxd;
-       int done = 0, bytes = 0;
-       while (done < budget) {
-@@ -1377,7 +1444,7 @@ static int mtk_poll_rx(struct napi_struc
-               unsigned int pktlen;
-               dma_addr_t dma_addr;
-               u32 hash, reason;
--              int mac;
-+              int mac = 0;
-               ring = mtk_get_rx_ring(eth);
-               if (unlikely(!ring))
-@@ -1387,16 +1454,15 @@ static int mtk_poll_rx(struct napi_struc
-               rxd = (void *)ring->dma + idx * eth->soc->txrx.rxd_size;
-               data = ring->data[idx];
--              if (!mtk_rx_get_desc(&trxd, rxd))
-+              if (!mtk_rx_get_desc(eth, &trxd, rxd))
-                       break;
-               /* find out which mac the packet come from. values start at 1 */
--              if (MTK_HAS_CAPS(eth->soc->caps, MTK_SOC_MT7628) ||
--                  (trxd.rxd4 & RX_DMA_SPECIAL_TAG))
--                      mac = 0;
--              else
--                      mac = ((trxd.rxd4 >> RX_DMA_FPORT_SHIFT) &
--                             RX_DMA_FPORT_MASK) - 1;
-+              if (MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2))
-+                      mac = RX_DMA_GET_SPORT_V2(trxd.rxd5) - 1;
-+              else if (!MTK_HAS_CAPS(eth->soc->caps, MTK_SOC_MT7628) &&
-+                       !(trxd.rxd4 & RX_DMA_SPECIAL_TAG))
-+                      mac = RX_DMA_GET_SPORT(trxd.rxd4) - 1;
-               if (unlikely(mac < 0 || mac >= MTK_MAC_COUNT ||
-                            !eth->netdev[mac]))
-@@ -1442,7 +1508,7 @@ static int mtk_poll_rx(struct napi_struc
-               pktlen = RX_DMA_GET_PLEN0(trxd.rxd2);
-               skb->dev = netdev;
-               skb_put(skb, pktlen);
--              if (trxd.rxd4 & eth->rx_dma_l4_valid)
-+              if (trxd.rxd4 & eth->soc->txrx.rx_dma_l4_valid)
-                       skb->ip_summed = CHECKSUM_UNNECESSARY;
-               else
-                       skb_checksum_none_assert(skb);
-@@ -1460,10 +1526,25 @@ static int mtk_poll_rx(struct napi_struc
-                       mtk_ppe_check_skb(eth->ppe, skb,
-                                         trxd.rxd4 & MTK_RXD4_FOE_ENTRY);
--              if (netdev->features & NETIF_F_HW_VLAN_CTAG_RX &&
--                  (trxd.rxd2 & RX_DMA_VTAG))
--                      __vlan_hwaccel_put_tag(skb, htons(ETH_P_8021Q),
--                                             RX_DMA_VID(trxd.rxd3));
-+              if (netdev->features & NETIF_F_HW_VLAN_CTAG_RX) {
-+                      if (MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2)) {
-+                              if (trxd.rxd3 & RX_DMA_VTAG_V2)
-+                                      __vlan_hwaccel_put_tag(skb,
-+                                              htons(RX_DMA_VPID(trxd.rxd4)),
-+                                              RX_DMA_VID(trxd.rxd4));
-+                      } else if (trxd.rxd2 & RX_DMA_VTAG) {
-+                              __vlan_hwaccel_put_tag(skb, htons(ETH_P_8021Q),
-+                                                     RX_DMA_VID(trxd.rxd3));
-+                      }
-+
-+                      /* If the device is attached to a dsa switch, the special
-+                       * tag inserted in VLAN field by hw switch can * be offloaded
-+                       * by RX HW VLAN offload. Clear vlan info.
-+                       */
-+                      if (netdev_uses_dsa(netdev))
-+                              __vlan_hwaccel_clear_tag(skb);
-+              }
-+
-               skb_record_rx_queue(skb, 0);
-               napi_gro_receive(napi, skb);
-@@ -1475,7 +1556,7 @@ release_desc:
-               if (MTK_HAS_CAPS(eth->soc->caps, MTK_SOC_MT7628))
-                       rxd->rxd2 = RX_DMA_LSO;
-               else
--                      rxd->rxd2 = RX_DMA_PLEN0(ring->buf_size);
-+                      rxd->rxd2 = RX_DMA_PREP_PLEN0(ring->buf_size);
-               ring->calc_idx = idx;
-@@ -1677,7 +1758,8 @@ static int mtk_napi_rx(struct napi_struc
-       do {
-               int rx_done;
--              mtk_w32(eth, MTK_RX_DONE_INT, reg_map->pdma.irq_status);
-+              mtk_w32(eth, eth->soc->txrx.rx_irq_done_mask,
-+                      reg_map->pdma.irq_status);
-               rx_done = mtk_poll_rx(napi, budget - rx_done_total, eth);
-               rx_done_total += rx_done;
-@@ -1691,10 +1773,11 @@ static int mtk_napi_rx(struct napi_struc
-               if (rx_done_total == budget)
-                       return budget;
--      } while (mtk_r32(eth, reg_map->pdma.irq_status) & MTK_RX_DONE_INT);
-+      } while (mtk_r32(eth, reg_map->pdma.irq_status) &
-+               eth->soc->txrx.rx_irq_done_mask);
-       if (napi_complete_done(napi, rx_done_total))
--              mtk_rx_irq_enable(eth, MTK_RX_DONE_INT);
-+              mtk_rx_irq_enable(eth, eth->soc->txrx.rx_irq_done_mask);
-       return rx_done_total;
- }
-@@ -1704,7 +1787,7 @@ static int mtk_tx_alloc(struct mtk_eth *
-       const struct mtk_soc_data *soc = eth->soc;
-       struct mtk_tx_ring *ring = &eth->tx_ring;
-       int i, sz = soc->txrx.txd_size;
--      struct mtk_tx_dma *txd;
-+      struct mtk_tx_dma_v2 *txd;
-       ring->buf = kcalloc(MTK_DMA_SIZE, sizeof(*ring->buf),
-                              GFP_KERNEL);
-@@ -1724,13 +1807,19 @@ static int mtk_tx_alloc(struct mtk_eth *
-               txd->txd2 = next_ptr;
-               txd->txd3 = TX_DMA_LS0 | TX_DMA_OWNER_CPU;
-               txd->txd4 = 0;
-+              if (MTK_HAS_CAPS(soc->caps, MTK_NETSYS_V2)) {
-+                      txd->txd5 = 0;
-+                      txd->txd6 = 0;
-+                      txd->txd7 = 0;
-+                      txd->txd8 = 0;
-+              }
-       }
-       /* On MT7688 (PDMA only) this driver uses the ring->dma structs
-        * only as the framework. The real HW descriptors are the PDMA
-        * descriptors in ring->dma_pdma.
-        */
--      if (!MTK_HAS_CAPS(eth->soc->caps, MTK_QDMA)) {
-+      if (!MTK_HAS_CAPS(soc->caps, MTK_QDMA)) {
-               ring->dma_pdma = dma_alloc_coherent(eth->dma_dev, MTK_DMA_SIZE * sz,
-                                                   &ring->phys_pdma, GFP_KERNEL);
-               if (!ring->dma_pdma)
-@@ -1810,13 +1899,11 @@ static int mtk_rx_alloc(struct mtk_eth *
-       struct mtk_rx_ring *ring;
-       int rx_data_len, rx_dma_size;
-       int i;
--      u32 offset = 0;
-       if (rx_flag == MTK_RX_FLAGS_QDMA) {
-               if (ring_no)
-                       return -EINVAL;
-               ring = &eth->rx_ring_qdma;
--              offset = 0x1000;
-       } else {
-               ring = &eth->rx_ring[ring_no];
-       }
-@@ -1852,7 +1939,7 @@ static int mtk_rx_alloc(struct mtk_eth *
-               return -ENOMEM;
-       for (i = 0; i < rx_dma_size; i++) {
--              struct mtk_rx_dma *rxd;
-+              struct mtk_rx_dma_v2 *rxd;
-               dma_addr_t dma_addr = dma_map_single(eth->dma_dev,
-                               ring->data[i] + NET_SKB_PAD + eth->ip_align,
-@@ -1867,26 +1954,47 @@ static int mtk_rx_alloc(struct mtk_eth *
-               if (MTK_HAS_CAPS(eth->soc->caps, MTK_SOC_MT7628))
-                       rxd->rxd2 = RX_DMA_LSO;
-               else
--                      rxd->rxd2 = RX_DMA_PLEN0(ring->buf_size);
-+                      rxd->rxd2 = RX_DMA_PREP_PLEN0(ring->buf_size);
-               rxd->rxd3 = 0;
-               rxd->rxd4 = 0;
-+              if (MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2)) {
-+                      rxd->rxd5 = 0;
-+                      rxd->rxd6 = 0;
-+                      rxd->rxd7 = 0;
-+                      rxd->rxd8 = 0;
-+              }
-       }
-       ring->dma_size = rx_dma_size;
-       ring->calc_idx_update = false;
-       ring->calc_idx = rx_dma_size - 1;
--      ring->crx_idx_reg = reg_map->pdma.pcrx_ptr + ring_no * MTK_QRX_OFFSET;
-+      if (rx_flag == MTK_RX_FLAGS_QDMA)
-+              ring->crx_idx_reg = reg_map->qdma.qcrx_ptr +
-+                                  ring_no * MTK_QRX_OFFSET;
-+      else
-+              ring->crx_idx_reg = reg_map->pdma.pcrx_ptr +
-+                                  ring_no * MTK_QRX_OFFSET;
-       /* make sure that all changes to the dma ring are flushed before we
-        * continue
-        */
-       wmb();
--      mtk_w32(eth, ring->phys,
--              reg_map->pdma.rx_ptr + ring_no * MTK_QRX_OFFSET + offset);
--      mtk_w32(eth, rx_dma_size,
--              reg_map->pdma.rx_cnt_cfg + ring_no * MTK_QRX_OFFSET + offset);
--      mtk_w32(eth, ring->calc_idx, ring->crx_idx_reg + offset);
--      mtk_w32(eth, MTK_PST_DRX_IDX_CFG(ring_no), reg_map->pdma.rst_idx + offset);
-+      if (rx_flag == MTK_RX_FLAGS_QDMA) {
-+              mtk_w32(eth, ring->phys,
-+                      reg_map->qdma.rx_ptr + ring_no * MTK_QRX_OFFSET);
-+              mtk_w32(eth, rx_dma_size,
-+                      reg_map->qdma.rx_cnt_cfg + ring_no * MTK_QRX_OFFSET);
-+              mtk_w32(eth, MTK_PST_DRX_IDX_CFG(ring_no),
-+                      reg_map->qdma.rst_idx);
-+      } else {
-+              mtk_w32(eth, ring->phys,
-+                      reg_map->pdma.rx_ptr + ring_no * MTK_QRX_OFFSET);
-+              mtk_w32(eth, rx_dma_size,
-+                      reg_map->pdma.rx_cnt_cfg + ring_no * MTK_QRX_OFFSET);
-+              mtk_w32(eth, MTK_PST_DRX_IDX_CFG(ring_no),
-+                      reg_map->pdma.rst_idx);
-+      }
-+      mtk_w32(eth, ring->calc_idx, ring->crx_idx_reg);
-       return 0;
- }
-@@ -2311,7 +2419,7 @@ static irqreturn_t mtk_handle_irq_rx(int
-       eth->rx_events++;
-       if (likely(napi_schedule_prep(&eth->rx_napi))) {
-               __napi_schedule(&eth->rx_napi);
--              mtk_rx_irq_disable(eth, MTK_RX_DONE_INT);
-+              mtk_rx_irq_disable(eth, eth->soc->txrx.rx_irq_done_mask);
-       }
-       return IRQ_HANDLED;
-@@ -2335,8 +2443,10 @@ static irqreturn_t mtk_handle_irq(int ir
-       struct mtk_eth *eth = _eth;
-       const struct mtk_reg_map *reg_map = eth->soc->reg_map;
--      if (mtk_r32(eth, reg_map->pdma.irq_mask) & MTK_RX_DONE_INT) {
--              if (mtk_r32(eth, reg_map->pdma.irq_status) & MTK_RX_DONE_INT)
-+      if (mtk_r32(eth, reg_map->pdma.irq_mask) &
-+          eth->soc->txrx.rx_irq_done_mask) {
-+              if (mtk_r32(eth, reg_map->pdma.irq_status) &
-+                  eth->soc->txrx.rx_irq_done_mask)
-                       mtk_handle_irq_rx(irq, _eth);
-       }
-       if (mtk_r32(eth, reg_map->tx_irq_mask) & MTK_TX_DONE_INT) {
-@@ -2354,16 +2464,16 @@ static void mtk_poll_controller(struct n
-       struct mtk_eth *eth = mac->hw;
-       mtk_tx_irq_disable(eth, MTK_TX_DONE_INT);
--      mtk_rx_irq_disable(eth, MTK_RX_DONE_INT);
-+      mtk_rx_irq_disable(eth, eth->soc->txrx.rx_irq_done_mask);
-       mtk_handle_irq_rx(eth->irq[2], dev);
-       mtk_tx_irq_enable(eth, MTK_TX_DONE_INT);
--      mtk_rx_irq_enable(eth, MTK_RX_DONE_INT);
-+      mtk_rx_irq_enable(eth, eth->soc->txrx.rx_irq_done_mask);
- }
- #endif
- static int mtk_start_dma(struct mtk_eth *eth)
- {
--      u32 rx_2b_offset = (NET_IP_ALIGN == 2) ? MTK_RX_2B_OFFSET : 0;
-+      u32 val, rx_2b_offset = (NET_IP_ALIGN == 2) ? MTK_RX_2B_OFFSET : 0;
-       const struct mtk_reg_map *reg_map = eth->soc->reg_map;
-       int err;
-@@ -2374,12 +2484,19 @@ static int mtk_start_dma(struct mtk_eth
-       }
-       if (MTK_HAS_CAPS(eth->soc->caps, MTK_QDMA)) {
--              mtk_w32(eth,
--                      MTK_TX_WB_DDONE | MTK_TX_DMA_EN |
--                      MTK_TX_BT_32DWORDS | MTK_NDP_CO_PRO |
--                      MTK_RX_DMA_EN | MTK_RX_2B_OFFSET |
--                      MTK_RX_BT_32DWORDS,
--                      reg_map->qdma.glo_cfg);
-+              val = mtk_r32(eth, reg_map->qdma.glo_cfg);
-+              val |= MTK_TX_DMA_EN | MTK_RX_DMA_EN |
-+                     MTK_TX_BT_32DWORDS | MTK_NDP_CO_PRO |
-+                     MTK_RX_2B_OFFSET | MTK_TX_WB_DDONE;
-+
-+              if (MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2))
-+                      val |= MTK_MUTLI_CNT | MTK_RESV_BUF |
-+                             MTK_WCOMP_EN | MTK_DMAD_WR_WDONE |
-+                             MTK_CHK_DDONE_EN;
-+              else
-+                      val |= MTK_RX_BT_32DWORDS;
-+              mtk_w32(eth, val, reg_map->qdma.glo_cfg);
-+
-               mtk_w32(eth,
-                       MTK_RX_DMA_EN | rx_2b_offset |
-                       MTK_RX_BT_32DWORDS | MTK_MULTI_EN,
-@@ -2453,7 +2570,7 @@ static int mtk_open(struct net_device *d
-               napi_enable(&eth->tx_napi);
-               napi_enable(&eth->rx_napi);
-               mtk_tx_irq_enable(eth, MTK_TX_DONE_INT);
--              mtk_rx_irq_enable(eth, MTK_RX_DONE_INT);
-+              mtk_rx_irq_enable(eth, eth->soc->txrx.rx_irq_done_mask);
-               refcount_set(&eth->dma_refcnt, 1);
-       }
-       else
-@@ -2505,7 +2622,7 @@ static int mtk_stop(struct net_device *d
-       mtk_gdm_config(eth, MTK_GDMA_DROP_ALL);
-       mtk_tx_irq_disable(eth, MTK_TX_DONE_INT);
--      mtk_rx_irq_disable(eth, MTK_RX_DONE_INT);
-+      mtk_rx_irq_disable(eth, eth->soc->txrx.rx_irq_done_mask);
-       napi_disable(&eth->tx_napi);
-       napi_disable(&eth->rx_napi);
-@@ -2665,9 +2782,25 @@ static int mtk_hw_init(struct mtk_eth *e
-               return 0;
-       }
--      /* Non-MT7628 handling... */
--      ethsys_reset(eth, RSTCTRL_FE);
--      ethsys_reset(eth, RSTCTRL_PPE);
-+      val = RSTCTRL_FE | RSTCTRL_PPE;
-+      if (MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2)) {
-+              regmap_write(eth->ethsys, ETHSYS_FE_RST_CHK_IDLE_EN, 0);
-+
-+              val |= RSTCTRL_ETH;
-+              if (MTK_HAS_CAPS(eth->soc->caps, MTK_RSTCTRL_PPE1))
-+                      val |= RSTCTRL_PPE1;
-+      }
-+
-+      ethsys_reset(eth, val);
-+
-+      if (MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2)) {
-+              regmap_write(eth->ethsys, ETHSYS_FE_RST_CHK_IDLE_EN,
-+                           0x3ffffff);
-+
-+              /* Set FE to PDMAv2 if necessary */
-+              val = mtk_r32(eth, MTK_FE_GLO_MISC);
-+              mtk_w32(eth,  val | BIT(4), MTK_FE_GLO_MISC);
-+      }
-       if (eth->pctl) {
-               /* Set GE2 driving and slew rate */
-@@ -2706,11 +2839,47 @@ static int mtk_hw_init(struct mtk_eth *e
-       /* FE int grouping */
-       mtk_w32(eth, MTK_TX_DONE_INT, reg_map->pdma.int_grp);
--      mtk_w32(eth, MTK_RX_DONE_INT, reg_map->pdma.int_grp + 4);
-+      mtk_w32(eth, eth->soc->txrx.rx_irq_done_mask, reg_map->pdma.int_grp + 4);
-       mtk_w32(eth, MTK_TX_DONE_INT, reg_map->qdma.int_grp);
--      mtk_w32(eth, MTK_RX_DONE_INT, reg_map->qdma.int_grp + 4);
-+      mtk_w32(eth, eth->soc->txrx.rx_irq_done_mask, reg_map->qdma.int_grp + 4);
-       mtk_w32(eth, 0x21021000, MTK_FE_INT_GRP);
-+      if (MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2)) {
-+              /* PSE should not drop port8 and port9 packets */
-+              mtk_w32(eth, 0x00000300, PSE_DROP_CFG);
-+
-+              /* PSE Free Queue Flow Control  */
-+              mtk_w32(eth, 0x01fa01f4, PSE_FQFC_CFG2);
-+
-+              /* PSE config input queue threshold */
-+              mtk_w32(eth, 0x001a000e, PSE_IQ_REV(1));
-+              mtk_w32(eth, 0x01ff001a, PSE_IQ_REV(2));
-+              mtk_w32(eth, 0x000e01ff, PSE_IQ_REV(3));
-+              mtk_w32(eth, 0x000e000e, PSE_IQ_REV(4));
-+              mtk_w32(eth, 0x000e000e, PSE_IQ_REV(5));
-+              mtk_w32(eth, 0x000e000e, PSE_IQ_REV(6));
-+              mtk_w32(eth, 0x000e000e, PSE_IQ_REV(7));
-+              mtk_w32(eth, 0x000e000e, PSE_IQ_REV(8));
-+
-+              /* PSE config output queue threshold */
-+              mtk_w32(eth, 0x000f000a, PSE_OQ_TH(1));
-+              mtk_w32(eth, 0x001a000f, PSE_OQ_TH(2));
-+              mtk_w32(eth, 0x000f001a, PSE_OQ_TH(3));
-+              mtk_w32(eth, 0x01ff000f, PSE_OQ_TH(4));
-+              mtk_w32(eth, 0x000f000f, PSE_OQ_TH(5));
-+              mtk_w32(eth, 0x0006000f, PSE_OQ_TH(6));
-+              mtk_w32(eth, 0x00060006, PSE_OQ_TH(7));
-+              mtk_w32(eth, 0x00060006, PSE_OQ_TH(8));
-+
-+              /* GDM and CDM Threshold */
-+              mtk_w32(eth, 0x00000004, MTK_GDM2_THRES);
-+              mtk_w32(eth, 0x00000004, MTK_CDMW0_THRES);
-+              mtk_w32(eth, 0x00000004, MTK_CDMW1_THRES);
-+              mtk_w32(eth, 0x00000004, MTK_CDME0_THRES);
-+              mtk_w32(eth, 0x00000004, MTK_CDME1_THRES);
-+              mtk_w32(eth, 0x00000004, MTK_CDMM_THRES);
-+      }
-+
-       return 0;
- err_disable_pm:
-@@ -3240,12 +3409,8 @@ static int mtk_probe(struct platform_dev
-       if (IS_ERR(eth->base))
-               return PTR_ERR(eth->base);
--      if (MTK_HAS_CAPS(eth->soc->caps, MTK_SOC_MT7628)) {
--              eth->rx_dma_l4_valid = RX_DMA_L4_VALID_PDMA;
-+      if (MTK_HAS_CAPS(eth->soc->caps, MTK_SOC_MT7628))
-               eth->ip_align = NET_IP_ALIGN;
--      } else {
--              eth->rx_dma_l4_valid = RX_DMA_L4_VALID;
--      }
-       spin_lock_init(&eth->page_lock);
-       spin_lock_init(&eth->tx_irq_lock);
-@@ -3481,6 +3646,10 @@ static const struct mtk_soc_data mt2701_
-       .txrx = {
-               .txd_size = sizeof(struct mtk_tx_dma),
-               .rxd_size = sizeof(struct mtk_rx_dma),
-+              .rx_irq_done_mask = MTK_RX_DONE_INT,
-+              .rx_dma_l4_valid = RX_DMA_L4_VALID,
-+              .dma_max_len = MTK_TX_DMA_BUF_LEN,
-+              .dma_len_offset = 16,
-       },
- };
-@@ -3494,6 +3663,10 @@ static const struct mtk_soc_data mt7621_
-       .txrx = {
-               .txd_size = sizeof(struct mtk_tx_dma),
-               .rxd_size = sizeof(struct mtk_rx_dma),
-+              .rx_irq_done_mask = MTK_RX_DONE_INT,
-+              .rx_dma_l4_valid = RX_DMA_L4_VALID,
-+              .dma_max_len = MTK_TX_DMA_BUF_LEN,
-+              .dma_len_offset = 16,
-       },
- };
-@@ -3508,6 +3681,10 @@ static const struct mtk_soc_data mt7622_
-       .txrx = {
-               .txd_size = sizeof(struct mtk_tx_dma),
-               .rxd_size = sizeof(struct mtk_rx_dma),
-+              .rx_irq_done_mask = MTK_RX_DONE_INT,
-+              .rx_dma_l4_valid = RX_DMA_L4_VALID,
-+              .dma_max_len = MTK_TX_DMA_BUF_LEN,
-+              .dma_len_offset = 16,
-       },
- };
-@@ -3521,6 +3698,10 @@ static const struct mtk_soc_data mt7623_
-       .txrx = {
-               .txd_size = sizeof(struct mtk_tx_dma),
-               .rxd_size = sizeof(struct mtk_rx_dma),
-+              .rx_irq_done_mask = MTK_RX_DONE_INT,
-+              .rx_dma_l4_valid = RX_DMA_L4_VALID,
-+              .dma_max_len = MTK_TX_DMA_BUF_LEN,
-+              .dma_len_offset = 16,
-       },
- };
-@@ -3534,6 +3715,10 @@ static const struct mtk_soc_data mt7629_
-       .txrx = {
-               .txd_size = sizeof(struct mtk_tx_dma),
-               .rxd_size = sizeof(struct mtk_rx_dma),
-+              .rx_irq_done_mask = MTK_RX_DONE_INT,
-+              .rx_dma_l4_valid = RX_DMA_L4_VALID,
-+              .dma_max_len = MTK_TX_DMA_BUF_LEN,
-+              .dma_len_offset = 16,
-       },
- };
-@@ -3546,6 +3731,10 @@ static const struct mtk_soc_data rt5350_
-       .txrx = {
-               .txd_size = sizeof(struct mtk_tx_dma),
-               .rxd_size = sizeof(struct mtk_rx_dma),
-+              .rx_irq_done_mask = MTK_RX_DONE_INT,
-+              .rx_dma_l4_valid = RX_DMA_L4_VALID_PDMA,
-+              .dma_max_len = MTK_TX_DMA_BUF_LEN,
-+              .dma_len_offset = 16,
-       },
- };
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-@@ -23,6 +23,7 @@
- #define MTK_MAX_RX_LENGTH     1536
- #define MTK_MAX_RX_LENGTH_2K  2048
- #define MTK_TX_DMA_BUF_LEN    0x3fff
-+#define MTK_TX_DMA_BUF_LEN_V2 0xffff
- #define MTK_DMA_SIZE          512
- #define MTK_NAPI_WEIGHT               64
- #define MTK_MAC_COUNT         2
-@@ -83,6 +84,10 @@
- #define MTK_CDMQ_IG_CTRL      0x1400
- #define MTK_CDMQ_STAG_EN      BIT(0)
-+/* CDMP Ingress Control Register */
-+#define MTK_CDMP_IG_CTRL      0x400
-+#define MTK_CDMP_STAG_EN      BIT(0)
-+
- /* CDMP Exgress Control Register */
- #define MTK_CDMP_EG_CTRL      0x404
-@@ -102,13 +107,38 @@
- /* Unicast Filter MAC Address Register - High */
- #define MTK_GDMA_MAC_ADRH(x)  (0x50C + (x * 0x1000))
-+/* FE global misc reg*/
-+#define MTK_FE_GLO_MISC         0x124
-+
-+/* PSE Free Queue Flow Control  */
-+#define PSE_FQFC_CFG1         0x100
-+#define PSE_FQFC_CFG2         0x104
-+#define PSE_DROP_CFG          0x108
-+
-+/* PSE Input Queue Reservation Register*/
-+#define PSE_IQ_REV(x)         (0x140 + (((x) - 1) << 2))
-+
-+/* PSE Output Queue Threshold Register*/
-+#define PSE_OQ_TH(x)          (0x160 + (((x) - 1) << 2))
-+
-+/* GDM and CDM Threshold */
-+#define MTK_GDM2_THRES                0x1530
-+#define MTK_CDMW0_THRES               0x164c
-+#define MTK_CDMW1_THRES               0x1650
-+#define MTK_CDME0_THRES               0x1654
-+#define MTK_CDME1_THRES               0x1658
-+#define MTK_CDMM_THRES                0x165c
-+
- /* PDMA HW LRO Control Registers */
- #define MTK_PDMA_LRO_CTRL_DW0 0x980
- #define MTK_LRO_EN                    BIT(0)
- #define MTK_L3_CKS_UPD_EN             BIT(7)
-+#define MTK_L3_CKS_UPD_EN_V2          BIT(19)
- #define MTK_LRO_ALT_PKT_CNT_MODE      BIT(21)
- #define MTK_LRO_RING_RELINQUISH_REQ   (0x7 << 26)
-+#define MTK_LRO_RING_RELINQUISH_REQ_V2        (0xf << 24)
- #define MTK_LRO_RING_RELINQUISH_DONE  (0x7 << 29)
-+#define MTK_LRO_RING_RELINQUISH_DONE_V2       (0xf << 28)
- #define MTK_PDMA_LRO_CTRL_DW1 0x984
- #define MTK_PDMA_LRO_CTRL_DW2 0x988
-@@ -180,6 +210,13 @@
- #define MTK_TX_DMA_EN         BIT(0)
- #define MTK_DMA_BUSY_TIMEOUT_US       1000000
-+/* QDMA V2 Global Configuration Register */
-+#define MTK_CHK_DDONE_EN      BIT(28)
-+#define MTK_DMAD_WR_WDONE     BIT(26)
-+#define MTK_WCOMP_EN          BIT(24)
-+#define MTK_RESV_BUF          (0x40 << 16)
-+#define MTK_MUTLI_CNT         (0x4 << 12)
-+
- /* QDMA Flow Control Register */
- #define FC_THRES_DROP_MODE    BIT(20)
- #define FC_THRES_DROP_EN      (7 << 16)
-@@ -199,11 +236,32 @@
- #define MTK_RX_DONE_INT               MTK_RX_DONE_DLY
- #define MTK_TX_DONE_INT               MTK_TX_DONE_DLY
-+#define MTK_RX_DONE_INT_V2    BIT(14)
-+
- /* QDMA Interrupt grouping registers */
- #define MTK_RLS_DONE_INT      BIT(0)
- #define MTK_STAT_OFFSET               0x40
-+/* QDMA TX NUM */
-+#define MTK_QDMA_TX_NUM               16
-+#define MTK_QDMA_TX_MASK      (MTK_QDMA_TX_NUM - 1)
-+#define QID_BITS_V2(x)                (((x) & 0x3f) << 16)
-+#define MTK_QDMA_GMAC2_QID    8
-+
-+#define MTK_TX_DMA_BUF_SHIFT  8
-+
-+/* QDMA V2 descriptor txd6 */
-+#define TX_DMA_INS_VLAN_V2    BIT(16)
-+/* QDMA V2 descriptor txd5 */
-+#define TX_DMA_CHKSUM_V2      (0x7 << 28)
-+#define TX_DMA_TSO_V2         BIT(31)
-+
-+/* QDMA V2 descriptor txd4 */
-+#define TX_DMA_FPORT_SHIFT_V2 8
-+#define TX_DMA_FPORT_MASK_V2  0xf
-+#define TX_DMA_SWC_V2         BIT(30)
-+
- #define MTK_WDMA0_BASE                0x2800
- #define MTK_WDMA1_BASE                0x2c00
-@@ -217,10 +275,9 @@
- /* QDMA descriptor txd3 */
- #define TX_DMA_OWNER_CPU      BIT(31)
- #define TX_DMA_LS0            BIT(30)
--#define TX_DMA_PLEN0(_x)      (((_x) & MTK_TX_DMA_BUF_LEN) << 16)
--#define TX_DMA_PLEN1(_x)      ((_x) & MTK_TX_DMA_BUF_LEN)
-+#define TX_DMA_PLEN0(x)               (((x) & eth->soc->txrx.dma_max_len) << eth->soc->txrx.dma_len_offset)
-+#define TX_DMA_PLEN1(x)               ((x) & eth->soc->txrx.dma_max_len)
- #define TX_DMA_SWC            BIT(14)
--#define TX_DMA_SDL(_x)                (((_x) & 0x3fff) << 16)
- /* PDMA on MT7628 */
- #define TX_DMA_DONE           BIT(31)
-@@ -230,12 +287,14 @@
- /* QDMA descriptor rxd2 */
- #define RX_DMA_DONE           BIT(31)
- #define RX_DMA_LSO            BIT(30)
--#define RX_DMA_PLEN0(_x)      (((_x) & 0x3fff) << 16)
--#define RX_DMA_GET_PLEN0(_x)  (((_x) >> 16) & 0x3fff)
-+#define RX_DMA_PREP_PLEN0(x)  (((x) & eth->soc->txrx.dma_max_len) << eth->soc->txrx.dma_len_offset)
-+#define RX_DMA_GET_PLEN0(x)   (((x) >> eth->soc->txrx.dma_len_offset) & eth->soc->txrx.dma_max_len)
- #define RX_DMA_VTAG           BIT(15)
- /* QDMA descriptor rxd3 */
--#define RX_DMA_VID(_x)                ((_x) & 0xfff)
-+#define RX_DMA_VID(x)         ((x) & VLAN_VID_MASK)
-+#define RX_DMA_TCI(x)         ((x) & (VLAN_PRIO_MASK | VLAN_VID_MASK))
-+#define RX_DMA_VPID(x)                (((x) >> 16) & 0xffff)
- /* QDMA descriptor rxd4 */
- #define MTK_RXD4_FOE_ENTRY    GENMASK(13, 0)
-@@ -246,10 +305,15 @@
- /* QDMA descriptor rxd4 */
- #define RX_DMA_L4_VALID               BIT(24)
- #define RX_DMA_L4_VALID_PDMA  BIT(30)         /* when PDMA is used */
--#define RX_DMA_FPORT_SHIFT    19
--#define RX_DMA_FPORT_MASK     0x7
- #define RX_DMA_SPECIAL_TAG    BIT(22)
-+#define RX_DMA_GET_SPORT(x)   (((x) >> 19) & 0xf)
-+#define RX_DMA_GET_SPORT_V2(x)        (((x) >> 26) & 0x7)
-+
-+/* PDMA V2 descriptor rxd3 */
-+#define RX_DMA_VTAG_V2                BIT(0)
-+#define RX_DMA_L4_VALID_V2    BIT(2)
-+
- /* PHY Indirect Access Control registers */
- #define MTK_PHY_IAC           0x10004
- #define PHY_IAC_ACCESS                BIT(31)
-@@ -371,6 +435,16 @@
- #define ETHSYS_TRGMII_MT7621_DDR_PLL  BIT(5)
- /* ethernet reset control register */
-+#define ETHSYS_RSTCTRL                        0x34
-+#define RSTCTRL_FE                    BIT(6)
-+#define RSTCTRL_PPE                   BIT(31)
-+#define RSTCTRL_PPE1                  BIT(30)
-+#define RSTCTRL_ETH                   BIT(23)
-+
-+/* ethernet reset check idle register */
-+#define ETHSYS_FE_RST_CHK_IDLE_EN     0x28
-+
-+/* ethernet reset control register */
- #define ETHSYS_RSTCTRL                0x34
- #define RSTCTRL_FE            BIT(6)
- #define RSTCTRL_PPE           BIT(31)
-@@ -454,6 +528,17 @@ struct mtk_rx_dma {
-       unsigned int rxd4;
- } __packed __aligned(4);
-+struct mtk_rx_dma_v2 {
-+      unsigned int rxd1;
-+      unsigned int rxd2;
-+      unsigned int rxd3;
-+      unsigned int rxd4;
-+      unsigned int rxd5;
-+      unsigned int rxd6;
-+      unsigned int rxd7;
-+      unsigned int rxd8;
-+} __packed __aligned(4);
-+
- struct mtk_tx_dma {
-       unsigned int txd1;
-       unsigned int txd2;
-@@ -461,6 +546,17 @@ struct mtk_tx_dma {
-       unsigned int txd4;
- } __packed __aligned(4);
-+struct mtk_tx_dma_v2 {
-+      unsigned int txd1;
-+      unsigned int txd2;
-+      unsigned int txd3;
-+      unsigned int txd4;
-+      unsigned int txd5;
-+      unsigned int txd6;
-+      unsigned int txd7;
-+      unsigned int txd8;
-+} __packed __aligned(4);
-+
- struct mtk_eth;
- struct mtk_mac;
-@@ -647,7 +743,9 @@ enum mkt_eth_capabilities {
-       MTK_SHARED_INT_BIT,
-       MTK_TRGMII_MT7621_CLK_BIT,
-       MTK_QDMA_BIT,
-+      MTK_NETSYS_V2_BIT,
-       MTK_SOC_MT7628_BIT,
-+      MTK_RSTCTRL_PPE1_BIT,
-       /* MUX BITS*/
-       MTK_ETH_MUX_GDM1_TO_GMAC1_ESW_BIT,
-@@ -679,7 +777,9 @@ enum mkt_eth_capabilities {
- #define MTK_SHARED_INT                BIT(MTK_SHARED_INT_BIT)
- #define MTK_TRGMII_MT7621_CLK BIT(MTK_TRGMII_MT7621_CLK_BIT)
- #define MTK_QDMA              BIT(MTK_QDMA_BIT)
-+#define MTK_NETSYS_V2         BIT(MTK_NETSYS_V2_BIT)
- #define MTK_SOC_MT7628                BIT(MTK_SOC_MT7628_BIT)
-+#define MTK_RSTCTRL_PPE1      BIT(MTK_RSTCTRL_PPE1_BIT)
- #define MTK_ETH_MUX_GDM1_TO_GMAC1_ESW         \
-       BIT(MTK_ETH_MUX_GDM1_TO_GMAC1_ESW_BIT)
-@@ -756,6 +856,7 @@ struct mtk_tx_dma_desc_info {
-       dma_addr_t      addr;
-       u32             size;
-       u16             vlan_tci;
-+      u16             qid;
-       u8              gso:1;
-       u8              csum:1;
-       u8              vlan:1;
-@@ -813,6 +914,10 @@ struct mtk_reg_map {
-  *                            the extra setup for those pins used by GMAC.
-  * @txd_size                  Tx DMA descriptor size.
-  * @rxd_size                  Rx DMA descriptor size.
-+ * @rx_irq_done_mask          Rx irq done register mask.
-+ * @rx_dma_l4_valid           Rx DMA valid register mask.
-+ * @dma_max_len                       Max DMA tx/rx buffer length.
-+ * @dma_len_offset            Tx/Rx DMA length field offset.
-  */
- struct mtk_soc_data {
-       const struct mtk_reg_map *reg_map;
-@@ -825,6 +930,10 @@ struct mtk_soc_data {
-       struct {
-               u32     txd_size;
-               u32     rxd_size;
-+              u32     rx_irq_done_mask;
-+              u32     rx_dma_l4_valid;
-+              u32     dma_max_len;
-+              u32     dma_len_offset;
-       } txrx;
- };
-@@ -943,7 +1052,6 @@ struct mtk_eth {
-       u32                             tx_bytes;
-       struct dim                      tx_dim;
--      u32                             rx_dma_l4_valid;
-       int                             ip_align;
-       struct mtk_ppe                  *ppe;
diff --git a/target/linux/generic/backport-5.15/702-v5.19-28-net-ethernet-mtk_eth_soc-convert-ring-dma-pointer-to.patch b/target/linux/generic/backport-5.15/702-v5.19-28-net-ethernet-mtk_eth_soc-convert-ring-dma-pointer-to.patch
deleted file mode 100644 (file)
index 1ee9bb5..0000000
+++ /dev/null
@@ -1,135 +0,0 @@
-From: Lorenzo Bianconi <[email protected]>
-Date: Fri, 20 May 2022 20:11:37 +0200
-Subject: [PATCH] net: ethernet: mtk_eth_soc: convert ring dma pointer to void
-
-Simplify the code converting {tx,rx} ring dma pointer to void
-
-Signed-off-by: Lorenzo Bianconi <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-@@ -957,18 +957,15 @@ static int mtk_init_fq_dma(struct mtk_et
-       return 0;
- }
--static inline void *mtk_qdma_phys_to_virt(struct mtk_tx_ring *ring, u32 desc)
-+static void *mtk_qdma_phys_to_virt(struct mtk_tx_ring *ring, u32 desc)
- {
--      void *ret = ring->dma;
--
--      return ret + (desc - ring->phys);
-+      return ring->dma + (desc - ring->phys);
- }
- static struct mtk_tx_buf *mtk_desc_to_tx_buf(struct mtk_tx_ring *ring,
--                                           struct mtk_tx_dma *txd,
--                                           u32 txd_size)
-+                                           void *txd, u32 txd_size)
- {
--      int idx = ((void *)txd - (void *)ring->dma) / txd_size;
-+      int idx = (txd - ring->dma) / txd_size;
-       return &ring->buf[idx];
- }
-@@ -976,13 +973,12 @@ static struct mtk_tx_buf *mtk_desc_to_tx
- static struct mtk_tx_dma *qdma_to_pdma(struct mtk_tx_ring *ring,
-                                      struct mtk_tx_dma *dma)
- {
--      return ring->dma_pdma - ring->dma + dma;
-+      return ring->dma_pdma - (struct mtk_tx_dma *)ring->dma + dma;
- }
--static int txd_to_idx(struct mtk_tx_ring *ring, struct mtk_tx_dma *dma,
--                    u32 txd_size)
-+static int txd_to_idx(struct mtk_tx_ring *ring, void *dma, u32 txd_size)
- {
--      return ((void *)dma - (void *)ring->dma) / txd_size;
-+      return (dma - ring->dma) / txd_size;
- }
- static void mtk_tx_unmap(struct mtk_eth *eth, struct mtk_tx_buf *tx_buf,
-@@ -1399,7 +1395,7 @@ static struct mtk_rx_ring *mtk_get_rx_ri
-               ring = &eth->rx_ring[i];
-               idx = NEXT_DESP_IDX(ring->calc_idx, ring->dma_size);
--              rxd = (void *)ring->dma + idx * eth->soc->txrx.rxd_size;
-+              rxd = ring->dma + idx * eth->soc->txrx.rxd_size;
-               if (rxd->rxd2 & RX_DMA_DONE) {
-                       ring->calc_idx_update = true;
-                       return ring;
-@@ -1451,7 +1447,7 @@ static int mtk_poll_rx(struct napi_struc
-                       goto rx_done;
-               idx = NEXT_DESP_IDX(ring->calc_idx, ring->dma_size);
--              rxd = (void *)ring->dma + idx * eth->soc->txrx.rxd_size;
-+              rxd = ring->dma + idx * eth->soc->txrx.rxd_size;
-               data = ring->data[idx];
-               if (!mtk_rx_get_desc(eth, &trxd, rxd))
-@@ -1658,7 +1654,7 @@ static int mtk_poll_tx_pdma(struct mtk_e
-               mtk_tx_unmap(eth, tx_buf, true);
--              desc = (void *)ring->dma + cpu * eth->soc->txrx.txd_size;
-+              desc = ring->dma + cpu * eth->soc->txrx.txd_size;
-               ring->last_free = desc;
-               atomic_inc(&ring->free_count);
-@@ -1803,7 +1799,7 @@ static int mtk_tx_alloc(struct mtk_eth *
-               int next = (i + 1) % MTK_DMA_SIZE;
-               u32 next_ptr = ring->phys + next * sz;
--              txd = (void *)ring->dma + i * sz;
-+              txd = ring->dma + i * sz;
-               txd->txd2 = next_ptr;
-               txd->txd3 = TX_DMA_LS0 | TX_DMA_OWNER_CPU;
-               txd->txd4 = 0;
-@@ -1833,7 +1829,7 @@ static int mtk_tx_alloc(struct mtk_eth *
-       ring->dma_size = MTK_DMA_SIZE;
-       atomic_set(&ring->free_count, MTK_DMA_SIZE - 2);
--      ring->next_free = &ring->dma[0];
-+      ring->next_free = ring->dma;
-       ring->last_free = (void *)txd;
-       ring->last_free_ptr = (u32)(ring->phys + ((MTK_DMA_SIZE - 1) * sz));
-       ring->thresh = MAX_SKB_FRAGS;
-@@ -1948,7 +1944,7 @@ static int mtk_rx_alloc(struct mtk_eth *
-               if (unlikely(dma_mapping_error(eth->dma_dev, dma_addr)))
-                       return -ENOMEM;
--              rxd = (void *)ring->dma + i * eth->soc->txrx.rxd_size;
-+              rxd = ring->dma + i * eth->soc->txrx.rxd_size;
-               rxd->rxd1 = (unsigned int)dma_addr;
-               if (MTK_HAS_CAPS(eth->soc->caps, MTK_SOC_MT7628))
-@@ -2010,7 +2006,7 @@ static void mtk_rx_clean(struct mtk_eth
-                       if (!ring->data[i])
-                               continue;
--                      rxd = (void *)ring->dma + i * eth->soc->txrx.rxd_size;
-+                      rxd = ring->dma + i * eth->soc->txrx.rxd_size;
-                       if (!rxd->rxd1)
-                               continue;
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-@@ -689,7 +689,7 @@ struct mtk_tx_buf {
-  *                    are present
-  */
- struct mtk_tx_ring {
--      struct mtk_tx_dma *dma;
-+      void *dma;
-       struct mtk_tx_buf *buf;
-       dma_addr_t phys;
-       struct mtk_tx_dma *next_free;
-@@ -719,7 +719,7 @@ enum mtk_rx_flags {
-  * @calc_idx:         The current head of ring
-  */
- struct mtk_rx_ring {
--      struct mtk_rx_dma *dma;
-+      void *dma;
-       u8 **data;
-       dma_addr_t phys;
-       u16 frag_size;
diff --git a/target/linux/generic/backport-5.15/702-v5.19-29-net-ethernet-mtk_eth_soc-convert-scratch_ring-pointe.patch b/target/linux/generic/backport-5.15/702-v5.19-29-net-ethernet-mtk_eth_soc-convert-scratch_ring-pointe.patch
deleted file mode 100644 (file)
index af77ee3..0000000
+++ /dev/null
@@ -1,33 +0,0 @@
-From: Lorenzo Bianconi <[email protected]>
-Date: Fri, 20 May 2022 20:11:38 +0200
-Subject: [PATCH] net: ethernet: mtk_eth_soc: convert scratch_ring pointer to
- void
-
-Simplify the code converting scratch_ring pointer to void
-
-Signed-off-by: Lorenzo Bianconi <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-@@ -933,7 +933,7 @@ static int mtk_init_fq_dma(struct mtk_et
-       for (i = 0; i < cnt; i++) {
-               struct mtk_tx_dma_v2 *txd;
--              txd = (void *)eth->scratch_ring + i * soc->txrx.txd_size;
-+              txd = eth->scratch_ring + i * soc->txrx.txd_size;
-               txd->txd1 = dma_addr + i * MTK_QDMA_PAGE_SIZE;
-               if (i < cnt - 1)
-                       txd->txd2 = eth->phy_scratch_ring +
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-@@ -1029,7 +1029,7 @@ struct mtk_eth {
-       struct mtk_rx_ring              rx_ring_qdma;
-       struct napi_struct              tx_napi;
-       struct napi_struct              rx_napi;
--      struct mtk_tx_dma               *scratch_ring;
-+      void                            *scratch_ring;
-       dma_addr_t                      phy_scratch_ring;
-       void                            *scratch_head;
-       struct clk                      *clks[MTK_CLK_MAX];
diff --git a/target/linux/generic/backport-5.15/702-v5.19-30-net-ethernet-mtk_eth_soc-introduce-support-for-mt798.patch b/target/linux/generic/backport-5.15/702-v5.19-30-net-ethernet-mtk_eth_soc-introduce-support-for-mt798.patch
deleted file mode 100644 (file)
index cceb79b..0000000
+++ /dev/null
@@ -1,138 +0,0 @@
-From: Lorenzo Bianconi <[email protected]>
-Date: Fri, 20 May 2022 20:11:39 +0200
-Subject: [PATCH] net: ethernet: mtk_eth_soc: introduce support for mt7986
- chipset
-
-Add support for mt7986-eth driver available on mt7986 soc.
-
-Tested-by: Sam Shih <[email protected]>
-Signed-off-by: Lorenzo Bianconi <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-@@ -87,6 +87,43 @@ static const struct mtk_reg_map mt7628_r
-       },
- };
-+static const struct mtk_reg_map mt7986_reg_map = {
-+      .tx_irq_mask            = 0x461c,
-+      .tx_irq_status          = 0x4618,
-+      .pdma = {
-+              .rx_ptr         = 0x6100,
-+              .rx_cnt_cfg     = 0x6104,
-+              .pcrx_ptr       = 0x6108,
-+              .glo_cfg        = 0x6204,
-+              .rst_idx        = 0x6208,
-+              .delay_irq      = 0x620c,
-+              .irq_status     = 0x6220,
-+              .irq_mask       = 0x6228,
-+              .int_grp        = 0x6250,
-+      },
-+      .qdma = {
-+              .qtx_cfg        = 0x4400,
-+              .rx_ptr         = 0x4500,
-+              .rx_cnt_cfg     = 0x4504,
-+              .qcrx_ptr       = 0x4508,
-+              .glo_cfg        = 0x4604,
-+              .rst_idx        = 0x4608,
-+              .delay_irq      = 0x460c,
-+              .fc_th          = 0x4610,
-+              .int_grp        = 0x4620,
-+              .hred           = 0x4644,
-+              .ctx_ptr        = 0x4700,
-+              .dtx_ptr        = 0x4704,
-+              .crx_ptr        = 0x4710,
-+              .drx_ptr        = 0x4714,
-+              .fq_head        = 0x4720,
-+              .fq_tail        = 0x4724,
-+              .fq_count       = 0x4728,
-+              .fq_blen        = 0x472c,
-+      },
-+      .gdm1_cnt               = 0x1c00,
-+};
-+
- /* strings used by ethtool */
- static const struct mtk_ethtool_stats {
-       char str[ETH_GSTRING_LEN];
-@@ -110,7 +147,7 @@ static const char * const mtk_clks_sourc
-       "ethif", "sgmiitop", "esw", "gp0", "gp1", "gp2", "fe", "trgpll",
-       "sgmii_tx250m", "sgmii_rx250m", "sgmii_cdr_ref", "sgmii_cdr_fb",
-       "sgmii2_tx250m", "sgmii2_rx250m", "sgmii2_cdr_ref", "sgmii2_cdr_fb",
--      "sgmii_ck", "eth2pll",
-+      "sgmii_ck", "eth2pll", "wocpu0", "wocpu1", "netsys0", "netsys1"
- };
- void mtk_w32(struct mtk_eth *eth, u32 val, unsigned reg)
-@@ -3718,6 +3755,21 @@ static const struct mtk_soc_data mt7629_
-       },
- };
-+static const struct mtk_soc_data mt7986_data = {
-+      .reg_map = &mt7986_reg_map,
-+      .ana_rgc3 = 0x128,
-+      .caps = MT7986_CAPS,
-+      .required_clks = MT7986_CLKS_BITMAP,
-+      .required_pctl = false,
-+      .txrx = {
-+              .txd_size = sizeof(struct mtk_tx_dma_v2),
-+              .rxd_size = sizeof(struct mtk_rx_dma_v2),
-+              .rx_irq_done_mask = MTK_RX_DONE_INT_V2,
-+              .dma_max_len = MTK_TX_DMA_BUF_LEN_V2,
-+              .dma_len_offset = 8,
-+      },
-+};
-+
- static const struct mtk_soc_data rt5350_data = {
-       .reg_map = &mt7628_reg_map,
-       .caps = MT7628_CAPS,
-@@ -3740,6 +3792,7 @@ const struct of_device_id of_mtk_match[]
-       { .compatible = "mediatek,mt7622-eth", .data = &mt7622_data},
-       { .compatible = "mediatek,mt7623-eth", .data = &mt7623_data},
-       { .compatible = "mediatek,mt7629-eth", .data = &mt7629_data},
-+      { .compatible = "mediatek,mt7986-eth", .data = &mt7986_data},
-       { .compatible = "ralink,rt5350-eth", .data = &rt5350_data},
-       {},
- };
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-@@ -624,6 +624,10 @@ enum mtk_clks_map {
-       MTK_CLK_SGMII2_CDR_FB,
-       MTK_CLK_SGMII_CK,
-       MTK_CLK_ETH2PLL,
-+      MTK_CLK_WOCPU0,
-+      MTK_CLK_WOCPU1,
-+      MTK_CLK_NETSYS0,
-+      MTK_CLK_NETSYS1,
-       MTK_CLK_MAX
- };
-@@ -654,6 +658,16 @@ enum mtk_clks_map {
-                                BIT(MTK_CLK_SGMII2_CDR_FB) | \
-                                BIT(MTK_CLK_SGMII_CK) | \
-                                BIT(MTK_CLK_ETH2PLL) | BIT(MTK_CLK_SGMIITOP))
-+#define MT7986_CLKS_BITMAP    (BIT(MTK_CLK_FE) | BIT(MTK_CLK_GP2) | BIT(MTK_CLK_GP1) | \
-+                               BIT(MTK_CLK_WOCPU1) | BIT(MTK_CLK_WOCPU0) | \
-+                               BIT(MTK_CLK_SGMII_TX_250M) | \
-+                               BIT(MTK_CLK_SGMII_RX_250M) | \
-+                               BIT(MTK_CLK_SGMII_CDR_REF) | \
-+                               BIT(MTK_CLK_SGMII_CDR_FB) | \
-+                               BIT(MTK_CLK_SGMII2_TX_250M) | \
-+                               BIT(MTK_CLK_SGMII2_RX_250M) | \
-+                               BIT(MTK_CLK_SGMII2_CDR_REF) | \
-+                               BIT(MTK_CLK_SGMII2_CDR_FB))
- enum mtk_dev_state {
-       MTK_HW_INIT,
-@@ -852,6 +866,10 @@ enum mkt_eth_capabilities {
-                     MTK_MUX_U3_GMAC2_TO_QPHY | \
-                     MTK_MUX_GMAC12_TO_GEPHY_SGMII | MTK_QDMA)
-+#define MT7986_CAPS  (MTK_GMAC1_SGMII | MTK_GMAC2_SGMII | \
-+                    MTK_MUX_GMAC12_TO_GEPHY_SGMII | MTK_QDMA | \
-+                    MTK_NETSYS_V2 | MTK_RSTCTRL_PPE1)
-+
- struct mtk_tx_dma_desc_info {
-       dma_addr_t      addr;
-       u32             size;
diff --git a/target/linux/generic/backport-5.15/702-v5.19-31-net-ethernet-mtk_eth_soc-fix-error-code-in-mtk_flow_.patch b/target/linux/generic/backport-5.15/702-v5.19-31-net-ethernet-mtk_eth_soc-fix-error-code-in-mtk_flow_.patch
deleted file mode 100644 (file)
index e490333..0000000
+++ /dev/null
@@ -1,25 +0,0 @@
-From: Dan Carpenter <[email protected]>
-Date: Thu, 19 May 2022 17:08:00 +0300
-Subject: [PATCH] net: ethernet: mtk_eth_soc: fix error code in
- mtk_flow_offload_replace()
-
-Preserve the error code from mtk_foe_entry_commit().  Do not return
-success.
-
-Fixes: c4f033d9e03e ("net: ethernet: mtk_eth_soc: rework hardware flow table management")
-Signed-off-by: Dan Carpenter <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
-
---- a/drivers/net/ethernet/mediatek/mtk_ppe_offload.c
-+++ b/drivers/net/ethernet/mediatek/mtk_ppe_offload.c
-@@ -434,7 +434,8 @@ mtk_flow_offload_replace(struct mtk_eth
-       memcpy(&entry->data, &foe, sizeof(entry->data));
-       entry->wed_index = wed_index;
--      if (mtk_foe_entry_commit(eth->ppe, entry) < 0)
-+      err = mtk_foe_entry_commit(eth->ppe, entry);
-+      if (err < 0)
-               goto free;
-       err = rhashtable_insert_fast(&eth->flow_table, &entry->node,
diff --git a/target/linux/generic/backport-5.15/702-v5.19-33-net-ethernet-mtk_eth_soc-enable-rx-cksum-offload-for.patch b/target/linux/generic/backport-5.15/702-v5.19-33-net-ethernet-mtk_eth_soc-enable-rx-cksum-offload-for.patch
deleted file mode 100644 (file)
index cfb6ca4..0000000
+++ /dev/null
@@ -1,47 +0,0 @@
-From: Lorenzo Bianconi <[email protected]>
-Date: Mon, 6 Jun 2022 21:49:00 +0200
-Subject: [PATCH] net: ethernet: mtk_eth_soc: enable rx cksum offload for
- MTK_NETSYS_V2
-
-Enable rx checksum offload for mt7986 chipset.
-
-Signed-off-by: Lorenzo Bianconi <[email protected]>
-Link: https://lore.kernel.org/r/c8699805c18f7fd38315fcb8da2787676d83a32c.1654544585.git.lorenzo@kernel.org
-Signed-off-by: Jakub Kicinski <[email protected]>
----
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-@@ -1473,8 +1473,8 @@ static int mtk_poll_rx(struct napi_struc
-       int done = 0, bytes = 0;
-       while (done < budget) {
-+              unsigned int pktlen, *rxdcsum;
-               struct net_device *netdev;
--              unsigned int pktlen;
-               dma_addr_t dma_addr;
-               u32 hash, reason;
-               int mac = 0;
-@@ -1541,7 +1541,13 @@ static int mtk_poll_rx(struct napi_struc
-               pktlen = RX_DMA_GET_PLEN0(trxd.rxd2);
-               skb->dev = netdev;
-               skb_put(skb, pktlen);
--              if (trxd.rxd4 & eth->soc->txrx.rx_dma_l4_valid)
-+
-+              if (MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2))
-+                      rxdcsum = &trxd.rxd3;
-+              else
-+                      rxdcsum = &trxd.rxd4;
-+
-+              if (*rxdcsum & eth->soc->txrx.rx_dma_l4_valid)
-                       skb->ip_summed = CHECKSUM_UNNECESSARY;
-               else
-                       skb_checksum_none_assert(skb);
-@@ -3765,6 +3771,7 @@ static const struct mtk_soc_data mt7986_
-               .txd_size = sizeof(struct mtk_tx_dma_v2),
-               .rxd_size = sizeof(struct mtk_rx_dma_v2),
-               .rx_irq_done_mask = MTK_RX_DONE_INT_V2,
-+              .rx_dma_l4_valid = RX_DMA_L4_VALID_V2,
-               .dma_max_len = MTK_TX_DMA_BUF_LEN_V2,
-               .dma_len_offset = 8,
-       },
diff --git a/target/linux/generic/backport-5.15/702-v5.19-34-eth-mtk_ppe-fix-up-after-merge.patch b/target/linux/generic/backport-5.15/702-v5.19-34-eth-mtk_ppe-fix-up-after-merge.patch
deleted file mode 100644 (file)
index 5303ca4..0000000
+++ /dev/null
@@ -1,28 +0,0 @@
-From: Jakub Kicinski <[email protected]>
-Date: Thu, 19 May 2022 18:25:55 -0700
-Subject: [PATCH] eth: mtk_ppe: fix up after merge
-
-I missed this in the barrage of GCC 12 warnings. Commit cf2df74e202d
-("net: fix dev_fill_forward_path with pppoe + bridge") changed
-the pointer into an array.
-
-Fixes: d7e6f5836038 ("Merge git://git.kernel.org/pub/scm/linux/kernel/git/netdev/net")
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Jakub Kicinski <[email protected]>
----
-
---- a/drivers/net/ethernet/mediatek/mtk_ppe_offload.c
-+++ b/drivers/net/ethernet/mediatek/mtk_ppe_offload.c
-@@ -90,10 +90,11 @@ mtk_flow_get_wdma_info(struct net_device
- {
-       struct net_device_path_ctx ctx = {
-               .dev = dev,
--              .daddr = addr,
-       };
-       struct net_device_path path = {};
-+      memcpy(ctx.daddr, addr, sizeof(ctx.daddr));
-+
-       if (!IS_ENABLED(CONFIG_NET_MEDIATEK_SOC_WED))
-               return -1;
diff --git a/target/linux/generic/backport-5.15/703-00-v5.16-net-convert-users-of-bitmap_foo-to-linkmode_foo.patch b/target/linux/generic/backport-5.15/703-00-v5.16-net-convert-users-of-bitmap_foo-to-linkmode_foo.patch
deleted file mode 100644 (file)
index 5737da6..0000000
+++ /dev/null
@@ -1,948 +0,0 @@
-From 4973056cceacc70966396039fae99867dfafd796 Mon Sep 17 00:00:00 2001
-From: Sean Anderson <[email protected]>
-Date: Fri, 22 Oct 2021 18:41:04 -0400
-Subject: [PATCH] net: convert users of bitmap_foo() to linkmode_foo()
-
-This converts instances of
-       bitmap_foo(args..., __ETHTOOL_LINK_MODE_MASK_NBITS)
-to
-       linkmode_foo(args...)
-
-I manually fixed up some lines to prevent them from being excessively
-long. Otherwise, this change was generated with the following semantic
-patch:
-
-// Generated with
-// echo linux/linkmode.h > includes
-// git grep -Flf includes include/ | cut -f 2- -d / | cat includes - \
-// | sort | uniq | tee new_includes | wc -l && mv new_includes includes
-// and repeating until the number stopped going up
-@i@
-@@
-
-(
- #include <linux/acpi_mdio.h>
-|
- #include <linux/brcmphy.h>
-|
- #include <linux/dsa/loop.h>
-|
- #include <linux/dsa/sja1105.h>
-|
- #include <linux/ethtool.h>
-|
- #include <linux/ethtool_netlink.h>
-|
- #include <linux/fec.h>
-|
- #include <linux/fs_enet_pd.h>
-|
- #include <linux/fsl/enetc_mdio.h>
-|
- #include <linux/fwnode_mdio.h>
-|
- #include <linux/linkmode.h>
-|
- #include <linux/lsm_audit.h>
-|
- #include <linux/mdio-bitbang.h>
-|
- #include <linux/mdio.h>
-|
- #include <linux/mdio-mux.h>
-|
- #include <linux/mii.h>
-|
- #include <linux/mii_timestamper.h>
-|
- #include <linux/mlx5/accel.h>
-|
- #include <linux/mlx5/cq.h>
-|
- #include <linux/mlx5/device.h>
-|
- #include <linux/mlx5/driver.h>
-|
- #include <linux/mlx5/eswitch.h>
-|
- #include <linux/mlx5/fs.h>
-|
- #include <linux/mlx5/port.h>
-|
- #include <linux/mlx5/qp.h>
-|
- #include <linux/mlx5/rsc_dump.h>
-|
- #include <linux/mlx5/transobj.h>
-|
- #include <linux/mlx5/vport.h>
-|
- #include <linux/of_mdio.h>
-|
- #include <linux/of_net.h>
-|
- #include <linux/pcs-lynx.h>
-|
- #include <linux/pcs/pcs-xpcs.h>
-|
- #include <linux/phy.h>
-|
- #include <linux/phy_led_triggers.h>
-|
- #include <linux/phylink.h>
-|
- #include <linux/platform_data/bcmgenet.h>
-|
- #include <linux/platform_data/xilinx-ll-temac.h>
-|
- #include <linux/pxa168_eth.h>
-|
- #include <linux/qed/qed_eth_if.h>
-|
- #include <linux/qed/qed_fcoe_if.h>
-|
- #include <linux/qed/qed_if.h>
-|
- #include <linux/qed/qed_iov_if.h>
-|
- #include <linux/qed/qed_iscsi_if.h>
-|
- #include <linux/qed/qed_ll2_if.h>
-|
- #include <linux/qed/qed_nvmetcp_if.h>
-|
- #include <linux/qed/qed_rdma_if.h>
-|
- #include <linux/sfp.h>
-|
- #include <linux/sh_eth.h>
-|
- #include <linux/smsc911x.h>
-|
- #include <linux/soc/nxp/lpc32xx-misc.h>
-|
- #include <linux/stmmac.h>
-|
- #include <linux/sunrpc/svc_rdma.h>
-|
- #include <linux/sxgbe_platform.h>
-|
- #include <net/cfg80211.h>
-|
- #include <net/dsa.h>
-|
- #include <net/mac80211.h>
-|
- #include <net/selftests.h>
-|
- #include <rdma/ib_addr.h>
-|
- #include <rdma/ib_cache.h>
-|
- #include <rdma/ib_cm.h>
-|
- #include <rdma/ib_hdrs.h>
-|
- #include <rdma/ib_mad.h>
-|
- #include <rdma/ib_marshall.h>
-|
- #include <rdma/ib_pack.h>
-|
- #include <rdma/ib_pma.h>
-|
- #include <rdma/ib_sa.h>
-|
- #include <rdma/ib_smi.h>
-|
- #include <rdma/ib_umem.h>
-|
- #include <rdma/ib_umem_odp.h>
-|
- #include <rdma/ib_verbs.h>
-|
- #include <rdma/iw_cm.h>
-|
- #include <rdma/mr_pool.h>
-|
- #include <rdma/opa_addr.h>
-|
- #include <rdma/opa_port_info.h>
-|
- #include <rdma/opa_smi.h>
-|
- #include <rdma/opa_vnic.h>
-|
- #include <rdma/rdma_cm.h>
-|
- #include <rdma/rdma_cm_ib.h>
-|
- #include <rdma/rdmavt_cq.h>
-|
- #include <rdma/rdma_vt.h>
-|
- #include <rdma/rdmavt_qp.h>
-|
- #include <rdma/rw.h>
-|
- #include <rdma/tid_rdma_defs.h>
-|
- #include <rdma/uverbs_ioctl.h>
-|
- #include <rdma/uverbs_named_ioctl.h>
-|
- #include <rdma/uverbs_std_types.h>
-|
- #include <rdma/uverbs_types.h>
-|
- #include <soc/mscc/ocelot.h>
-|
- #include <soc/mscc/ocelot_ptp.h>
-|
- #include <soc/mscc/ocelot_vcap.h>
-|
- #include <trace/events/ib_mad.h>
-|
- #include <trace/events/rdma_core.h>
-|
- #include <trace/events/rdma.h>
-|
- #include <trace/events/rpcrdma.h>
-|
- #include <uapi/linux/ethtool.h>
-|
- #include <uapi/linux/ethtool_netlink.h>
-|
- #include <uapi/linux/mdio.h>
-|
- #include <uapi/linux/mii.h>
-)
-
-@depends on i@
-expression list args;
-@@
-
-(
-- bitmap_zero(args, __ETHTOOL_LINK_MODE_MASK_NBITS)
-+ linkmode_zero(args)
-|
-- bitmap_copy(args, __ETHTOOL_LINK_MODE_MASK_NBITS)
-+ linkmode_copy(args)
-|
-- bitmap_and(args, __ETHTOOL_LINK_MODE_MASK_NBITS)
-+ linkmode_and(args)
-|
-- bitmap_or(args, __ETHTOOL_LINK_MODE_MASK_NBITS)
-+ linkmode_or(args)
-|
-- bitmap_empty(args, ETHTOOL_LINK_MODE_MASK_NBITS)
-+ linkmode_empty(args)
-|
-- bitmap_andnot(args, __ETHTOOL_LINK_MODE_MASK_NBITS)
-+ linkmode_andnot(args)
-|
-- bitmap_equal(args, __ETHTOOL_LINK_MODE_MASK_NBITS)
-+ linkmode_equal(args)
-|
-- bitmap_intersects(args, __ETHTOOL_LINK_MODE_MASK_NBITS)
-+ linkmode_intersects(args)
-|
-- bitmap_subset(args, __ETHTOOL_LINK_MODE_MASK_NBITS)
-+ linkmode_subset(args)
-)
-
-Add missing linux/mii.h include to mellanox. -DaveM
-
-Signed-off-by: Sean Anderson <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/dsa/b53/b53_common.c              |  6 ++----
- drivers/net/dsa/bcm_sf2.c                     |  8 +++----
- drivers/net/dsa/hirschmann/hellcreek.c        |  6 ++----
- drivers/net/dsa/lantiq_gswip.c                | 14 ++++++-------
- drivers/net/dsa/microchip/ksz8795.c           |  8 +++----
- drivers/net/dsa/mv88e6xxx/chip.c              |  5 ++---
- drivers/net/dsa/ocelot/felix_vsc9959.c        |  8 +++----
- drivers/net/dsa/ocelot/seville_vsc9953.c      |  8 +++----
- drivers/net/dsa/qca/ar9331.c                  | 10 ++++-----
- drivers/net/dsa/sja1105/sja1105_main.c        |  7 +++----
- drivers/net/dsa/xrs700x/xrs700x.c             |  8 +++----
- drivers/net/ethernet/amd/xgbe/xgbe-ethtool.c  |  8 +++----
- drivers/net/ethernet/atheros/ag71xx.c         |  8 +++----
- drivers/net/ethernet/cadence/macb_main.c      | 11 +++++-----
- .../net/ethernet/freescale/enetc/enetc_pf.c   |  8 +++----
- .../net/ethernet/huawei/hinic/hinic_ethtool.c | 10 ++++-----
- .../net/ethernet/intel/ixgbe/ixgbe_ethtool.c  |  5 ++---
- drivers/net/ethernet/marvell/mvneta.c         | 10 ++++-----
- .../net/ethernet/marvell/mvpp2/mvpp2_main.c   |  7 +++----
- .../marvell/octeontx2/nic/otx2_ethtool.c      |  5 ++---
- drivers/net/ethernet/marvell/pxa168_eth.c     |  3 +--
- .../net/ethernet/mellanox/mlx4/en_ethtool.c   | 21 +++++++------------
- .../microchip/sparx5/sparx5_phylink.c         |  7 +++----
- drivers/net/ethernet/mscc/ocelot_net.c        |  7 +++----
- .../ethernet/pensando/ionic/ionic_ethtool.c   |  3 +--
- .../net/ethernet/xilinx/xilinx_axienet_main.c |  8 +++----
- drivers/net/pcs/pcs-xpcs.c                    |  2 +-
- drivers/net/phy/sfp-bus.c                     |  2 +-
- net/ethtool/ioctl.c                           |  7 +++----
- 29 files changed, 87 insertions(+), 133 deletions(-)
-
---- a/drivers/net/dsa/b53/b53_common.c
-+++ b/drivers/net/dsa/b53/b53_common.c
-@@ -1349,10 +1349,8 @@ void b53_phylink_validate(struct dsa_swi
-               phylink_set(mask, 100baseT_Full);
-       }
--      bitmap_and(supported, supported, mask,
--                 __ETHTOOL_LINK_MODE_MASK_NBITS);
--      bitmap_and(state->advertising, state->advertising, mask,
--                 __ETHTOOL_LINK_MODE_MASK_NBITS);
-+      linkmode_and(supported, supported, mask);
-+      linkmode_and(state->advertising, state->advertising, mask);
-       phylink_helper_basex_speed(state);
- }
---- a/drivers/net/dsa/bcm_sf2.c
-+++ b/drivers/net/dsa/bcm_sf2.c
-@@ -692,7 +692,7 @@ static void bcm_sf2_sw_validate(struct d
-           state->interface != PHY_INTERFACE_MODE_GMII &&
-           state->interface != PHY_INTERFACE_MODE_INTERNAL &&
-           state->interface != PHY_INTERFACE_MODE_MOCA) {
--              bitmap_zero(supported, __ETHTOOL_LINK_MODE_MASK_NBITS);
-+              linkmode_zero(supported);
-               if (port != core_readl(priv, CORE_IMP0_PRT_ID))
-                       dev_err(ds->dev,
-                               "Unsupported interface: %d for port %d\n",
-@@ -720,10 +720,8 @@ static void bcm_sf2_sw_validate(struct d
-       phylink_set(mask, 100baseT_Half);
-       phylink_set(mask, 100baseT_Full);
--      bitmap_and(supported, supported, mask,
--                 __ETHTOOL_LINK_MODE_MASK_NBITS);
--      bitmap_and(state->advertising, state->advertising, mask,
--                 __ETHTOOL_LINK_MODE_MASK_NBITS);
-+      linkmode_and(supported, supported, mask);
-+      linkmode_and(state->advertising, state->advertising, mask);
- }
- static void bcm_sf2_sw_mac_config(struct dsa_switch *ds, int port,
---- a/drivers/net/dsa/hirschmann/hellcreek.c
-+++ b/drivers/net/dsa/hirschmann/hellcreek.c
-@@ -1476,10 +1476,8 @@ static void hellcreek_phylink_validate(s
-       else
-               phylink_set(mask, 1000baseT_Full);
--      bitmap_and(supported, supported, mask,
--                 __ETHTOOL_LINK_MODE_MASK_NBITS);
--      bitmap_and(state->advertising, state->advertising, mask,
--                 __ETHTOOL_LINK_MODE_MASK_NBITS);
-+      linkmode_and(supported, supported, mask);
-+      linkmode_and(state->advertising, state->advertising, mask);
- }
- static int
---- a/drivers/net/dsa/lantiq_gswip.c
-+++ b/drivers/net/dsa/lantiq_gswip.c
-@@ -1452,10 +1452,8 @@ static void gswip_phylink_set_capab(unsi
-       phylink_set(mask, 100baseT_Half);
-       phylink_set(mask, 100baseT_Full);
--      bitmap_and(supported, supported, mask,
--                 __ETHTOOL_LINK_MODE_MASK_NBITS);
--      bitmap_and(state->advertising, state->advertising, mask,
--                 __ETHTOOL_LINK_MODE_MASK_NBITS);
-+      linkmode_and(supported, supported, mask);
-+      linkmode_and(state->advertising, state->advertising, mask);
- }
- static void gswip_xrx200_phylink_validate(struct dsa_switch *ds, int port,
-@@ -1483,7 +1481,7 @@ static void gswip_xrx200_phylink_validat
-                       goto unsupported;
-               break;
-       default:
--              bitmap_zero(supported, __ETHTOOL_LINK_MODE_MASK_NBITS);
-+              linkmode_zero(supported);
-               dev_err(ds->dev, "Unsupported port: %i\n", port);
-               return;
-       }
-@@ -1493,7 +1491,7 @@ static void gswip_xrx200_phylink_validat
-       return;
- unsupported:
--      bitmap_zero(supported, __ETHTOOL_LINK_MODE_MASK_NBITS);
-+      linkmode_zero(supported);
-       dev_err(ds->dev, "Unsupported interface '%s' for port %d\n",
-               phy_modes(state->interface), port);
- }
-@@ -1523,7 +1521,7 @@ static void gswip_xrx300_phylink_validat
-                       goto unsupported;
-               break;
-       default:
--              bitmap_zero(supported, __ETHTOOL_LINK_MODE_MASK_NBITS);
-+              linkmode_zero(supported);
-               dev_err(ds->dev, "Unsupported port: %i\n", port);
-               return;
-       }
-@@ -1533,7 +1531,7 @@ static void gswip_xrx300_phylink_validat
-       return;
- unsupported:
--      bitmap_zero(supported, __ETHTOOL_LINK_MODE_MASK_NBITS);
-+      linkmode_zero(supported);
-       dev_err(ds->dev, "Unsupported interface '%s' for port %d\n",
-               phy_modes(state->interface), port);
- }
---- a/drivers/net/dsa/microchip/ksz8795.c
-+++ b/drivers/net/dsa/microchip/ksz8795.c
-@@ -1542,15 +1542,13 @@ static void ksz8_validate(struct dsa_swi
-       phylink_set(mask, 100baseT_Half);
-       phylink_set(mask, 100baseT_Full);
--      bitmap_and(supported, supported, mask,
--                 __ETHTOOL_LINK_MODE_MASK_NBITS);
--      bitmap_and(state->advertising, state->advertising, mask,
--                 __ETHTOOL_LINK_MODE_MASK_NBITS);
-+      linkmode_and(supported, supported, mask);
-+      linkmode_and(state->advertising, state->advertising, mask);
-       return;
- unsupported:
--      bitmap_zero(supported, __ETHTOOL_LINK_MODE_MASK_NBITS);
-+      linkmode_zero(supported);
-       dev_err(ds->dev, "Unsupported interface: %s, port: %d\n",
-               phy_modes(state->interface), port);
- }
---- a/drivers/net/dsa/mv88e6xxx/chip.c
-+++ b/drivers/net/dsa/mv88e6xxx/chip.c
-@@ -683,9 +683,8 @@ static void mv88e6xxx_validate(struct ds
-       if (chip->info->ops->phylink_validate)
-               chip->info->ops->phylink_validate(chip, port, mask, state);
--      bitmap_and(supported, supported, mask, __ETHTOOL_LINK_MODE_MASK_NBITS);
--      bitmap_and(state->advertising, state->advertising, mask,
--                 __ETHTOOL_LINK_MODE_MASK_NBITS);
-+      linkmode_and(supported, supported, mask);
-+      linkmode_and(state->advertising, state->advertising, mask);
-       /* We can only operate at 2500BaseX or 1000BaseX.  If requested
-        * to advertise both, only report advertising at 2500BaseX.
---- a/drivers/net/dsa/ocelot/felix_vsc9959.c
-+++ b/drivers/net/dsa/ocelot/felix_vsc9959.c
-@@ -944,7 +944,7 @@ static void vsc9959_phylink_validate(str
-       if (state->interface != PHY_INTERFACE_MODE_NA &&
-           state->interface != ocelot_port->phy_mode) {
--              bitmap_zero(supported, __ETHTOOL_LINK_MODE_MASK_NBITS);
-+              linkmode_zero(supported);
-               return;
-       }
-@@ -966,10 +966,8 @@ static void vsc9959_phylink_validate(str
-               phylink_set(mask, 2500baseX_Full);
-       }
--      bitmap_and(supported, supported, mask,
--                 __ETHTOOL_LINK_MODE_MASK_NBITS);
--      bitmap_and(state->advertising, state->advertising, mask,
--                 __ETHTOOL_LINK_MODE_MASK_NBITS);
-+      linkmode_and(supported, supported, mask);
-+      linkmode_and(state->advertising, state->advertising, mask);
- }
- static int vsc9959_prevalidate_phy_mode(struct ocelot *ocelot, int port,
---- a/drivers/net/dsa/ocelot/seville_vsc9953.c
-+++ b/drivers/net/dsa/ocelot/seville_vsc9953.c
-@@ -1000,7 +1000,7 @@ static void vsc9953_phylink_validate(str
-       if (state->interface != PHY_INTERFACE_MODE_NA &&
-           state->interface != ocelot_port->phy_mode) {
--              bitmap_zero(supported, __ETHTOOL_LINK_MODE_MASK_NBITS);
-+              linkmode_zero(supported);
-               return;
-       }
-@@ -1019,10 +1019,8 @@ static void vsc9953_phylink_validate(str
-               phylink_set(mask, 2500baseX_Full);
-       }
--      bitmap_and(supported, supported, mask,
--                 __ETHTOOL_LINK_MODE_MASK_NBITS);
--      bitmap_and(state->advertising, state->advertising, mask,
--                 __ETHTOOL_LINK_MODE_MASK_NBITS);
-+      linkmode_and(supported, supported, mask);
-+      linkmode_and(state->advertising, state->advertising, mask);
- }
- static int vsc9953_prevalidate_phy_mode(struct ocelot *ocelot, int port,
---- a/drivers/net/dsa/qca/ar9331.c
-+++ b/drivers/net/dsa/qca/ar9331.c
-@@ -522,7 +522,7 @@ static void ar9331_sw_phylink_validate(s
-                       goto unsupported;
-               break;
-       default:
--              bitmap_zero(supported, __ETHTOOL_LINK_MODE_MASK_NBITS);
-+              linkmode_zero(supported);
-               dev_err(ds->dev, "Unsupported port: %i\n", port);
-               return;
-       }
-@@ -536,15 +536,13 @@ static void ar9331_sw_phylink_validate(s
-       phylink_set(mask, 100baseT_Half);
-       phylink_set(mask, 100baseT_Full);
--      bitmap_and(supported, supported, mask,
--                 __ETHTOOL_LINK_MODE_MASK_NBITS);
--      bitmap_and(state->advertising, state->advertising, mask,
--                 __ETHTOOL_LINK_MODE_MASK_NBITS);
-+      linkmode_and(supported, supported, mask);
-+      linkmode_and(state->advertising, state->advertising, mask);
-       return;
- unsupported:
--      bitmap_zero(supported, __ETHTOOL_LINK_MODE_MASK_NBITS);
-+      linkmode_zero(supported);
-       dev_err(ds->dev, "Unsupported interface: %d, port: %d\n",
-               state->interface, port);
- }
---- a/drivers/net/dsa/sja1105/sja1105_main.c
-+++ b/drivers/net/dsa/sja1105/sja1105_main.c
-@@ -1360,7 +1360,7 @@ static void sja1105_phylink_validate(str
-        */
-       if (state->interface != PHY_INTERFACE_MODE_NA &&
-           sja1105_phy_mode_mismatch(priv, port, state->interface)) {
--              bitmap_zero(supported, __ETHTOOL_LINK_MODE_MASK_NBITS);
-+              linkmode_zero(supported);
-               return;
-       }
-@@ -1380,9 +1380,8 @@ static void sja1105_phylink_validate(str
-               phylink_set(mask, 2500baseX_Full);
-       }
--      bitmap_and(supported, supported, mask, __ETHTOOL_LINK_MODE_MASK_NBITS);
--      bitmap_and(state->advertising, state->advertising, mask,
--                 __ETHTOOL_LINK_MODE_MASK_NBITS);
-+      linkmode_and(supported, supported, mask);
-+      linkmode_and(state->advertising, state->advertising, mask);
- }
- static int
---- a/drivers/net/dsa/xrs700x/xrs700x.c
-+++ b/drivers/net/dsa/xrs700x/xrs700x.c
-@@ -457,7 +457,7 @@ static void xrs700x_phylink_validate(str
-               phylink_set(mask, 1000baseT_Full);
-               break;
-       default:
--              bitmap_zero(supported, __ETHTOOL_LINK_MODE_MASK_NBITS);
-+              linkmode_zero(supported);
-               dev_err(ds->dev, "Unsupported port: %i\n", port);
-               return;
-       }
-@@ -468,10 +468,8 @@ static void xrs700x_phylink_validate(str
-       phylink_set(mask, 10baseT_Full);
-       phylink_set(mask, 100baseT_Full);
--      bitmap_and(supported, supported, mask,
--                 __ETHTOOL_LINK_MODE_MASK_NBITS);
--      bitmap_and(state->advertising, state->advertising, mask,
--                 __ETHTOOL_LINK_MODE_MASK_NBITS);
-+      linkmode_and(supported, supported, mask);
-+      linkmode_and(state->advertising, state->advertising, mask);
- }
- static void xrs700x_mac_link_up(struct dsa_switch *ds, int port,
---- a/drivers/net/ethernet/amd/xgbe/xgbe-ethtool.c
-+++ b/drivers/net/ethernet/amd/xgbe/xgbe-ethtool.c
-@@ -374,9 +374,8 @@ static int xgbe_set_link_ksettings(struc
-                 __ETHTOOL_LINK_MODE_MASK_NBITS, cmd->link_modes.advertising,
-                 __ETHTOOL_LINK_MODE_MASK_NBITS, lks->link_modes.supported);
--      bitmap_and(advertising,
--                 cmd->link_modes.advertising, lks->link_modes.supported,
--                 __ETHTOOL_LINK_MODE_MASK_NBITS);
-+      linkmode_and(advertising, cmd->link_modes.advertising,
-+                   lks->link_modes.supported);
-       if ((cmd->base.autoneg == AUTONEG_ENABLE) &&
-           bitmap_empty(advertising, __ETHTOOL_LINK_MODE_MASK_NBITS)) {
-@@ -389,8 +388,7 @@ static int xgbe_set_link_ksettings(struc
-       pdata->phy.autoneg = cmd->base.autoneg;
-       pdata->phy.speed = speed;
-       pdata->phy.duplex = cmd->base.duplex;
--      bitmap_copy(lks->link_modes.advertising, advertising,
--                  __ETHTOOL_LINK_MODE_MASK_NBITS);
-+      linkmode_copy(lks->link_modes.advertising, advertising);
-       if (cmd->base.autoneg == AUTONEG_ENABLE)
-               XGBE_SET_ADV(lks, Autoneg);
---- a/drivers/net/ethernet/atheros/ag71xx.c
-+++ b/drivers/net/ethernet/atheros/ag71xx.c
-@@ -1082,14 +1082,12 @@ static void ag71xx_mac_validate(struct p
-               phylink_set(mask, 1000baseX_Full);
-       }
--      bitmap_and(supported, supported, mask,
--                 __ETHTOOL_LINK_MODE_MASK_NBITS);
--      bitmap_and(state->advertising, state->advertising, mask,
--                 __ETHTOOL_LINK_MODE_MASK_NBITS);
-+      linkmode_and(supported, supported, mask);
-+      linkmode_and(state->advertising, state->advertising, mask);
-       return;
- unsupported:
--      bitmap_zero(supported, __ETHTOOL_LINK_MODE_MASK_NBITS);
-+      linkmode_zero(supported);
- }
- static void ag71xx_mac_pcs_get_state(struct phylink_config *config,
---- a/drivers/net/ethernet/cadence/macb_main.c
-+++ b/drivers/net/ethernet/cadence/macb_main.c
-@@ -523,21 +523,21 @@ static void macb_validate(struct phylink
-           state->interface != PHY_INTERFACE_MODE_SGMII &&
-           state->interface != PHY_INTERFACE_MODE_10GBASER &&
-           !phy_interface_mode_is_rgmii(state->interface)) {
--              bitmap_zero(supported, __ETHTOOL_LINK_MODE_MASK_NBITS);
-+              linkmode_zero(supported);
-               return;
-       }
-       if (!macb_is_gem(bp) &&
-           (state->interface == PHY_INTERFACE_MODE_GMII ||
-            phy_interface_mode_is_rgmii(state->interface))) {
--              bitmap_zero(supported, __ETHTOOL_LINK_MODE_MASK_NBITS);
-+              linkmode_zero(supported);
-               return;
-       }
-       if (state->interface == PHY_INTERFACE_MODE_10GBASER &&
-           !(bp->caps & MACB_CAPS_HIGH_SPEED &&
-             bp->caps & MACB_CAPS_PCS)) {
--              bitmap_zero(supported, __ETHTOOL_LINK_MODE_MASK_NBITS);
-+              linkmode_zero(supported);
-               return;
-       }
-@@ -576,9 +576,8 @@ static void macb_validate(struct phylink
-                       phylink_set(mask, 1000baseT_Half);
-       }
- out:
--      bitmap_and(supported, supported, mask, __ETHTOOL_LINK_MODE_MASK_NBITS);
--      bitmap_and(state->advertising, state->advertising, mask,
--                 __ETHTOOL_LINK_MODE_MASK_NBITS);
-+      linkmode_and(supported, supported, mask);
-+      linkmode_and(state->advertising, state->advertising, mask);
- }
- static void macb_usx_pcs_link_up(struct phylink_pcs *pcs, unsigned int mode,
---- a/drivers/net/ethernet/freescale/enetc/enetc_pf.c
-+++ b/drivers/net/ethernet/freescale/enetc/enetc_pf.c
-@@ -965,7 +965,7 @@ static void enetc_pl_mac_validate(struct
-           state->interface != PHY_INTERFACE_MODE_2500BASEX &&
-           state->interface != PHY_INTERFACE_MODE_USXGMII &&
-           !phy_interface_mode_is_rgmii(state->interface)) {
--              bitmap_zero(supported, __ETHTOOL_LINK_MODE_MASK_NBITS);
-+              linkmode_zero(supported);
-               return;
-       }
-@@ -988,10 +988,8 @@ static void enetc_pl_mac_validate(struct
-               phylink_set(mask, 2500baseX_Full);
-       }
--      bitmap_and(supported, supported, mask,
--                 __ETHTOOL_LINK_MODE_MASK_NBITS);
--      bitmap_and(state->advertising, state->advertising, mask,
--                 __ETHTOOL_LINK_MODE_MASK_NBITS);
-+      linkmode_and(supported, supported, mask);
-+      linkmode_and(state->advertising, state->advertising, mask);
- }
- static void enetc_pl_mac_config(struct phylink_config *config,
---- a/drivers/net/ethernet/huawei/hinic/hinic_ethtool.c
-+++ b/drivers/net/ethernet/huawei/hinic/hinic_ethtool.c
-@@ -322,12 +322,10 @@ static int hinic_get_link_ksettings(stru
-               }
-       }
--      bitmap_copy(link_ksettings->link_modes.supported,
--                  (unsigned long *)&settings.supported,
--                  __ETHTOOL_LINK_MODE_MASK_NBITS);
--      bitmap_copy(link_ksettings->link_modes.advertising,
--                  (unsigned long *)&settings.advertising,
--                  __ETHTOOL_LINK_MODE_MASK_NBITS);
-+      linkmode_copy(link_ksettings->link_modes.supported,
-+                    (unsigned long *)&settings.supported);
-+      linkmode_copy(link_ksettings->link_modes.advertising,
-+                    (unsigned long *)&settings.advertising);
-       return 0;
- }
---- a/drivers/net/ethernet/intel/ixgbe/ixgbe_ethtool.c
-+++ b/drivers/net/ethernet/intel/ixgbe/ixgbe_ethtool.c
-@@ -467,9 +467,8 @@ static int ixgbe_set_link_ksettings(stru
-                * this function does not support duplex forcing, but can
-                * limit the advertising of the adapter to the specified speed
-                */
--              if (!bitmap_subset(cmd->link_modes.advertising,
--                                 cmd->link_modes.supported,
--                                 __ETHTOOL_LINK_MODE_MASK_NBITS))
-+              if (!linkmode_subset(cmd->link_modes.advertising,
-+                                   cmd->link_modes.supported))
-                       return -EINVAL;
-               /* only allow one speed at a time if no autoneg */
---- a/drivers/net/ethernet/marvell/mvneta.c
-+++ b/drivers/net/ethernet/marvell/mvneta.c
-@@ -3835,14 +3835,14 @@ static void mvneta_validate(struct phyli
-        */
-       if (phy_interface_mode_is_8023z(state->interface)) {
-               if (!phylink_test(state->advertising, Autoneg)) {
--                      bitmap_zero(supported, __ETHTOOL_LINK_MODE_MASK_NBITS);
-+                      linkmode_zero(supported);
-                       return;
-               }
-       } else if (state->interface != PHY_INTERFACE_MODE_NA &&
-                  state->interface != PHY_INTERFACE_MODE_QSGMII &&
-                  state->interface != PHY_INTERFACE_MODE_SGMII &&
-                  !phy_interface_mode_is_rgmii(state->interface)) {
--              bitmap_zero(supported, __ETHTOOL_LINK_MODE_MASK_NBITS);
-+              linkmode_zero(supported);
-               return;
-       }
-@@ -3871,10 +3871,8 @@ static void mvneta_validate(struct phyli
-               phylink_set(mask, 100baseT_Full);
-       }
--      bitmap_and(supported, supported, mask,
--                 __ETHTOOL_LINK_MODE_MASK_NBITS);
--      bitmap_and(state->advertising, state->advertising, mask,
--                 __ETHTOOL_LINK_MODE_MASK_NBITS);
-+      linkmode_and(supported, supported, mask);
-+      linkmode_and(state->advertising, state->advertising, mask);
-       /* We can only operate at 2500BaseX or 1000BaseX.  If requested
-        * to advertise both, only report advertising at 2500BaseX.
---- a/drivers/net/ethernet/marvell/mvpp2/mvpp2_main.c
-+++ b/drivers/net/ethernet/marvell/mvpp2/mvpp2_main.c
-@@ -6377,15 +6377,14 @@ static void mvpp2_phylink_validate(struc
-               goto empty_set;
-       }
--      bitmap_and(supported, supported, mask, __ETHTOOL_LINK_MODE_MASK_NBITS);
--      bitmap_and(state->advertising, state->advertising, mask,
--                 __ETHTOOL_LINK_MODE_MASK_NBITS);
-+      linkmode_and(supported, supported, mask);
-+      linkmode_and(state->advertising, state->advertising, mask);
-       phylink_helper_basex_speed(state);
-       return;
- empty_set:
--      bitmap_zero(supported, __ETHTOOL_LINK_MODE_MASK_NBITS);
-+      linkmode_zero(supported);
- }
- static void mvpp2_xlg_config(struct mvpp2_port *port, unsigned int mode,
---- a/drivers/net/ethernet/marvell/octeontx2/nic/otx2_ethtool.c
-+++ b/drivers/net/ethernet/marvell/octeontx2/nic/otx2_ethtool.c
-@@ -1172,9 +1172,8 @@ static int otx2_set_link_ksettings(struc
-       otx2_get_link_ksettings(netdev, &cur_ks);
-       /* Check requested modes against supported modes by hardware */
--      if (!bitmap_subset(cmd->link_modes.advertising,
--                         cur_ks.link_modes.supported,
--                         __ETHTOOL_LINK_MODE_MASK_NBITS))
-+      if (!linkmode_subset(cmd->link_modes.advertising,
-+                           cur_ks.link_modes.supported))
-               return -EINVAL;
-       mutex_lock(&mbox->lock);
---- a/drivers/net/ethernet/marvell/pxa168_eth.c
-+++ b/drivers/net/ethernet/marvell/pxa168_eth.c
-@@ -977,8 +977,7 @@ static int pxa168_init_phy(struct net_de
-       cmd.base.phy_address = pep->phy_addr;
-       cmd.base.speed = pep->phy_speed;
-       cmd.base.duplex = pep->phy_duplex;
--      bitmap_copy(cmd.link_modes.advertising, PHY_BASIC_FEATURES,
--                  __ETHTOOL_LINK_MODE_MASK_NBITS);
-+      linkmode_copy(cmd.link_modes.advertising, PHY_BASIC_FEATURES);
-       cmd.base.autoneg = AUTONEG_ENABLE;
-       if (cmd.base.speed != 0)
---- a/drivers/net/ethernet/mellanox/mlx4/en_ethtool.c
-+++ b/drivers/net/ethernet/mellanox/mlx4/en_ethtool.c
-@@ -39,6 +39,7 @@
- #include <linux/in.h>
- #include <net/ip.h>
- #include <linux/bitmap.h>
-+#include <linux/mii.h>
- #include "mlx4_en.h"
- #include "en_port.h"
-@@ -643,10 +644,8 @@ static unsigned long *ptys2ethtool_link_
-               unsigned int i;                                         \
-               cfg = &ptys2ethtool_map[reg_];                          \
-               cfg->speed = speed_;                                    \
--              bitmap_zero(cfg->supported,                             \
--                          __ETHTOOL_LINK_MODE_MASK_NBITS);            \
--              bitmap_zero(cfg->advertised,                            \
--                          __ETHTOOL_LINK_MODE_MASK_NBITS);            \
-+              linkmode_zero(cfg->supported);                          \
-+              linkmode_zero(cfg->advertised);                         \
-               for (i = 0 ; i < ARRAY_SIZE(modes) ; ++i) {             \
-                       __set_bit(modes[i], cfg->supported);            \
-                       __set_bit(modes[i], cfg->advertised);           \
-@@ -702,10 +701,8 @@ static void ptys2ethtool_update_link_mod
-       int i;
-       for (i = 0; i < MLX4_LINK_MODES_SZ; i++) {
-               if (eth_proto & MLX4_PROT_MASK(i))
--                      bitmap_or(link_modes, link_modes,
--                                ptys2ethtool_link_mode(&ptys2ethtool_map[i],
--                                                       report),
--                                __ETHTOOL_LINK_MODE_MASK_NBITS);
-+                      linkmode_or(link_modes, link_modes,
-+                                  ptys2ethtool_link_mode(&ptys2ethtool_map[i], report));
-       }
- }
-@@ -716,11 +713,9 @@ static u32 ethtool2ptys_link_modes(const
-       u32 ptys_modes = 0;
-       for (i = 0; i < MLX4_LINK_MODES_SZ; i++) {
--              if (bitmap_intersects(
--                          ptys2ethtool_link_mode(&ptys2ethtool_map[i],
--                                                 report),
--                          link_modes,
--                          __ETHTOOL_LINK_MODE_MASK_NBITS))
-+              ulong *map_mode = ptys2ethtool_link_mode(&ptys2ethtool_map[i],
-+                                                       report);
-+              if (linkmode_intersects(map_mode, link_modes))
-                       ptys_modes |= 1 << i;
-       }
-       return ptys_modes;
---- a/drivers/net/ethernet/microchip/sparx5/sparx5_phylink.c
-+++ b/drivers/net/ethernet/microchip/sparx5/sparx5_phylink.c
-@@ -92,12 +92,11 @@ static void sparx5_phylink_validate(stru
-               }
-               break;
-       default:
--              bitmap_zero(supported, __ETHTOOL_LINK_MODE_MASK_NBITS);
-+              linkmode_zero(supported);
-               return;
-       }
--      bitmap_and(supported, supported, mask, __ETHTOOL_LINK_MODE_MASK_NBITS);
--      bitmap_and(state->advertising, state->advertising, mask,
--                 __ETHTOOL_LINK_MODE_MASK_NBITS);
-+      linkmode_and(supported, supported, mask);
-+      linkmode_and(state->advertising, state->advertising, mask);
- }
- static void sparx5_phylink_mac_config(struct phylink_config *config,
---- a/drivers/net/ethernet/mscc/ocelot_net.c
-+++ b/drivers/net/ethernet/mscc/ocelot_net.c
-@@ -1509,7 +1509,7 @@ static void vsc7514_phylink_validate(str
-       if (state->interface != PHY_INTERFACE_MODE_NA &&
-           state->interface != ocelot_port->phy_mode) {
--              bitmap_zero(supported, __ETHTOOL_LINK_MODE_MASK_NBITS);
-+              linkmode_zero(supported);
-               return;
-       }
-@@ -1528,9 +1528,8 @@ static void vsc7514_phylink_validate(str
-       phylink_set(mask, 2500baseT_Full);
-       phylink_set(mask, 2500baseX_Full);
--      bitmap_and(supported, supported, mask, __ETHTOOL_LINK_MODE_MASK_NBITS);
--      bitmap_and(state->advertising, state->advertising, mask,
--                 __ETHTOOL_LINK_MODE_MASK_NBITS);
-+      linkmode_and(supported, supported, mask);
-+      linkmode_and(state->advertising, state->advertising, mask);
- }
- static void vsc7514_phylink_mac_config(struct phylink_config *config,
---- a/drivers/net/ethernet/pensando/ionic/ionic_ethtool.c
-+++ b/drivers/net/ethernet/pensando/ionic/ionic_ethtool.c
-@@ -228,8 +228,7 @@ static int ionic_get_link_ksettings(stru
-               break;
-       }
--      bitmap_copy(ks->link_modes.advertising, ks->link_modes.supported,
--                  __ETHTOOL_LINK_MODE_MASK_NBITS);
-+      linkmode_copy(ks->link_modes.advertising, ks->link_modes.supported);
-       ethtool_link_ksettings_add_link_mode(ks, supported, FEC_BASER);
-       ethtool_link_ksettings_add_link_mode(ks, supported, FEC_RS);
---- a/drivers/net/ethernet/xilinx/xilinx_axienet_main.c
-+++ b/drivers/net/ethernet/xilinx/xilinx_axienet_main.c
-@@ -1565,7 +1565,7 @@ static void axienet_validate(struct phyl
-                       netdev_warn(ndev, "Cannot use PHY mode %s, supported: %s\n",
-                                   phy_modes(state->interface),
-                                   phy_modes(lp->phy_mode));
--                      bitmap_zero(supported, __ETHTOOL_LINK_MODE_MASK_NBITS);
-+                      linkmode_zero(supported);
-                       return;
-               }
-       }
-@@ -1598,10 +1598,8 @@ static void axienet_validate(struct phyl
-               break;
-       }
--      bitmap_and(supported, supported, mask,
--                 __ETHTOOL_LINK_MODE_MASK_NBITS);
--      bitmap_and(state->advertising, state->advertising, mask,
--                 __ETHTOOL_LINK_MODE_MASK_NBITS);
-+      linkmode_and(supported, supported, mask);
-+      linkmode_and(state->advertising, state->advertising, mask);
- }
- static void axienet_mac_pcs_get_state(struct phylink_config *config,
---- a/drivers/net/pcs/pcs-xpcs.c
-+++ b/drivers/net/pcs/pcs-xpcs.c
-@@ -637,7 +637,7 @@ void xpcs_validate(struct dw_xpcs *xpcs,
-       if (state->interface == PHY_INTERFACE_MODE_NA)
-               return;
--      bitmap_zero(xpcs_supported, __ETHTOOL_LINK_MODE_MASK_NBITS);
-+      linkmode_zero(xpcs_supported);
-       compat = xpcs_find_compat(xpcs->id, state->interface);
---- a/drivers/net/phy/sfp-bus.c
-+++ b/drivers/net/phy/sfp-bus.c
-@@ -379,7 +379,7 @@ void sfp_parse_support(struct sfp_bus *b
-       if (bus->sfp_quirk)
-               bus->sfp_quirk->modes(id, modes);
--      bitmap_or(support, support, modes, __ETHTOOL_LINK_MODE_MASK_NBITS);
-+      linkmode_or(support, support, modes);
-       phylink_set(support, Autoneg);
-       phylink_set(support, Pause);
---- a/net/ethtool/ioctl.c
-+++ b/net/ethtool/ioctl.c
-@@ -335,7 +335,7 @@ EXPORT_SYMBOL(ethtool_intersect_link_mas
- void ethtool_convert_legacy_u32_to_link_mode(unsigned long *dst,
-                                            u32 legacy_u32)
- {
--      bitmap_zero(dst, __ETHTOOL_LINK_MODE_MASK_NBITS);
-+      linkmode_zero(dst);
-       dst[0] = legacy_u32;
- }
- EXPORT_SYMBOL(ethtool_convert_legacy_u32_to_link_mode);
-@@ -350,11 +350,10 @@ bool ethtool_convert_link_mode_to_legacy
-       if (__ETHTOOL_LINK_MODE_MASK_NBITS > 32) {
-               __ETHTOOL_DECLARE_LINK_MODE_MASK(ext);
--              bitmap_zero(ext, __ETHTOOL_LINK_MODE_MASK_NBITS);
-+              linkmode_zero(ext);
-               bitmap_fill(ext, 32);
-               bitmap_complement(ext, ext, __ETHTOOL_LINK_MODE_MASK_NBITS);
--              if (bitmap_intersects(ext, src,
--                                    __ETHTOOL_LINK_MODE_MASK_NBITS)) {
-+              if (linkmode_intersects(ext, src)) {
-                       /* src mask goes beyond bit 31 */
-                       retval = false;
-               }
diff --git a/target/linux/generic/backport-5.15/703-01-v5.16-net-phylink-add-MAC-phy_interface_t-bitmap.patch b/target/linux/generic/backport-5.15/703-01-v5.16-net-phylink-add-MAC-phy_interface_t-bitmap.patch
deleted file mode 100644 (file)
index 885c2fc..0000000
+++ /dev/null
@@ -1,24 +0,0 @@
-From 38c310eb46f5f80213a92093af11af270c209a76 Mon Sep 17 00:00:00 2001
-From: Russell King <[email protected]>
-Date: Tue, 26 Oct 2021 11:06:06 +0100
-Subject: [PATCH] net: phylink: add MAC phy_interface_t bitmap
-
-Add a phy_interface_t bitmap so the MAC driver can specifiy which PHY
-interface modes it supports.
-
-Signed-off-by: Russell King <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- include/linux/phylink.h | 1 +
- 1 file changed, 1 insertion(+)
-
---- a/include/linux/phylink.h
-+++ b/include/linux/phylink.h
-@@ -78,6 +78,7 @@ struct phylink_config {
-       bool ovr_an_inband;
-       void (*get_fixed_state)(struct phylink_config *config,
-                               struct phylink_link_state *state);
-+      DECLARE_PHY_INTERFACE_MASK(supported_interfaces);
- };
- /**
diff --git a/target/linux/generic/backport-5.15/703-02-v5.16-net-phylink-use-supported_interfaces-for-phylink-val.patch b/target/linux/generic/backport-5.15/703-02-v5.16-net-phylink-use-supported_interfaces-for-phylink-val.patch
deleted file mode 100644 (file)
index 9800884..0000000
+++ /dev/null
@@ -1,98 +0,0 @@
-From d25f3a74f30aace819163dfa54f2a4b8ca1dc932 Mon Sep 17 00:00:00 2001
-From: "Russell King (Oracle)" <[email protected]>
-Date: Tue, 26 Oct 2021 11:06:11 +0100
-Subject: [PATCH] net: phylink: use supported_interfaces for phylink
- validation
-
-If the network device supplies a supported interface bitmap, we can use
-that during phylink's validation to simplify MAC drivers in two ways by
-using the supported_interfaces bitmap to:
-
-1. reject unsupported interfaces before calling into the MAC driver.
-2. generate the set of all supported link modes across all supported
-   interfaces (used mainly for SFP, but also some 10G PHYs.)
-
-Suggested-by: Sean Anderson <[email protected]>
-Signed-off-by: Russell King (Oracle) <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/phy/phylink.c | 36 ++++++++++++++++++++++++++++++++++++
- include/linux/phylink.h   | 12 ++++++++++--
- 2 files changed, 46 insertions(+), 2 deletions(-)
-
---- a/drivers/net/phy/phylink.c
-+++ b/drivers/net/phy/phylink.c
-@@ -155,9 +155,45 @@ static const char *phylink_an_mode_str(u
-       return mode < ARRAY_SIZE(modestr) ? modestr[mode] : "unknown";
- }
-+static int phylink_validate_any(struct phylink *pl, unsigned long *supported,
-+                              struct phylink_link_state *state)
-+{
-+      __ETHTOOL_DECLARE_LINK_MODE_MASK(all_adv) = { 0, };
-+      __ETHTOOL_DECLARE_LINK_MODE_MASK(all_s) = { 0, };
-+      __ETHTOOL_DECLARE_LINK_MODE_MASK(s);
-+      struct phylink_link_state t;
-+      int intf;
-+
-+      for (intf = 0; intf < PHY_INTERFACE_MODE_MAX; intf++) {
-+              if (test_bit(intf, pl->config->supported_interfaces)) {
-+                      linkmode_copy(s, supported);
-+
-+                      t = *state;
-+                      t.interface = intf;
-+                      pl->mac_ops->validate(pl->config, s, &t);
-+                      linkmode_or(all_s, all_s, s);
-+                      linkmode_or(all_adv, all_adv, t.advertising);
-+              }
-+      }
-+
-+      linkmode_copy(supported, all_s);
-+      linkmode_copy(state->advertising, all_adv);
-+
-+      return phylink_is_empty_linkmode(supported) ? -EINVAL : 0;
-+}
-+
- static int phylink_validate(struct phylink *pl, unsigned long *supported,
-                           struct phylink_link_state *state)
- {
-+      if (!phy_interface_empty(pl->config->supported_interfaces)) {
-+              if (state->interface == PHY_INTERFACE_MODE_NA)
-+                      return phylink_validate_any(pl, supported, state);
-+
-+              if (!test_bit(state->interface,
-+                            pl->config->supported_interfaces))
-+                      return -EINVAL;
-+      }
-+
-       pl->mac_ops->validate(pl->config, supported, state);
-       return phylink_is_empty_linkmode(supported) ? -EINVAL : 0;
---- a/include/linux/phylink.h
-+++ b/include/linux/phylink.h
-@@ -68,6 +68,8 @@ enum phylink_op_type {
-  * @ovr_an_inband: if true, override PCS to MLO_AN_INBAND
-  * @get_fixed_state: callback to execute to determine the fixed link state,
-  *                 if MAC link is at %MLO_AN_FIXED mode.
-+ * @supported_interfaces: bitmap describing which PHY_INTERFACE_MODE_xxx
-+ *                        are supported by the MAC/PCS.
-  */
- struct phylink_config {
-       struct device *dev;
-@@ -136,8 +138,14 @@ struct phylink_mac_ops {
-  * based on @state->advertising and/or @state->speed and update
-  * @state->interface accordingly. See phylink_helper_basex_speed().
-  *
-- * When @state->interface is %PHY_INTERFACE_MODE_NA, phylink expects the
-- * MAC driver to return all supported link modes.
-+ * When @config->supported_interfaces has been set, phylink will iterate
-+ * over the supported interfaces to determine the full capability of the
-+ * MAC. The validation function must not print errors if @state->interface
-+ * is set to an unexpected value.
-+ *
-+ * When @config->supported_interfaces is empty, phylink will call this
-+ * function with @state->interface set to %PHY_INTERFACE_MODE_NA, and
-+ * expects the MAC driver to return all supported link modes.
-  *
-  * If the @state->interface mode is not supported, then the @supported
-  * mask must be cleared.
diff --git a/target/linux/generic/backport-5.15/703-03-v5.16-net-dsa-populate-supported_interfaces-member.patch b/target/linux/generic/backport-5.15/703-03-v5.16-net-dsa-populate-supported_interfaces-member.patch
deleted file mode 100644 (file)
index b438786..0000000
+++ /dev/null
@@ -1,63 +0,0 @@
-From c07c6e8eb4b38bae921f9e2f108d1e7f8e14226e Mon Sep 17 00:00:00 2001
-From: =?UTF-8?q?Marek=20Beh=C3=BAn?= <[email protected]>
-Date: Thu, 28 Oct 2021 18:00:14 +0100
-Subject: [PATCH] net: dsa: populate supported_interfaces member
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-Add a new DSA switch operation, phylink_get_interfaces, which should
-fill in which PHY_INTERFACE_MODE_* are supported by given port.
-
-Use this before phylink_create() to fill phylinks supported_interfaces
-member, allowing phylink to determine which PHY_INTERFACE_MODEs are
-supported.
-
-Signed-off-by: Marek Behún <[email protected]>
-[tweaked patch and description to add more complete support -- rmk]
-Signed-off-by: Russell King <[email protected]>
-Signed-off-by: Russell King (Oracle) <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- include/net/dsa.h | 2 ++
- net/dsa/port.c    | 4 ++++
- net/dsa/slave.c   | 4 ++++
- 3 files changed, 10 insertions(+)
-
---- a/include/net/dsa.h
-+++ b/include/net/dsa.h
-@@ -654,6 +654,8 @@ struct dsa_switch_ops {
-       /*
-        * PHYLINK integration
-        */
-+      void    (*phylink_get_interfaces)(struct dsa_switch *ds, int port,
-+                                        unsigned long *supported_interfaces);
-       void    (*phylink_validate)(struct dsa_switch *ds, int port,
-                                   unsigned long *supported,
-                                   struct phylink_link_state *state);
---- a/net/dsa/port.c
-+++ b/net/dsa/port.c
-@@ -1188,6 +1188,10 @@ static int dsa_port_phylink_register(str
-       dp->pl_config.type = PHYLINK_DEV;
-       dp->pl_config.pcs_poll = ds->pcs_poll;
-+      if (ds->ops->phylink_get_interfaces)
-+              ds->ops->phylink_get_interfaces(ds, dp->index,
-+                                      dp->pl_config.supported_interfaces);
-+
-       dp->pl = phylink_create(&dp->pl_config, of_fwnode_handle(port_dn),
-                               mode, &dsa_port_phylink_mac_ops);
-       if (IS_ERR(dp->pl)) {
---- a/net/dsa/slave.c
-+++ b/net/dsa/slave.c
-@@ -1837,6 +1837,10 @@ static int dsa_slave_phy_setup(struct ne
-               dp->pl_config.poll_fixed_state = true;
-       }
-+      if (ds->ops->phylink_get_interfaces)
-+              ds->ops->phylink_get_interfaces(ds, dp->index,
-+                                      dp->pl_config.supported_interfaces);
-+
-       dp->pl = phylink_create(&dp->pl_config, of_fwnode_handle(port_dn), mode,
-                               &dsa_port_phylink_mac_ops);
-       if (IS_ERR(dp->pl)) {
diff --git a/target/linux/generic/backport-5.15/703-04-v5.17-net-dsa-consolidate-phylink-creation.patch b/target/linux/generic/backport-5.15/703-04-v5.17-net-dsa-consolidate-phylink-creation.patch
deleted file mode 100644 (file)
index 9b67a8a..0000000
+++ /dev/null
@@ -1,149 +0,0 @@
-From 21bd64bd717dedac96f53b668144cbe37d3c12d4 Mon Sep 17 00:00:00 2001
-From: "Russell King (Oracle)" <[email protected]>
-Date: Tue, 30 Nov 2021 13:09:55 +0000
-Subject: [PATCH] net: dsa: consolidate phylink creation
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-The code in port.c and slave.c creating the phylink instance is very
-similar - let's consolidate this into a single function.
-
-Signed-off-by: Russell King (Oracle) <[email protected]>
-Reviewed-by: Marek Behún <[email protected]>
-Reviewed-by: Andrew Lunn <[email protected]>
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- net/dsa/dsa_priv.h |  2 +-
- net/dsa/port.c     | 44 ++++++++++++++++++++++++++++----------------
- net/dsa/slave.c    | 19 +++----------------
- 3 files changed, 32 insertions(+), 33 deletions(-)
-
---- a/net/dsa/dsa_priv.h
-+++ b/net/dsa/dsa_priv.h
-@@ -261,13 +261,13 @@ int dsa_port_mrp_add_ring_role(const str
-                              const struct switchdev_obj_ring_role_mrp *mrp);
- int dsa_port_mrp_del_ring_role(const struct dsa_port *dp,
-                              const struct switchdev_obj_ring_role_mrp *mrp);
-+int dsa_port_phylink_create(struct dsa_port *dp);
- int dsa_port_link_register_of(struct dsa_port *dp);
- void dsa_port_link_unregister_of(struct dsa_port *dp);
- int dsa_port_hsr_join(struct dsa_port *dp, struct net_device *hsr);
- void dsa_port_hsr_leave(struct dsa_port *dp, struct net_device *hsr);
- int dsa_port_tag_8021q_vlan_add(struct dsa_port *dp, u16 vid, bool broadcast);
- void dsa_port_tag_8021q_vlan_del(struct dsa_port *dp, u16 vid, bool broadcast);
--extern const struct phylink_mac_ops dsa_port_phylink_mac_ops;
- static inline bool dsa_port_offloads_bridge_port(struct dsa_port *dp,
-                                                const struct net_device *dev)
---- a/net/dsa/port.c
-+++ b/net/dsa/port.c
-@@ -1092,7 +1092,7 @@ static void dsa_port_phylink_mac_link_up
-                                    speed, duplex, tx_pause, rx_pause);
- }
--const struct phylink_mac_ops dsa_port_phylink_mac_ops = {
-+static const struct phylink_mac_ops dsa_port_phylink_mac_ops = {
-       .validate = dsa_port_phylink_validate,
-       .mac_pcs_get_state = dsa_port_phylink_mac_pcs_get_state,
-       .mac_config = dsa_port_phylink_mac_config,
-@@ -1101,6 +1101,30 @@ const struct phylink_mac_ops dsa_port_ph
-       .mac_link_up = dsa_port_phylink_mac_link_up,
- };
-+int dsa_port_phylink_create(struct dsa_port *dp)
-+{
-+      struct dsa_switch *ds = dp->ds;
-+      phy_interface_t mode;
-+      int err;
-+
-+      err = of_get_phy_mode(dp->dn, &mode);
-+      if (err)
-+              mode = PHY_INTERFACE_MODE_NA;
-+
-+      if (ds->ops->phylink_get_interfaces)
-+              ds->ops->phylink_get_interfaces(ds, dp->index,
-+                                      dp->pl_config.supported_interfaces);
-+
-+      dp->pl = phylink_create(&dp->pl_config, of_fwnode_handle(dp->dn),
-+                              mode, &dsa_port_phylink_mac_ops);
-+      if (IS_ERR(dp->pl)) {
-+              pr_err("error creating PHYLINK: %ld\n", PTR_ERR(dp->pl));
-+              return PTR_ERR(dp->pl);
-+      }
-+
-+      return 0;
-+}
-+
- static int dsa_port_setup_phy_of(struct dsa_port *dp, bool enable)
- {
-       struct dsa_switch *ds = dp->ds;
-@@ -1177,27 +1201,15 @@ static int dsa_port_phylink_register(str
- {
-       struct dsa_switch *ds = dp->ds;
-       struct device_node *port_dn = dp->dn;
--      phy_interface_t mode;
-       int err;
--      err = of_get_phy_mode(port_dn, &mode);
--      if (err)
--              mode = PHY_INTERFACE_MODE_NA;
--
-       dp->pl_config.dev = ds->dev;
-       dp->pl_config.type = PHYLINK_DEV;
-       dp->pl_config.pcs_poll = ds->pcs_poll;
--      if (ds->ops->phylink_get_interfaces)
--              ds->ops->phylink_get_interfaces(ds, dp->index,
--                                      dp->pl_config.supported_interfaces);
--
--      dp->pl = phylink_create(&dp->pl_config, of_fwnode_handle(port_dn),
--                              mode, &dsa_port_phylink_mac_ops);
--      if (IS_ERR(dp->pl)) {
--              pr_err("error creating PHYLINK: %ld\n", PTR_ERR(dp->pl));
--              return PTR_ERR(dp->pl);
--      }
-+      err = dsa_port_phylink_create(dp);
-+      if (err)
-+              return err;
-       err = phylink_of_phy_connect(dp->pl, port_dn, 0);
-       if (err && err != -ENODEV) {
---- a/net/dsa/slave.c
-+++ b/net/dsa/slave.c
-@@ -1817,14 +1817,9 @@ static int dsa_slave_phy_setup(struct ne
-       struct dsa_port *dp = dsa_slave_to_port(slave_dev);
-       struct device_node *port_dn = dp->dn;
-       struct dsa_switch *ds = dp->ds;
--      phy_interface_t mode;
-       u32 phy_flags = 0;
-       int ret;
--      ret = of_get_phy_mode(port_dn, &mode);
--      if (ret)
--              mode = PHY_INTERFACE_MODE_NA;
--
-       dp->pl_config.dev = &slave_dev->dev;
-       dp->pl_config.type = PHYLINK_NETDEV;
-@@ -1837,17 +1832,9 @@ static int dsa_slave_phy_setup(struct ne
-               dp->pl_config.poll_fixed_state = true;
-       }
--      if (ds->ops->phylink_get_interfaces)
--              ds->ops->phylink_get_interfaces(ds, dp->index,
--                                      dp->pl_config.supported_interfaces);
--
--      dp->pl = phylink_create(&dp->pl_config, of_fwnode_handle(port_dn), mode,
--                              &dsa_port_phylink_mac_ops);
--      if (IS_ERR(dp->pl)) {
--              netdev_err(slave_dev,
--                         "error creating PHYLINK: %ld\n", PTR_ERR(dp->pl));
--              return PTR_ERR(dp->pl);
--      }
-+      ret = dsa_port_phylink_create(dp);
-+      if (ret)
-+              return ret;
-       if (ds->ops->get_phy_flags)
-               phy_flags = ds->ops->get_phy_flags(ds, dp->index);
diff --git a/target/linux/generic/backport-5.15/703-05-v5.17-net-dsa-replace-phylink_get_interfaces-with-phylink_.patch b/target/linux/generic/backport-5.15/703-05-v5.17-net-dsa-replace-phylink_get_interfaces-with-phylink_.patch
deleted file mode 100644 (file)
index 1d9616c..0000000
+++ /dev/null
@@ -1,51 +0,0 @@
-From 072eea6c22b2af680c3949e64f9adde278c71e68 Mon Sep 17 00:00:00 2001
-From: "Russell King (Oracle)" <[email protected]>
-Date: Tue, 30 Nov 2021 13:10:01 +0000
-Subject: [PATCH] net: dsa: replace phylink_get_interfaces() with
- phylink_get_caps()
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-Phylink needs slightly more information than phylink_get_interfaces()
-allows us to get from the DSA drivers - we need the MAC capabilities.
-Replace the phylink_get_interfaces() method with phylink_get_caps() to
-allow DSA drivers to fill in the phylink_config MAC capabilities field
-as well.
-
-Signed-off-by: Russell King (Oracle) <[email protected]>
-Reviewed-by: Marek Behún <[email protected]>
-Reviewed-by: Andrew Lunn <[email protected]>
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- include/net/dsa.h | 4 ++--
- net/dsa/port.c    | 5 ++---
- 2 files changed, 4 insertions(+), 5 deletions(-)
-
---- a/include/net/dsa.h
-+++ b/include/net/dsa.h
-@@ -654,8 +654,8 @@ struct dsa_switch_ops {
-       /*
-        * PHYLINK integration
-        */
--      void    (*phylink_get_interfaces)(struct dsa_switch *ds, int port,
--                                        unsigned long *supported_interfaces);
-+      void    (*phylink_get_caps)(struct dsa_switch *ds, int port,
-+                                  struct phylink_config *config);
-       void    (*phylink_validate)(struct dsa_switch *ds, int port,
-                                   unsigned long *supported,
-                                   struct phylink_link_state *state);
---- a/net/dsa/port.c
-+++ b/net/dsa/port.c
-@@ -1111,9 +1111,8 @@ int dsa_port_phylink_create(struct dsa_p
-       if (err)
-               mode = PHY_INTERFACE_MODE_NA;
--      if (ds->ops->phylink_get_interfaces)
--              ds->ops->phylink_get_interfaces(ds, dp->index,
--                                      dp->pl_config.supported_interfaces);
-+      if (ds->ops->phylink_get_caps)
-+              ds->ops->phylink_get_caps(ds, dp->index, &dp->pl_config);
-       dp->pl = phylink_create(&dp->pl_config, of_fwnode_handle(dp->dn),
-                               mode, &dsa_port_phylink_mac_ops);
diff --git a/target/linux/generic/backport-5.15/703-06-v5.18-net-dsa-add-support-for-phylink-mac_select_pcs.patch b/target/linux/generic/backport-5.15/703-06-v5.18-net-dsa-add-support-for-phylink-mac_select_pcs.patch
deleted file mode 100644 (file)
index 9791ad2..0000000
+++ /dev/null
@@ -1,59 +0,0 @@
-From bde018222c6b084ac32933a9f933581dd83da18e Mon Sep 17 00:00:00 2001
-From: "Russell King (Oracle)" <[email protected]>
-Date: Thu, 17 Feb 2022 18:30:35 +0000
-Subject: [PATCH] net: dsa: add support for phylink mac_select_pcs()
-
-Add DSA support for the phylink mac_select_pcs() method so DSA drivers
-can return provide phylink with the appropriate PCS for the PHY
-interface mode.
-
-Signed-off-by: Russell King (Oracle) <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- include/net/dsa.h |  3 +++
- net/dsa/port.c    | 15 +++++++++++++++
- 2 files changed, 18 insertions(+)
-
---- a/include/net/dsa.h
-+++ b/include/net/dsa.h
-@@ -659,6 +659,9 @@ struct dsa_switch_ops {
-       void    (*phylink_validate)(struct dsa_switch *ds, int port,
-                                   unsigned long *supported,
-                                   struct phylink_link_state *state);
-+      struct phylink_pcs *(*phylink_mac_select_pcs)(struct dsa_switch *ds,
-+                                                    int port,
-+                                                    phy_interface_t iface);
-       int     (*phylink_mac_link_state)(struct dsa_switch *ds, int port,
-                                         struct phylink_link_state *state);
-       void    (*phylink_mac_config)(struct dsa_switch *ds, int port,
---- a/net/dsa/port.c
-+++ b/net/dsa/port.c
-@@ -1028,6 +1028,20 @@ static void dsa_port_phylink_mac_pcs_get
-       }
- }
-+static struct phylink_pcs *
-+dsa_port_phylink_mac_select_pcs(struct phylink_config *config,
-+                              phy_interface_t interface)
-+{
-+      struct dsa_port *dp = container_of(config, struct dsa_port, pl_config);
-+      struct dsa_switch *ds = dp->ds;
-+      struct phylink_pcs *pcs = NULL;
-+
-+      if (ds->ops->phylink_mac_select_pcs)
-+              pcs = ds->ops->phylink_mac_select_pcs(ds, dp->index, interface);
-+
-+      return pcs;
-+}
-+
- static void dsa_port_phylink_mac_config(struct phylink_config *config,
-                                       unsigned int mode,
-                                       const struct phylink_link_state *state)
-@@ -1094,6 +1108,7 @@ static void dsa_port_phylink_mac_link_up
- static const struct phylink_mac_ops dsa_port_phylink_mac_ops = {
-       .validate = dsa_port_phylink_validate,
-+      .mac_select_pcs = dsa_port_phylink_mac_select_pcs,
-       .mac_pcs_get_state = dsa_port_phylink_mac_pcs_get_state,
-       .mac_config = dsa_port_phylink_mac_config,
-       .mac_an_restart = dsa_port_phylink_mac_an_restart,
diff --git a/target/linux/generic/backport-5.15/703-07-v5.16-net-phy-add-phy_interface_t-bitmap-support.patch b/target/linux/generic/backport-5.15/703-07-v5.16-net-phy-add-phy_interface_t-bitmap-support.patch
deleted file mode 100644 (file)
index 1a7817b..0000000
+++ /dev/null
@@ -1,61 +0,0 @@
-From 8e20f591f204f8db7f1182918f8e2285d3f589e0 Mon Sep 17 00:00:00 2001
-From: "Russell King (Oracle)" <[email protected]>
-Date: Tue, 26 Oct 2021 11:06:01 +0100
-Subject: [PATCH] net: phy: add phy_interface_t bitmap support
-
-Add support for a bitmap for phy interface modes, which includes:
-- a macro to declare the interface bitmap
-- an inline helper to zero the interface bitmap
-- an inline helper to detect an empty interface bitmap
-- inline helpers to do a bitwise AND and OR operations on two interface
-  bitmaps
-
-Signed-off-by: Russell King (Oracle) <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- include/linux/phy.h | 34 ++++++++++++++++++++++++++++++++++
- 1 file changed, 34 insertions(+)
-
---- a/include/linux/phy.h
-+++ b/include/linux/phy.h
-@@ -155,6 +155,40 @@ typedef enum {
-       PHY_INTERFACE_MODE_MAX,
- } phy_interface_t;
-+/* PHY interface mode bitmap handling */
-+#define DECLARE_PHY_INTERFACE_MASK(name) \
-+      DECLARE_BITMAP(name, PHY_INTERFACE_MODE_MAX)
-+
-+static inline void phy_interface_zero(unsigned long *intf)
-+{
-+      bitmap_zero(intf, PHY_INTERFACE_MODE_MAX);
-+}
-+
-+static inline bool phy_interface_empty(const unsigned long *intf)
-+{
-+      return bitmap_empty(intf, PHY_INTERFACE_MODE_MAX);
-+}
-+
-+static inline void phy_interface_and(unsigned long *dst, const unsigned long *a,
-+                                   const unsigned long *b)
-+{
-+      bitmap_and(dst, a, b, PHY_INTERFACE_MODE_MAX);
-+}
-+
-+static inline void phy_interface_or(unsigned long *dst, const unsigned long *a,
-+                                  const unsigned long *b)
-+{
-+      bitmap_or(dst, a, b, PHY_INTERFACE_MODE_MAX);
-+}
-+
-+static inline void phy_interface_set_rgmii(unsigned long *intf)
-+{
-+      __set_bit(PHY_INTERFACE_MODE_RGMII, intf);
-+      __set_bit(PHY_INTERFACE_MODE_RGMII_ID, intf);
-+      __set_bit(PHY_INTERFACE_MODE_RGMII_RXID, intf);
-+      __set_bit(PHY_INTERFACE_MODE_RGMII_TXID, intf);
-+}
-+
- /*
-  * phy_supported_speeds - return all speeds currently supported by a PHY device
-  */
diff --git a/target/linux/generic/backport-5.15/703-08-v5.17-net-phylink-add-mac_select_pcs-method-to-phylink_mac.patch b/target/linux/generic/backport-5.15/703-08-v5.17-net-phylink-add-mac_select_pcs-method-to-phylink_mac.patch
deleted file mode 100644 (file)
index 5d5ac4b..0000000
+++ /dev/null
@@ -1,197 +0,0 @@
-From d1e86325af377129adb7fc6f34eb044ca6068b47 Mon Sep 17 00:00:00 2001
-From: "Russell King (Oracle)" <[email protected]>
-Date: Wed, 15 Dec 2021 15:34:15 +0000
-Subject: [PATCH] net: phylink: add mac_select_pcs() method to phylink_mac_ops
-
-mac_select_pcs() allows us to have an explicit point to query which
-PCS the MAC wishes to use for a particular PHY interface mode, thereby
-allowing us to add support to validate the link settings with the PCS.
-
-Phylink will also use this to select the PCS to be used during a major
-configuration event without the MAC driver needing to call
-phylink_set_pcs().
-
-Note that if mac_select_pcs() is present, the supported_interfaces
-bitmap must be filled in; this avoids mac_select_pcs() being called
-with PHY_INTERFACE_MODE_NA when we want to get support for all
-interface types. Phylink will return an error in phylink_create()
-unless this condition is satisfied.
-
-Signed-off-by: Russell King (Oracle) <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/phy/phylink.c | 68 +++++++++++++++++++++++++++++++++------
- include/linux/phylink.h   | 18 +++++++++++
- 2 files changed, 77 insertions(+), 9 deletions(-)
-
---- a/drivers/net/phy/phylink.c
-+++ b/drivers/net/phy/phylink.c
-@@ -155,6 +155,23 @@ static const char *phylink_an_mode_str(u
-       return mode < ARRAY_SIZE(modestr) ? modestr[mode] : "unknown";
- }
-+static int phylink_validate_mac_and_pcs(struct phylink *pl,
-+                                      unsigned long *supported,
-+                                      struct phylink_link_state *state)
-+{
-+      struct phylink_pcs *pcs;
-+
-+      if (pl->mac_ops->mac_select_pcs) {
-+              pcs = pl->mac_ops->mac_select_pcs(pl->config, state->interface);
-+              if (IS_ERR(pcs))
-+                      return PTR_ERR(pcs);
-+      }
-+
-+      pl->mac_ops->validate(pl->config, supported, state);
-+
-+      return phylink_is_empty_linkmode(supported) ? -EINVAL : 0;
-+}
-+
- static int phylink_validate_any(struct phylink *pl, unsigned long *supported,
-                               struct phylink_link_state *state)
- {
-@@ -170,9 +187,10 @@ static int phylink_validate_any(struct p
-                       t = *state;
-                       t.interface = intf;
--                      pl->mac_ops->validate(pl->config, s, &t);
--                      linkmode_or(all_s, all_s, s);
--                      linkmode_or(all_adv, all_adv, t.advertising);
-+                      if (!phylink_validate_mac_and_pcs(pl, s, &t)) {
-+                              linkmode_or(all_s, all_s, s);
-+                              linkmode_or(all_adv, all_adv, t.advertising);
-+                      }
-               }
-       }
-@@ -194,9 +212,7 @@ static int phylink_validate(struct phyli
-                       return -EINVAL;
-       }
--      pl->mac_ops->validate(pl->config, supported, state);
--
--      return phylink_is_empty_linkmode(supported) ? -EINVAL : 0;
-+      return phylink_validate_mac_and_pcs(pl, supported, state);
- }
- static int phylink_parse_fixedlink(struct phylink *pl,
-@@ -486,10 +502,21 @@ static void phylink_mac_pcs_an_restart(s
- static void phylink_major_config(struct phylink *pl, bool restart,
-                                 const struct phylink_link_state *state)
- {
-+      struct phylink_pcs *pcs = NULL;
-       int err;
-       phylink_dbg(pl, "major config %s\n", phy_modes(state->interface));
-+      if (pl->mac_ops->mac_select_pcs) {
-+              pcs = pl->mac_ops->mac_select_pcs(pl->config, state->interface);
-+              if (IS_ERR(pcs)) {
-+                      phylink_err(pl,
-+                                  "mac_select_pcs unexpectedly failed: %pe\n",
-+                                  pcs);
-+                      return;
-+              }
-+      }
-+
-       if (pl->mac_ops->mac_prepare) {
-               err = pl->mac_ops->mac_prepare(pl->config, pl->cur_link_an_mode,
-                                              state->interface);
-@@ -500,6 +527,12 @@ static void phylink_major_config(struct
-               }
-       }
-+      /* If we have a new PCS, switch to the new PCS after preparing the MAC
-+       * for the change.
-+       */
-+      if (pcs)
-+              phylink_set_pcs(pl, pcs);
-+
-       phylink_mac_config(pl, state);
-       if (pl->pcs_ops) {
-@@ -879,6 +912,14 @@ struct phylink *phylink_create(struct ph
-       struct phylink *pl;
-       int ret;
-+      /* Validate the supplied configuration */
-+      if (mac_ops->mac_select_pcs &&
-+          phy_interface_empty(config->supported_interfaces)) {
-+              dev_err(config->dev,
-+                      "phylink: error: empty supported_interfaces but mac_select_pcs() method present\n");
-+              return ERR_PTR(-EINVAL);
-+      }
-+
-       pl = kzalloc(sizeof(*pl), GFP_KERNEL);
-       if (!pl)
-               return ERR_PTR(-ENOMEM);
-@@ -947,9 +988,10 @@ EXPORT_SYMBOL_GPL(phylink_create);
-  * @pl: a pointer to a &struct phylink returned from phylink_create()
-  * @pcs: a pointer to the &struct phylink_pcs
-  *
-- * Bind the MAC PCS to phylink.  This may be called after phylink_create(),
-- * in mac_prepare() or mac_config() methods if it is desired to dynamically
-- * change the PCS.
-+ * Bind the MAC PCS to phylink.  This may be called after phylink_create().
-+ * If it is desired to dynamically change the PCS, then the preferred method
-+ * is to use mac_select_pcs(), but it may also be called in mac_prepare()
-+ * or mac_config().
-  *
-  * Please note that there are behavioural changes with the mac_config()
-  * callback if a PCS is present (denoting a newer setup) so removing a PCS
-@@ -960,6 +1002,14 @@ void phylink_set_pcs(struct phylink *pl,
- {
-       pl->pcs = pcs;
-       pl->pcs_ops = pcs->ops;
-+
-+      if (!pl->phylink_disable_state &&
-+          pl->cfg_link_an_mode == MLO_AN_INBAND) {
-+              if (pl->config->pcs_poll || pcs->poll)
-+                      mod_timer(&pl->link_poll, jiffies + HZ);
-+              else
-+                      del_timer(&pl->link_poll);
-+      }
- }
- EXPORT_SYMBOL_GPL(phylink_set_pcs);
---- a/include/linux/phylink.h
-+++ b/include/linux/phylink.h
-@@ -86,6 +86,7 @@ struct phylink_config {
- /**
-  * struct phylink_mac_ops - MAC operations structure.
-  * @validate: Validate and update the link configuration.
-+ * @mac_select_pcs: Select a PCS for the interface mode.
-  * @mac_pcs_get_state: Read the current link state from the hardware.
-  * @mac_prepare: prepare for a major reconfiguration of the interface.
-  * @mac_config: configure the MAC for the selected mode and state.
-@@ -100,6 +101,8 @@ struct phylink_mac_ops {
-       void (*validate)(struct phylink_config *config,
-                        unsigned long *supported,
-                        struct phylink_link_state *state);
-+      struct phylink_pcs *(*mac_select_pcs)(struct phylink_config *config,
-+                                            phy_interface_t interface);
-       void (*mac_pcs_get_state)(struct phylink_config *config,
-                                 struct phylink_link_state *state);
-       int (*mac_prepare)(struct phylink_config *config, unsigned int mode,
-@@ -152,6 +155,21 @@ struct phylink_mac_ops {
-  */
- void validate(struct phylink_config *config, unsigned long *supported,
-             struct phylink_link_state *state);
-+/**
-+ * mac_select_pcs: Select a PCS for the interface mode.
-+ * @config: a pointer to a &struct phylink_config.
-+ * @interface: PHY interface mode for PCS
-+ *
-+ * Return the &struct phylink_pcs for the specified interface mode, or
-+ * NULL if none is required, or an error pointer on error.
-+ *
-+ * This must not modify any state. It is used to query which PCS should
-+ * be used. Phylink will use this during validation to ensure that the
-+ * configuration is valid, and when setting a configuration to internally
-+ * set the PCS that will be used.
-+ */
-+struct phylink_pcs *mac_select_pcs(struct phylink_config *config,
-+                                 phy_interface_t interface);
- /**
-  * mac_pcs_get_state() - Read the current inband link state from the hardware
diff --git a/target/linux/generic/backport-5.15/703-09-v5.17-net-phylink-add-generic-validate-implementation.patch b/target/linux/generic/backport-5.15/703-09-v5.17-net-phylink-add-generic-validate-implementation.patch
deleted file mode 100644 (file)
index f30a566..0000000
+++ /dev/null
@@ -1,341 +0,0 @@
-From 34ae2c09d46a2d0abd907e139b466f798e4095a8 Mon Sep 17 00:00:00 2001
-From: "Russell King (Oracle)" <[email protected]>
-Date: Mon, 15 Nov 2021 10:00:27 +0000
-Subject: [PATCH] net: phylink: add generic validate implementation
-
-Add a generic validate() implementation using the supported_interfaces
-and a bitmask of MAC pause/speed/duplex capabilities. This allows us
-to entirely eliminate many driver private validate() implementations.
-
-We expose the underlying phylink_get_linkmodes() function so that
-drivers which have special needs can still benefit from conversion.
-
-Signed-off-by: Russell King (Oracle) <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/phy/phylink.c | 252 ++++++++++++++++++++++++++++++++++++++
- include/linux/phylink.h   |  31 +++++
- 2 files changed, 283 insertions(+)
-
---- a/drivers/net/phy/phylink.c
-+++ b/drivers/net/phy/phylink.c
-@@ -172,6 +172,258 @@ static int phylink_validate_mac_and_pcs(
-       return phylink_is_empty_linkmode(supported) ? -EINVAL : 0;
- }
-+static void phylink_caps_to_linkmodes(unsigned long *linkmodes,
-+                                    unsigned long caps)
-+{
-+      if (caps & MAC_SYM_PAUSE)
-+              __set_bit(ETHTOOL_LINK_MODE_Pause_BIT, linkmodes);
-+
-+      if (caps & MAC_ASYM_PAUSE)
-+              __set_bit(ETHTOOL_LINK_MODE_Asym_Pause_BIT, linkmodes);
-+
-+      if (caps & MAC_10HD)
-+              __set_bit(ETHTOOL_LINK_MODE_10baseT_Half_BIT, linkmodes);
-+
-+      if (caps & MAC_10FD)
-+              __set_bit(ETHTOOL_LINK_MODE_10baseT_Full_BIT, linkmodes);
-+
-+      if (caps & MAC_100HD) {
-+              __set_bit(ETHTOOL_LINK_MODE_100baseT_Half_BIT, linkmodes);
-+              __set_bit(ETHTOOL_LINK_MODE_100baseFX_Half_BIT, linkmodes);
-+      }
-+
-+      if (caps & MAC_100FD) {
-+              __set_bit(ETHTOOL_LINK_MODE_100baseT_Full_BIT, linkmodes);
-+              __set_bit(ETHTOOL_LINK_MODE_100baseT1_Full_BIT, linkmodes);
-+              __set_bit(ETHTOOL_LINK_MODE_100baseFX_Full_BIT, linkmodes);
-+      }
-+
-+      if (caps & MAC_1000HD)
-+              __set_bit(ETHTOOL_LINK_MODE_1000baseT_Half_BIT, linkmodes);
-+
-+      if (caps & MAC_1000FD) {
-+              __set_bit(ETHTOOL_LINK_MODE_1000baseT_Full_BIT, linkmodes);
-+              __set_bit(ETHTOOL_LINK_MODE_1000baseX_Full_BIT, linkmodes);
-+              __set_bit(ETHTOOL_LINK_MODE_1000baseT1_Full_BIT, linkmodes);
-+      }
-+
-+      if (caps & MAC_2500FD) {
-+              __set_bit(ETHTOOL_LINK_MODE_2500baseT_Full_BIT, linkmodes);
-+              __set_bit(ETHTOOL_LINK_MODE_2500baseX_Full_BIT, linkmodes);
-+      }
-+
-+      if (caps & MAC_5000FD)
-+              __set_bit(ETHTOOL_LINK_MODE_5000baseT_Full_BIT, linkmodes);
-+
-+      if (caps & MAC_10000FD) {
-+              __set_bit(ETHTOOL_LINK_MODE_10000baseT_Full_BIT, linkmodes);
-+              __set_bit(ETHTOOL_LINK_MODE_10000baseKX4_Full_BIT, linkmodes);
-+              __set_bit(ETHTOOL_LINK_MODE_10000baseKR_Full_BIT, linkmodes);
-+              __set_bit(ETHTOOL_LINK_MODE_10000baseR_FEC_BIT, linkmodes);
-+              __set_bit(ETHTOOL_LINK_MODE_10000baseCR_Full_BIT, linkmodes);
-+              __set_bit(ETHTOOL_LINK_MODE_10000baseSR_Full_BIT, linkmodes);
-+              __set_bit(ETHTOOL_LINK_MODE_10000baseLR_Full_BIT, linkmodes);
-+              __set_bit(ETHTOOL_LINK_MODE_10000baseLRM_Full_BIT, linkmodes);
-+              __set_bit(ETHTOOL_LINK_MODE_10000baseER_Full_BIT, linkmodes);
-+      }
-+
-+      if (caps & MAC_25000FD) {
-+              __set_bit(ETHTOOL_LINK_MODE_25000baseCR_Full_BIT, linkmodes);
-+              __set_bit(ETHTOOL_LINK_MODE_25000baseKR_Full_BIT, linkmodes);
-+              __set_bit(ETHTOOL_LINK_MODE_25000baseSR_Full_BIT, linkmodes);
-+      }
-+
-+      if (caps & MAC_40000FD) {
-+              __set_bit(ETHTOOL_LINK_MODE_40000baseKR4_Full_BIT, linkmodes);
-+              __set_bit(ETHTOOL_LINK_MODE_40000baseCR4_Full_BIT, linkmodes);
-+              __set_bit(ETHTOOL_LINK_MODE_40000baseSR4_Full_BIT, linkmodes);
-+              __set_bit(ETHTOOL_LINK_MODE_40000baseLR4_Full_BIT, linkmodes);
-+      }
-+
-+      if (caps & MAC_50000FD) {
-+              __set_bit(ETHTOOL_LINK_MODE_50000baseCR2_Full_BIT, linkmodes);
-+              __set_bit(ETHTOOL_LINK_MODE_50000baseKR2_Full_BIT, linkmodes);
-+              __set_bit(ETHTOOL_LINK_MODE_50000baseSR2_Full_BIT, linkmodes);
-+              __set_bit(ETHTOOL_LINK_MODE_50000baseKR_Full_BIT, linkmodes);
-+              __set_bit(ETHTOOL_LINK_MODE_50000baseSR_Full_BIT, linkmodes);
-+              __set_bit(ETHTOOL_LINK_MODE_50000baseCR_Full_BIT, linkmodes);
-+              __set_bit(ETHTOOL_LINK_MODE_50000baseLR_ER_FR_Full_BIT,
-+                        linkmodes);
-+              __set_bit(ETHTOOL_LINK_MODE_50000baseDR_Full_BIT, linkmodes);
-+      }
-+
-+      if (caps & MAC_56000FD) {
-+              __set_bit(ETHTOOL_LINK_MODE_56000baseKR4_Full_BIT, linkmodes);
-+              __set_bit(ETHTOOL_LINK_MODE_56000baseCR4_Full_BIT, linkmodes);
-+              __set_bit(ETHTOOL_LINK_MODE_56000baseSR4_Full_BIT, linkmodes);
-+              __set_bit(ETHTOOL_LINK_MODE_56000baseLR4_Full_BIT, linkmodes);
-+      }
-+
-+      if (caps & MAC_100000FD) {
-+              __set_bit(ETHTOOL_LINK_MODE_100000baseKR4_Full_BIT, linkmodes);
-+              __set_bit(ETHTOOL_LINK_MODE_100000baseSR4_Full_BIT, linkmodes);
-+              __set_bit(ETHTOOL_LINK_MODE_100000baseCR4_Full_BIT, linkmodes);
-+              __set_bit(ETHTOOL_LINK_MODE_100000baseLR4_ER4_Full_BIT,
-+                        linkmodes);
-+              __set_bit(ETHTOOL_LINK_MODE_100000baseKR2_Full_BIT, linkmodes);
-+              __set_bit(ETHTOOL_LINK_MODE_100000baseSR2_Full_BIT, linkmodes);
-+              __set_bit(ETHTOOL_LINK_MODE_100000baseCR2_Full_BIT, linkmodes);
-+              __set_bit(ETHTOOL_LINK_MODE_100000baseLR2_ER2_FR2_Full_BIT,
-+                        linkmodes);
-+              __set_bit(ETHTOOL_LINK_MODE_100000baseDR2_Full_BIT, linkmodes);
-+              __set_bit(ETHTOOL_LINK_MODE_100000baseKR_Full_BIT, linkmodes);
-+              __set_bit(ETHTOOL_LINK_MODE_100000baseSR_Full_BIT, linkmodes);
-+              __set_bit(ETHTOOL_LINK_MODE_100000baseLR_ER_FR_Full_BIT,
-+                        linkmodes);
-+              __set_bit(ETHTOOL_LINK_MODE_100000baseCR_Full_BIT, linkmodes);
-+              __set_bit(ETHTOOL_LINK_MODE_100000baseDR_Full_BIT, linkmodes);
-+      }
-+
-+      if (caps & MAC_200000FD) {
-+              __set_bit(ETHTOOL_LINK_MODE_200000baseKR4_Full_BIT, linkmodes);
-+              __set_bit(ETHTOOL_LINK_MODE_200000baseSR4_Full_BIT, linkmodes);
-+              __set_bit(ETHTOOL_LINK_MODE_200000baseLR4_ER4_FR4_Full_BIT,
-+                        linkmodes);
-+              __set_bit(ETHTOOL_LINK_MODE_200000baseDR4_Full_BIT, linkmodes);
-+              __set_bit(ETHTOOL_LINK_MODE_200000baseCR4_Full_BIT, linkmodes);
-+              __set_bit(ETHTOOL_LINK_MODE_200000baseKR2_Full_BIT, linkmodes);
-+              __set_bit(ETHTOOL_LINK_MODE_200000baseSR2_Full_BIT, linkmodes);
-+              __set_bit(ETHTOOL_LINK_MODE_200000baseLR2_ER2_FR2_Full_BIT,
-+                        linkmodes);
-+              __set_bit(ETHTOOL_LINK_MODE_200000baseDR2_Full_BIT, linkmodes);
-+              __set_bit(ETHTOOL_LINK_MODE_200000baseCR2_Full_BIT, linkmodes);
-+      }
-+
-+      if (caps & MAC_400000FD) {
-+              __set_bit(ETHTOOL_LINK_MODE_400000baseKR8_Full_BIT, linkmodes);
-+              __set_bit(ETHTOOL_LINK_MODE_400000baseSR8_Full_BIT, linkmodes);
-+              __set_bit(ETHTOOL_LINK_MODE_400000baseLR8_ER8_FR8_Full_BIT,
-+                        linkmodes);
-+              __set_bit(ETHTOOL_LINK_MODE_400000baseDR8_Full_BIT, linkmodes);
-+              __set_bit(ETHTOOL_LINK_MODE_400000baseCR8_Full_BIT, linkmodes);
-+              __set_bit(ETHTOOL_LINK_MODE_400000baseKR4_Full_BIT, linkmodes);
-+              __set_bit(ETHTOOL_LINK_MODE_400000baseSR4_Full_BIT, linkmodes);
-+              __set_bit(ETHTOOL_LINK_MODE_400000baseLR4_ER4_FR4_Full_BIT,
-+                        linkmodes);
-+              __set_bit(ETHTOOL_LINK_MODE_400000baseDR4_Full_BIT, linkmodes);
-+              __set_bit(ETHTOOL_LINK_MODE_400000baseCR4_Full_BIT, linkmodes);
-+      }
-+}
-+
-+/**
-+ * phylink_get_linkmodes() - get acceptable link modes
-+ * @linkmodes: ethtool linkmode mask (must be already initialised)
-+ * @interface: phy interface mode defined by &typedef phy_interface_t
-+ * @mac_capabilities: bitmask of MAC capabilities
-+ *
-+ * Set all possible pause, speed and duplex linkmodes in @linkmodes that
-+ * are supported by the @interface mode and @mac_capabilities. @linkmodes
-+ * must have been initialised previously.
-+ */
-+void phylink_get_linkmodes(unsigned long *linkmodes, phy_interface_t interface,
-+                         unsigned long mac_capabilities)
-+{
-+      unsigned long caps = MAC_SYM_PAUSE | MAC_ASYM_PAUSE;
-+
-+      switch (interface) {
-+      case PHY_INTERFACE_MODE_USXGMII:
-+              caps |= MAC_10000FD | MAC_5000FD | MAC_2500FD;
-+              fallthrough;
-+
-+      case PHY_INTERFACE_MODE_RGMII_TXID:
-+      case PHY_INTERFACE_MODE_RGMII_RXID:
-+      case PHY_INTERFACE_MODE_RGMII_ID:
-+      case PHY_INTERFACE_MODE_RGMII:
-+      case PHY_INTERFACE_MODE_QSGMII:
-+      case PHY_INTERFACE_MODE_SGMII:
-+      case PHY_INTERFACE_MODE_GMII:
-+              caps |= MAC_1000HD | MAC_1000FD;
-+              fallthrough;
-+
-+      case PHY_INTERFACE_MODE_REVRMII:
-+      case PHY_INTERFACE_MODE_RMII:
-+      case PHY_INTERFACE_MODE_REVMII:
-+      case PHY_INTERFACE_MODE_MII:
-+              caps |= MAC_10HD | MAC_10FD;
-+              fallthrough;
-+
-+      case PHY_INTERFACE_MODE_100BASEX:
-+              caps |= MAC_100HD | MAC_100FD;
-+              break;
-+
-+      case PHY_INTERFACE_MODE_TBI:
-+      case PHY_INTERFACE_MODE_MOCA:
-+      case PHY_INTERFACE_MODE_RTBI:
-+      case PHY_INTERFACE_MODE_1000BASEX:
-+              caps |= MAC_1000HD;
-+              fallthrough;
-+      case PHY_INTERFACE_MODE_TRGMII:
-+              caps |= MAC_1000FD;
-+              break;
-+
-+      case PHY_INTERFACE_MODE_2500BASEX:
-+              caps |= MAC_2500FD;
-+              break;
-+
-+      case PHY_INTERFACE_MODE_5GBASER:
-+              caps |= MAC_5000FD;
-+              break;
-+
-+      case PHY_INTERFACE_MODE_XGMII:
-+      case PHY_INTERFACE_MODE_RXAUI:
-+      case PHY_INTERFACE_MODE_XAUI:
-+      case PHY_INTERFACE_MODE_10GBASER:
-+      case PHY_INTERFACE_MODE_10GKR:
-+              caps |= MAC_10000FD;
-+              break;
-+
-+      case PHY_INTERFACE_MODE_25GBASER:
-+              caps |= MAC_25000FD;
-+              break;
-+
-+      case PHY_INTERFACE_MODE_XLGMII:
-+              caps |= MAC_40000FD;
-+              break;
-+
-+      case PHY_INTERFACE_MODE_INTERNAL:
-+              caps |= ~0;
-+              break;
-+
-+      case PHY_INTERFACE_MODE_NA:
-+      case PHY_INTERFACE_MODE_MAX:
-+      case PHY_INTERFACE_MODE_SMII:
-+              break;
-+      }
-+
-+      phylink_caps_to_linkmodes(linkmodes, caps & mac_capabilities);
-+}
-+EXPORT_SYMBOL_GPL(phylink_get_linkmodes);
-+
-+/**
-+ * phylink_generic_validate() - generic validate() callback implementation
-+ * @config: a pointer to a &struct phylink_config.
-+ * @supported: ethtool bitmask for supported link modes.
-+ * @state: a pointer to a &struct phylink_link_state.
-+ *
-+ * Generic implementation of the validate() callback that MAC drivers can
-+ * use when they pass the range of supported interfaces and MAC capabilities.
-+ * This makes use of phylink_get_linkmodes().
-+ */
-+void phylink_generic_validate(struct phylink_config *config,
-+                            unsigned long *supported,
-+                            struct phylink_link_state *state)
-+{
-+      __ETHTOOL_DECLARE_LINK_MODE_MASK(mask) = { 0, };
-+
-+      phylink_set_port_modes(mask);
-+      phylink_set(mask, Autoneg);
-+      phylink_get_linkmodes(mask, state->interface, config->mac_capabilities);
-+
-+      linkmode_and(supported, supported, mask);
-+      linkmode_and(state->advertising, state->advertising, mask);
-+}
-+EXPORT_SYMBOL_GPL(phylink_generic_validate);
-+
- static int phylink_validate_any(struct phylink *pl, unsigned long *supported,
-                               struct phylink_link_state *state)
- {
---- a/include/linux/phylink.h
-+++ b/include/linux/phylink.h
-@@ -20,6 +20,29 @@ enum {
-       MLO_AN_PHY = 0, /* Conventional PHY */
-       MLO_AN_FIXED,   /* Fixed-link mode */
-       MLO_AN_INBAND,  /* In-band protocol */
-+
-+      MAC_SYM_PAUSE   = BIT(0),
-+      MAC_ASYM_PAUSE  = BIT(1),
-+      MAC_10HD        = BIT(2),
-+      MAC_10FD        = BIT(3),
-+      MAC_10          = MAC_10HD | MAC_10FD,
-+      MAC_100HD       = BIT(4),
-+      MAC_100FD       = BIT(5),
-+      MAC_100         = MAC_100HD | MAC_100FD,
-+      MAC_1000HD      = BIT(6),
-+      MAC_1000FD      = BIT(7),
-+      MAC_1000        = MAC_1000HD | MAC_1000FD,
-+      MAC_2500FD      = BIT(8),
-+      MAC_5000FD      = BIT(9),
-+      MAC_10000FD     = BIT(10),
-+      MAC_20000FD     = BIT(11),
-+      MAC_25000FD     = BIT(12),
-+      MAC_40000FD     = BIT(13),
-+      MAC_50000FD     = BIT(14),
-+      MAC_56000FD     = BIT(15),
-+      MAC_100000FD    = BIT(16),
-+      MAC_200000FD    = BIT(17),
-+      MAC_400000FD    = BIT(18),
- };
- static inline bool phylink_autoneg_inband(unsigned int mode)
-@@ -70,6 +93,7 @@ enum phylink_op_type {
-  *                 if MAC link is at %MLO_AN_FIXED mode.
-  * @supported_interfaces: bitmap describing which PHY_INTERFACE_MODE_xxx
-  *                        are supported by the MAC/PCS.
-+ * @mac_capabilities: MAC pause/speed/duplex capabilities.
-  */
- struct phylink_config {
-       struct device *dev;
-@@ -81,6 +105,7 @@ struct phylink_config {
-       void (*get_fixed_state)(struct phylink_config *config,
-                               struct phylink_link_state *state);
-       DECLARE_PHY_INTERFACE_MASK(supported_interfaces);
-+      unsigned long mac_capabilities;
- };
- /**
-@@ -462,6 +487,12 @@ void pcs_link_up(struct phylink_pcs *pcs
-                phy_interface_t interface, int speed, int duplex);
- #endif
-+void phylink_get_linkmodes(unsigned long *linkmodes, phy_interface_t interface,
-+                         unsigned long mac_capabilities);
-+void phylink_generic_validate(struct phylink_config *config,
-+                            unsigned long *supported,
-+                            struct phylink_link_state *state);
-+
- struct phylink *phylink_create(struct phylink_config *, struct fwnode_handle *,
-                              phy_interface_t iface,
-                              const struct phylink_mac_ops *mac_ops);
diff --git a/target/linux/generic/backport-5.15/703-11-v5.17-net-phylink-add-pcs_validate-method.patch b/target/linux/generic/backport-5.15/703-11-v5.17-net-phylink-add-pcs_validate-method.patch
deleted file mode 100644 (file)
index 524ce9b..0000000
+++ /dev/null
@@ -1,106 +0,0 @@
-From 0d22d4b626a4eaa3196019092eb6c1919e9f8caa Mon Sep 17 00:00:00 2001
-From: "Russell King (Oracle)" <[email protected]>
-Date: Wed, 15 Dec 2021 15:34:20 +0000
-Subject: [PATCH] net: phylink: add pcs_validate() method
-
-Add a hook for PCS to validate the link parameters. This avoids MAC
-drivers having to have knowledge of their PCS in their validate()
-method, thereby allowing several MAC drivers to be simplfied.
-
-Signed-off-by: Russell King (Oracle) <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/phy/phylink.c | 31 +++++++++++++++++++++++++++++++
- include/linux/phylink.h   | 20 ++++++++++++++++++++
- 2 files changed, 51 insertions(+)
-
---- a/drivers/net/phy/phylink.c
-+++ b/drivers/net/phy/phylink.c
-@@ -160,13 +160,44 @@ static int phylink_validate_mac_and_pcs(
-                                       struct phylink_link_state *state)
- {
-       struct phylink_pcs *pcs;
-+      int ret;
-+      /* Get the PCS for this interface mode */
-       if (pl->mac_ops->mac_select_pcs) {
-               pcs = pl->mac_ops->mac_select_pcs(pl->config, state->interface);
-               if (IS_ERR(pcs))
-                       return PTR_ERR(pcs);
-+      } else {
-+              pcs = pl->pcs;
-       }
-+      if (pcs) {
-+              /* The PCS, if present, must be setup before phylink_create()
-+               * has been called. If the ops is not initialised, print an
-+               * error and backtrace rather than oopsing the kernel.
-+               */
-+              if (!pcs->ops) {
-+                      phylink_err(pl, "interface %s: uninitialised PCS\n",
-+                                  phy_modes(state->interface));
-+                      dump_stack();
-+                      return -EINVAL;
-+              }
-+
-+              /* Validate the link parameters with the PCS */
-+              if (pcs->ops->pcs_validate) {
-+                      ret = pcs->ops->pcs_validate(pcs, supported, state);
-+                      if (ret < 0 || phylink_is_empty_linkmode(supported))
-+                              return -EINVAL;
-+
-+                      /* Ensure the advertising mask is a subset of the
-+                       * supported mask.
-+                       */
-+                      linkmode_and(state->advertising, state->advertising,
-+                                   supported);
-+              }
-+      }
-+
-+      /* Then validate the link parameters with the MAC */
-       pl->mac_ops->validate(pl->config, supported, state);
-       return phylink_is_empty_linkmode(supported) ? -EINVAL : 0;
---- a/include/linux/phylink.h
-+++ b/include/linux/phylink.h
-@@ -398,6 +398,7 @@ struct phylink_pcs {
- /**
-  * struct phylink_pcs_ops - MAC PCS operations structure.
-+ * @pcs_validate: validate the link configuration.
-  * @pcs_get_state: read the current MAC PCS link state from the hardware.
-  * @pcs_config: configure the MAC PCS for the selected mode and state.
-  * @pcs_an_restart: restart 802.3z BaseX autonegotiation.
-@@ -405,6 +406,8 @@ struct phylink_pcs {
-  *               (where necessary).
-  */
- struct phylink_pcs_ops {
-+      int (*pcs_validate)(struct phylink_pcs *pcs, unsigned long *supported,
-+                          const struct phylink_link_state *state);
-       void (*pcs_get_state)(struct phylink_pcs *pcs,
-                             struct phylink_link_state *state);
-       int (*pcs_config)(struct phylink_pcs *pcs, unsigned int mode,
-@@ -418,6 +421,23 @@ struct phylink_pcs_ops {
- #if 0 /* For kernel-doc purposes only. */
- /**
-+ * pcs_validate() - validate the link configuration.
-+ * @pcs: a pointer to a &struct phylink_pcs.
-+ * @supported: ethtool bitmask for supported link modes.
-+ * @state: a const pointer to a &struct phylink_link_state.
-+ *
-+ * Validate the interface mode, and advertising's autoneg bit, removing any
-+ * media ethtool link modes that would not be supportable from the supported
-+ * mask. Phylink will propagate the changes to the advertising mask. See the
-+ * &struct phylink_mac_ops validate() method.
-+ *
-+ * Returns -EINVAL if the interface mode/autoneg mode is not supported.
-+ * Returns non-zero positive if the link state can be supported.
-+ */
-+int pcs_validate(struct phylink_pcs *pcs, unsigned long *supported,
-+               const struct phylink_link_state *state);
-+
-+/**
-  * pcs_get_state() - Read the current inband link state from the hardware
-  * @pcs: a pointer to a &struct phylink_pcs.
-  * @state: a pointer to a &struct phylink_link_state.
diff --git a/target/linux/generic/backport-5.15/703-12-v5.17-net-phylink-add-legacy_pre_march2020-indicator.patch b/target/linux/generic/backport-5.15/703-12-v5.17-net-phylink-add-legacy_pre_march2020-indicator.patch
deleted file mode 100644 (file)
index 16d5da9..0000000
+++ /dev/null
@@ -1,43 +0,0 @@
-From 3e5b1feccea7db576353ffc302f78d522e4116e6 Mon Sep 17 00:00:00 2001
-From: "Russell King (Oracle)" <[email protected]>
-Date: Thu, 9 Dec 2021 13:11:32 +0000
-Subject: [PATCH] net: phylink: add legacy_pre_march2020 indicator
-
-Add a boolean to phylink_config to indicate whether a driver has not
-been updated for the changes in commit 7cceb599d15d ("net: phylink:
-avoid mac_config calls"), and thus are reliant on the old behaviour.
-
-We were currently keying the phylink behaviour on the presence of a
-PCS, but this is sub-optimal for modern drivers that may not have a
-PCS.
-
-This commit merely introduces the new flag, but does not add any use,
-since we need all legacy drivers to set this flag before it can be
-used. Once these legacy drivers have been updated, we can remove this
-flag.
-
-Signed-off-by: Russell King (Oracle) <[email protected]>
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- include/linux/phylink.h | 3 +++
- 1 file changed, 3 insertions(+)
-
---- a/include/linux/phylink.h
-+++ b/include/linux/phylink.h
-@@ -84,6 +84,8 @@ enum phylink_op_type {
-  * struct phylink_config - PHYLINK configuration structure
-  * @dev: a pointer to a struct device associated with the MAC
-  * @type: operation type of PHYLINK instance
-+ * @legacy_pre_march2020: driver has not been updated for March 2020 updates
-+ *    (See commit 7cceb599d15d ("net: phylink: avoid mac_config calls")
-  * @pcs_poll: MAC PCS cannot provide link change interrupt
-  * @poll_fixed_state: if true, starts link_poll,
-  *                  if MAC link is at %MLO_AN_FIXED mode.
-@@ -98,6 +100,7 @@ enum phylink_op_type {
- struct phylink_config {
-       struct device *dev;
-       enum phylink_op_type type;
-+      bool legacy_pre_march2020;
-       bool pcs_poll;
-       bool poll_fixed_state;
-       bool mac_managed_pm;
diff --git a/target/linux/generic/backport-5.15/703-13-v5.17-net-dsa-mark-DSA-phylink-as-legacy_pre_march2020.patch b/target/linux/generic/backport-5.15/703-13-v5.17-net-dsa-mark-DSA-phylink-as-legacy_pre_march2020.patch
deleted file mode 100644 (file)
index 8498819..0000000
+++ /dev/null
@@ -1,36 +0,0 @@
-From 0a9f0794d9bd67e590a9488afe87fbb0419d9539 Mon Sep 17 00:00:00 2001
-From: "Russell King (Oracle)" <[email protected]>
-Date: Thu, 9 Dec 2021 13:11:38 +0000
-Subject: [PATCH] net: dsa: mark DSA phylink as legacy_pre_march2020
-
-The majority of DSA drivers do not make use of the PCS support, and
-thus operate in legacy mode. In order to preserve this behaviour in
-future, we need to set the legacy_pre_march2020 flag so phylink knows
-this may require the legacy calls.
-
-There are some DSA drivers that do make use of PCS support, and these
-will continue operating as before - legacy_pre_march2020 will not
-prevent split-PCS support enabling the newer phylink behaviour.
-
-Signed-off-by: Russell King (Oracle) <[email protected]>
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- net/dsa/port.c | 7 +++++++
- 1 file changed, 7 insertions(+)
-
---- a/net/dsa/port.c
-+++ b/net/dsa/port.c
-@@ -1126,6 +1126,13 @@ int dsa_port_phylink_create(struct dsa_p
-       if (err)
-               mode = PHY_INTERFACE_MODE_NA;
-+      /* Presence of phylink_mac_link_state or phylink_mac_an_restart is
-+       * an indicator of a legacy phylink driver.
-+       */
-+      if (ds->ops->phylink_mac_link_state ||
-+          ds->ops->phylink_mac_an_restart)
-+              dp->pl_config.legacy_pre_march2020 = true;
-+
-       if (ds->ops->phylink_get_caps)
-               ds->ops->phylink_get_caps(ds, dp->index, &dp->pl_config);
diff --git a/target/linux/generic/backport-5.15/703-14-v5.17-net-phylink-use-legacy_pre_march2020.patch b/target/linux/generic/backport-5.15/703-14-v5.17-net-phylink-use-legacy_pre_march2020.patch
deleted file mode 100644 (file)
index 73e5306..0000000
+++ /dev/null
@@ -1,115 +0,0 @@
-From 001f4261fe4d5ae710cf1f445b6cae6d9d3ae26e Mon Sep 17 00:00:00 2001
-From: "Russell King (Oracle)" <[email protected]>
-Date: Thu, 9 Dec 2021 13:11:48 +0000
-Subject: [PATCH] net: phylink: use legacy_pre_march2020
-
-Use the legacy flag to indicate whether we should operate in legacy
-mode. This allows us to stop using the presence of a PCS as an
-indicator to the age of the phylink user, and make PCS presence
-optional.
-
-Legacy mode involves:
-1) calling mac_config() whenever the link comes up
-2) calling mac_config() whenever the inband advertisement changes,
-   possibly followed by a call to mac_an_restart()
-3) making use of mac_an_restart()
-4) making use of mac_pcs_get_state()
-
-All the above functionality was moved to a seperate "PCS" block of
-operations in March 2020.
-
-Update the documents to indicate that the differences that this flag
-makes.
-
-Signed-off-by: Russell King (Oracle) <[email protected]>
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- drivers/net/phy/phylink.c | 12 ++++++------
- include/linux/phylink.h   | 17 +++++++++++++++++
- 2 files changed, 23 insertions(+), 6 deletions(-)
-
---- a/drivers/net/phy/phylink.c
-+++ b/drivers/net/phy/phylink.c
-@@ -777,7 +777,7 @@ static void phylink_mac_pcs_an_restart(s
-           phylink_autoneg_inband(pl->cur_link_an_mode)) {
-               if (pl->pcs_ops)
-                       pl->pcs_ops->pcs_an_restart(pl->pcs);
--              else
-+              else if (pl->config->legacy_pre_march2020)
-                       pl->mac_ops->mac_an_restart(pl->config);
-       }
- }
-@@ -855,7 +855,7 @@ static int phylink_change_inband_advert(
-       if (test_bit(PHYLINK_DISABLE_STOPPED, &pl->phylink_disable_state))
-               return 0;
--      if (!pl->pcs_ops) {
-+      if (!pl->pcs_ops && pl->config->legacy_pre_march2020) {
-               /* Legacy method */
-               phylink_mac_config(pl, &pl->link_config);
-               phylink_mac_pcs_an_restart(pl);
-@@ -900,7 +900,8 @@ static void phylink_mac_pcs_get_state(st
-       if (pl->pcs_ops)
-               pl->pcs_ops->pcs_get_state(pl->pcs, state);
--      else if (pl->mac_ops->mac_pcs_get_state)
-+      else if (pl->mac_ops->mac_pcs_get_state &&
-+               pl->config->legacy_pre_march2020)
-               pl->mac_ops->mac_pcs_get_state(pl->config, state);
-       else
-               state->link = 0;
-@@ -1094,12 +1095,11 @@ static void phylink_resolve(struct work_
-                       }
-                       phylink_major_config(pl, false, &link_state);
-                       pl->link_config.interface = link_state.interface;
--              } else if (!pl->pcs_ops) {
-+              } else if (!pl->pcs_ops && pl->config->legacy_pre_march2020) {
-                       /* The interface remains unchanged, only the speed,
-                        * duplex or pause settings have changed. Call the
-                        * old mac_config() method to configure the MAC/PCS
--                       * only if we do not have a PCS installed (an
--                       * unconverted user.)
-+                       * only if we do not have a legacy MAC driver.
-                        */
-                       phylink_mac_config(pl, &link_state);
-               }
---- a/include/linux/phylink.h
-+++ b/include/linux/phylink.h
-@@ -210,6 +210,10 @@ struct phylink_pcs *mac_select_pcs(struc
-  * negotiation completion state in @state->an_complete, and link up state
-  * in @state->link. If possible, @state->lp_advertising should also be
-  * populated.
-+ *
-+ * Note: This is a legacy method. This function will not be called unless
-+ * legacy_pre_march2020 is set in &struct phylink_config and there is no
-+ * PCS attached.
-  */
- void mac_pcs_get_state(struct phylink_config *config,
-                      struct phylink_link_state *state);
-@@ -250,6 +254,15 @@ int mac_prepare(struct phylink_config *c
-  * guaranteed to be correct, and so any mac_config() implementation must
-  * never reference these fields.
-  *
-+ * Note: For legacy March 2020 drivers (drivers with legacy_pre_march2020 set
-+ * in their &phylnk_config and which don't have a PCS), this function will be
-+ * called on each link up event, and to also change the in-band advert. For
-+ * non-legacy drivers, it will only be called to reconfigure the MAC for a
-+ * "major" change in e.g. interface mode. It will not be called for changes
-+ * in speed, duplex or pause modes or to change the in-band advertisement.
-+ * In any case, it is strongly preferred that speed, duplex and pause settings
-+ * are handled in the mac_link_up() method and not in this method.
-+ *
-  * (this requires a rewrite - please refer to mac_link_up() for situations
-  *  where the PCS and MAC are not tightly integrated.)
-  *
-@@ -334,6 +347,10 @@ int mac_finish(struct phylink_config *co
- /**
-  * mac_an_restart() - restart 802.3z BaseX autonegotiation
-  * @config: a pointer to a &struct phylink_config.
-+ *
-+ * Note: This is a legacy method. This function will not be called unless
-+ * legacy_pre_march2020 is set in &struct phylink_config and there is no
-+ * PCS attached.
-  */
- void mac_an_restart(struct phylink_config *config);
diff --git a/target/linux/generic/backport-5.15/703-15-v5.18-net-phy-phylink-fix-DSA-mac_select_pcs-introduction.patch b/target/linux/generic/backport-5.15/703-15-v5.18-net-phy-phylink-fix-DSA-mac_select_pcs-introduction.patch
deleted file mode 100644 (file)
index 924d0e9..0000000
+++ /dev/null
@@ -1,88 +0,0 @@
-From 1054457006d4a14de4ae4132030e33d7eedaeba1 Mon Sep 17 00:00:00 2001
-From: "Russell King (Oracle)" <[email protected]>
-Date: Mon, 21 Feb 2022 17:10:52 +0000
-Subject: [PATCH] net: phy: phylink: fix DSA mac_select_pcs() introduction
-
-Vladimir Oltean reports that probing on DSA drivers that aren't yet
-populating supported_interfaces now fails. Fix this by allowing
-phylink to detect whether DSA actually provides an underlying
-mac_select_pcs() implementation.
-
-Reported-by: Vladimir Oltean <[email protected]>
-Fixes: bde018222c6b ("net: dsa: add support for phylink mac_select_pcs()")
-Signed-off-by: Russell King (Oracle) <[email protected]>
-Tested-by: Vladimir Oltean <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- drivers/net/phy/phylink.c | 14 +++++++++++---
- net/dsa/port.c            |  2 +-
- 2 files changed, 12 insertions(+), 4 deletions(-)
-
---- a/drivers/net/phy/phylink.c
-+++ b/drivers/net/phy/phylink.c
-@@ -74,6 +74,7 @@ struct phylink {
-       struct work_struct resolve;
-       bool mac_link_dropped;
-+      bool using_mac_select_pcs;
-       struct sfp_bus *sfp_bus;
-       bool sfp_may_have_phy;
-@@ -163,7 +164,7 @@ static int phylink_validate_mac_and_pcs(
-       int ret;
-       /* Get the PCS for this interface mode */
--      if (pl->mac_ops->mac_select_pcs) {
-+      if (pl->using_mac_select_pcs) {
-               pcs = pl->mac_ops->mac_select_pcs(pl->config, state->interface);
-               if (IS_ERR(pcs))
-                       return PTR_ERR(pcs);
-@@ -790,7 +791,7 @@ static void phylink_major_config(struct
-       phylink_dbg(pl, "major config %s\n", phy_modes(state->interface));
--      if (pl->mac_ops->mac_select_pcs) {
-+      if (pl->using_mac_select_pcs) {
-               pcs = pl->mac_ops->mac_select_pcs(pl->config, state->interface);
-               if (IS_ERR(pcs)) {
-                       phylink_err(pl,
-@@ -1192,11 +1193,17 @@ struct phylink *phylink_create(struct ph
-                              phy_interface_t iface,
-                              const struct phylink_mac_ops *mac_ops)
- {
-+      bool using_mac_select_pcs = false;
-       struct phylink *pl;
-       int ret;
--      /* Validate the supplied configuration */
-       if (mac_ops->mac_select_pcs &&
-+          mac_ops->mac_select_pcs(config, PHY_INTERFACE_MODE_NA) !=
-+            ERR_PTR(-EOPNOTSUPP))
-+              using_mac_select_pcs = true;
-+
-+      /* Validate the supplied configuration */
-+      if (using_mac_select_pcs &&
-           phy_interface_empty(config->supported_interfaces)) {
-               dev_err(config->dev,
-                       "phylink: error: empty supported_interfaces but mac_select_pcs() method present\n");
-@@ -1221,6 +1228,7 @@ struct phylink *phylink_create(struct ph
-               return ERR_PTR(-EINVAL);
-       }
-+      pl->using_mac_select_pcs = using_mac_select_pcs;
-       pl->phy_state.interface = iface;
-       pl->link_interface = iface;
-       if (iface == PHY_INTERFACE_MODE_MOCA)
---- a/net/dsa/port.c
-+++ b/net/dsa/port.c
-@@ -1033,8 +1033,8 @@ dsa_port_phylink_mac_select_pcs(struct p
-                               phy_interface_t interface)
- {
-       struct dsa_port *dp = container_of(config, struct dsa_port, pl_config);
-+      struct phylink_pcs *pcs = ERR_PTR(-EOPNOTSUPP);
-       struct dsa_switch *ds = dp->ds;
--      struct phylink_pcs *pcs = NULL;
-       if (ds->ops->phylink_mac_select_pcs)
-               pcs = ds->ops->phylink_mac_select_pcs(ds, dp->index, interface);
diff --git a/target/linux/generic/backport-5.15/703-16-v5.16-net-mvneta-populate-supported_interfaces-member.patch b/target/linux/generic/backport-5.15/703-16-v5.16-net-mvneta-populate-supported_interfaces-member.patch
deleted file mode 100644 (file)
index f21fa4b..0000000
+++ /dev/null
@@ -1,48 +0,0 @@
-From fdedb695e6a8657302341cda81d519ef04f9acaa Mon Sep 17 00:00:00 2001
-From: Russell King <[email protected]>
-Date: Wed, 27 Oct 2021 10:03:43 +0100
-Subject: [PATCH] net: mvneta: populate supported_interfaces member
-
-Populate the phy_interface_t bitmap for the Marvell mvneta driver with
-interfaces modes supported by the MAC.
-
-Signed-off-by: Russell King <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/ethernet/marvell/mvneta.c | 25 +++++++++++++++++++++++++
- 1 file changed, 25 insertions(+)
-
---- a/drivers/net/ethernet/marvell/mvneta.c
-+++ b/drivers/net/ethernet/marvell/mvneta.c
-@@ -5180,6 +5180,31 @@ static int mvneta_probe(struct platform_
-       pp->phylink_config.dev = &dev->dev;
-       pp->phylink_config.type = PHYLINK_NETDEV;
-+      phy_interface_set_rgmii(pp->phylink_config.supported_interfaces);
-+      __set_bit(PHY_INTERFACE_MODE_QSGMII,
-+                pp->phylink_config.supported_interfaces);
-+      if (comphy) {
-+              /* If a COMPHY is present, we can support any of the serdes
-+               * modes and switch between them.
-+               */
-+              __set_bit(PHY_INTERFACE_MODE_SGMII,
-+                        pp->phylink_config.supported_interfaces);
-+              __set_bit(PHY_INTERFACE_MODE_1000BASEX,
-+                        pp->phylink_config.supported_interfaces);
-+              __set_bit(PHY_INTERFACE_MODE_2500BASEX,
-+                        pp->phylink_config.supported_interfaces);
-+      } else if (phy_mode == PHY_INTERFACE_MODE_2500BASEX) {
-+              /* No COMPHY, with only 2500BASE-X mode supported */
-+              __set_bit(PHY_INTERFACE_MODE_2500BASEX,
-+                        pp->phylink_config.supported_interfaces);
-+      } else if (phy_mode == PHY_INTERFACE_MODE_1000BASEX ||
-+                 phy_mode == PHY_INTERFACE_MODE_SGMII) {
-+              /* No COMPHY, we can switch between 1000BASE-X and SGMII */
-+              __set_bit(PHY_INTERFACE_MODE_1000BASEX,
-+                        pp->phylink_config.supported_interfaces);
-+              __set_bit(PHY_INTERFACE_MODE_SGMII,
-+                        pp->phylink_config.supported_interfaces);
-+      }
-       phylink = phylink_create(&pp->phylink_config, pdev->dev.fwnode,
-                                phy_mode, &mvneta_phylink_ops);
diff --git a/target/linux/generic/backport-5.15/703-17-v5.16-net-mvneta-remove-interface-checks-in-mvneta_validat.patch b/target/linux/generic/backport-5.15/703-17-v5.16-net-mvneta-remove-interface-checks-in-mvneta_validat.patch
deleted file mode 100644 (file)
index e287e39..0000000
+++ /dev/null
@@ -1,35 +0,0 @@
-From d9ca72807ecb236f679b960c70ef5b7d4a5f0222 Mon Sep 17 00:00:00 2001
-From: "Russell King (Oracle)" <[email protected]>
-Date: Wed, 27 Oct 2021 10:03:48 +0100
-Subject: [PATCH] net: mvneta: remove interface checks in mvneta_validate()
-
-As phylink checks the interface mode against the supported_interfaces
-bitmap, we no longer need to validate the interface mode in the
-validation function. Remove this to simplify it.
-
-Signed-off-by: Russell King (Oracle) <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/ethernet/marvell/mvneta.c | 11 ++---------
- 1 file changed, 2 insertions(+), 9 deletions(-)
-
---- a/drivers/net/ethernet/marvell/mvneta.c
-+++ b/drivers/net/ethernet/marvell/mvneta.c
-@@ -3833,15 +3833,8 @@ static void mvneta_validate(struct phyli
-        * "Bit 2 Field InBandAnEn In-band Auto-Negotiation enable. ...
-        * When <PortType> = 1 (1000BASE-X) this field must be set to 1."
-        */
--      if (phy_interface_mode_is_8023z(state->interface)) {
--              if (!phylink_test(state->advertising, Autoneg)) {
--                      linkmode_zero(supported);
--                      return;
--              }
--      } else if (state->interface != PHY_INTERFACE_MODE_NA &&
--                 state->interface != PHY_INTERFACE_MODE_QSGMII &&
--                 state->interface != PHY_INTERFACE_MODE_SGMII &&
--                 !phy_interface_mode_is_rgmii(state->interface)) {
-+      if (phy_interface_mode_is_8023z(state->interface) &&
-+          !phylink_test(state->advertising, Autoneg)) {
-               linkmode_zero(supported);
-               return;
-       }
diff --git a/target/linux/generic/backport-5.15/703-18-v5.16-net-mvneta-drop-use-of-phylink_helper_basex_speed.patch b/target/linux/generic/backport-5.15/703-18-v5.16-net-mvneta-drop-use-of-phylink_helper_basex_speed.patch
deleted file mode 100644 (file)
index 9121612..0000000
+++ /dev/null
@@ -1,55 +0,0 @@
-From 099cbfa286ab937d8213c2dc5c0b401969b78042 Mon Sep 17 00:00:00 2001
-From: "Russell King (Oracle)" <[email protected]>
-Date: Wed, 27 Oct 2021 10:03:53 +0100
-Subject: [PATCH] net: mvneta: drop use of phylink_helper_basex_speed()
-
-Now that we have a better method to select SFP interface modes, we
-no longer need to use phylink_helper_basex_speed() in a driver's
-validation function, and we can also get rid of our hack to indicate
-both 1000base-X and 2500base-X if the comphy is present to make that
-work. Remove this hack and use of phylink_helper_basex_speed().
-
-Signed-off-by: Russell King (Oracle) <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/ethernet/marvell/mvneta.c | 12 +++---------
- 1 file changed, 3 insertions(+), 9 deletions(-)
-
---- a/drivers/net/ethernet/marvell/mvneta.c
-+++ b/drivers/net/ethernet/marvell/mvneta.c
-@@ -3824,8 +3824,6 @@ static void mvneta_validate(struct phyli
-                           unsigned long *supported,
-                           struct phylink_link_state *state)
- {
--      struct net_device *ndev = to_net_dev(config->dev);
--      struct mvneta_port *pp = netdev_priv(ndev);
-       __ETHTOOL_DECLARE_LINK_MODE_MASK(mask) = { 0, };
-       /* We only support QSGMII, SGMII, 802.3z and RGMII modes.
-@@ -3847,11 +3845,12 @@ static void mvneta_validate(struct phyli
-       phylink_set(mask, Pause);
-       /* Half-duplex at speeds higher than 100Mbit is unsupported */
--      if (pp->comphy || state->interface != PHY_INTERFACE_MODE_2500BASEX) {
-+      if (state->interface != PHY_INTERFACE_MODE_2500BASEX) {
-               phylink_set(mask, 1000baseT_Full);
-               phylink_set(mask, 1000baseX_Full);
-       }
--      if (pp->comphy || state->interface == PHY_INTERFACE_MODE_2500BASEX) {
-+
-+      if (state->interface == PHY_INTERFACE_MODE_2500BASEX) {
-               phylink_set(mask, 2500baseT_Full);
-               phylink_set(mask, 2500baseX_Full);
-       }
-@@ -3866,11 +3865,6 @@ static void mvneta_validate(struct phyli
-       linkmode_and(supported, supported, mask);
-       linkmode_and(state->advertising, state->advertising, mask);
--
--      /* We can only operate at 2500BaseX or 1000BaseX.  If requested
--       * to advertise both, only report advertising at 2500BaseX.
--       */
--      phylink_helper_basex_speed(state);
- }
- static void mvneta_mac_pcs_get_state(struct phylink_config *config,
diff --git a/target/linux/generic/backport-5.15/703-19-v5.17-net-mvneta-use-phylink_generic_validate.patch b/target/linux/generic/backport-5.15/703-19-v5.17-net-mvneta-use-phylink_generic_validate.patch
deleted file mode 100644 (file)
index 209dfbc..0000000
+++ /dev/null
@@ -1,72 +0,0 @@
-From 02a0988b98930491db95966fb8086072e47dabb6 Mon Sep 17 00:00:00 2001
-From: "Russell King (Oracle)" <[email protected]>
-Date: Mon, 15 Nov 2021 10:00:32 +0000
-Subject: [PATCH] net: mvneta: use phylink_generic_validate()
-
-Convert mvneta to use phylink_generic_validate() for the bulk of its
-validate() implementation. This network adapter has a restriction
-that for 802.3z links, autonegotiation must be enabled.
-
-Signed-off-by: Russell King (Oracle) <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/ethernet/marvell/mvneta.c | 34 ++++-----------------------
- 1 file changed, 4 insertions(+), 30 deletions(-)
-
---- a/drivers/net/ethernet/marvell/mvneta.c
-+++ b/drivers/net/ethernet/marvell/mvneta.c
-@@ -3824,8 +3824,6 @@ static void mvneta_validate(struct phyli
-                           unsigned long *supported,
-                           struct phylink_link_state *state)
- {
--      __ETHTOOL_DECLARE_LINK_MODE_MASK(mask) = { 0, };
--
-       /* We only support QSGMII, SGMII, 802.3z and RGMII modes.
-        * When in 802.3z mode, we must have AN enabled:
-        * "Bit 2 Field InBandAnEn In-band Auto-Negotiation enable. ...
-@@ -3837,34 +3835,7 @@ static void mvneta_validate(struct phyli
-               return;
-       }
--      /* Allow all the expected bits */
--      phylink_set(mask, Autoneg);
--      phylink_set_port_modes(mask);
--
--      /* Asymmetric pause is unsupported */
--      phylink_set(mask, Pause);
--
--      /* Half-duplex at speeds higher than 100Mbit is unsupported */
--      if (state->interface != PHY_INTERFACE_MODE_2500BASEX) {
--              phylink_set(mask, 1000baseT_Full);
--              phylink_set(mask, 1000baseX_Full);
--      }
--
--      if (state->interface == PHY_INTERFACE_MODE_2500BASEX) {
--              phylink_set(mask, 2500baseT_Full);
--              phylink_set(mask, 2500baseX_Full);
--      }
--
--      if (!phy_interface_mode_is_8023z(state->interface)) {
--              /* 10M and 100M are only supported in non-802.3z mode */
--              phylink_set(mask, 10baseT_Half);
--              phylink_set(mask, 10baseT_Full);
--              phylink_set(mask, 100baseT_Half);
--              phylink_set(mask, 100baseT_Full);
--      }
--
--      linkmode_and(supported, supported, mask);
--      linkmode_and(state->advertising, state->advertising, mask);
-+      phylink_generic_validate(config, supported, state);
- }
- static void mvneta_mac_pcs_get_state(struct phylink_config *config,
-@@ -5167,6 +5138,9 @@ static int mvneta_probe(struct platform_
-       pp->phylink_config.dev = &dev->dev;
-       pp->phylink_config.type = PHYLINK_NETDEV;
-+      pp->phylink_config.mac_capabilities = MAC_SYM_PAUSE | MAC_10 |
-+              MAC_100 | MAC_1000FD | MAC_2500FD;
-+
-       phy_interface_set_rgmii(pp->phylink_config.supported_interfaces);
-       __set_bit(PHY_INTERFACE_MODE_QSGMII,
-                 pp->phylink_config.supported_interfaces);
diff --git a/target/linux/generic/backport-5.15/703-20-v5.17-net-mvneta-mark-as-a-legacy_pre_march2020-driver.patch b/target/linux/generic/backport-5.15/703-20-v5.17-net-mvneta-mark-as-a-legacy_pre_march2020-driver.patch
deleted file mode 100644 (file)
index 3171756..0000000
+++ /dev/null
@@ -1,29 +0,0 @@
-From 2106be4fdf3223d9c5bd485e6ef094139e3197ba Mon Sep 17 00:00:00 2001
-From: "Russell King (Oracle)" <[email protected]>
-Date: Sun, 12 Dec 2021 13:01:21 +0000
-Subject: [PATCH] net: mvneta: mark as a legacy_pre_march2020 driver
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-mvneta provides mac_an_restart and mac_pcs_get_state methods, so needs
-to be marked as a legacy driver. Marek spotted that mvneta had stopped
-working in 2500base-X mode - thanks for reporting.
-
-Reported-by: Marek Behún <[email protected]>
-Signed-off-by: Russell King (Oracle) <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/ethernet/marvell/mvneta.c | 1 +
- 1 file changed, 1 insertion(+)
-
---- a/drivers/net/ethernet/marvell/mvneta.c
-+++ b/drivers/net/ethernet/marvell/mvneta.c
-@@ -5138,6 +5138,7 @@ static int mvneta_probe(struct platform_
-       pp->phylink_config.dev = &dev->dev;
-       pp->phylink_config.type = PHYLINK_NETDEV;
-+      pp->phylink_config.legacy_pre_march2020 = true;
-       pp->phylink_config.mac_capabilities = MAC_SYM_PAUSE | MAC_10 |
-               MAC_100 | MAC_1000FD | MAC_2500FD;
diff --git a/target/linux/generic/backport-5.15/704-01-v5.17-net-mtk_eth_soc-populate-supported_interfaces-member.patch b/target/linux/generic/backport-5.15/704-01-v5.17-net-mtk_eth_soc-populate-supported_interfaces-member.patch
deleted file mode 100644 (file)
index affb87b..0000000
+++ /dev/null
@@ -1,43 +0,0 @@
-From 83800d29f0c578e82554e7d4c6bfdbdf9b6cf428 Mon Sep 17 00:00:00 2001
-From: "Russell King (Oracle)" <[email protected]>
-Date: Tue, 16 Nov 2021 10:06:43 +0000
-Subject: [PATCH] net: mtk_eth_soc: populate supported_interfaces member
-
-Populate the phy interface mode bitmap for the Mediatek driver with
-interfaces modes supported by the MAC.
-
-Signed-off-by: Russell King (Oracle) <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/ethernet/mediatek/mtk_eth_soc.c | 20 ++++++++++++++++++++
- 1 file changed, 20 insertions(+)
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-@@ -3361,6 +3361,26 @@ static int mtk_add_mac(struct mtk_eth *e
-       mac->phylink_config.dev = &eth->netdev[id]->dev;
-       mac->phylink_config.type = PHYLINK_NETDEV;
-+      __set_bit(PHY_INTERFACE_MODE_MII,
-+                mac->phylink_config.supported_interfaces);
-+      __set_bit(PHY_INTERFACE_MODE_GMII,
-+                mac->phylink_config.supported_interfaces);
-+
-+      if (MTK_HAS_CAPS(mac->hw->soc->caps, MTK_RGMII))
-+              phy_interface_set_rgmii(mac->phylink_config.supported_interfaces);
-+
-+      if (MTK_HAS_CAPS(mac->hw->soc->caps, MTK_TRGMII) && !mac->id)
-+              __set_bit(PHY_INTERFACE_MODE_TRGMII,
-+                        mac->phylink_config.supported_interfaces);
-+
-+      if (MTK_HAS_CAPS(mac->hw->soc->caps, MTK_SGMII)) {
-+              __set_bit(PHY_INTERFACE_MODE_SGMII,
-+                        mac->phylink_config.supported_interfaces);
-+              __set_bit(PHY_INTERFACE_MODE_1000BASEX,
-+                        mac->phylink_config.supported_interfaces);
-+              __set_bit(PHY_INTERFACE_MODE_2500BASEX,
-+                        mac->phylink_config.supported_interfaces);
-+      }
-       phylink = phylink_create(&mac->phylink_config,
-                                of_fwnode_handle(mac->of_node),
diff --git a/target/linux/generic/backport-5.15/704-02-v5.17-net-mtk_eth_soc-remove-interface-checks-in-mtk_valid.patch b/target/linux/generic/backport-5.15/704-02-v5.17-net-mtk_eth_soc-remove-interface-checks-in-mtk_valid.patch
deleted file mode 100644 (file)
index 432e23d..0000000
+++ /dev/null
@@ -1,75 +0,0 @@
-From db81ca153814475d7e07365d46a4d1134bd122e2 Mon Sep 17 00:00:00 2001
-From: "Russell King (Oracle)" <[email protected]>
-Date: Tue, 16 Nov 2021 10:06:48 +0000
-Subject: [PATCH] net: mtk_eth_soc: remove interface checks in mtk_validate()
-
-As phylink checks the interface mode against the supported_interfaces
-bitmap, we no longer need to validate the interface mode, nor handle
-PHY_INTERFACE_MODE_NA in the validation function. Remove these to
-simplify the implementation.
-
-Signed-off-by: Russell King (Oracle) <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/ethernet/mediatek/mtk_eth_soc.c | 34 ---------------------
- 1 file changed, 34 deletions(-)
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-@@ -577,24 +577,8 @@ static void mtk_validate(struct phylink_
-                        unsigned long *supported,
-                        struct phylink_link_state *state)
- {
--      struct mtk_mac *mac = container_of(config, struct mtk_mac,
--                                         phylink_config);
-       __ETHTOOL_DECLARE_LINK_MODE_MASK(mask) = { 0, };
--      if (state->interface != PHY_INTERFACE_MODE_NA &&
--          state->interface != PHY_INTERFACE_MODE_MII &&
--          state->interface != PHY_INTERFACE_MODE_GMII &&
--          !(MTK_HAS_CAPS(mac->hw->soc->caps, MTK_RGMII) &&
--            phy_interface_mode_is_rgmii(state->interface)) &&
--          !(MTK_HAS_CAPS(mac->hw->soc->caps, MTK_TRGMII) &&
--            !mac->id && state->interface == PHY_INTERFACE_MODE_TRGMII) &&
--          !(MTK_HAS_CAPS(mac->hw->soc->caps, MTK_SGMII) &&
--            (state->interface == PHY_INTERFACE_MODE_SGMII ||
--             phy_interface_mode_is_8023z(state->interface)))) {
--              linkmode_zero(supported);
--              return;
--      }
--
-       phylink_set_port_modes(mask);
-       phylink_set(mask, Autoneg);
-@@ -621,7 +605,6 @@ static void mtk_validate(struct phylink_
-       case PHY_INTERFACE_MODE_MII:
-       case PHY_INTERFACE_MODE_RMII:
-       case PHY_INTERFACE_MODE_REVMII:
--      case PHY_INTERFACE_MODE_NA:
-       default:
-               phylink_set(mask, 10baseT_Half);
-               phylink_set(mask, 10baseT_Full);
-@@ -630,23 +613,6 @@ static void mtk_validate(struct phylink_
-               break;
-       }
--      if (state->interface == PHY_INTERFACE_MODE_NA) {
--              if (MTK_HAS_CAPS(mac->hw->soc->caps, MTK_SGMII)) {
--                      phylink_set(mask, 1000baseT_Full);
--                      phylink_set(mask, 1000baseX_Full);
--                      phylink_set(mask, 2500baseX_Full);
--              }
--              if (MTK_HAS_CAPS(mac->hw->soc->caps, MTK_RGMII)) {
--                      phylink_set(mask, 1000baseT_Full);
--                      phylink_set(mask, 1000baseT_Half);
--                      phylink_set(mask, 1000baseX_Full);
--              }
--              if (MTK_HAS_CAPS(mac->hw->soc->caps, MTK_GEPHY)) {
--                      phylink_set(mask, 1000baseT_Full);
--                      phylink_set(mask, 1000baseT_Half);
--              }
--      }
--
-       phylink_set(mask, Pause);
-       phylink_set(mask, Asym_Pause);
diff --git a/target/linux/generic/backport-5.15/704-03-v5.17-net-mtk_eth_soc-drop-use-of-phylink_helper_basex_spe.patch b/target/linux/generic/backport-5.15/704-03-v5.17-net-mtk_eth_soc-drop-use-of-phylink_helper_basex_spe.patch
deleted file mode 100644 (file)
index 7585f7c..0000000
+++ /dev/null
@@ -1,42 +0,0 @@
-From 71d927494463c4f016d828e1134da26b7e961af5 Mon Sep 17 00:00:00 2001
-From: "Russell King (Oracle)" <[email protected]>
-Date: Tue, 16 Nov 2021 10:06:53 +0000
-Subject: [PATCH] net: mtk_eth_soc: drop use of phylink_helper_basex_speed()
-
-Now that we have a better method to select SFP interface modes, we
-no longer need to use phylink_helper_basex_speed() in a driver's
-validation function, and we can also get rid of our hack to indicate
-both 1000base-X and 2500base-X if the comphy is present to make that
-work. Remove this hack and use of phylink_helper_basex_speed().
-
-Signed-off-by: Russell King (Oracle) <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/ethernet/mediatek/mtk_eth_soc.c | 8 ++------
- 1 file changed, 2 insertions(+), 6 deletions(-)
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-@@ -587,8 +587,9 @@ static void mtk_validate(struct phylink_
-               phylink_set(mask, 1000baseT_Full);
-               break;
-       case PHY_INTERFACE_MODE_1000BASEX:
--      case PHY_INTERFACE_MODE_2500BASEX:
-               phylink_set(mask, 1000baseX_Full);
-+              break;
-+      case PHY_INTERFACE_MODE_2500BASEX:
-               phylink_set(mask, 2500baseX_Full);
-               break;
-       case PHY_INTERFACE_MODE_GMII:
-@@ -618,11 +619,6 @@ static void mtk_validate(struct phylink_
-       linkmode_and(supported, supported, mask);
-       linkmode_and(state->advertising, state->advertising, mask);
--
--      /* We can only operate at 2500BaseX or 1000BaseX. If requested
--       * to advertise both, only report advertising at 2500BaseX.
--       */
--      phylink_helper_basex_speed(state);
- }
- static const struct phylink_mac_ops mtk_phylink_ops = {
diff --git a/target/linux/generic/backport-5.15/704-04-v5.17-net-mtk_eth_soc-use-phylink_generic_validate.patch b/target/linux/generic/backport-5.15/704-04-v5.17-net-mtk_eth_soc-use-phylink_generic_validate.patch
deleted file mode 100644 (file)
index 69b6906..0000000
+++ /dev/null
@@ -1,84 +0,0 @@
-From a4238f6ce151afa331375d74a5033b76da637644 Mon Sep 17 00:00:00 2001
-From: "Russell King (Oracle)" <[email protected]>
-Date: Tue, 16 Nov 2021 10:06:58 +0000
-Subject: [PATCH] net: mtk_eth_soc: use phylink_generic_validate()
-
-mtk_eth_soc has no special behaviour in its validation implementation,
-so can be switched to phylink_generic_validate().
-
-Signed-off-by: Russell King (Oracle) <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/ethernet/mediatek/mtk_eth_soc.c | 53 ++-------------------
- 1 file changed, 4 insertions(+), 49 deletions(-)
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-@@ -573,56 +573,8 @@ static void mtk_mac_link_up(struct phyli
-       mtk_w32(mac->hw, mcr, MTK_MAC_MCR(mac->id));
- }
--static void mtk_validate(struct phylink_config *config,
--                       unsigned long *supported,
--                       struct phylink_link_state *state)
--{
--      __ETHTOOL_DECLARE_LINK_MODE_MASK(mask) = { 0, };
--
--      phylink_set_port_modes(mask);
--      phylink_set(mask, Autoneg);
--
--      switch (state->interface) {
--      case PHY_INTERFACE_MODE_TRGMII:
--              phylink_set(mask, 1000baseT_Full);
--              break;
--      case PHY_INTERFACE_MODE_1000BASEX:
--              phylink_set(mask, 1000baseX_Full);
--              break;
--      case PHY_INTERFACE_MODE_2500BASEX:
--              phylink_set(mask, 2500baseX_Full);
--              break;
--      case PHY_INTERFACE_MODE_GMII:
--      case PHY_INTERFACE_MODE_RGMII:
--      case PHY_INTERFACE_MODE_RGMII_ID:
--      case PHY_INTERFACE_MODE_RGMII_RXID:
--      case PHY_INTERFACE_MODE_RGMII_TXID:
--              phylink_set(mask, 1000baseT_Half);
--              fallthrough;
--      case PHY_INTERFACE_MODE_SGMII:
--              phylink_set(mask, 1000baseT_Full);
--              phylink_set(mask, 1000baseX_Full);
--              fallthrough;
--      case PHY_INTERFACE_MODE_MII:
--      case PHY_INTERFACE_MODE_RMII:
--      case PHY_INTERFACE_MODE_REVMII:
--      default:
--              phylink_set(mask, 10baseT_Half);
--              phylink_set(mask, 10baseT_Full);
--              phylink_set(mask, 100baseT_Half);
--              phylink_set(mask, 100baseT_Full);
--              break;
--      }
--
--      phylink_set(mask, Pause);
--      phylink_set(mask, Asym_Pause);
--
--      linkmode_and(supported, supported, mask);
--      linkmode_and(state->advertising, state->advertising, mask);
--}
--
- static const struct phylink_mac_ops mtk_phylink_ops = {
--      .validate = mtk_validate,
-+      .validate = phylink_generic_validate,
-       .mac_pcs_get_state = mtk_mac_pcs_get_state,
-       .mac_an_restart = mtk_mac_an_restart,
-       .mac_config = mtk_mac_config,
-@@ -3323,6 +3275,9 @@ static int mtk_add_mac(struct mtk_eth *e
-       mac->phylink_config.dev = &eth->netdev[id]->dev;
-       mac->phylink_config.type = PHYLINK_NETDEV;
-+      mac->phylink_config.mac_capabilities = MAC_ASYM_PAUSE | MAC_SYM_PAUSE |
-+              MAC_10 | MAC_100 | MAC_1000 | MAC_2500FD;
-+
-       __set_bit(PHY_INTERFACE_MODE_MII,
-                 mac->phylink_config.supported_interfaces);
-       __set_bit(PHY_INTERFACE_MODE_GMII,
diff --git a/target/linux/generic/backport-5.15/704-05-v5.17-net-mtk_eth_soc-mark-as-a-legacy_pre_march2020-drive.patch b/target/linux/generic/backport-5.15/704-05-v5.17-net-mtk_eth_soc-mark-as-a-legacy_pre_march2020-drive.patch
deleted file mode 100644 (file)
index 680d20b..0000000
+++ /dev/null
@@ -1,29 +0,0 @@
-From b06515367facfadcf5e70cf6f39db749cf4eb5e3 Mon Sep 17 00:00:00 2001
-From: "Russell King (Oracle)" <[email protected]>
-Date: Thu, 9 Dec 2021 13:11:43 +0000
-Subject: [PATCH] net: mtk_eth_soc: mark as a legacy_pre_march2020 driver
-
-mtk_eth_soc has not been updated for commit 7cceb599d15d ("net: phylink:
-avoid mac_config calls"), and makes use of state->speed and
-state->duplex in contravention of the phylink documentation. This makes
-reliant on the legacy behaviours, so mark it as a legacy driver.
-
-Signed-off-by: Russell King (Oracle) <[email protected]>
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- drivers/net/ethernet/mediatek/mtk_eth_soc.c | 4 ++++
- 1 file changed, 4 insertions(+)
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-@@ -3275,6 +3275,10 @@ static int mtk_add_mac(struct mtk_eth *e
-       mac->phylink_config.dev = &eth->netdev[id]->dev;
-       mac->phylink_config.type = PHYLINK_NETDEV;
-+      /* This driver makes use of state->speed/state->duplex in
-+       * mac_config
-+       */
-+      mac->phylink_config.legacy_pre_march2020 = true;
-       mac->phylink_config.mac_capabilities = MAC_ASYM_PAUSE | MAC_SYM_PAUSE |
-               MAC_10 | MAC_100 | MAC_1000 | MAC_2500FD;
diff --git a/target/linux/generic/backport-5.15/704-06-v5.19-eth-mtk_eth_soc-remove-a-copy-of-the-NAPI_POLL_WEIGH.patch b/target/linux/generic/backport-5.15/704-06-v5.19-eth-mtk_eth_soc-remove-a-copy-of-the-NAPI_POLL_WEIGH.patch
deleted file mode 100644 (file)
index 4cdd03a..0000000
+++ /dev/null
@@ -1,40 +0,0 @@
-From 889e3691b9d6573de133da1f5e78f590e52152cd Mon Sep 17 00:00:00 2001
-From: Jakub Kicinski <[email protected]>
-Date: Thu, 28 Apr 2022 14:23:13 -0700
-Subject: [PATCH] eth: mtk_eth_soc: remove a copy of the NAPI_POLL_WEIGHT
- define
-
-Defining local versions of NAPI_POLL_WEIGHT with the same
-values in the drivers just makes refactoring harder.
-
-Signed-off-by: Jakub Kicinski <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/ethernet/mediatek/mtk_eth_soc.c | 4 ++--
- drivers/net/ethernet/mediatek/mtk_eth_soc.h | 1 -
- 2 files changed, 2 insertions(+), 3 deletions(-)
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-@@ -3574,9 +3574,9 @@ static int mtk_probe(struct platform_dev
-        */
-       init_dummy_netdev(&eth->dummy_dev);
-       netif_napi_add(&eth->dummy_dev, &eth->tx_napi, mtk_napi_tx,
--                     MTK_NAPI_WEIGHT);
-+                     NAPI_POLL_WEIGHT);
-       netif_napi_add(&eth->dummy_dev, &eth->rx_napi, mtk_napi_rx,
--                     MTK_NAPI_WEIGHT);
-+                     NAPI_POLL_WEIGHT);
-       platform_set_drvdata(pdev, eth);
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-@@ -25,7 +25,6 @@
- #define MTK_TX_DMA_BUF_LEN    0x3fff
- #define MTK_TX_DMA_BUF_LEN_V2 0xffff
- #define MTK_DMA_SIZE          512
--#define MTK_NAPI_WEIGHT               64
- #define MTK_MAC_COUNT         2
- #define MTK_RX_ETH_HLEN               (ETH_HLEN + ETH_FCS_LEN)
- #define MTK_RX_HLEN           (NET_SKB_PAD + MTK_RX_ETH_HLEN + NET_IP_ALIGN)
diff --git a/target/linux/generic/backport-5.15/704-07-v5.19-mtk_eth_soc-remove-unused-mac-mode.patch b/target/linux/generic/backport-5.15/704-07-v5.19-mtk_eth_soc-remove-unused-mac-mode.patch
deleted file mode 100644 (file)
index fd6bd1b..0000000
+++ /dev/null
@@ -1,35 +0,0 @@
-From 0600bdde1fae75fb9bad72033d28edddc72b44b2 Mon Sep 17 00:00:00 2001
-From: "Russell King (Oracle)" <[email protected]>
-Date: Wed, 18 May 2022 15:54:31 +0100
-Subject: [PATCH 01/12] net: mtk_eth_soc: remove unused mac->mode
-
-mac->mode is only ever written to in one location, and is thus
-superflous. Remove it.
-
-Signed-off-by: Russell King (Oracle) <[email protected]>
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- drivers/net/ethernet/mediatek/mtk_eth_soc.c | 1 -
- drivers/net/ethernet/mediatek/mtk_eth_soc.h | 1 -
- 2 files changed, 2 deletions(-)
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-@@ -3270,7 +3270,6 @@ static int mtk_add_mac(struct mtk_eth *e
-       /* mac config is not set */
-       mac->interface = PHY_INTERFACE_MODE_NA;
--      mac->mode = MLO_AN_PHY;
-       mac->speed = SPEED_UNKNOWN;
-       mac->phylink_config.dev = &eth->netdev[id]->dev;
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-@@ -1086,7 +1086,6 @@ struct mtk_eth {
- struct mtk_mac {
-       int                             id;
-       phy_interface_t                 interface;
--      unsigned int                    mode;
-       int                             speed;
-       struct device_node              *of_node;
-       struct phylink                  *phylink;
diff --git a/target/linux/generic/backport-5.15/704-08-v5.19-net-mtk_eth_soc-remove-unused-sgmii-flags.patch b/target/linux/generic/backport-5.15/704-08-v5.19-net-mtk_eth_soc-remove-unused-sgmii-flags.patch
deleted file mode 100644 (file)
index a15914b..0000000
+++ /dev/null
@@ -1,40 +0,0 @@
-From 5a7a2f4b29d7546244da7d8bbc1962fce5b230f2 Mon Sep 17 00:00:00 2001
-From: "Russell King (Oracle)" <[email protected]>
-Date: Wed, 18 May 2022 15:54:36 +0100
-Subject: [PATCH 02/12] net: mtk_eth_soc: remove unused sgmii flags
-
-The "flags" member of struct mtk_sgmii appears to be unused, as are
-the MTK_SGMII_PHYSPEED_* and MTK_HAS_FLAGS() macros. Remove them.
-
-Signed-off-by: Russell King (Oracle) <[email protected]>
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- drivers/net/ethernet/mediatek/mtk_eth_soc.h | 8 --------
- 1 file changed, 8 deletions(-)
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-@@ -957,23 +957,15 @@ struct mtk_soc_data {
- /* currently no SoC has more than 2 macs */
- #define MTK_MAX_DEVS                  2
--#define MTK_SGMII_PHYSPEED_AN          BIT(31)
--#define MTK_SGMII_PHYSPEED_MASK        GENMASK(2, 0)
--#define MTK_SGMII_PHYSPEED_1000        BIT(0)
--#define MTK_SGMII_PHYSPEED_2500        BIT(1)
--#define MTK_HAS_FLAGS(flags, _x)       (((flags) & (_x)) == (_x))
--
- /* struct mtk_sgmii -  This is the structure holding sgmii regmap and its
-  *                     characteristics
-  * @regmap:            The register map pointing at the range used to setup
-  *                     SGMII modes
-- * @flags:             The enum refers to which mode the sgmii wants to run on
-  * @ana_rgc3:          The offset refers to register ANA_RGC3 related to regmap
-  */
- struct mtk_sgmii {
-       struct regmap   *regmap[MTK_MAX_DEVS];
--      u32             flags[MTK_MAX_DEVS];
-       u32             ana_rgc3;
- };
diff --git a/target/linux/generic/backport-5.15/704-09-v5.19-net-mtk_eth_soc-add-mask-and-update-PCS-speed-defini.patch b/target/linux/generic/backport-5.15/704-09-v5.19-net-mtk_eth_soc-add-mask-and-update-PCS-speed-defini.patch
deleted file mode 100644 (file)
index e16bc87..0000000
+++ /dev/null
@@ -1,40 +0,0 @@
-From bc5e93e0cd22e360eda23859b939280205567580 Mon Sep 17 00:00:00 2001
-From: "Russell King (Oracle)" <[email protected]>
-Date: Wed, 18 May 2022 15:54:42 +0100
-Subject: [PATCH 03/12] net: mtk_eth_soc: add mask and update PCS speed
- definitions
-
-The PCS speed setting is a two bit field, but it is defined as two
-separate bits. Add a bitfield mask for the speed definitions, an
- use the FIELD_PREP() macro to define each PCS speed.
-
-Signed-off-by: Russell King (Oracle) <[email protected]>
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- drivers/net/ethernet/mediatek/mtk_eth_soc.h | 8 +++++---
- 1 file changed, 5 insertions(+), 3 deletions(-)
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-@@ -17,6 +17,7 @@
- #include <linux/phylink.h>
- #include <linux/rhashtable.h>
- #include <linux/dim.h>
-+#include <linux/bitfield.h>
- #include "mtk_ppe.h"
- #define MTK_QDMA_PAGE_SIZE    2048
-@@ -474,9 +475,10 @@
- #define SGMSYS_SGMII_MODE             0x20
- #define SGMII_IF_MODE_BIT0            BIT(0)
- #define SGMII_SPEED_DUPLEX_AN         BIT(1)
--#define SGMII_SPEED_10                        0x0
--#define SGMII_SPEED_100                       BIT(2)
--#define SGMII_SPEED_1000              BIT(3)
-+#define SGMII_SPEED_MASK              GENMASK(3, 2)
-+#define SGMII_SPEED_10                        FIELD_PREP(SGMII_SPEED_MASK, 0)
-+#define SGMII_SPEED_100                       FIELD_PREP(SGMII_SPEED_MASK, 1)
-+#define SGMII_SPEED_1000              FIELD_PREP(SGMII_SPEED_MASK, 2)
- #define SGMII_DUPLEX_FULL             BIT(4)
- #define SGMII_IF_MODE_BIT5            BIT(5)
- #define SGMII_REMOTE_FAULT_DIS                BIT(8)
diff --git a/target/linux/generic/backport-5.15/704-10-v5.19-net-mtk_eth_soc-correct-802.3z-speed-setting.patch b/target/linux/generic/backport-5.15/704-10-v5.19-net-mtk_eth_soc-correct-802.3z-speed-setting.patch
deleted file mode 100644 (file)
index fb1ee4e..0000000
+++ /dev/null
@@ -1,60 +0,0 @@
-From 7da3f901f8ecb425105fad39a0f5de73306abe52 Mon Sep 17 00:00:00 2001
-From: "Russell King (Oracle)" <[email protected]>
-Date: Wed, 18 May 2022 15:54:47 +0100
-Subject: [PATCH 04/12] net: mtk_eth_soc: correct 802.3z speed setting
-
-Phylink does not guarantee that state->speed will be set correctly in
-the mac_config() call, so it's a bug that the driver makes use of it.
-Moreover, it is making use of it in a function that is only ever called
-for 1000BASE-X and 2500BASE-X which operate at a fixed speed which
-happens to be the same setting irrespective of the interface mode. We
-can simply remove the switch statement and just set the SGMII interface
-speed.
-
-Signed-off-by: Russell King (Oracle) <[email protected]>
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- drivers/net/ethernet/mediatek/mtk_sgmii.c | 18 +++++-------------
- 1 file changed, 5 insertions(+), 13 deletions(-)
-
---- a/drivers/net/ethernet/mediatek/mtk_sgmii.c
-+++ b/drivers/net/ethernet/mediatek/mtk_sgmii.c
-@@ -34,6 +34,7 @@ int mtk_sgmii_init(struct mtk_sgmii *ss,
-       return 0;
- }
-+/* For SGMII interface mode */
- int mtk_sgmii_setup_mode_an(struct mtk_sgmii *ss, int id)
- {
-       unsigned int val;
-@@ -60,6 +61,9 @@ int mtk_sgmii_setup_mode_an(struct mtk_s
-       return 0;
- }
-+/* For 1000BASE-X and 2500BASE-X interface modes, which operate at a
-+ * fixed speed.
-+ */
- int mtk_sgmii_setup_mode_force(struct mtk_sgmii *ss, int id,
-                              const struct phylink_link_state *state)
- {
-@@ -82,19 +86,7 @@ int mtk_sgmii_setup_mode_force(struct mt
-       /* SGMII force mode setting */
-       regmap_read(ss->regmap[id], SGMSYS_SGMII_MODE, &val);
-       val &= ~SGMII_IF_MODE_MASK;
--
--      switch (state->speed) {
--      case SPEED_10:
--              val |= SGMII_SPEED_10;
--              break;
--      case SPEED_100:
--              val |= SGMII_SPEED_100;
--              break;
--      case SPEED_2500:
--      case SPEED_1000:
--              val |= SGMII_SPEED_1000;
--              break;
--      }
-+      val |= SGMII_SPEED_1000;
-       if (state->duplex == DUPLEX_FULL)
-               val |= SGMII_DUPLEX_FULL;
diff --git a/target/linux/generic/backport-5.15/704-11-v5.19-net-mtk_eth_soc-correct-802.3z-duplex-setting.patch b/target/linux/generic/backport-5.15/704-11-v5.19-net-mtk_eth_soc-correct-802.3z-duplex-setting.patch
deleted file mode 100644 (file)
index 93743ad..0000000
+++ /dev/null
@@ -1,101 +0,0 @@
-From a459187390bb221827f9c07866c3a5ffbdf9622b Mon Sep 17 00:00:00 2001
-From: Russell King <[email protected]>
-Date: Wed, 18 May 2022 15:54:52 +0100
-Subject: [PATCH 05/12] net: mtk_eth_soc: correct 802.3z duplex setting
-
-Phylink does not guarantee that state->duplex will be set correctly in
-the mac_config() call, so it's a bug that the driver makes use of it.
-
-Move the 802.3z PCS duplex configuration to mac_link_up().
-
-Signed-off-by: Russell King <[email protected]>
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- drivers/net/ethernet/mediatek/mtk_eth_soc.c | 16 +++++++++++----
- drivers/net/ethernet/mediatek/mtk_eth_soc.h |  1 +
- drivers/net/ethernet/mediatek/mtk_sgmii.c   | 22 +++++++++++++++------
- 3 files changed, 29 insertions(+), 10 deletions(-)
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-@@ -542,8 +542,18 @@ static void mtk_mac_link_up(struct phyli
- {
-       struct mtk_mac *mac = container_of(config, struct mtk_mac,
-                                          phylink_config);
--      u32 mcr = mtk_r32(mac->hw, MTK_MAC_MCR(mac->id));
-+      u32 mcr;
-+      if (phy_interface_mode_is_8023z(interface)) {
-+              struct mtk_eth *eth = mac->hw;
-+
-+              /* Decide how GMAC and SGMIISYS be mapped */
-+              int sid = (MTK_HAS_CAPS(eth->soc->caps, MTK_SHARED_SGMII)) ?
-+                         0 : mac->id;
-+              mtk_sgmii_link_up(eth->sgmii, sid, speed, duplex);
-+      }
-+
-+      mcr = mtk_r32(mac->hw, MTK_MAC_MCR(mac->id));
-       mcr &= ~(MAC_MCR_SPEED_100 | MAC_MCR_SPEED_1000 |
-                MAC_MCR_FORCE_DPX | MAC_MCR_FORCE_TX_FC |
-                MAC_MCR_FORCE_RX_FC);
-@@ -3274,9 +3284,7 @@ static int mtk_add_mac(struct mtk_eth *e
-       mac->phylink_config.dev = &eth->netdev[id]->dev;
-       mac->phylink_config.type = PHYLINK_NETDEV;
--      /* This driver makes use of state->speed/state->duplex in
--       * mac_config
--       */
-+      /* This driver makes use of state->speed in mac_config */
-       mac->phylink_config.legacy_pre_march2020 = true;
-       mac->phylink_config.mac_capabilities = MAC_ASYM_PAUSE | MAC_SYM_PAUSE |
-               MAC_10 | MAC_100 | MAC_1000 | MAC_2500FD;
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-@@ -1104,6 +1104,7 @@ int mtk_sgmii_init(struct mtk_sgmii *ss,
- int mtk_sgmii_setup_mode_an(struct mtk_sgmii *ss, int id);
- int mtk_sgmii_setup_mode_force(struct mtk_sgmii *ss, int id,
-                              const struct phylink_link_state *state);
-+void mtk_sgmii_link_up(struct mtk_sgmii *ss, int id, int speed, int duplex);
- void mtk_sgmii_restart_an(struct mtk_eth *eth, int mac_id);
- int mtk_gmac_sgmii_path_setup(struct mtk_eth *eth, int mac_id);
---- a/drivers/net/ethernet/mediatek/mtk_sgmii.c
-+++ b/drivers/net/ethernet/mediatek/mtk_sgmii.c
-@@ -83,14 +83,10 @@ int mtk_sgmii_setup_mode_force(struct mt
-       val &= ~SGMII_AN_ENABLE;
-       regmap_write(ss->regmap[id], SGMSYS_PCS_CONTROL_1, val);
--      /* SGMII force mode setting */
-+      /* Set the speed etc but leave the duplex unchanged */
-       regmap_read(ss->regmap[id], SGMSYS_SGMII_MODE, &val);
--      val &= ~SGMII_IF_MODE_MASK;
-+      val &= SGMII_DUPLEX_FULL | ~SGMII_IF_MODE_MASK;
-       val |= SGMII_SPEED_1000;
--
--      if (state->duplex == DUPLEX_FULL)
--              val |= SGMII_DUPLEX_FULL;
--
-       regmap_write(ss->regmap[id], SGMSYS_SGMII_MODE, val);
-       /* Release PHYA power down state */
-@@ -101,6 +97,20 @@ int mtk_sgmii_setup_mode_force(struct mt
-       return 0;
- }
-+/* For 1000BASE-X and 2500BASE-X interface modes */
-+void mtk_sgmii_link_up(struct mtk_sgmii *ss, int id, int speed, int duplex)
-+{
-+      unsigned int val;
-+
-+      /* SGMII force duplex setting */
-+      regmap_read(ss->regmap[id], SGMSYS_SGMII_MODE, &val);
-+      val &= ~SGMII_DUPLEX_FULL;
-+      if (duplex == DUPLEX_FULL)
-+              val |= SGMII_DUPLEX_FULL;
-+
-+      regmap_write(ss->regmap[id], SGMSYS_SGMII_MODE, val);
-+}
-+
- void mtk_sgmii_restart_an(struct mtk_eth *eth, int mac_id)
- {
-       struct mtk_sgmii *ss = eth->sgmii;
diff --git a/target/linux/generic/backport-5.15/704-12-v5.19-net-mtk_eth_soc-stop-passing-phylink-state-to-sgmii-.patch b/target/linux/generic/backport-5.15/704-12-v5.19-net-mtk_eth_soc-stop-passing-phylink-state-to-sgmii-.patch
deleted file mode 100644 (file)
index 6556bb7..0000000
+++ /dev/null
@@ -1,60 +0,0 @@
-From 4ce5a0bd3958ed248f0325bfcb95339f7c74feb2 Mon Sep 17 00:00:00 2001
-From: "Russell King (Oracle)" <[email protected]>
-Date: Wed, 18 May 2022 15:54:57 +0100
-Subject: [PATCH 06/12] net: mtk_eth_soc: stop passing phylink state to sgmii
- setup
-
-Now that mtk_sgmii_setup_mode_force() only uses the interface mode
-from the phylink state, pass just the interface mode into this
-function.
-
-Signed-off-by: Russell King (Oracle) <[email protected]>
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- drivers/net/ethernet/mediatek/mtk_eth_soc.c | 2 +-
- drivers/net/ethernet/mediatek/mtk_eth_soc.h | 2 +-
- drivers/net/ethernet/mediatek/mtk_sgmii.c   | 4 ++--
- 3 files changed, 4 insertions(+), 4 deletions(-)
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-@@ -437,7 +437,7 @@ static void mtk_mac_config(struct phylin
-               /* Setup SGMIISYS with the determined property */
-               if (state->interface != PHY_INTERFACE_MODE_SGMII)
-                       err = mtk_sgmii_setup_mode_force(eth->sgmii, sid,
--                                                       state);
-+                                                       state->interface);
-               else if (phylink_autoneg_inband(mode))
-                       err = mtk_sgmii_setup_mode_an(eth->sgmii, sid);
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-@@ -1103,7 +1103,7 @@ int mtk_sgmii_init(struct mtk_sgmii *ss,
-                  u32 ana_rgc3);
- int mtk_sgmii_setup_mode_an(struct mtk_sgmii *ss, int id);
- int mtk_sgmii_setup_mode_force(struct mtk_sgmii *ss, int id,
--                             const struct phylink_link_state *state);
-+                             phy_interface_t interface);
- void mtk_sgmii_link_up(struct mtk_sgmii *ss, int id, int speed, int duplex);
- void mtk_sgmii_restart_an(struct mtk_eth *eth, int mac_id);
---- a/drivers/net/ethernet/mediatek/mtk_sgmii.c
-+++ b/drivers/net/ethernet/mediatek/mtk_sgmii.c
-@@ -65,7 +65,7 @@ int mtk_sgmii_setup_mode_an(struct mtk_s
-  * fixed speed.
-  */
- int mtk_sgmii_setup_mode_force(struct mtk_sgmii *ss, int id,
--                             const struct phylink_link_state *state)
-+                             phy_interface_t interface)
- {
-       unsigned int val;
-@@ -74,7 +74,7 @@ int mtk_sgmii_setup_mode_force(struct mt
-       regmap_read(ss->regmap[id], ss->ana_rgc3, &val);
-       val &= ~RG_PHY_SPEED_MASK;
--      if (state->interface == PHY_INTERFACE_MODE_2500BASEX)
-+      if (interface == PHY_INTERFACE_MODE_2500BASEX)
-               val |= RG_PHY_SPEED_3_125G;
-       regmap_write(ss->regmap[id], ss->ana_rgc3, val);
diff --git a/target/linux/generic/backport-5.15/704-13-v5.19-net-mtk_eth_soc-provide-mtk_sgmii_config.patch b/target/linux/generic/backport-5.15/704-13-v5.19-net-mtk_eth_soc-provide-mtk_sgmii_config.patch
deleted file mode 100644 (file)
index 0e22c7f..0000000
+++ /dev/null
@@ -1,89 +0,0 @@
-From 1ec619ee4a052fb9ac48b57554ac2722a0bfe73c Mon Sep 17 00:00:00 2001
-From: "Russell King (Oracle)" <[email protected]>
-Date: Wed, 18 May 2022 15:55:02 +0100
-Subject: [PATCH 07/12] net: mtk_eth_soc: provide mtk_sgmii_config()
-
-Provide mtk_sgmii_config() to wrap up the decisions about which SGMII
-configuration will be called.
-
-Signed-off-by: Russell King (Oracle) <[email protected]>
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- drivers/net/ethernet/mediatek/mtk_eth_soc.c |  7 +------
- drivers/net/ethernet/mediatek/mtk_eth_soc.h |  5 ++---
- drivers/net/ethernet/mediatek/mtk_sgmii.c   | 20 +++++++++++++++++---
- 3 files changed, 20 insertions(+), 12 deletions(-)
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-@@ -435,12 +435,7 @@ static void mtk_mac_config(struct phylin
-                      0 : mac->id;
-               /* Setup SGMIISYS with the determined property */
--              if (state->interface != PHY_INTERFACE_MODE_SGMII)
--                      err = mtk_sgmii_setup_mode_force(eth->sgmii, sid,
--                                                       state->interface);
--              else if (phylink_autoneg_inband(mode))
--                      err = mtk_sgmii_setup_mode_an(eth->sgmii, sid);
--
-+              err = mtk_sgmii_config(eth->sgmii, sid, mode, state->interface);
-               if (err)
-                       goto init_err;
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-@@ -1101,9 +1101,8 @@ u32 mtk_r32(struct mtk_eth *eth, unsigne
- int mtk_sgmii_init(struct mtk_sgmii *ss, struct device_node *np,
-                  u32 ana_rgc3);
--int mtk_sgmii_setup_mode_an(struct mtk_sgmii *ss, int id);
--int mtk_sgmii_setup_mode_force(struct mtk_sgmii *ss, int id,
--                             phy_interface_t interface);
-+int mtk_sgmii_config(struct mtk_sgmii *ss, int id, unsigned int mode,
-+                   phy_interface_t interface);
- void mtk_sgmii_link_up(struct mtk_sgmii *ss, int id, int speed, int duplex);
- void mtk_sgmii_restart_an(struct mtk_eth *eth, int mac_id);
---- a/drivers/net/ethernet/mediatek/mtk_sgmii.c
-+++ b/drivers/net/ethernet/mediatek/mtk_sgmii.c
-@@ -35,7 +35,7 @@ int mtk_sgmii_init(struct mtk_sgmii *ss,
- }
- /* For SGMII interface mode */
--int mtk_sgmii_setup_mode_an(struct mtk_sgmii *ss, int id)
-+static int mtk_sgmii_setup_mode_an(struct mtk_sgmii *ss, int id)
- {
-       unsigned int val;
-@@ -64,8 +64,8 @@ int mtk_sgmii_setup_mode_an(struct mtk_s
- /* For 1000BASE-X and 2500BASE-X interface modes, which operate at a
-  * fixed speed.
-  */
--int mtk_sgmii_setup_mode_force(struct mtk_sgmii *ss, int id,
--                             phy_interface_t interface)
-+static int mtk_sgmii_setup_mode_force(struct mtk_sgmii *ss, int id,
-+                                    phy_interface_t interface)
- {
-       unsigned int val;
-@@ -97,6 +97,20 @@ int mtk_sgmii_setup_mode_force(struct mt
-       return 0;
- }
-+int mtk_sgmii_config(struct mtk_sgmii *ss, int id, unsigned int mode,
-+                   phy_interface_t interface)
-+{
-+      int err = 0;
-+
-+      /* Setup SGMIISYS with the determined property */
-+      if (interface != PHY_INTERFACE_MODE_SGMII)
-+              err = mtk_sgmii_setup_mode_force(ss, id, interface);
-+      else if (phylink_autoneg_inband(mode))
-+              err = mtk_sgmii_setup_mode_an(ss, id);
-+
-+      return err;
-+}
-+
- /* For 1000BASE-X and 2500BASE-X interface modes */
- void mtk_sgmii_link_up(struct mtk_sgmii *ss, int id, int speed, int duplex)
- {
diff --git a/target/linux/generic/backport-5.15/704-14-v5.19-net-mtk_eth_soc-add-fixme-comment-for-state-speed-us.patch b/target/linux/generic/backport-5.15/704-14-v5.19-net-mtk_eth_soc-add-fixme-comment-for-state-speed-us.patch
deleted file mode 100644 (file)
index 8080a2c..0000000
+++ /dev/null
@@ -1,38 +0,0 @@
-From 650a49bc65df6b0e0051a8f62d7c22d95a8f350d Mon Sep 17 00:00:00 2001
-From: "Russell King (Oracle)" <[email protected]>
-Date: Wed, 18 May 2022 15:55:07 +0100
-Subject: [PATCH 08/12] net: mtk_eth_soc: add fixme comment for state->speed
- use
-
-Add a fixme comment for the last remaining incorrect usage of
-state->speed in the mac_config() method, which is strangely in a code
-path which is only run when the PHY interface mode changes.
-
-This means if we are in RGMII mode, changes in state->speed will not
-cause the INTF_MODE, TRGMII_RCK_CTRL and TRGMII_TCK_CTRL registers to
-be set according to the speed, nor will the TRGPLL clock be set to the
-correct value.
-
-Signed-off-by: Russell King (Oracle) <[email protected]>
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- drivers/net/ethernet/mediatek/mtk_eth_soc.c | 8 ++++++++
- 1 file changed, 8 insertions(+)
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-@@ -374,6 +374,14 @@ static void mtk_mac_config(struct phylin
-                                                             state->interface))
-                                       goto err_phy;
-                       } else {
-+                              /* FIXME: this is incorrect. Not only does it
-+                               * use state->speed (which is not guaranteed
-+                               * to be correct) but it also makes use of it
-+                               * in a code path that will only be reachable
-+                               * when the PHY interface mode changes, not
-+                               * when the speed changes. Consequently, RGMII
-+                               * is probably broken.
-+                               */
-                               mtk_gmac0_rgmii_adjust(mac->hw,
-                                                      state->interface,
-                                                      state->speed);
diff --git a/target/linux/generic/backport-5.15/704-16-v5.19-net-mtk_eth_soc-move-restoration-of-SYSCFG0-to-mac_f.patch b/target/linux/generic/backport-5.15/704-16-v5.19-net-mtk_eth_soc-move-restoration-of-SYSCFG0-to-mac_f.patch
deleted file mode 100644 (file)
index b03ef43..0000000
+++ /dev/null
@@ -1,57 +0,0 @@
-From 21089867278deb2a110b685e3cd33f64f9ce41e2 Mon Sep 17 00:00:00 2001
-From: "Russell King (Oracle)" <[email protected]>
-Date: Wed, 18 May 2022 15:55:17 +0100
-Subject: [PATCH 10/12] net: mtk_eth_soc: move restoration of SYSCFG0 to
- mac_finish()
-
-The SGMIISYS configuration is performed while ETHSYS_SYSCFG0 is in a
-disabled state. In order to preserve this when we switch to phylink_pcs
-we need to move the restoration of this register to the mac_finish()
-callback.
-
-Signed-off-by: Russell King (Oracle) <[email protected]>
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- drivers/net/ethernet/mediatek/mtk_eth_soc.c | 11 +++++++++--
- drivers/net/ethernet/mediatek/mtk_eth_soc.h |  1 +
- 2 files changed, 10 insertions(+), 2 deletions(-)
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-@@ -447,8 +447,8 @@ static void mtk_mac_config(struct phylin
-               if (err)
-                       goto init_err;
--              regmap_update_bits(eth->ethsys, ETHSYS_SYSCFG0,
--                                 SYSCFG0_SGMII_MASK, val);
-+              /* Save the syscfg0 value for mac_finish */
-+              mac->syscfg0 = val;
-       } else if (phylink_autoneg_inband(mode)) {
-               dev_err(eth->dev,
-                       "In-band mode not supported in non SGMII mode!\n");
-@@ -472,8 +472,15 @@ static int mtk_mac_finish(struct phylink
- {
-       struct mtk_mac *mac = container_of(config, struct mtk_mac,
-                                          phylink_config);
-+      struct mtk_eth *eth = mac->hw;
-       u32 mcr_cur, mcr_new;
-+      /* Enable SGMII */
-+      if (interface == PHY_INTERFACE_MODE_SGMII ||
-+          phy_interface_mode_is_8023z(interface))
-+              regmap_update_bits(eth->ethsys, ETHSYS_SYSCFG0,
-+                                 SYSCFG0_SGMII_MASK, mac->syscfg0);
-+
-       /* Setup gmac */
-       mcr_cur = mtk_r32(mac->hw, MTK_MAC_MCR(mac->id));
-       mcr_new = mcr_cur;
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-@@ -1088,6 +1088,7 @@ struct mtk_mac {
-       struct mtk_hw_stats             *hw_stats;
-       __be32                          hwlro_ip[MTK_MAX_LRO_IP_CNT];
-       int                             hwlro_ip_cnt;
-+      unsigned int                    syscfg0;
- };
- /* the struct describing the SoC. these are declared in the soc_xyz.c files */
diff --git a/target/linux/generic/backport-5.15/704-17-v5.19-net-mtk_eth_soc-convert-code-structure-to-suit-split.patch b/target/linux/generic/backport-5.15/704-17-v5.19-net-mtk_eth_soc-convert-code-structure-to-suit-split.patch
deleted file mode 100644 (file)
index 4c84703..0000000
+++ /dev/null
@@ -1,254 +0,0 @@
-From 901f3fbe13c3e56f0742e02717ccbfabbc95c463 Mon Sep 17 00:00:00 2001
-From: "Russell King (Oracle)" <[email protected]>
-Date: Wed, 18 May 2022 15:55:22 +0100
-Subject: [PATCH 11/12] net: mtk_eth_soc: convert code structure to suit split
- PCS support
-
-Provide a mtk_pcs structure which encapsulates everything that the PCS
-functions need (the regmap and ana_rgc3 offset), and use this in the
-PCS functions. Provide shim functions to convert from the existing
-"mtk_sgmii_*" interface to the converted PCS functions.
-
-Signed-off-by: Russell King (Oracle) <[email protected]>
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- drivers/net/ethernet/mediatek/mtk_eth_soc.h |  15 ++-
- drivers/net/ethernet/mediatek/mtk_sgmii.c   | 123 +++++++++++---------
- 2 files changed, 79 insertions(+), 59 deletions(-)
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-@@ -959,16 +959,23 @@ struct mtk_soc_data {
- /* currently no SoC has more than 2 macs */
- #define MTK_MAX_DEVS                  2
--/* struct mtk_sgmii -  This is the structure holding sgmii regmap and its
-- *                     characteristics
-+/* struct mtk_pcs -    This structure holds each sgmii regmap and associated
-+ *                     data
-  * @regmap:            The register map pointing at the range used to setup
-  *                     SGMII modes
-  * @ana_rgc3:          The offset refers to register ANA_RGC3 related to regmap
-  */
-+struct mtk_pcs {
-+      struct regmap   *regmap;
-+      u32             ana_rgc3;
-+};
-+/* struct mtk_sgmii -  This is the structure holding sgmii regmap and its
-+ *                     characteristics
-+ * @pcs                Array of individual PCS structures
-+ */
- struct mtk_sgmii {
--      struct regmap   *regmap[MTK_MAX_DEVS];
--      u32             ana_rgc3;
-+      struct mtk_pcs  pcs[MTK_MAX_DEVS];
- };
- /* struct mtk_eth -   This is the main datasructure for holding the state
---- a/drivers/net/ethernet/mediatek/mtk_sgmii.c
-+++ b/drivers/net/ethernet/mediatek/mtk_sgmii.c
-@@ -9,90 +9,71 @@
- #include <linux/mfd/syscon.h>
- #include <linux/of.h>
-+#include <linux/phylink.h>
- #include <linux/regmap.h>
- #include "mtk_eth_soc.h"
--int mtk_sgmii_init(struct mtk_sgmii *ss, struct device_node *r, u32 ana_rgc3)
--{
--      struct device_node *np;
--      int i;
--
--      ss->ana_rgc3 = ana_rgc3;
--
--      for (i = 0; i < MTK_MAX_DEVS; i++) {
--              np = of_parse_phandle(r, "mediatek,sgmiisys", i);
--              if (!np)
--                      break;
--
--              ss->regmap[i] = syscon_node_to_regmap(np);
--              of_node_put(np);
--              if (IS_ERR(ss->regmap[i]))
--                      return PTR_ERR(ss->regmap[i]);
--      }
--
--      return 0;
--}
--
- /* For SGMII interface mode */
--static int mtk_sgmii_setup_mode_an(struct mtk_sgmii *ss, int id)
-+static int mtk_pcs_setup_mode_an(struct mtk_pcs *mpcs)
- {
-       unsigned int val;
--      if (!ss->regmap[id])
-+      if (!mpcs->regmap)
-               return -EINVAL;
-       /* Setup the link timer and QPHY power up inside SGMIISYS */
--      regmap_write(ss->regmap[id], SGMSYS_PCS_LINK_TIMER,
-+      regmap_write(mpcs->regmap, SGMSYS_PCS_LINK_TIMER,
-                    SGMII_LINK_TIMER_DEFAULT);
--      regmap_read(ss->regmap[id], SGMSYS_SGMII_MODE, &val);
-+      regmap_read(mpcs->regmap, SGMSYS_SGMII_MODE, &val);
-       val |= SGMII_REMOTE_FAULT_DIS;
--      regmap_write(ss->regmap[id], SGMSYS_SGMII_MODE, val);
-+      regmap_write(mpcs->regmap, SGMSYS_SGMII_MODE, val);
--      regmap_read(ss->regmap[id], SGMSYS_PCS_CONTROL_1, &val);
-+      regmap_read(mpcs->regmap, SGMSYS_PCS_CONTROL_1, &val);
-       val |= SGMII_AN_RESTART;
--      regmap_write(ss->regmap[id], SGMSYS_PCS_CONTROL_1, val);
-+      regmap_write(mpcs->regmap, SGMSYS_PCS_CONTROL_1, val);
--      regmap_read(ss->regmap[id], SGMSYS_QPHY_PWR_STATE_CTRL, &val);
-+      regmap_read(mpcs->regmap, SGMSYS_QPHY_PWR_STATE_CTRL, &val);
-       val &= ~SGMII_PHYA_PWD;
--      regmap_write(ss->regmap[id], SGMSYS_QPHY_PWR_STATE_CTRL, val);
-+      regmap_write(mpcs->regmap, SGMSYS_QPHY_PWR_STATE_CTRL, val);
-       return 0;
-+
- }
- /* For 1000BASE-X and 2500BASE-X interface modes, which operate at a
-  * fixed speed.
-  */
--static int mtk_sgmii_setup_mode_force(struct mtk_sgmii *ss, int id,
--                                    phy_interface_t interface)
-+static int mtk_pcs_setup_mode_force(struct mtk_pcs *mpcs,
-+                                  phy_interface_t interface)
- {
-       unsigned int val;
--      if (!ss->regmap[id])
-+      if (!mpcs->regmap)
-               return -EINVAL;
--      regmap_read(ss->regmap[id], ss->ana_rgc3, &val);
-+      regmap_read(mpcs->regmap, mpcs->ana_rgc3, &val);
-       val &= ~RG_PHY_SPEED_MASK;
-       if (interface == PHY_INTERFACE_MODE_2500BASEX)
-               val |= RG_PHY_SPEED_3_125G;
--      regmap_write(ss->regmap[id], ss->ana_rgc3, val);
-+      regmap_write(mpcs->regmap, mpcs->ana_rgc3, val);
-       /* Disable SGMII AN */
--      regmap_read(ss->regmap[id], SGMSYS_PCS_CONTROL_1, &val);
-+      regmap_read(mpcs->regmap, SGMSYS_PCS_CONTROL_1, &val);
-       val &= ~SGMII_AN_ENABLE;
--      regmap_write(ss->regmap[id], SGMSYS_PCS_CONTROL_1, val);
-+      regmap_write(mpcs->regmap, SGMSYS_PCS_CONTROL_1, val);
-       /* Set the speed etc but leave the duplex unchanged */
--      regmap_read(ss->regmap[id], SGMSYS_SGMII_MODE, &val);
-+      regmap_read(mpcs->regmap, SGMSYS_SGMII_MODE, &val);
-       val &= SGMII_DUPLEX_FULL | ~SGMII_IF_MODE_MASK;
-       val |= SGMII_SPEED_1000;
--      regmap_write(ss->regmap[id], SGMSYS_SGMII_MODE, val);
-+      regmap_write(mpcs->regmap, SGMSYS_SGMII_MODE, val);
-       /* Release PHYA power down state */
--      regmap_read(ss->regmap[id], SGMSYS_QPHY_PWR_STATE_CTRL, &val);
-+      regmap_read(mpcs->regmap, SGMSYS_QPHY_PWR_STATE_CTRL, &val);
-       val &= ~SGMII_PHYA_PWD;
--      regmap_write(ss->regmap[id], SGMSYS_QPHY_PWR_STATE_CTRL, val);
-+      regmap_write(mpcs->regmap, SGMSYS_QPHY_PWR_STATE_CTRL, val);
-       return 0;
- }
-@@ -100,44 +81,76 @@ static int mtk_sgmii_setup_mode_force(st
- int mtk_sgmii_config(struct mtk_sgmii *ss, int id, unsigned int mode,
-                    phy_interface_t interface)
- {
-+      struct mtk_pcs *mpcs = &ss->pcs[id];
-       int err = 0;
-       /* Setup SGMIISYS with the determined property */
-       if (interface != PHY_INTERFACE_MODE_SGMII)
--              err = mtk_sgmii_setup_mode_force(ss, id, interface);
-+              err = mtk_pcs_setup_mode_force(mpcs, interface);
-       else if (phylink_autoneg_inband(mode))
--              err = mtk_sgmii_setup_mode_an(ss, id);
-+              err = mtk_pcs_setup_mode_an(mpcs);
-       return err;
- }
--/* For 1000BASE-X and 2500BASE-X interface modes */
--void mtk_sgmii_link_up(struct mtk_sgmii *ss, int id, int speed, int duplex)
-+static void mtk_pcs_restart_an(struct mtk_pcs *mpcs)
-+{
-+      unsigned int val;
-+
-+      if (!mpcs->regmap)
-+              return;
-+
-+      regmap_read(mpcs->regmap, SGMSYS_PCS_CONTROL_1, &val);
-+      val |= SGMII_AN_RESTART;
-+      regmap_write(mpcs->regmap, SGMSYS_PCS_CONTROL_1, val);
-+}
-+
-+static void mtk_pcs_link_up(struct mtk_pcs *mpcs, int speed, int duplex)
- {
-       unsigned int val;
-       /* SGMII force duplex setting */
--      regmap_read(ss->regmap[id], SGMSYS_SGMII_MODE, &val);
-+      regmap_read(mpcs->regmap, SGMSYS_SGMII_MODE, &val);
-       val &= ~SGMII_DUPLEX_FULL;
-       if (duplex == DUPLEX_FULL)
-               val |= SGMII_DUPLEX_FULL;
--      regmap_write(ss->regmap[id], SGMSYS_SGMII_MODE, val);
-+      regmap_write(mpcs->regmap, SGMSYS_SGMII_MODE, val);
-+}
-+
-+/* For 1000BASE-X and 2500BASE-X interface modes */
-+void mtk_sgmii_link_up(struct mtk_sgmii *ss, int id, int speed, int duplex)
-+{
-+      mtk_pcs_link_up(&ss->pcs[id], speed, duplex);
-+}
-+
-+int mtk_sgmii_init(struct mtk_sgmii *ss, struct device_node *r, u32 ana_rgc3)
-+{
-+      struct device_node *np;
-+      int i;
-+
-+      for (i = 0; i < MTK_MAX_DEVS; i++) {
-+              np = of_parse_phandle(r, "mediatek,sgmiisys", i);
-+              if (!np)
-+                      break;
-+
-+              ss->pcs[i].ana_rgc3 = ana_rgc3;
-+              ss->pcs[i].regmap = syscon_node_to_regmap(np);
-+              of_node_put(np);
-+              if (IS_ERR(ss->pcs[i].regmap))
-+                      return PTR_ERR(ss->pcs[i].regmap);
-+      }
-+
-+      return 0;
- }
- void mtk_sgmii_restart_an(struct mtk_eth *eth, int mac_id)
- {
--      struct mtk_sgmii *ss = eth->sgmii;
--      unsigned int val, sid;
-+      unsigned int sid;
-       /* Decide how GMAC and SGMIISYS be mapped */
-       sid = (MTK_HAS_CAPS(eth->soc->caps, MTK_SHARED_SGMII)) ?
-              0 : mac_id;
--      if (!ss->regmap[sid])
--              return;
--
--      regmap_read(ss->regmap[sid], SGMSYS_PCS_CONTROL_1, &val);
--      val |= SGMII_AN_RESTART;
--      regmap_write(ss->regmap[sid], SGMSYS_PCS_CONTROL_1, val);
-+      mtk_pcs_restart_an(&eth->sgmii->pcs[sid]);
- }
diff --git a/target/linux/generic/backport-5.15/704-18-v5.19-net-mtk_eth_soc-partially-convert-to-phylink_pcs.patch b/target/linux/generic/backport-5.15/704-18-v5.19-net-mtk_eth_soc-partially-convert-to-phylink_pcs.patch
deleted file mode 100644 (file)
index 0f7e451..0000000
+++ /dev/null
@@ -1,262 +0,0 @@
-From 14a44ab0330d290fade1403a920e299cc56d7300 Mon Sep 17 00:00:00 2001
-From: "Russell King (Oracle)" <[email protected]>
-Date: Wed, 18 May 2022 15:55:28 +0100
-Subject: [PATCH 12/12] net: mtk_eth_soc: partially convert to phylink_pcs
-
-Partially convert mtk_eth_soc to phylink_pcs, moving the configuration,
-link up and AN restart over. However, it seems mac_pcs_get_state()
-doesn't actually get the state from the PCS, so we can't convert that
-over without a better understanding of the hardware.
-
-Signed-off-by: Russell King (Oracle) <[email protected]>
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- drivers/net/ethernet/mediatek/mtk_eth_soc.c | 49 ++++++++----------
- drivers/net/ethernet/mediatek/mtk_eth_soc.h |  7 ++-
- drivers/net/ethernet/mediatek/mtk_sgmii.c   | 55 +++++++++++----------
- 3 files changed, 53 insertions(+), 58 deletions(-)
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-@@ -310,6 +310,25 @@ static void mtk_gmac0_rgmii_adjust(struc
-       mtk_w32(eth, val, TRGMII_TCK_CTRL);
- }
-+static struct phylink_pcs *mtk_mac_select_pcs(struct phylink_config *config,
-+                                            phy_interface_t interface)
-+{
-+      struct mtk_mac *mac = container_of(config, struct mtk_mac,
-+                                         phylink_config);
-+      struct mtk_eth *eth = mac->hw;
-+      unsigned int sid;
-+
-+      if (interface == PHY_INTERFACE_MODE_SGMII ||
-+          phy_interface_mode_is_8023z(interface)) {
-+              sid = (MTK_HAS_CAPS(eth->soc->caps, MTK_SHARED_SGMII)) ?
-+                     0 : mac->id;
-+
-+              return mtk_sgmii_select_pcs(eth->sgmii, sid);
-+      }
-+
-+      return NULL;
-+}
-+
- static void mtk_mac_config(struct phylink_config *config, unsigned int mode,
-                          const struct phylink_link_state *state)
- {
-@@ -317,7 +336,7 @@ static void mtk_mac_config(struct phylin
-                                          phylink_config);
-       struct mtk_eth *eth = mac->hw;
-       int val, ge_mode, err = 0;
--      u32 sid, i;
-+      u32 i;
-       /* MT76x8 has no hardware settings between for the MAC */
-       if (!MTK_HAS_CAPS(eth->soc->caps, MTK_SOC_MT7628) &&
-@@ -438,15 +457,6 @@ static void mtk_mac_config(struct phylin
-                                  SYSCFG0_SGMII_MASK,
-                                  ~(u32)SYSCFG0_SGMII_MASK);
--              /* Decide how GMAC and SGMIISYS be mapped */
--              sid = (MTK_HAS_CAPS(eth->soc->caps, MTK_SHARED_SGMII)) ?
--                     0 : mac->id;
--
--              /* Setup SGMIISYS with the determined property */
--              err = mtk_sgmii_config(eth->sgmii, sid, mode, state->interface);
--              if (err)
--                      goto init_err;
--
-               /* Save the syscfg0 value for mac_finish */
-               mac->syscfg0 = val;
-       } else if (phylink_autoneg_inband(mode)) {
-@@ -526,14 +536,6 @@ static void mtk_mac_pcs_get_state(struct
-               state->pause |= MLO_PAUSE_TX;
- }
--static void mtk_mac_an_restart(struct phylink_config *config)
--{
--      struct mtk_mac *mac = container_of(config, struct mtk_mac,
--                                         phylink_config);
--
--      mtk_sgmii_restart_an(mac->hw, mac->id);
--}
--
- static void mtk_mac_link_down(struct phylink_config *config, unsigned int mode,
-                             phy_interface_t interface)
- {
-@@ -554,15 +556,6 @@ static void mtk_mac_link_up(struct phyli
-                                          phylink_config);
-       u32 mcr;
--      if (phy_interface_mode_is_8023z(interface)) {
--              struct mtk_eth *eth = mac->hw;
--
--              /* Decide how GMAC and SGMIISYS be mapped */
--              int sid = (MTK_HAS_CAPS(eth->soc->caps, MTK_SHARED_SGMII)) ?
--                         0 : mac->id;
--              mtk_sgmii_link_up(eth->sgmii, sid, speed, duplex);
--      }
--
-       mcr = mtk_r32(mac->hw, MTK_MAC_MCR(mac->id));
-       mcr &= ~(MAC_MCR_SPEED_100 | MAC_MCR_SPEED_1000 |
-                MAC_MCR_FORCE_DPX | MAC_MCR_FORCE_TX_FC |
-@@ -595,8 +588,8 @@ static void mtk_mac_link_up(struct phyli
- static const struct phylink_mac_ops mtk_phylink_ops = {
-       .validate = phylink_generic_validate,
-+      .mac_select_pcs = mtk_mac_select_pcs,
-       .mac_pcs_get_state = mtk_mac_pcs_get_state,
--      .mac_an_restart = mtk_mac_an_restart,
-       .mac_config = mtk_mac_config,
-       .mac_finish = mtk_mac_finish,
-       .mac_link_down = mtk_mac_link_down,
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-@@ -964,10 +964,12 @@ struct mtk_soc_data {
-  * @regmap:            The register map pointing at the range used to setup
-  *                     SGMII modes
-  * @ana_rgc3:          The offset refers to register ANA_RGC3 related to regmap
-+ * @pcs:               Phylink PCS structure
-  */
- struct mtk_pcs {
-       struct regmap   *regmap;
-       u32             ana_rgc3;
-+      struct phylink_pcs pcs;
- };
- /* struct mtk_sgmii -  This is the structure holding sgmii regmap and its
-@@ -1107,12 +1109,9 @@ void mtk_stats_update_mac(struct mtk_mac
- void mtk_w32(struct mtk_eth *eth, u32 val, unsigned reg);
- u32 mtk_r32(struct mtk_eth *eth, unsigned reg);
-+struct phylink_pcs *mtk_sgmii_select_pcs(struct mtk_sgmii *ss, int id);
- int mtk_sgmii_init(struct mtk_sgmii *ss, struct device_node *np,
-                  u32 ana_rgc3);
--int mtk_sgmii_config(struct mtk_sgmii *ss, int id, unsigned int mode,
--                   phy_interface_t interface);
--void mtk_sgmii_link_up(struct mtk_sgmii *ss, int id, int speed, int duplex);
--void mtk_sgmii_restart_an(struct mtk_eth *eth, int mac_id);
- int mtk_gmac_sgmii_path_setup(struct mtk_eth *eth, int mac_id);
- int mtk_gmac_gephy_path_setup(struct mtk_eth *eth, int mac_id);
---- a/drivers/net/ethernet/mediatek/mtk_sgmii.c
-+++ b/drivers/net/ethernet/mediatek/mtk_sgmii.c
-@@ -14,14 +14,16 @@
- #include "mtk_eth_soc.h"
-+static struct mtk_pcs *pcs_to_mtk_pcs(struct phylink_pcs *pcs)
-+{
-+      return container_of(pcs, struct mtk_pcs, pcs);
-+}
-+
- /* For SGMII interface mode */
- static int mtk_pcs_setup_mode_an(struct mtk_pcs *mpcs)
- {
-       unsigned int val;
--      if (!mpcs->regmap)
--              return -EINVAL;
--
-       /* Setup the link timer and QPHY power up inside SGMIISYS */
-       regmap_write(mpcs->regmap, SGMSYS_PCS_LINK_TIMER,
-                    SGMII_LINK_TIMER_DEFAULT);
-@@ -50,9 +52,6 @@ static int mtk_pcs_setup_mode_force(stru
- {
-       unsigned int val;
--      if (!mpcs->regmap)
--              return -EINVAL;
--
-       regmap_read(mpcs->regmap, mpcs->ana_rgc3, &val);
-       val &= ~RG_PHY_SPEED_MASK;
-       if (interface == PHY_INTERFACE_MODE_2500BASEX)
-@@ -78,10 +77,12 @@ static int mtk_pcs_setup_mode_force(stru
-       return 0;
- }
--int mtk_sgmii_config(struct mtk_sgmii *ss, int id, unsigned int mode,
--                   phy_interface_t interface)
-+static int mtk_pcs_config(struct phylink_pcs *pcs, unsigned int mode,
-+                        phy_interface_t interface,
-+                        const unsigned long *advertising,
-+                        bool permit_pause_to_mac)
- {
--      struct mtk_pcs *mpcs = &ss->pcs[id];
-+      struct mtk_pcs *mpcs = pcs_to_mtk_pcs(pcs);
-       int err = 0;
-       /* Setup SGMIISYS with the determined property */
-@@ -93,22 +94,25 @@ int mtk_sgmii_config(struct mtk_sgmii *s
-       return err;
- }
--static void mtk_pcs_restart_an(struct mtk_pcs *mpcs)
-+static void mtk_pcs_restart_an(struct phylink_pcs *pcs)
- {
-+      struct mtk_pcs *mpcs = pcs_to_mtk_pcs(pcs);
-       unsigned int val;
--      if (!mpcs->regmap)
--              return;
--
-       regmap_read(mpcs->regmap, SGMSYS_PCS_CONTROL_1, &val);
-       val |= SGMII_AN_RESTART;
-       regmap_write(mpcs->regmap, SGMSYS_PCS_CONTROL_1, val);
- }
--static void mtk_pcs_link_up(struct mtk_pcs *mpcs, int speed, int duplex)
-+static void mtk_pcs_link_up(struct phylink_pcs *pcs, unsigned int mode,
-+                          phy_interface_t interface, int speed, int duplex)
- {
-+      struct mtk_pcs *mpcs = pcs_to_mtk_pcs(pcs);
-       unsigned int val;
-+      if (!phy_interface_mode_is_8023z(interface))
-+              return;
-+
-       /* SGMII force duplex setting */
-       regmap_read(mpcs->regmap, SGMSYS_SGMII_MODE, &val);
-       val &= ~SGMII_DUPLEX_FULL;
-@@ -118,11 +122,11 @@ static void mtk_pcs_link_up(struct mtk_p
-       regmap_write(mpcs->regmap, SGMSYS_SGMII_MODE, val);
- }
--/* For 1000BASE-X and 2500BASE-X interface modes */
--void mtk_sgmii_link_up(struct mtk_sgmii *ss, int id, int speed, int duplex)
--{
--      mtk_pcs_link_up(&ss->pcs[id], speed, duplex);
--}
-+static const struct phylink_pcs_ops mtk_pcs_ops = {
-+      .pcs_config = mtk_pcs_config,
-+      .pcs_an_restart = mtk_pcs_restart_an,
-+      .pcs_link_up = mtk_pcs_link_up,
-+};
- int mtk_sgmii_init(struct mtk_sgmii *ss, struct device_node *r, u32 ana_rgc3)
- {
-@@ -139,18 +143,17 @@ int mtk_sgmii_init(struct mtk_sgmii *ss,
-               of_node_put(np);
-               if (IS_ERR(ss->pcs[i].regmap))
-                       return PTR_ERR(ss->pcs[i].regmap);
-+
-+              ss->pcs[i].pcs.ops = &mtk_pcs_ops;
-       }
-       return 0;
- }
--void mtk_sgmii_restart_an(struct mtk_eth *eth, int mac_id)
-+struct phylink_pcs *mtk_sgmii_select_pcs(struct mtk_sgmii *ss, int id)
- {
--      unsigned int sid;
--
--      /* Decide how GMAC and SGMIISYS be mapped */
--      sid = (MTK_HAS_CAPS(eth->soc->caps, MTK_SHARED_SGMII)) ?
--             0 : mac_id;
-+      if (!ss->pcs[id].regmap)
-+              return NULL;
--      mtk_pcs_restart_an(&eth->sgmii->pcs[sid]);
-+      return &ss->pcs[id].pcs;
- }
diff --git a/target/linux/generic/backport-5.15/705-01-v5.17-net-dsa-mt7530-iterate-using-dsa_switch_for_each_use.patch b/target/linux/generic/backport-5.15/705-01-v5.17-net-dsa-mt7530-iterate-using-dsa_switch_for_each_use.patch
deleted file mode 100644 (file)
index f65b0ca..0000000
+++ /dev/null
@@ -1,106 +0,0 @@
-From 505560028b6deb9b4385cf6100f05ca6f4aacaf8 Mon Sep 17 00:00:00 2001
-From: Vladimir Oltean <[email protected]>
-Date: Mon, 6 Dec 2021 18:57:49 +0200
-Subject: [PATCH 01/13] net: dsa: mt7530: iterate using
- dsa_switch_for_each_user_port in bridging ops
-
-Avoid repeated calls to dsa_to_port() (some hidden behind dsa_is_user_port
-and some in plain sight) by keeping two struct dsa_port references: one
-to the port passed as argument, and another to the other ports of the
-switch that we're iterating over.
-
-dsa_to_port(ds, i) gets replaced by other_dp, i gets replaced by
-other_port which is derived from other_dp->index, dsa_is_user_port is
-handled by the DSA iterator.
-
-Signed-off-by: Vladimir Oltean <[email protected]>
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- drivers/net/dsa/mt7530.c | 52 +++++++++++++++++++++++-----------------
- 1 file changed, 30 insertions(+), 22 deletions(-)
-
---- a/drivers/net/dsa/mt7530.c
-+++ b/drivers/net/dsa/mt7530.c
-@@ -1425,27 +1425,31 @@ static int
- mt7530_port_bridge_join(struct dsa_switch *ds, int port,
-                       struct net_device *bridge)
- {
--      struct mt7530_priv *priv = ds->priv;
-+      struct dsa_port *dp = dsa_to_port(ds, port), *other_dp;
-       u32 port_bitmap = BIT(MT7530_CPU_PORT);
--      int i;
-+      struct mt7530_priv *priv = ds->priv;
-       mutex_lock(&priv->reg_mutex);
--      for (i = 0; i < MT7530_NUM_PORTS; i++) {
-+      dsa_switch_for_each_user_port(other_dp, ds) {
-+              int other_port = other_dp->index;
-+
-+              if (dp == other_dp)
-+                      continue;
-+
-               /* Add this port to the port matrix of the other ports in the
-                * same bridge. If the port is disabled, port matrix is kept
-                * and not being setup until the port becomes enabled.
-                */
--              if (dsa_is_user_port(ds, i) && i != port) {
--                      if (dsa_to_port(ds, i)->bridge_dev != bridge)
--                              continue;
--                      if (priv->ports[i].enable)
--                              mt7530_set(priv, MT7530_PCR_P(i),
--                                         PCR_MATRIX(BIT(port)));
--                      priv->ports[i].pm |= PCR_MATRIX(BIT(port));
-+              if (other_dp->bridge_dev != bridge)
-+                      continue;
--                      port_bitmap |= BIT(i);
--              }
-+              if (priv->ports[other_port].enable)
-+                      mt7530_set(priv, MT7530_PCR_P(other_port),
-+                                 PCR_MATRIX(BIT(port)));
-+              priv->ports[other_port].pm |= PCR_MATRIX(BIT(port));
-+
-+              port_bitmap |= BIT(other_port);
-       }
-       /* Add the all other ports to this port matrix. */
-@@ -1550,24 +1554,28 @@ static void
- mt7530_port_bridge_leave(struct dsa_switch *ds, int port,
-                        struct net_device *bridge)
- {
-+      struct dsa_port *dp = dsa_to_port(ds, port), *other_dp;
-       struct mt7530_priv *priv = ds->priv;
--      int i;
-       mutex_lock(&priv->reg_mutex);
--      for (i = 0; i < MT7530_NUM_PORTS; i++) {
-+      dsa_switch_for_each_user_port(other_dp, ds) {
-+              int other_port = other_dp->index;
-+
-+              if (dp == other_dp)
-+                      continue;
-+
-               /* Remove this port from the port matrix of the other ports
-                * in the same bridge. If the port is disabled, port matrix
-                * is kept and not being setup until the port becomes enabled.
-                */
--              if (dsa_is_user_port(ds, i) && i != port) {
--                      if (dsa_to_port(ds, i)->bridge_dev != bridge)
--                              continue;
--                      if (priv->ports[i].enable)
--                              mt7530_clear(priv, MT7530_PCR_P(i),
--                                           PCR_MATRIX(BIT(port)));
--                      priv->ports[i].pm &= ~PCR_MATRIX(BIT(port));
--              }
-+              if (other_dp->bridge_dev != bridge)
-+                      continue;
-+
-+              if (priv->ports[other_port].enable)
-+                      mt7530_clear(priv, MT7530_PCR_P(other_port),
-+                                   PCR_MATRIX(BIT(port)));
-+              priv->ports[other_port].pm &= ~PCR_MATRIX(BIT(port));
-       }
-       /* Set the cpu port to be the only one in the port matrix of
diff --git a/target/linux/generic/backport-5.15/705-02-v5.19-net-dsa-mt7530-populate-supported_interfaces-and-mac.patch b/target/linux/generic/backport-5.15/705-02-v5.19-net-dsa-mt7530-populate-supported_interfaces-and-mac.patch
deleted file mode 100644 (file)
index e04bb11..0000000
+++ /dev/null
@@ -1,166 +0,0 @@
-From a1da54bcd664fc27169386db966575675ac3ccb0 Mon Sep 17 00:00:00 2001
-From: "Russell King (Oracle)" <[email protected]>
-Date: Mon, 11 Apr 2022 10:46:01 +0100
-Subject: [PATCH 02/13] net: dsa: mt7530: populate supported_interfaces and
- mac_capabilities
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-Populate the supported interfaces and MAC capabilities for mt7530,
-mt7531 and mt7621 DSA switches. Filling this in will enable phylink
-to pre-check the PHY interface mode against the the supported
-interfaces bitmap prior to calling the validate function, and will
-eventually allow us to convert to using the generic validation.
-
-Tested-by: Marek Behún <[email protected]>
-Signed-off-by: Russell King (Oracle) <[email protected]>
-Signed-off-by: Paolo Abeni <[email protected]>
----
- drivers/net/dsa/mt7530.c | 74 ++++++++++++++++++++++++++++++++++++++++
- drivers/net/dsa/mt7530.h |  2 ++
- 2 files changed, 76 insertions(+)
-
---- a/drivers/net/dsa/mt7530.c
-+++ b/drivers/net/dsa/mt7530.c
-@@ -2687,6 +2687,32 @@ mt7531_setup(struct dsa_switch *ds)
-       return 0;
- }
-+static void mt7530_mac_port_get_caps(struct dsa_switch *ds, int port,
-+                                   struct phylink_config *config)
-+{
-+      switch (port) {
-+      case 0 ... 4: /* Internal phy */
-+              __set_bit(PHY_INTERFACE_MODE_GMII,
-+                        config->supported_interfaces);
-+              break;
-+
-+      case 5: /* 2nd cpu port with phy of port 0 or 4 / external phy */
-+              phy_interface_set_rgmii(config->supported_interfaces);
-+              __set_bit(PHY_INTERFACE_MODE_MII,
-+                        config->supported_interfaces);
-+              __set_bit(PHY_INTERFACE_MODE_GMII,
-+                        config->supported_interfaces);
-+              break;
-+
-+      case 6: /* 1st cpu port */
-+              __set_bit(PHY_INTERFACE_MODE_RGMII,
-+                        config->supported_interfaces);
-+              __set_bit(PHY_INTERFACE_MODE_TRGMII,
-+                        config->supported_interfaces);
-+              break;
-+      }
-+}
-+
- static bool
- mt7530_phy_mode_supported(struct dsa_switch *ds, int port,
-                         const struct phylink_link_state *state)
-@@ -2723,6 +2749,37 @@ static bool mt7531_is_rgmii_port(struct
-       return (port == 5) && (priv->p5_intf_sel != P5_INTF_SEL_GMAC5_SGMII);
- }
-+static void mt7531_mac_port_get_caps(struct dsa_switch *ds, int port,
-+                                   struct phylink_config *config)
-+{
-+      struct mt7530_priv *priv = ds->priv;
-+
-+      switch (port) {
-+      case 0 ... 4: /* Internal phy */
-+              __set_bit(PHY_INTERFACE_MODE_GMII,
-+                        config->supported_interfaces);
-+              break;
-+
-+      case 5: /* 2nd cpu port supports either rgmii or sgmii/8023z */
-+              if (mt7531_is_rgmii_port(priv, port)) {
-+                      phy_interface_set_rgmii(config->supported_interfaces);
-+                      break;
-+              }
-+              fallthrough;
-+
-+      case 6: /* 1st cpu port supports sgmii/8023z only */
-+              __set_bit(PHY_INTERFACE_MODE_SGMII,
-+                        config->supported_interfaces);
-+              __set_bit(PHY_INTERFACE_MODE_1000BASEX,
-+                        config->supported_interfaces);
-+              __set_bit(PHY_INTERFACE_MODE_2500BASEX,
-+                        config->supported_interfaces);
-+
-+              config->mac_capabilities |= MAC_2500FD;
-+              break;
-+      }
-+}
-+
- static bool
- mt7531_phy_mode_supported(struct dsa_switch *ds, int port,
-                         const struct phylink_link_state *state)
-@@ -3199,6 +3256,18 @@ mt7531_cpu_port_config(struct dsa_switch
-       return 0;
- }
-+static void mt753x_phylink_get_caps(struct dsa_switch *ds, int port,
-+                                  struct phylink_config *config)
-+{
-+      struct mt7530_priv *priv = ds->priv;
-+
-+      /* This switch only supports full-duplex at 1Gbps */
-+      config->mac_capabilities = MAC_ASYM_PAUSE | MAC_SYM_PAUSE |
-+                                 MAC_10 | MAC_100 | MAC_1000FD;
-+
-+      priv->info->mac_port_get_caps(ds, port, config);
-+}
-+
- static void
- mt7530_mac_port_validate(struct dsa_switch *ds, int port,
-                        unsigned long *supported)
-@@ -3435,6 +3504,7 @@ static const struct dsa_switch_ops mt753
-       .port_vlan_del          = mt7530_port_vlan_del,
-       .port_mirror_add        = mt753x_port_mirror_add,
-       .port_mirror_del        = mt753x_port_mirror_del,
-+      .phylink_get_caps       = mt753x_phylink_get_caps,
-       .phylink_validate       = mt753x_phylink_validate,
-       .phylink_mac_link_state = mt753x_phylink_mac_link_state,
-       .phylink_mac_config     = mt753x_phylink_mac_config,
-@@ -3452,6 +3522,7 @@ static const struct mt753x_info mt753x_t
-               .phy_read = mt7530_phy_read,
-               .phy_write = mt7530_phy_write,
-               .pad_setup = mt7530_pad_clk_setup,
-+              .mac_port_get_caps = mt7530_mac_port_get_caps,
-               .phy_mode_supported = mt7530_phy_mode_supported,
-               .mac_port_validate = mt7530_mac_port_validate,
-               .mac_port_get_state = mt7530_phylink_mac_link_state,
-@@ -3463,6 +3534,7 @@ static const struct mt753x_info mt753x_t
-               .phy_read = mt7530_phy_read,
-               .phy_write = mt7530_phy_write,
-               .pad_setup = mt7530_pad_clk_setup,
-+              .mac_port_get_caps = mt7530_mac_port_get_caps,
-               .phy_mode_supported = mt7530_phy_mode_supported,
-               .mac_port_validate = mt7530_mac_port_validate,
-               .mac_port_get_state = mt7530_phylink_mac_link_state,
-@@ -3475,6 +3547,7 @@ static const struct mt753x_info mt753x_t
-               .phy_write = mt7531_ind_phy_write,
-               .pad_setup = mt7531_pad_setup,
-               .cpu_port_config = mt7531_cpu_port_config,
-+              .mac_port_get_caps = mt7531_mac_port_get_caps,
-               .phy_mode_supported = mt7531_phy_mode_supported,
-               .mac_port_validate = mt7531_mac_port_validate,
-               .mac_port_get_state = mt7531_phylink_mac_link_state,
-@@ -3537,6 +3610,7 @@ mt7530_probe(struct mdio_device *mdiodev
-        */
-       if (!priv->info->sw_setup || !priv->info->pad_setup ||
-           !priv->info->phy_read || !priv->info->phy_write ||
-+          !priv->info->mac_port_get_caps ||
-           !priv->info->phy_mode_supported ||
-           !priv->info->mac_port_validate ||
-           !priv->info->mac_port_get_state || !priv->info->mac_port_config)
---- a/drivers/net/dsa/mt7530.h
-+++ b/drivers/net/dsa/mt7530.h
-@@ -807,6 +807,8 @@ struct mt753x_info {
-       int (*phy_write)(struct mt7530_priv *priv, int port, int regnum, u16 val);
-       int (*pad_setup)(struct dsa_switch *ds, phy_interface_t interface);
-       int (*cpu_port_config)(struct dsa_switch *ds, int port);
-+      void (*mac_port_get_caps)(struct dsa_switch *ds, int port,
-+                                struct phylink_config *config);
-       bool (*phy_mode_supported)(struct dsa_switch *ds, int port,
-                                  const struct phylink_link_state *state);
-       void (*mac_port_validate)(struct dsa_switch *ds, int port,
diff --git a/target/linux/generic/backport-5.15/705-03-v5.19-net-dsa-mt7530-remove-interface-checks.patch b/target/linux/generic/backport-5.15/705-03-v5.19-net-dsa-mt7530-remove-interface-checks.patch
deleted file mode 100644 (file)
index 31be0e7..0000000
+++ /dev/null
@@ -1,172 +0,0 @@
-From e3f6719e2269868ca129b05da50cd55786848954 Mon Sep 17 00:00:00 2001
-From: "Russell King (Oracle)" <[email protected]>
-Date: Mon, 11 Apr 2022 10:46:06 +0100
-Subject: [PATCH 03/13] net: dsa: mt7530: remove interface checks
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-As phylink checks the interface mode against the supported_interfaces
-bitmap, we no longer need to validate the interface mode, nor handle
-PHY_INTERFACE_MODE_NA in the validation function. Remove these to
-simplify the implementation.
-
-Tested-by: Marek Behún <[email protected]>
-Signed-off-by: Russell King (Oracle) <[email protected]>
-Signed-off-by: Paolo Abeni <[email protected]>
----
- drivers/net/dsa/mt7530.c | 82 ----------------------------------------
- drivers/net/dsa/mt7530.h |  2 -
- 2 files changed, 84 deletions(-)
-
---- a/drivers/net/dsa/mt7530.c
-+++ b/drivers/net/dsa/mt7530.c
-@@ -2713,37 +2713,6 @@ static void mt7530_mac_port_get_caps(str
-       }
- }
--static bool
--mt7530_phy_mode_supported(struct dsa_switch *ds, int port,
--                        const struct phylink_link_state *state)
--{
--      struct mt7530_priv *priv = ds->priv;
--
--      switch (port) {
--      case 0 ... 4: /* Internal phy */
--              if (state->interface != PHY_INTERFACE_MODE_GMII)
--                      return false;
--              break;
--      case 5: /* 2nd cpu port with phy of port 0 or 4 / external phy */
--              if (!phy_interface_mode_is_rgmii(state->interface) &&
--                  state->interface != PHY_INTERFACE_MODE_MII &&
--                  state->interface != PHY_INTERFACE_MODE_GMII)
--                      return false;
--              break;
--      case 6: /* 1st cpu port */
--              if (state->interface != PHY_INTERFACE_MODE_RGMII &&
--                  state->interface != PHY_INTERFACE_MODE_TRGMII)
--                      return false;
--              break;
--      default:
--              dev_err(priv->dev, "%s: unsupported port: %i\n", __func__,
--                      port);
--              return false;
--      }
--
--      return true;
--}
--
- static bool mt7531_is_rgmii_port(struct mt7530_priv *priv, u32 port)
- {
-       return (port == 5) && (priv->p5_intf_sel != P5_INTF_SEL_GMAC5_SGMII);
-@@ -2780,44 +2749,6 @@ static void mt7531_mac_port_get_caps(str
-       }
- }
--static bool
--mt7531_phy_mode_supported(struct dsa_switch *ds, int port,
--                        const struct phylink_link_state *state)
--{
--      struct mt7530_priv *priv = ds->priv;
--
--      switch (port) {
--      case 0 ... 4: /* Internal phy */
--              if (state->interface != PHY_INTERFACE_MODE_GMII)
--                      return false;
--              break;
--      case 5: /* 2nd cpu port supports either rgmii or sgmii/8023z */
--              if (mt7531_is_rgmii_port(priv, port))
--                      return phy_interface_mode_is_rgmii(state->interface);
--              fallthrough;
--      case 6: /* 1st cpu port supports sgmii/8023z only */
--              if (state->interface != PHY_INTERFACE_MODE_SGMII &&
--                  !phy_interface_mode_is_8023z(state->interface))
--                      return false;
--              break;
--      default:
--              dev_err(priv->dev, "%s: unsupported port: %i\n", __func__,
--                      port);
--              return false;
--      }
--
--      return true;
--}
--
--static bool
--mt753x_phy_mode_supported(struct dsa_switch *ds, int port,
--                        const struct phylink_link_state *state)
--{
--      struct mt7530_priv *priv = ds->priv;
--
--      return priv->info->phy_mode_supported(ds, port, state);
--}
--
- static int
- mt753x_pad_setup(struct dsa_switch *ds, const struct phylink_link_state *state)
- {
-@@ -3072,9 +3003,6 @@ mt753x_phylink_mac_config(struct dsa_swi
-       struct mt7530_priv *priv = ds->priv;
-       u32 mcr_cur, mcr_new;
--      if (!mt753x_phy_mode_supported(ds, port, state))
--              goto unsupported;
--
-       switch (port) {
-       case 0 ... 4: /* Internal phy */
-               if (state->interface != PHY_INTERFACE_MODE_GMII)
-@@ -3290,12 +3218,6 @@ mt753x_phylink_validate(struct dsa_switc
-       __ETHTOOL_DECLARE_LINK_MODE_MASK(mask) = { 0, };
-       struct mt7530_priv *priv = ds->priv;
--      if (state->interface != PHY_INTERFACE_MODE_NA &&
--          !mt753x_phy_mode_supported(ds, port, state)) {
--              linkmode_zero(supported);
--              return;
--      }
--
-       phylink_set_port_modes(mask);
-       if (state->interface != PHY_INTERFACE_MODE_TRGMII &&
-@@ -3523,7 +3445,6 @@ static const struct mt753x_info mt753x_t
-               .phy_write = mt7530_phy_write,
-               .pad_setup = mt7530_pad_clk_setup,
-               .mac_port_get_caps = mt7530_mac_port_get_caps,
--              .phy_mode_supported = mt7530_phy_mode_supported,
-               .mac_port_validate = mt7530_mac_port_validate,
-               .mac_port_get_state = mt7530_phylink_mac_link_state,
-               .mac_port_config = mt7530_mac_config,
-@@ -3535,7 +3456,6 @@ static const struct mt753x_info mt753x_t
-               .phy_write = mt7530_phy_write,
-               .pad_setup = mt7530_pad_clk_setup,
-               .mac_port_get_caps = mt7530_mac_port_get_caps,
--              .phy_mode_supported = mt7530_phy_mode_supported,
-               .mac_port_validate = mt7530_mac_port_validate,
-               .mac_port_get_state = mt7530_phylink_mac_link_state,
-               .mac_port_config = mt7530_mac_config,
-@@ -3548,7 +3468,6 @@ static const struct mt753x_info mt753x_t
-               .pad_setup = mt7531_pad_setup,
-               .cpu_port_config = mt7531_cpu_port_config,
-               .mac_port_get_caps = mt7531_mac_port_get_caps,
--              .phy_mode_supported = mt7531_phy_mode_supported,
-               .mac_port_validate = mt7531_mac_port_validate,
-               .mac_port_get_state = mt7531_phylink_mac_link_state,
-               .mac_port_config = mt7531_mac_config,
-@@ -3611,7 +3530,6 @@ mt7530_probe(struct mdio_device *mdiodev
-       if (!priv->info->sw_setup || !priv->info->pad_setup ||
-           !priv->info->phy_read || !priv->info->phy_write ||
-           !priv->info->mac_port_get_caps ||
--          !priv->info->phy_mode_supported ||
-           !priv->info->mac_port_validate ||
-           !priv->info->mac_port_get_state || !priv->info->mac_port_config)
-               return -EINVAL;
---- a/drivers/net/dsa/mt7530.h
-+++ b/drivers/net/dsa/mt7530.h
-@@ -809,8 +809,6 @@ struct mt753x_info {
-       int (*cpu_port_config)(struct dsa_switch *ds, int port);
-       void (*mac_port_get_caps)(struct dsa_switch *ds, int port,
-                                 struct phylink_config *config);
--      bool (*phy_mode_supported)(struct dsa_switch *ds, int port,
--                                 const struct phylink_link_state *state);
-       void (*mac_port_validate)(struct dsa_switch *ds, int port,
-                                 unsigned long *supported);
-       int (*mac_port_get_state)(struct dsa_switch *ds, int port,
diff --git a/target/linux/generic/backport-5.15/705-04-v5.19-net-dsa-mt7530-drop-use-of-phylink_helper_basex_spee.patch b/target/linux/generic/backport-5.15/705-04-v5.19-net-dsa-mt7530-drop-use-of-phylink_helper_basex_spee.patch
deleted file mode 100644 (file)
index 2a5d5ae..0000000
+++ /dev/null
@@ -1,34 +0,0 @@
-From 58344a3b85f1bd5ffddfc2c11f6f2bf688b5f990 Mon Sep 17 00:00:00 2001
-From: "Russell King (Oracle)" <[email protected]>
-Date: Mon, 11 Apr 2022 10:46:12 +0100
-Subject: [PATCH 04/13] net: dsa: mt7530: drop use of
- phylink_helper_basex_speed()
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-Now that we have a better method to select SFP interface modes, we
-no longer need to use phylink_helper_basex_speed() in a driver's
-validation function.
-
-Tested-by: Marek Behún <[email protected]>
-Signed-off-by: Russell King (Oracle) <[email protected]>
-Signed-off-by: Paolo Abeni <[email protected]>
----
- drivers/net/dsa/mt7530.c | 5 -----
- 1 file changed, 5 deletions(-)
-
---- a/drivers/net/dsa/mt7530.c
-+++ b/drivers/net/dsa/mt7530.c
-@@ -3242,11 +3242,6 @@ mt753x_phylink_validate(struct dsa_switc
-       linkmode_and(supported, supported, mask);
-       linkmode_and(state->advertising, state->advertising, mask);
--
--      /* We can only operate at 2500BaseX or 1000BaseX.  If requested
--       * to advertise both, only report advertising at 2500BaseX.
--       */
--      phylink_helper_basex_speed(state);
- }
- static int
diff --git a/target/linux/generic/backport-5.15/705-05-v5.19-net-dsa-mt7530-only-indicate-linkmodes-that-can-be-s.patch b/target/linux/generic/backport-5.15/705-05-v5.19-net-dsa-mt7530-only-indicate-linkmodes-that-can-be-s.patch
deleted file mode 100644 (file)
index ad67231..0000000
+++ /dev/null
@@ -1,86 +0,0 @@
-From 3c1d788a62dc648d1846049b66119ebb69dedd52 Mon Sep 17 00:00:00 2001
-From: "Russell King (Oracle)" <[email protected]>
-Date: Mon, 11 Apr 2022 10:46:17 +0100
-Subject: [PATCH 05/13] net: dsa: mt7530: only indicate linkmodes that can be
- supported
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-Now that mt7530 is not using the basex helper, it becomes unnecessary to
-indicate support for both 1000baseX and 2500baseX when one of the 803.3z
-PHY interface modes is being selected. Ensure that the driver indicates
-only those linkmodes that can actually be supported by the PHY interface
-mode.
-
-Tested-by: Marek Behún <[email protected]>
-Signed-off-by: Russell King (Oracle) <[email protected]>
-Signed-off-by: Paolo Abeni <[email protected]>
----
- drivers/net/dsa/mt7530.c | 12 ++++++++----
- drivers/net/dsa/mt7530.h |  1 +
- 2 files changed, 9 insertions(+), 4 deletions(-)
-
---- a/drivers/net/dsa/mt7530.c
-+++ b/drivers/net/dsa/mt7530.c
-@@ -2820,12 +2820,13 @@ static int mt7531_rgmii_setup(struct mt7
- }
- static void mt7531_sgmii_validate(struct mt7530_priv *priv, int port,
-+                                phy_interface_t interface,
-                                 unsigned long *supported)
- {
-       /* Port5 supports ethier RGMII or SGMII.
-        * Port6 supports SGMII only.
-        */
--      if (port == 6) {
-+      if (port == 6 && interface == PHY_INTERFACE_MODE_2500BASEX) {
-               phylink_set(supported, 2500baseX_Full);
-               phylink_set(supported, 2500baseT_Full);
-       }
-@@ -3198,16 +3199,18 @@ static void mt753x_phylink_get_caps(stru
- static void
- mt7530_mac_port_validate(struct dsa_switch *ds, int port,
-+                       phy_interface_t interface,
-                        unsigned long *supported)
- {
- }
- static void mt7531_mac_port_validate(struct dsa_switch *ds, int port,
-+                                   phy_interface_t interface,
-                                    unsigned long *supported)
- {
-       struct mt7530_priv *priv = ds->priv;
--      mt7531_sgmii_validate(priv, port, supported);
-+      mt7531_sgmii_validate(priv, port, interface, supported);
- }
- static void
-@@ -3230,12 +3233,13 @@ mt753x_phylink_validate(struct dsa_switc
-       }
-       /* This switch only supports 1G full-duplex. */
--      if (state->interface != PHY_INTERFACE_MODE_MII) {
-+      if (state->interface != PHY_INTERFACE_MODE_MII &&
-+          state->interface != PHY_INTERFACE_MODE_2500BASEX) {
-               phylink_set(mask, 1000baseT_Full);
-               phylink_set(mask, 1000baseX_Full);
-       }
--      priv->info->mac_port_validate(ds, port, mask);
-+      priv->info->mac_port_validate(ds, port, state->interface, mask);
-       phylink_set(mask, Pause);
-       phylink_set(mask, Asym_Pause);
---- a/drivers/net/dsa/mt7530.h
-+++ b/drivers/net/dsa/mt7530.h
-@@ -810,6 +810,7 @@ struct mt753x_info {
-       void (*mac_port_get_caps)(struct dsa_switch *ds, int port,
-                                 struct phylink_config *config);
-       void (*mac_port_validate)(struct dsa_switch *ds, int port,
-+                                phy_interface_t interface,
-                                 unsigned long *supported);
-       int (*mac_port_get_state)(struct dsa_switch *ds, int port,
-                                 struct phylink_link_state *state);
diff --git a/target/linux/generic/backport-5.15/705-06-v5.19-net-dsa-mt7530-switch-to-use-phylink_get_linkmodes.patch b/target/linux/generic/backport-5.15/705-06-v5.19-net-dsa-mt7530-switch-to-use-phylink_get_linkmodes.patch
deleted file mode 100644 (file)
index 8d9802f..0000000
+++ /dev/null
@@ -1,131 +0,0 @@
-From 1c2211cb15dd3957fb26c0e1615eceb5db851ad6 Mon Sep 17 00:00:00 2001
-From: "Russell King (Oracle)" <[email protected]>
-Date: Mon, 11 Apr 2022 10:46:22 +0100
-Subject: [PATCH 06/13] net: dsa: mt7530: switch to use phylink_get_linkmodes()
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-Switch mt7530 to use phylink_get_linkmodes() to generate the ethtool
-linkmodes that can be supported. We are unable to use the generic
-helper for this as pause modes are dependent on the interface as
-the Autoneg bit depends on the interface mode.
-
-Tested-by: Marek Behún <[email protected]>
-Signed-off-by: Russell King (Oracle) <[email protected]>
-Signed-off-by: Paolo Abeni <[email protected]>
----
- drivers/net/dsa/mt7530.c | 57 ++++------------------------------------
- 1 file changed, 5 insertions(+), 52 deletions(-)
-
---- a/drivers/net/dsa/mt7530.c
-+++ b/drivers/net/dsa/mt7530.c
-@@ -2819,19 +2819,6 @@ static int mt7531_rgmii_setup(struct mt7
-       return 0;
- }
--static void mt7531_sgmii_validate(struct mt7530_priv *priv, int port,
--                                phy_interface_t interface,
--                                unsigned long *supported)
--{
--      /* Port5 supports ethier RGMII or SGMII.
--       * Port6 supports SGMII only.
--       */
--      if (port == 6 && interface == PHY_INTERFACE_MODE_2500BASEX) {
--              phylink_set(supported, 2500baseX_Full);
--              phylink_set(supported, 2500baseT_Full);
--      }
--}
--
- static void
- mt7531_sgmii_link_up_force(struct dsa_switch *ds, int port,
-                          unsigned int mode, phy_interface_t interface,
-@@ -3198,51 +3185,21 @@ static void mt753x_phylink_get_caps(stru
- }
- static void
--mt7530_mac_port_validate(struct dsa_switch *ds, int port,
--                       phy_interface_t interface,
--                       unsigned long *supported)
--{
--}
--
--static void mt7531_mac_port_validate(struct dsa_switch *ds, int port,
--                                   phy_interface_t interface,
--                                   unsigned long *supported)
--{
--      struct mt7530_priv *priv = ds->priv;
--
--      mt7531_sgmii_validate(priv, port, interface, supported);
--}
--
--static void
- mt753x_phylink_validate(struct dsa_switch *ds, int port,
-                       unsigned long *supported,
-                       struct phylink_link_state *state)
- {
-       __ETHTOOL_DECLARE_LINK_MODE_MASK(mask) = { 0, };
--      struct mt7530_priv *priv = ds->priv;
-+      u32 caps;
-+
-+      caps = dsa_to_port(ds, port)->pl_config.mac_capabilities;
-       phylink_set_port_modes(mask);
-+      phylink_get_linkmodes(mask, state->interface, caps);
-       if (state->interface != PHY_INTERFACE_MODE_TRGMII &&
--          !phy_interface_mode_is_8023z(state->interface)) {
--              phylink_set(mask, 10baseT_Half);
--              phylink_set(mask, 10baseT_Full);
--              phylink_set(mask, 100baseT_Half);
--              phylink_set(mask, 100baseT_Full);
-+          !phy_interface_mode_is_8023z(state->interface))
-               phylink_set(mask, Autoneg);
--      }
--
--      /* This switch only supports 1G full-duplex. */
--      if (state->interface != PHY_INTERFACE_MODE_MII &&
--          state->interface != PHY_INTERFACE_MODE_2500BASEX) {
--              phylink_set(mask, 1000baseT_Full);
--              phylink_set(mask, 1000baseX_Full);
--      }
--
--      priv->info->mac_port_validate(ds, port, state->interface, mask);
--
--      phylink_set(mask, Pause);
--      phylink_set(mask, Asym_Pause);
-       linkmode_and(supported, supported, mask);
-       linkmode_and(state->advertising, state->advertising, mask);
-@@ -3444,7 +3401,6 @@ static const struct mt753x_info mt753x_t
-               .phy_write = mt7530_phy_write,
-               .pad_setup = mt7530_pad_clk_setup,
-               .mac_port_get_caps = mt7530_mac_port_get_caps,
--              .mac_port_validate = mt7530_mac_port_validate,
-               .mac_port_get_state = mt7530_phylink_mac_link_state,
-               .mac_port_config = mt7530_mac_config,
-       },
-@@ -3455,7 +3411,6 @@ static const struct mt753x_info mt753x_t
-               .phy_write = mt7530_phy_write,
-               .pad_setup = mt7530_pad_clk_setup,
-               .mac_port_get_caps = mt7530_mac_port_get_caps,
--              .mac_port_validate = mt7530_mac_port_validate,
-               .mac_port_get_state = mt7530_phylink_mac_link_state,
-               .mac_port_config = mt7530_mac_config,
-       },
-@@ -3467,7 +3422,6 @@ static const struct mt753x_info mt753x_t
-               .pad_setup = mt7531_pad_setup,
-               .cpu_port_config = mt7531_cpu_port_config,
-               .mac_port_get_caps = mt7531_mac_port_get_caps,
--              .mac_port_validate = mt7531_mac_port_validate,
-               .mac_port_get_state = mt7531_phylink_mac_link_state,
-               .mac_port_config = mt7531_mac_config,
-               .mac_pcs_an_restart = mt7531_sgmii_restart_an,
-@@ -3529,7 +3483,6 @@ mt7530_probe(struct mdio_device *mdiodev
-       if (!priv->info->sw_setup || !priv->info->pad_setup ||
-           !priv->info->phy_read || !priv->info->phy_write ||
-           !priv->info->mac_port_get_caps ||
--          !priv->info->mac_port_validate ||
-           !priv->info->mac_port_get_state || !priv->info->mac_port_config)
-               return -EINVAL;
diff --git a/target/linux/generic/backport-5.15/705-07-v5.19-net-dsa-mt7530-partially-convert-to-phylink_pcs.patch b/target/linux/generic/backport-5.15/705-07-v5.19-net-dsa-mt7530-partially-convert-to-phylink_pcs.patch
deleted file mode 100644 (file)
index 149c12c..0000000
+++ /dev/null
@@ -1,385 +0,0 @@
-From fd993fd59d96d5e2d5972ec4ca1f9651025c987b Mon Sep 17 00:00:00 2001
-From: "Russell King (Oracle)" <[email protected]>
-Date: Mon, 11 Apr 2022 10:46:27 +0100
-Subject: [PATCH 07/13] net: dsa: mt7530: partially convert to phylink_pcs
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-Partially convert the mt7530 driver to use phylink's PCS support. This
-is a partial implementation as we don't move anything into the
-pcs_config method yet - this driver supports SGMII or 1000BASE-X
-without in-band.
-
-Tested-by: Marek Behún <[email protected]>
-Signed-off-by: Russell King (Oracle) <[email protected]>
-Signed-off-by: Paolo Abeni <[email protected]>
----
- drivers/net/dsa/mt7530.c | 144 +++++++++++++++++++++++----------------
- drivers/net/dsa/mt7530.h |  21 +++---
- 2 files changed, 95 insertions(+), 70 deletions(-)
-
---- a/drivers/net/dsa/mt7530.c
-+++ b/drivers/net/dsa/mt7530.c
-@@ -25,6 +25,11 @@
- #include "mt7530.h"
-+static struct mt753x_pcs *pcs_to_mt753x_pcs(struct phylink_pcs *pcs)
-+{
-+      return container_of(pcs, struct mt753x_pcs, pcs);
-+}
-+
- /* String, offset, and register size in bytes if different from 4 bytes */
- static const struct mt7530_mib_desc mt7530_mib[] = {
-       MIB_DESC(1, 0x00, "TxDrop"),
-@@ -2819,12 +2824,11 @@ static int mt7531_rgmii_setup(struct mt7
-       return 0;
- }
--static void
--mt7531_sgmii_link_up_force(struct dsa_switch *ds, int port,
--                         unsigned int mode, phy_interface_t interface,
--                         int speed, int duplex)
-+static void mt7531_pcs_link_up(struct phylink_pcs *pcs, unsigned int mode,
-+                             phy_interface_t interface, int speed, int duplex)
- {
--      struct mt7530_priv *priv = ds->priv;
-+      struct mt7530_priv *priv = pcs_to_mt753x_pcs(pcs)->priv;
-+      int port = pcs_to_mt753x_pcs(pcs)->port;
-       unsigned int val;
-       /* For adjusting speed and duplex of SGMII force mode. */
-@@ -2850,6 +2854,9 @@ mt7531_sgmii_link_up_force(struct dsa_sw
-       /* MT7531 SGMII 1G force mode can only work in full duplex mode,
-        * no matter MT7531_SGMII_FORCE_HALF_DUPLEX is set or not.
-+       *
-+       * The speed check is unnecessary as the MAC capabilities apply
-+       * this restriction. --rmk
-        */
-       if ((speed == SPEED_10 || speed == SPEED_100) &&
-           duplex != DUPLEX_FULL)
-@@ -2925,9 +2932,10 @@ static int mt7531_sgmii_setup_mode_an(st
-       return 0;
- }
--static void mt7531_sgmii_restart_an(struct dsa_switch *ds, int port)
-+static void mt7531_pcs_an_restart(struct phylink_pcs *pcs)
- {
--      struct mt7530_priv *priv = ds->priv;
-+      struct mt7530_priv *priv = pcs_to_mt753x_pcs(pcs)->priv;
-+      int port = pcs_to_mt753x_pcs(pcs)->port;
-       u32 val;
-       /* Only restart AN when AN is enabled */
-@@ -2984,6 +2992,24 @@ mt753x_mac_config(struct dsa_switch *ds,
-       return priv->info->mac_port_config(ds, port, mode, state->interface);
- }
-+static struct phylink_pcs *
-+mt753x_phylink_mac_select_pcs(struct dsa_switch *ds, int port,
-+                            phy_interface_t interface)
-+{
-+      struct mt7530_priv *priv = ds->priv;
-+
-+      switch (interface) {
-+      case PHY_INTERFACE_MODE_TRGMII:
-+      case PHY_INTERFACE_MODE_SGMII:
-+      case PHY_INTERFACE_MODE_1000BASEX:
-+      case PHY_INTERFACE_MODE_2500BASEX:
-+              return &priv->pcs[port].pcs;
-+
-+      default:
-+              return NULL;
-+      }
-+}
-+
- static void
- mt753x_phylink_mac_config(struct dsa_switch *ds, int port, unsigned int mode,
-                         const struct phylink_link_state *state)
-@@ -3045,17 +3071,6 @@ unsupported:
-               mt7530_write(priv, MT7530_PMCR_P(port), mcr_new);
- }
--static void
--mt753x_phylink_mac_an_restart(struct dsa_switch *ds, int port)
--{
--      struct mt7530_priv *priv = ds->priv;
--
--      if (!priv->info->mac_pcs_an_restart)
--              return;
--
--      priv->info->mac_pcs_an_restart(ds, port);
--}
--
- static void mt753x_phylink_mac_link_down(struct dsa_switch *ds, int port,
-                                        unsigned int mode,
-                                        phy_interface_t interface)
-@@ -3065,16 +3080,13 @@ static void mt753x_phylink_mac_link_down
-       mt7530_clear(priv, MT7530_PMCR_P(port), PMCR_LINK_SETTINGS_MASK);
- }
--static void mt753x_mac_pcs_link_up(struct dsa_switch *ds, int port,
--                                 unsigned int mode, phy_interface_t interface,
--                                 int speed, int duplex)
-+static void mt753x_phylink_pcs_link_up(struct phylink_pcs *pcs,
-+                                     unsigned int mode,
-+                                     phy_interface_t interface,
-+                                     int speed, int duplex)
- {
--      struct mt7530_priv *priv = ds->priv;
--
--      if (!priv->info->mac_pcs_link_up)
--              return;
--
--      priv->info->mac_pcs_link_up(ds, port, mode, interface, speed, duplex);
-+      if (pcs->ops->pcs_link_up)
-+              pcs->ops->pcs_link_up(pcs, mode, interface, speed, duplex);
- }
- static void mt753x_phylink_mac_link_up(struct dsa_switch *ds, int port,
-@@ -3087,8 +3099,6 @@ static void mt753x_phylink_mac_link_up(s
-       struct mt7530_priv *priv = ds->priv;
-       u32 mcr;
--      mt753x_mac_pcs_link_up(ds, port, mode, interface, speed, duplex);
--
-       mcr = PMCR_RX_EN | PMCR_TX_EN | PMCR_FORCE_LNK;
-       /* MT753x MAC works in 1G full duplex mode for all up-clocked
-@@ -3166,6 +3176,8 @@ mt7531_cpu_port_config(struct dsa_switch
-               return ret;
-       mt7530_write(priv, MT7530_PMCR_P(port),
-                    PMCR_CPU_PORT_SETTING(priv->id));
-+      mt753x_phylink_pcs_link_up(&priv->pcs[port].pcs, MLO_AN_FIXED,
-+                                 interface, speed, DUPLEX_FULL);
-       mt753x_phylink_mac_link_up(ds, port, MLO_AN_FIXED, interface, NULL,
-                                  speed, DUPLEX_FULL, true, true);
-@@ -3205,16 +3217,13 @@ mt753x_phylink_validate(struct dsa_switc
-       linkmode_and(state->advertising, state->advertising, mask);
- }
--static int
--mt7530_phylink_mac_link_state(struct dsa_switch *ds, int port,
--                            struct phylink_link_state *state)
-+static void mt7530_pcs_get_state(struct phylink_pcs *pcs,
-+                               struct phylink_link_state *state)
- {
--      struct mt7530_priv *priv = ds->priv;
-+      struct mt7530_priv *priv = pcs_to_mt753x_pcs(pcs)->priv;
-+      int port = pcs_to_mt753x_pcs(pcs)->port;
-       u32 pmsr;
--      if (port < 0 || port >= MT7530_NUM_PORTS)
--              return -EINVAL;
--
-       pmsr = mt7530_read(priv, MT7530_PMSR_P(port));
-       state->link = (pmsr & PMSR_LINK);
-@@ -3241,8 +3250,6 @@ mt7530_phylink_mac_link_state(struct dsa
-               state->pause |= MLO_PAUSE_RX;
-       if (pmsr & PMSR_TX_FC)
-               state->pause |= MLO_PAUSE_TX;
--
--      return 1;
- }
- static int
-@@ -3284,32 +3291,49 @@ mt7531_sgmii_pcs_get_state_an(struct mt7
-       return 0;
- }
--static int
--mt7531_phylink_mac_link_state(struct dsa_switch *ds, int port,
--                            struct phylink_link_state *state)
-+static void mt7531_pcs_get_state(struct phylink_pcs *pcs,
-+                               struct phylink_link_state *state)
- {
--      struct mt7530_priv *priv = ds->priv;
-+      struct mt7530_priv *priv = pcs_to_mt753x_pcs(pcs)->priv;
-+      int port = pcs_to_mt753x_pcs(pcs)->port;
-       if (state->interface == PHY_INTERFACE_MODE_SGMII)
--              return mt7531_sgmii_pcs_get_state_an(priv, port, state);
--
--      return -EOPNOTSUPP;
-+              mt7531_sgmii_pcs_get_state_an(priv, port, state);
-+      else
-+              state->link = false;
- }
--static int
--mt753x_phylink_mac_link_state(struct dsa_switch *ds, int port,
--                            struct phylink_link_state *state)
-+static int mt753x_pcs_config(struct phylink_pcs *pcs, unsigned int mode,
-+                           phy_interface_t interface,
-+                           const unsigned long *advertising,
-+                           bool permit_pause_to_mac)
- {
--      struct mt7530_priv *priv = ds->priv;
-+      return 0;
-+}
--      return priv->info->mac_port_get_state(ds, port, state);
-+static void mt7530_pcs_an_restart(struct phylink_pcs *pcs)
-+{
- }
-+static const struct phylink_pcs_ops mt7530_pcs_ops = {
-+      .pcs_get_state = mt7530_pcs_get_state,
-+      .pcs_config = mt753x_pcs_config,
-+      .pcs_an_restart = mt7530_pcs_an_restart,
-+};
-+
-+static const struct phylink_pcs_ops mt7531_pcs_ops = {
-+      .pcs_get_state = mt7531_pcs_get_state,
-+      .pcs_config = mt753x_pcs_config,
-+      .pcs_an_restart = mt7531_pcs_an_restart,
-+      .pcs_link_up = mt7531_pcs_link_up,
-+};
-+
- static int
- mt753x_setup(struct dsa_switch *ds)
- {
-       struct mt7530_priv *priv = ds->priv;
-       int ret = priv->info->sw_setup(ds);
-+      int i;
-       if (ret)
-               return ret;
-@@ -3322,6 +3346,13 @@ mt753x_setup(struct dsa_switch *ds)
-       if (ret && priv->irq)
-               mt7530_free_irq_common(priv);
-+      /* Initialise the PCS devices */
-+      for (i = 0; i < priv->ds->num_ports; i++) {
-+              priv->pcs[i].pcs.ops = priv->info->pcs_ops;
-+              priv->pcs[i].priv = priv;
-+              priv->pcs[i].port = i;
-+      }
-+
-       return ret;
- }
-@@ -3384,9 +3415,8 @@ static const struct dsa_switch_ops mt753
-       .port_mirror_del        = mt753x_port_mirror_del,
-       .phylink_get_caps       = mt753x_phylink_get_caps,
-       .phylink_validate       = mt753x_phylink_validate,
--      .phylink_mac_link_state = mt753x_phylink_mac_link_state,
-+      .phylink_mac_select_pcs = mt753x_phylink_mac_select_pcs,
-       .phylink_mac_config     = mt753x_phylink_mac_config,
--      .phylink_mac_an_restart = mt753x_phylink_mac_an_restart,
-       .phylink_mac_link_down  = mt753x_phylink_mac_link_down,
-       .phylink_mac_link_up    = mt753x_phylink_mac_link_up,
-       .get_mac_eee            = mt753x_get_mac_eee,
-@@ -3396,36 +3426,34 @@ static const struct dsa_switch_ops mt753
- static const struct mt753x_info mt753x_table[] = {
-       [ID_MT7621] = {
-               .id = ID_MT7621,
-+              .pcs_ops = &mt7530_pcs_ops,
-               .sw_setup = mt7530_setup,
-               .phy_read = mt7530_phy_read,
-               .phy_write = mt7530_phy_write,
-               .pad_setup = mt7530_pad_clk_setup,
-               .mac_port_get_caps = mt7530_mac_port_get_caps,
--              .mac_port_get_state = mt7530_phylink_mac_link_state,
-               .mac_port_config = mt7530_mac_config,
-       },
-       [ID_MT7530] = {
-               .id = ID_MT7530,
-+              .pcs_ops = &mt7530_pcs_ops,
-               .sw_setup = mt7530_setup,
-               .phy_read = mt7530_phy_read,
-               .phy_write = mt7530_phy_write,
-               .pad_setup = mt7530_pad_clk_setup,
-               .mac_port_get_caps = mt7530_mac_port_get_caps,
--              .mac_port_get_state = mt7530_phylink_mac_link_state,
-               .mac_port_config = mt7530_mac_config,
-       },
-       [ID_MT7531] = {
-               .id = ID_MT7531,
-+              .pcs_ops = &mt7531_pcs_ops,
-               .sw_setup = mt7531_setup,
-               .phy_read = mt7531_ind_phy_read,
-               .phy_write = mt7531_ind_phy_write,
-               .pad_setup = mt7531_pad_setup,
-               .cpu_port_config = mt7531_cpu_port_config,
-               .mac_port_get_caps = mt7531_mac_port_get_caps,
--              .mac_port_get_state = mt7531_phylink_mac_link_state,
-               .mac_port_config = mt7531_mac_config,
--              .mac_pcs_an_restart = mt7531_sgmii_restart_an,
--              .mac_pcs_link_up = mt7531_sgmii_link_up_force,
-       },
- };
-@@ -3483,7 +3511,7 @@ mt7530_probe(struct mdio_device *mdiodev
-       if (!priv->info->sw_setup || !priv->info->pad_setup ||
-           !priv->info->phy_read || !priv->info->phy_write ||
-           !priv->info->mac_port_get_caps ||
--          !priv->info->mac_port_get_state || !priv->info->mac_port_config)
-+          !priv->info->mac_port_config)
-               return -EINVAL;
-       priv->id = priv->info->id;
---- a/drivers/net/dsa/mt7530.h
-+++ b/drivers/net/dsa/mt7530.h
-@@ -779,6 +779,12 @@ static const char *p5_intf_modes(unsigne
- struct mt7530_priv;
-+struct mt753x_pcs {
-+      struct phylink_pcs pcs;
-+      struct mt7530_priv *priv;
-+      int port;
-+};
-+
- /* struct mt753x_info -       This is the main data structure for holding the specific
-  *                    part for each supported device
-  * @sw_setup:         Holding the handler to a device initialization
-@@ -790,18 +796,14 @@ struct mt7530_priv;
-  *                    port
-  * @mac_port_validate:        Holding the way to set addition validate type for a
-  *                    certan MAC port
-- * @mac_port_get_state: Holding the way getting the MAC/PCS state for a certain
-- *                    MAC port
-  * @mac_port_config:  Holding the way setting up the PHY attribute to a
-  *                    certain MAC port
-- * @mac_pcs_an_restart        Holding the way restarting PCS autonegotiation for a
-- *                    certain MAC port
-- * @mac_pcs_link_up:  Holding the way setting up the PHY attribute to the pcs
-- *                    of the certain MAC port
-  */
- struct mt753x_info {
-       enum mt753x_id id;
-+      const struct phylink_pcs_ops *pcs_ops;
-+
-       int (*sw_setup)(struct dsa_switch *ds);
-       int (*phy_read)(struct mt7530_priv *priv, int port, int regnum);
-       int (*phy_write)(struct mt7530_priv *priv, int port, int regnum, u16 val);
-@@ -812,15 +814,9 @@ struct mt753x_info {
-       void (*mac_port_validate)(struct dsa_switch *ds, int port,
-                                 phy_interface_t interface,
-                                 unsigned long *supported);
--      int (*mac_port_get_state)(struct dsa_switch *ds, int port,
--                                struct phylink_link_state *state);
-       int (*mac_port_config)(struct dsa_switch *ds, int port,
-                              unsigned int mode,
-                              phy_interface_t interface);
--      void (*mac_pcs_an_restart)(struct dsa_switch *ds, int port);
--      void (*mac_pcs_link_up)(struct dsa_switch *ds, int port,
--                              unsigned int mode, phy_interface_t interface,
--                              int speed, int duplex);
- };
- /* struct mt7530_priv -       This is the main data structure for holding the state
-@@ -862,6 +858,7 @@ struct mt7530_priv {
-       u8                      mirror_tx;
-       struct mt7530_port      ports[MT7530_NUM_PORTS];
-+      struct mt753x_pcs       pcs[MT7530_NUM_PORTS];
-       /* protect among processes for registers access*/
-       struct mutex reg_mutex;
-       int irq;
diff --git a/target/linux/generic/backport-5.15/705-08-v5.19-net-dsa-mt7530-move-autoneg-handling-to-PCS-validati.patch b/target/linux/generic/backport-5.15/705-08-v5.19-net-dsa-mt7530-move-autoneg-handling-to-PCS-validati.patch
deleted file mode 100644 (file)
index 6e406ac..0000000
+++ /dev/null
@@ -1,80 +0,0 @@
-From 2b0ee6768f3ac09072e5fd60b36580924e1cfa1c Mon Sep 17 00:00:00 2001
-From: "Russell King (Oracle)" <[email protected]>
-Date: Mon, 11 Apr 2022 10:46:32 +0100
-Subject: [PATCH 08/13] net: dsa: mt7530: move autoneg handling to PCS
- validation
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-Move the autoneg bit handling to the PCS validation, which allows us to
-get rid of mt753x_phylink_validate() and rely on the default
-phylink_generic_validate() implementation for the MAC side.
-
-Tested-by: Marek Behún <[email protected]>
-Signed-off-by: Russell King (Oracle) <[email protected]>
-Signed-off-by: Paolo Abeni <[email protected]>
----
- drivers/net/dsa/mt7530.c | 28 ++++++++++------------------
- 1 file changed, 10 insertions(+), 18 deletions(-)
-
---- a/drivers/net/dsa/mt7530.c
-+++ b/drivers/net/dsa/mt7530.c
-@@ -3196,25 +3196,16 @@ static void mt753x_phylink_get_caps(stru
-       priv->info->mac_port_get_caps(ds, port, config);
- }
--static void
--mt753x_phylink_validate(struct dsa_switch *ds, int port,
--                      unsigned long *supported,
--                      struct phylink_link_state *state)
--{
--      __ETHTOOL_DECLARE_LINK_MODE_MASK(mask) = { 0, };
--      u32 caps;
--
--      caps = dsa_to_port(ds, port)->pl_config.mac_capabilities;
--
--      phylink_set_port_modes(mask);
--      phylink_get_linkmodes(mask, state->interface, caps);
-+static int mt753x_pcs_validate(struct phylink_pcs *pcs,
-+                             unsigned long *supported,
-+                             const struct phylink_link_state *state)
-+{
-+      /* Autonegotiation is not supported in TRGMII nor 802.3z modes */
-+      if (state->interface == PHY_INTERFACE_MODE_TRGMII ||
-+          phy_interface_mode_is_8023z(state->interface))
-+              phylink_clear(supported, Autoneg);
--      if (state->interface != PHY_INTERFACE_MODE_TRGMII &&
--          !phy_interface_mode_is_8023z(state->interface))
--              phylink_set(mask, Autoneg);
--
--      linkmode_and(supported, supported, mask);
--      linkmode_and(state->advertising, state->advertising, mask);
-+      return 0;
- }
- static void mt7530_pcs_get_state(struct phylink_pcs *pcs,
-@@ -3316,12 +3307,14 @@ static void mt7530_pcs_an_restart(struct
- }
- static const struct phylink_pcs_ops mt7530_pcs_ops = {
-+      .pcs_validate = mt753x_pcs_validate,
-       .pcs_get_state = mt7530_pcs_get_state,
-       .pcs_config = mt753x_pcs_config,
-       .pcs_an_restart = mt7530_pcs_an_restart,
- };
- static const struct phylink_pcs_ops mt7531_pcs_ops = {
-+      .pcs_validate = mt753x_pcs_validate,
-       .pcs_get_state = mt7531_pcs_get_state,
-       .pcs_config = mt753x_pcs_config,
-       .pcs_an_restart = mt7531_pcs_an_restart,
-@@ -3414,7 +3407,6 @@ static const struct dsa_switch_ops mt753
-       .port_mirror_add        = mt753x_port_mirror_add,
-       .port_mirror_del        = mt753x_port_mirror_del,
-       .phylink_get_caps       = mt753x_phylink_get_caps,
--      .phylink_validate       = mt753x_phylink_validate,
-       .phylink_mac_select_pcs = mt753x_phylink_mac_select_pcs,
-       .phylink_mac_config     = mt753x_phylink_mac_config,
-       .phylink_mac_link_down  = mt753x_phylink_mac_link_down,
diff --git a/target/linux/generic/backport-5.15/705-09-v5.19-net-dsa-mt7530-mark-as-non-legacy.patch b/target/linux/generic/backport-5.15/705-09-v5.19-net-dsa-mt7530-mark-as-non-legacy.patch
deleted file mode 100644 (file)
index afcfcab..0000000
+++ /dev/null
@@ -1,34 +0,0 @@
-From 5bc26de9bfaa6bb5539c09d4435dced98f429cfc Mon Sep 17 00:00:00 2001
-From: "Russell King (Oracle)" <[email protected]>
-Date: Mon, 11 Apr 2022 10:46:37 +0100
-Subject: [PATCH 09/13] net: dsa: mt7530: mark as non-legacy
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-The mt7530 driver does not make use of the speed, duplex, pause or
-advertisement in its phylink_mac_config() implementation, so it can be
-marked as a non-legacy driver.
-
-Tested-by: Marek Behún <[email protected]>
-Signed-off-by: Russell King (Oracle) <[email protected]>
-Signed-off-by: Paolo Abeni <[email protected]>
----
- drivers/net/dsa/mt7530.c | 6 ++++++
- 1 file changed, 6 insertions(+)
-
---- a/drivers/net/dsa/mt7530.c
-+++ b/drivers/net/dsa/mt7530.c
-@@ -3193,6 +3193,12 @@ static void mt753x_phylink_get_caps(stru
-       config->mac_capabilities = MAC_ASYM_PAUSE | MAC_SYM_PAUSE |
-                                  MAC_10 | MAC_100 | MAC_1000FD;
-+      /* This driver does not make use of the speed, duplex, pause or the
-+       * advertisement in its mac_config, so it is safe to mark this driver
-+       * as non-legacy.
-+       */
-+      config->legacy_pre_march2020 = false;
-+
-       priv->info->mac_port_get_caps(ds, port, config);
- }
diff --git a/target/linux/generic/backport-5.15/705-10-v5.19-net-dsa-mt753x-fix-pcs-conversion-regression.patch b/target/linux/generic/backport-5.15/705-10-v5.19-net-dsa-mt753x-fix-pcs-conversion-regression.patch
deleted file mode 100644 (file)
index bf2938d..0000000
+++ /dev/null
@@ -1,116 +0,0 @@
-From 1f15b5e8733115cee65342bcaafeaf0368809fae Mon Sep 17 00:00:00 2001
-From: "Russell King (Oracle)" <[email protected]>
-Date: Mon, 25 Apr 2022 22:28:02 +0100
-Subject: [PATCH 10/13] net: dsa: mt753x: fix pcs conversion regression
-
-Daniel Golle reports that the conversion of mt753x to phylink PCS caused
-an oops as below.
-
-The problem is with the placement of the PCS initialisation, which
-occurs after mt7531_setup() has been called. However, burited in this
-function is a call to setup the CPU port, which requires the PCS
-structure to be already setup.
-
-Fix this by changing the initialisation order.
-
-Unable to handle kernel NULL pointer dereference at virtual address 0000000000000020
-Mem abort info:
-  ESR = 0x96000005
-  EC = 0x25: DABT (current EL), IL = 32 bits
-  SET = 0, FnV = 0
-  EA = 0, S1PTW = 0
-  FSC = 0x05: level 1 translation fault
-Data abort info:
-  ISV = 0, ISS = 0x00000005
-  CM = 0, WnR = 0
-user pgtable: 4k pages, 39-bit VAs, pgdp=0000000046057000
-[0000000000000020] pgd=0000000000000000, p4d=0000000000000000, pud=0000000000000000
-Internal error: Oops: 96000005 [#1] SMP
-Modules linked in:
-CPU: 0 PID: 32 Comm: kworker/u4:1 Tainted: G S 5.18.0-rc3-next-20220422+ #0
-Hardware name: Bananapi BPI-R64 (DT)
-Workqueue: events_unbound deferred_probe_work_func
-pstate: 60000005 (nZCv daif -PAN -UAO -TCO -DIT -SSBS BTYPE=--)
-pc : mt7531_cpu_port_config+0xcc/0x1b0
-lr : mt7531_cpu_port_config+0xc0/0x1b0
-sp : ffffffc008d5b980
-x29: ffffffc008d5b990 x28: ffffff80060562c8 x27: 00000000f805633b
-x26: ffffff80001a8880 x25: 00000000000009c4 x24: 0000000000000016
-x23: ffffff8005eb6470 x22: 0000000000003600 x21: ffffff8006948080
-x20: 0000000000000000 x19: 0000000000000006 x18: 0000000000000000
-x17: 0000000000000001 x16: 0000000000000001 x15: 02963607fcee069e
-x14: 0000000000000000 x13: 0000000000000030 x12: 0101010101010101
-x11: ffffffc037302000 x10: 0000000000000870 x9 : ffffffc008d5b800
-x8 : ffffff800028f950 x7 : 0000000000000001 x6 : 00000000662b3000
-x5 : 00000000000002f0 x4 : 0000000000000000 x3 : ffffff800028f080
-x2 : 0000000000000000 x1 : ffffff800028f080 x0 : 0000000000000000
-Call trace:
- mt7531_cpu_port_config+0xcc/0x1b0
- mt753x_cpu_port_enable+0x24/0x1f0
- mt7531_setup+0x49c/0x5c0
- mt753x_setup+0x20/0x31c
- dsa_register_switch+0x8bc/0x1020
- mt7530_probe+0x118/0x200
- mdio_probe+0x30/0x64
- really_probe.part.0+0x98/0x280
- __driver_probe_device+0x94/0x140
- driver_probe_device+0x40/0x114
- __device_attach_driver+0xb0/0x10c
- bus_for_each_drv+0x64/0xa0
- __device_attach+0xa8/0x16c
- device_initial_probe+0x10/0x20
- bus_probe_device+0x94/0x9c
- deferred_probe_work_func+0x80/0xb4
- process_one_work+0x200/0x3a0
- worker_thread+0x260/0x4c0
- kthread+0xd4/0xe0
- ret_from_fork+0x10/0x20
-Code: 9409e911 937b7e60 8b0002a0 f9405800 (f9401005)
----[ end trace 0000000000000000 ]---
-
-Reported-by: Daniel Golle <[email protected]>
-Tested-by: Daniel Golle <[email protected]>
-Fixes: cbd1f243bc41 ("net: dsa: mt7530: partially convert to phylink_pcs")
-Signed-off-by: Russell King (Oracle) <[email protected]>
-Reviewed-by: Florian Fainelli <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- drivers/net/dsa/mt7530.c | 18 +++++++++---------
- 1 file changed, 9 insertions(+), 9 deletions(-)
-
---- a/drivers/net/dsa/mt7530.c
-+++ b/drivers/net/dsa/mt7530.c
-@@ -3331,9 +3331,16 @@ static int
- mt753x_setup(struct dsa_switch *ds)
- {
-       struct mt7530_priv *priv = ds->priv;
--      int ret = priv->info->sw_setup(ds);
--      int i;
-+      int i, ret;
-+      /* Initialise the PCS devices */
-+      for (i = 0; i < priv->ds->num_ports; i++) {
-+              priv->pcs[i].pcs.ops = priv->info->pcs_ops;
-+              priv->pcs[i].priv = priv;
-+              priv->pcs[i].port = i;
-+      }
-+
-+      ret = priv->info->sw_setup(ds);
-       if (ret)
-               return ret;
-@@ -3345,13 +3352,6 @@ mt753x_setup(struct dsa_switch *ds)
-       if (ret && priv->irq)
-               mt7530_free_irq_common(priv);
--      /* Initialise the PCS devices */
--      for (i = 0; i < priv->ds->num_ports; i++) {
--              priv->pcs[i].pcs.ops = priv->info->pcs_ops;
--              priv->pcs[i].priv = priv;
--              priv->pcs[i].port = i;
--      }
--
-       return ret;
- }
diff --git a/target/linux/generic/backport-5.15/705-11-v6.0-net-dsa-mt7530-rework-mt7530_hw_vlan_-add-del.patch b/target/linux/generic/backport-5.15/705-11-v6.0-net-dsa-mt7530-rework-mt7530_hw_vlan_-add-del.patch
deleted file mode 100644 (file)
index 320b5c1..0000000
+++ /dev/null
@@ -1,87 +0,0 @@
-From e26be16262e1fc1e9f1798c12762663bd9c265c6 Mon Sep 17 00:00:00 2001
-From: Frank Wunderlich <[email protected]>
-Date: Fri, 10 Jun 2022 19:05:37 +0200
-Subject: [PATCH 11/13] net: dsa: mt7530: rework mt7530_hw_vlan_{add,del}
-
-Rework vlan_add/vlan_del functions in preparation for dynamic cpu port.
-
-Currently BIT(MT7530_CPU_PORT) is added to new_members, even though
-mt7530_port_vlan_add() will be called on the CPU port too.
-
-Let DSA core decide when to call port_vlan_add for the CPU port, rather
-than doing it implicitly.
-
-We can do autonomous forwarding in a certain VLAN, but not add br0 to that
-VLAN and avoid flooding the CPU with those packets, if software knows it
-doesn't need to process them.
-
-Suggested-by: Vladimir Oltean <[email protected]>
-Signed-off-by: Frank Wunderlich <[email protected]>
-Reviewed-by: Vladimir Oltean <[email protected]>
-Reviewed-by: Florian Fainelli <[email protected]>
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- drivers/net/dsa/mt7530.c | 30 ++++++++++++------------------
- 1 file changed, 12 insertions(+), 18 deletions(-)
-
---- a/drivers/net/dsa/mt7530.c
-+++ b/drivers/net/dsa/mt7530.c
-@@ -1771,11 +1771,11 @@ static void
- mt7530_hw_vlan_add(struct mt7530_priv *priv,
-                  struct mt7530_hw_vlan_entry *entry)
- {
-+      struct dsa_port *dp = dsa_to_port(priv->ds, entry->port);
-       u8 new_members;
-       u32 val;
--      new_members = entry->old_members | BIT(entry->port) |
--                    BIT(MT7530_CPU_PORT);
-+      new_members = entry->old_members | BIT(entry->port);
-       /* Validate the entry with independent learning, create egress tag per
-        * VLAN and joining the port as one of the port members.
-@@ -1786,22 +1786,20 @@ mt7530_hw_vlan_add(struct mt7530_priv *p
-       /* Decide whether adding tag or not for those outgoing packets from the
-        * port inside the VLAN.
--       */
--      val = entry->untagged ? MT7530_VLAN_EGRESS_UNTAG :
--                              MT7530_VLAN_EGRESS_TAG;
--      mt7530_rmw(priv, MT7530_VAWD2,
--                 ETAG_CTRL_P_MASK(entry->port),
--                 ETAG_CTRL_P(entry->port, val));
--
--      /* CPU port is always taken as a tagged port for serving more than one
-+       * CPU port is always taken as a tagged port for serving more than one
-        * VLANs across and also being applied with egress type stack mode for
-        * that VLAN tags would be appended after hardware special tag used as
-        * DSA tag.
-        */
-+      if (dsa_port_is_cpu(dp))
-+              val = MT7530_VLAN_EGRESS_STACK;
-+      else if (entry->untagged)
-+              val = MT7530_VLAN_EGRESS_UNTAG;
-+      else
-+              val = MT7530_VLAN_EGRESS_TAG;
-       mt7530_rmw(priv, MT7530_VAWD2,
--                 ETAG_CTRL_P_MASK(MT7530_CPU_PORT),
--                 ETAG_CTRL_P(MT7530_CPU_PORT,
--                             MT7530_VLAN_EGRESS_STACK));
-+                 ETAG_CTRL_P_MASK(entry->port),
-+                 ETAG_CTRL_P(entry->port, val));
- }
- static void
-@@ -1820,11 +1818,7 @@ mt7530_hw_vlan_del(struct mt7530_priv *p
-               return;
-       }
--      /* If certain member apart from CPU port is still alive in the VLAN,
--       * the entry would be kept valid. Otherwise, the entry is got to be
--       * disabled.
--       */
--      if (new_members && new_members != BIT(MT7530_CPU_PORT)) {
-+      if (new_members) {
-               val = IVL_MAC | VTAG_EN | PORT_MEM(new_members) |
-                     VLAN_VALID;
-               mt7530_write(priv, MT7530_VAWD1, val);
diff --git a/target/linux/generic/backport-5.15/705-13-v6.0-net-dsa-mt7530-get-cpu-port-via-dp-cpu_dp-instead-of.patch b/target/linux/generic/backport-5.15/705-13-v6.0-net-dsa-mt7530-get-cpu-port-via-dp-cpu_dp-instead-of.patch
deleted file mode 100644 (file)
index eef19b4..0000000
+++ /dev/null
@@ -1,117 +0,0 @@
-From ad2606f6fafae3a7d41c4f2af5554c8f6adecbc7 Mon Sep 17 00:00:00 2001
-From: Frank Wunderlich <[email protected]>
-Date: Fri, 10 Jun 2022 19:05:39 +0200
-Subject: [PATCH 13/13] net: dsa: mt7530: get cpu-port via dp->cpu_dp instead
- of constant
-
-Replace last occurences of hardcoded cpu-port by cpu_dp member of
-dsa_port struct.
-
-Now the constant can be dropped.
-
-Suggested-by: Vladimir Oltean <[email protected]>
-Signed-off-by: Frank Wunderlich <[email protected]>
-Reviewed-by: Vladimir Oltean <[email protected]>
-Reviewed-by: Florian Fainelli <[email protected]>
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- drivers/net/dsa/mt7530.c | 27 ++++++++++++++++++++-------
- drivers/net/dsa/mt7530.h |  1 -
- 2 files changed, 20 insertions(+), 8 deletions(-)
-
---- a/drivers/net/dsa/mt7530.c
-+++ b/drivers/net/dsa/mt7530.c
-@@ -1275,6 +1275,7 @@ static int
- mt7530_port_enable(struct dsa_switch *ds, int port,
-                  struct phy_device *phy)
- {
-+      struct dsa_port *dp = dsa_to_port(ds, port);
-       struct mt7530_priv *priv = ds->priv;
-       mutex_lock(&priv->reg_mutex);
-@@ -1283,7 +1284,11 @@ mt7530_port_enable(struct dsa_switch *ds
-        * restore the port matrix if the port is the member of a certain
-        * bridge.
-        */
--      priv->ports[port].pm |= PCR_MATRIX(BIT(MT7530_CPU_PORT));
-+      if (dsa_port_is_user(dp)) {
-+              struct dsa_port *cpu_dp = dp->cpu_dp;
-+
-+              priv->ports[port].pm |= PCR_MATRIX(BIT(cpu_dp->index));
-+      }
-       priv->ports[port].enable = true;
-       mt7530_rmw(priv, MT7530_PCR_P(port), PCR_MATRIX_MASK,
-                  priv->ports[port].pm);
-@@ -1431,7 +1436,8 @@ mt7530_port_bridge_join(struct dsa_switc
-                       struct net_device *bridge)
- {
-       struct dsa_port *dp = dsa_to_port(ds, port), *other_dp;
--      u32 port_bitmap = BIT(MT7530_CPU_PORT);
-+      struct dsa_port *cpu_dp = dp->cpu_dp;
-+      u32 port_bitmap = BIT(cpu_dp->index);
-       struct mt7530_priv *priv = ds->priv;
-       mutex_lock(&priv->reg_mutex);
-@@ -1508,9 +1514,12 @@ mt7530_port_set_vlan_unaware(struct dsa_
-        * the CPU port get out of VLAN filtering mode.
-        */
-       if (all_user_ports_removed) {
--              mt7530_write(priv, MT7530_PCR_P(MT7530_CPU_PORT),
-+              struct dsa_port *dp = dsa_to_port(ds, port);
-+              struct dsa_port *cpu_dp = dp->cpu_dp;
-+
-+              mt7530_write(priv, MT7530_PCR_P(cpu_dp->index),
-                            PCR_MATRIX(dsa_user_ports(priv->ds)));
--              mt7530_write(priv, MT7530_PVC_P(MT7530_CPU_PORT), PORT_SPEC_TAG
-+              mt7530_write(priv, MT7530_PVC_P(cpu_dp->index), PORT_SPEC_TAG
-                            | PVC_EG_TAG(MT7530_VLAN_EG_CONSISTENT));
-       }
- }
-@@ -1560,6 +1569,7 @@ mt7530_port_bridge_leave(struct dsa_swit
-                        struct net_device *bridge)
- {
-       struct dsa_port *dp = dsa_to_port(ds, port), *other_dp;
-+      struct dsa_port *cpu_dp = dp->cpu_dp;
-       struct mt7530_priv *priv = ds->priv;
-       mutex_lock(&priv->reg_mutex);
-@@ -1588,8 +1598,8 @@ mt7530_port_bridge_leave(struct dsa_swit
-        */
-       if (priv->ports[port].enable)
-               mt7530_rmw(priv, MT7530_PCR_P(port), PCR_MATRIX_MASK,
--                         PCR_MATRIX(BIT(MT7530_CPU_PORT)));
--      priv->ports[port].pm = PCR_MATRIX(BIT(MT7530_CPU_PORT));
-+                         PCR_MATRIX(BIT(cpu_dp->index)));
-+      priv->ports[port].pm = PCR_MATRIX(BIT(cpu_dp->index));
-       /* When a port is removed from the bridge, the port would be set up
-        * back to the default as is at initial boot which is a VLAN-unaware
-@@ -1752,6 +1762,9 @@ static int
- mt7530_port_vlan_filtering(struct dsa_switch *ds, int port, bool vlan_filtering,
-                          struct netlink_ext_ack *extack)
- {
-+      struct dsa_port *dp = dsa_to_port(ds, port);
-+      struct dsa_port *cpu_dp = dp->cpu_dp;
-+
-       if (vlan_filtering) {
-               /* The port is being kept as VLAN-unaware port when bridge is
-                * set up with vlan_filtering not being set, Otherwise, the
-@@ -1759,7 +1772,7 @@ mt7530_port_vlan_filtering(struct dsa_sw
-                * for becoming a VLAN-aware port.
-                */
-               mt7530_port_set_vlan_aware(ds, port);
--              mt7530_port_set_vlan_aware(ds, MT7530_CPU_PORT);
-+              mt7530_port_set_vlan_aware(ds, cpu_dp->index);
-       } else {
-               mt7530_port_set_vlan_unaware(ds, port);
-       }
---- a/drivers/net/dsa/mt7530.h
-+++ b/drivers/net/dsa/mt7530.h
-@@ -8,7 +8,6 @@
- #define MT7530_NUM_PORTS              7
- #define MT7530_NUM_PHYS                       5
--#define MT7530_CPU_PORT                       6
- #define MT7530_NUM_FDB_RECORDS                2048
- #define MT7530_ALL_MEMBERS            0xff
diff --git a/target/linux/generic/backport-5.15/706-00-v6.0-net-ethernet-mtk_eth_soc-rely-on-page_pool-for-singl.patch b/target/linux/generic/backport-5.15/706-00-v6.0-net-ethernet-mtk_eth_soc-rely-on-page_pool-for-singl.patch
deleted file mode 100644 (file)
index f022f7b..0000000
+++ /dev/null
@@ -1,330 +0,0 @@
-From 23233e577ef973c2c5d0dd757a0a4605e34ecb57 Mon Sep 17 00:00:00 2001
-From: Lorenzo Bianconi <[email protected]>
-Date: Fri, 22 Jul 2022 09:19:36 +0200
-Subject: [PATCH] net: ethernet: mtk_eth_soc: rely on page_pool for single page
- buffers
-
-Rely on page_pool allocator for single page buffers in order to keep
-them dma mapped and add skb recycling support.
-
-Signed-off-by: Lorenzo Bianconi <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/ethernet/mediatek/Kconfig       |   1 +
- drivers/net/ethernet/mediatek/mtk_eth_soc.c | 185 +++++++++++++++-----
- drivers/net/ethernet/mediatek/mtk_eth_soc.h |  10 ++
- 3 files changed, 156 insertions(+), 40 deletions(-)
-
---- a/drivers/net/ethernet/mediatek/Kconfig
-+++ b/drivers/net/ethernet/mediatek/Kconfig
-@@ -16,6 +16,7 @@ config NET_MEDIATEK_SOC
-       depends on NET_DSA || !NET_DSA
-       select PHYLINK
-       select DIMLIB
-+      select PAGE_POOL
-       help
-         This driver supports the gigabit ethernet MACs in the
-         MediaTek SoC family.
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-@@ -1388,6 +1388,68 @@ static void mtk_update_rx_cpu_idx(struct
-       }
- }
-+static struct page_pool *mtk_create_page_pool(struct mtk_eth *eth,
-+                                            struct xdp_rxq_info *xdp_q,
-+                                            int id, int size)
-+{
-+      struct page_pool_params pp_params = {
-+              .order = 0,
-+              .flags = PP_FLAG_DMA_MAP | PP_FLAG_DMA_SYNC_DEV,
-+              .pool_size = size,
-+              .nid = NUMA_NO_NODE,
-+              .dev = eth->dma_dev,
-+              .dma_dir = DMA_FROM_DEVICE,
-+              .offset = MTK_PP_HEADROOM,
-+              .max_len = MTK_PP_MAX_BUF_SIZE,
-+      };
-+      struct page_pool *pp;
-+      int err;
-+
-+      pp = page_pool_create(&pp_params);
-+      if (IS_ERR(pp))
-+              return pp;
-+
-+      err = xdp_rxq_info_reg(xdp_q, &eth->dummy_dev, id,
-+                              eth->rx_napi.napi_id);
-+      if (err < 0)
-+              goto err_free_pp;
-+
-+      err = xdp_rxq_info_reg_mem_model(xdp_q, MEM_TYPE_PAGE_POOL, pp);
-+      if (err)
-+              goto err_unregister_rxq;
-+
-+      return pp;
-+
-+err_unregister_rxq:
-+      xdp_rxq_info_unreg(xdp_q);
-+err_free_pp:
-+      page_pool_destroy(pp);
-+
-+      return ERR_PTR(err);
-+}
-+
-+static void *mtk_page_pool_get_buff(struct page_pool *pp, dma_addr_t *dma_addr,
-+                                  gfp_t gfp_mask)
-+{
-+      struct page *page;
-+
-+      page = page_pool_alloc_pages(pp, gfp_mask | __GFP_NOWARN);
-+      if (!page)
-+              return NULL;
-+
-+      *dma_addr = page_pool_get_dma_addr(page) + MTK_PP_HEADROOM;
-+      return page_address(page);
-+}
-+
-+static void mtk_rx_put_buff(struct mtk_rx_ring *ring, void *data, bool napi)
-+{
-+      if (ring->page_pool)
-+              page_pool_put_full_page(ring->page_pool,
-+                                      virt_to_head_page(data), napi);
-+      else
-+              skb_free_frag(data);
-+}
-+
- static int mtk_poll_rx(struct napi_struct *napi, int budget,
-                      struct mtk_eth *eth)
- {
-@@ -1401,9 +1463,9 @@ static int mtk_poll_rx(struct napi_struc
-       while (done < budget) {
-               unsigned int pktlen, *rxdcsum;
-+              u32 hash, reason, reserve_len;
-               struct net_device *netdev;
-               dma_addr_t dma_addr;
--              u32 hash, reason;
-               int mac = 0;
-               ring = mtk_get_rx_ring(eth);
-@@ -1434,36 +1496,54 @@ static int mtk_poll_rx(struct napi_struc
-                       goto release_desc;
-               /* alloc new buffer */
--              if (ring->frag_size <= PAGE_SIZE)
--                      new_data = napi_alloc_frag(ring->frag_size);
--              else
--                      new_data = mtk_max_lro_buf_alloc(GFP_ATOMIC);
--              if (unlikely(!new_data)) {
--                      netdev->stats.rx_dropped++;
--                      goto release_desc;
--              }
--              dma_addr = dma_map_single(eth->dma_dev,
--                                        new_data + NET_SKB_PAD +
--                                        eth->ip_align,
--                                        ring->buf_size,
--                                        DMA_FROM_DEVICE);
--              if (unlikely(dma_mapping_error(eth->dma_dev, dma_addr))) {
--                      skb_free_frag(new_data);
--                      netdev->stats.rx_dropped++;
--                      goto release_desc;
--              }
-+              if (ring->page_pool) {
-+                      new_data = mtk_page_pool_get_buff(ring->page_pool,
-+                                                        &dma_addr,
-+                                                        GFP_ATOMIC);
-+                      if (unlikely(!new_data)) {
-+                              netdev->stats.rx_dropped++;
-+                              goto release_desc;
-+                      }
-+              } else {
-+                      if (ring->frag_size <= PAGE_SIZE)
-+                              new_data = napi_alloc_frag(ring->frag_size);
-+                      else
-+                              new_data = mtk_max_lro_buf_alloc(GFP_ATOMIC);
-+
-+                      if (unlikely(!new_data)) {
-+                              netdev->stats.rx_dropped++;
-+                              goto release_desc;
-+                      }
--              dma_unmap_single(eth->dma_dev, trxd.rxd1,
--                               ring->buf_size, DMA_FROM_DEVICE);
-+                      dma_addr = dma_map_single(eth->dma_dev,
-+                              new_data + NET_SKB_PAD + eth->ip_align,
-+                              ring->buf_size, DMA_FROM_DEVICE);
-+                      if (unlikely(dma_mapping_error(eth->dma_dev,
-+                                                     dma_addr))) {
-+                              skb_free_frag(new_data);
-+                              netdev->stats.rx_dropped++;
-+                              goto release_desc;
-+                      }
-+
-+                      dma_unmap_single(eth->dma_dev, trxd.rxd1,
-+                                       ring->buf_size, DMA_FROM_DEVICE);
-+              }
-               /* receive data */
-               skb = build_skb(data, ring->frag_size);
-               if (unlikely(!skb)) {
--                      skb_free_frag(data);
-+                      mtk_rx_put_buff(ring, data, true);
-                       netdev->stats.rx_dropped++;
-                       goto skip_rx;
-               }
--              skb_reserve(skb, NET_SKB_PAD + NET_IP_ALIGN);
-+
-+              if (ring->page_pool) {
-+                      reserve_len = MTK_PP_HEADROOM;
-+                      skb_mark_for_recycle(skb);
-+              } else {
-+                      reserve_len = NET_SKB_PAD + NET_IP_ALIGN;
-+              }
-+              skb_reserve(skb, reserve_len);
-               pktlen = RX_DMA_GET_PLEN0(trxd.rxd2);
-               skb->dev = netdev;
-@@ -1517,7 +1597,6 @@ static int mtk_poll_rx(struct napi_struc
- skip_rx:
-               ring->data[idx] = new_data;
-               rxd->rxd1 = (unsigned int)dma_addr;
--
- release_desc:
-               if (MTK_HAS_CAPS(eth->soc->caps, MTK_SOC_MT7628))
-                       rxd->rxd2 = RX_DMA_LSO;
-@@ -1525,7 +1604,6 @@ release_desc:
-                       rxd->rxd2 = RX_DMA_PREP_PLEN0(ring->buf_size);
-               ring->calc_idx = idx;
--
-               done++;
-       }
-@@ -1889,13 +1967,15 @@ static int mtk_rx_alloc(struct mtk_eth *
-       if (!ring->data)
-               return -ENOMEM;
--      for (i = 0; i < rx_dma_size; i++) {
--              if (ring->frag_size <= PAGE_SIZE)
--                      ring->data[i] = netdev_alloc_frag(ring->frag_size);
--              else
--                      ring->data[i] = mtk_max_lro_buf_alloc(GFP_KERNEL);
--              if (!ring->data[i])
--                      return -ENOMEM;
-+      if (!eth->hwlro) {
-+              struct page_pool *pp;
-+
-+              pp = mtk_create_page_pool(eth, &ring->xdp_q, ring_no,
-+                                        rx_dma_size);
-+              if (IS_ERR(pp))
-+                      return PTR_ERR(pp);
-+
-+              ring->page_pool = pp;
-       }
-       ring->dma = dma_alloc_coherent(eth->dma_dev,
-@@ -1906,16 +1986,33 @@ static int mtk_rx_alloc(struct mtk_eth *
-       for (i = 0; i < rx_dma_size; i++) {
-               struct mtk_rx_dma_v2 *rxd;
--
--              dma_addr_t dma_addr = dma_map_single(eth->dma_dev,
--                              ring->data[i] + NET_SKB_PAD + eth->ip_align,
--                              ring->buf_size,
--                              DMA_FROM_DEVICE);
--              if (unlikely(dma_mapping_error(eth->dma_dev, dma_addr)))
--                      return -ENOMEM;
-+              dma_addr_t dma_addr;
-+              void *data;
-               rxd = ring->dma + i * eth->soc->txrx.rxd_size;
-+              if (ring->page_pool) {
-+                      data = mtk_page_pool_get_buff(ring->page_pool,
-+                                                    &dma_addr, GFP_KERNEL);
-+                      if (!data)
-+                              return -ENOMEM;
-+              } else {
-+                      if (ring->frag_size <= PAGE_SIZE)
-+                              data = netdev_alloc_frag(ring->frag_size);
-+                      else
-+                              data = mtk_max_lro_buf_alloc(GFP_KERNEL);
-+
-+                      if (!data)
-+                              return -ENOMEM;
-+
-+                      dma_addr = dma_map_single(eth->dma_dev,
-+                              data + NET_SKB_PAD + eth->ip_align,
-+                              ring->buf_size, DMA_FROM_DEVICE);
-+                      if (unlikely(dma_mapping_error(eth->dma_dev,
-+                                                     dma_addr)))
-+                              return -ENOMEM;
-+              }
-               rxd->rxd1 = (unsigned int)dma_addr;
-+              ring->data[i] = data;
-               if (MTK_HAS_CAPS(eth->soc->caps, MTK_SOC_MT7628))
-                       rxd->rxd2 = RX_DMA_LSO;
-@@ -1931,6 +2028,7 @@ static int mtk_rx_alloc(struct mtk_eth *
-                       rxd->rxd8 = 0;
-               }
-       }
-+
-       ring->dma_size = rx_dma_size;
-       ring->calc_idx_update = false;
-       ring->calc_idx = rx_dma_size - 1;
-@@ -1982,7 +2080,7 @@ static void mtk_rx_clean(struct mtk_eth
-                       dma_unmap_single(eth->dma_dev, rxd->rxd1,
-                                        ring->buf_size, DMA_FROM_DEVICE);
--                      skb_free_frag(ring->data[i]);
-+                      mtk_rx_put_buff(ring, ring->data[i], false);
-               }
-               kfree(ring->data);
-               ring->data = NULL;
-@@ -1994,6 +2092,13 @@ static void mtk_rx_clean(struct mtk_eth
-                                 ring->dma, ring->phys);
-               ring->dma = NULL;
-       }
-+
-+      if (ring->page_pool) {
-+              if (xdp_rxq_info_is_reg(&ring->xdp_q))
-+                      xdp_rxq_info_unreg(&ring->xdp_q);
-+              page_pool_destroy(ring->page_pool);
-+              ring->page_pool = NULL;
-+      }
- }
- static int mtk_hwlro_rx_init(struct mtk_eth *eth)
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-@@ -18,6 +18,8 @@
- #include <linux/rhashtable.h>
- #include <linux/dim.h>
- #include <linux/bitfield.h>
-+#include <net/page_pool.h>
-+#include <linux/bpf_trace.h>
- #include "mtk_ppe.h"
- #define MTK_QDMA_PAGE_SIZE    2048
-@@ -49,6 +51,11 @@
- #define MTK_HW_FEATURES_MT7628        (NETIF_F_SG | NETIF_F_RXCSUM)
- #define NEXT_DESP_IDX(X, Y)   (((X) + 1) & ((Y) - 1))
-+#define MTK_PP_HEADROOM               XDP_PACKET_HEADROOM
-+#define MTK_PP_PAD            (MTK_PP_HEADROOM + \
-+                               SKB_DATA_ALIGN(sizeof(struct skb_shared_info)))
-+#define MTK_PP_MAX_BUF_SIZE   (PAGE_SIZE - MTK_PP_PAD)
-+
- #define MTK_QRX_OFFSET                0x10
- #define MTK_MAX_RX_RING_NUM   4
-@@ -743,6 +750,9 @@ struct mtk_rx_ring {
-       bool calc_idx_update;
-       u16 calc_idx;
-       u32 crx_idx_reg;
-+      /* page_pool */
-+      struct page_pool *page_pool;
-+      struct xdp_rxq_info xdp_q;
- };
- enum mkt_eth_capabilities {
diff --git a/target/linux/generic/backport-5.15/706-01-v6.0-net-ethernet-mtk_eth_soc-add-basic-XDP-support.patch b/target/linux/generic/backport-5.15/706-01-v6.0-net-ethernet-mtk_eth_soc-add-basic-XDP-support.patch
deleted file mode 100644 (file)
index 94efa92..0000000
+++ /dev/null
@@ -1,291 +0,0 @@
-From 7c26c20da5d420cde55618263be4aa2f6de53056 Mon Sep 17 00:00:00 2001
-From: Lorenzo Bianconi <[email protected]>
-Date: Fri, 22 Jul 2022 09:19:37 +0200
-Subject: [PATCH] net: ethernet: mtk_eth_soc: add basic XDP support
-
-Introduce basic XDP support to mtk_eth_soc driver.
-Supported XDP verdicts:
-- XDP_PASS
-- XDP_DROP
-- XDP_REDIRECT
-
-Signed-off-by: Lorenzo Bianconi <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/ethernet/mediatek/mtk_eth_soc.c | 162 +++++++++++++++++---
- drivers/net/ethernet/mediatek/mtk_eth_soc.h |   2 +
- 2 files changed, 145 insertions(+), 19 deletions(-)
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-@@ -1388,6 +1388,11 @@ static void mtk_update_rx_cpu_idx(struct
-       }
- }
-+static bool mtk_page_pool_enabled(struct mtk_eth *eth)
-+{
-+      return !eth->hwlro;
-+}
-+
- static struct page_pool *mtk_create_page_pool(struct mtk_eth *eth,
-                                             struct xdp_rxq_info *xdp_q,
-                                             int id, int size)
-@@ -1450,11 +1455,52 @@ static void mtk_rx_put_buff(struct mtk_r
-               skb_free_frag(data);
- }
-+static u32 mtk_xdp_run(struct mtk_eth *eth, struct mtk_rx_ring *ring,
-+                     struct xdp_buff *xdp, struct net_device *dev)
-+{
-+      struct bpf_prog *prog;
-+      u32 act = XDP_PASS;
-+
-+      rcu_read_lock();
-+
-+      prog = rcu_dereference(eth->prog);
-+      if (!prog)
-+              goto out;
-+
-+      act = bpf_prog_run_xdp(prog, xdp);
-+      switch (act) {
-+      case XDP_PASS:
-+              goto out;
-+      case XDP_REDIRECT:
-+              if (unlikely(xdp_do_redirect(dev, xdp, prog))) {
-+                      act = XDP_DROP;
-+                      break;
-+              }
-+              goto out;
-+      default:
-+              bpf_warn_invalid_xdp_action(act);
-+              fallthrough;
-+      case XDP_ABORTED:
-+              trace_xdp_exception(dev, prog, act);
-+              fallthrough;
-+      case XDP_DROP:
-+              break;
-+      }
-+
-+      page_pool_put_full_page(ring->page_pool,
-+                              virt_to_head_page(xdp->data), true);
-+out:
-+      rcu_read_unlock();
-+
-+      return act;
-+}
-+
- static int mtk_poll_rx(struct napi_struct *napi, int budget,
-                      struct mtk_eth *eth)
- {
-       struct dim_sample dim_sample = {};
-       struct mtk_rx_ring *ring;
-+      bool xdp_flush = false;
-       int idx;
-       struct sk_buff *skb;
-       u8 *data, *new_data;
-@@ -1463,9 +1509,9 @@ static int mtk_poll_rx(struct napi_struc
-       while (done < budget) {
-               unsigned int pktlen, *rxdcsum;
--              u32 hash, reason, reserve_len;
-               struct net_device *netdev;
-               dma_addr_t dma_addr;
-+              u32 hash, reason;
-               int mac = 0;
-               ring = mtk_get_rx_ring(eth);
-@@ -1495,8 +1541,14 @@ static int mtk_poll_rx(struct napi_struc
-               if (unlikely(test_bit(MTK_RESETTING, &eth->state)))
-                       goto release_desc;
-+              pktlen = RX_DMA_GET_PLEN0(trxd.rxd2);
-+
-               /* alloc new buffer */
-               if (ring->page_pool) {
-+                      struct page *page = virt_to_head_page(data);
-+                      struct xdp_buff xdp;
-+                      u32 ret;
-+
-                       new_data = mtk_page_pool_get_buff(ring->page_pool,
-                                                         &dma_addr,
-                                                         GFP_ATOMIC);
-@@ -1504,6 +1556,34 @@ static int mtk_poll_rx(struct napi_struc
-                               netdev->stats.rx_dropped++;
-                               goto release_desc;
-                       }
-+
-+                      dma_sync_single_for_cpu(eth->dma_dev,
-+                              page_pool_get_dma_addr(page) + MTK_PP_HEADROOM,
-+                              pktlen, page_pool_get_dma_dir(ring->page_pool));
-+
-+                      xdp_init_buff(&xdp, PAGE_SIZE, &ring->xdp_q);
-+                      xdp_prepare_buff(&xdp, data, MTK_PP_HEADROOM, pktlen,
-+                                       false);
-+                      xdp_buff_clear_frags_flag(&xdp);
-+
-+                      ret = mtk_xdp_run(eth, ring, &xdp, netdev);
-+                      if (ret == XDP_REDIRECT)
-+                              xdp_flush = true;
-+
-+                      if (ret != XDP_PASS)
-+                              goto skip_rx;
-+
-+                      skb = build_skb(data, PAGE_SIZE);
-+                      if (unlikely(!skb)) {
-+                              page_pool_put_full_page(ring->page_pool,
-+                                                      page, true);
-+                              netdev->stats.rx_dropped++;
-+                              goto skip_rx;
-+                      }
-+
-+                      skb_reserve(skb, xdp.data - xdp.data_hard_start);
-+                      skb_put(skb, xdp.data_end - xdp.data);
-+                      skb_mark_for_recycle(skb);
-               } else {
-                       if (ring->frag_size <= PAGE_SIZE)
-                               new_data = napi_alloc_frag(ring->frag_size);
-@@ -1527,27 +1607,20 @@ static int mtk_poll_rx(struct napi_struc
-                       dma_unmap_single(eth->dma_dev, trxd.rxd1,
-                                        ring->buf_size, DMA_FROM_DEVICE);
--              }
--              /* receive data */
--              skb = build_skb(data, ring->frag_size);
--              if (unlikely(!skb)) {
--                      mtk_rx_put_buff(ring, data, true);
--                      netdev->stats.rx_dropped++;
--                      goto skip_rx;
--              }
-+                      skb = build_skb(data, ring->frag_size);
-+                      if (unlikely(!skb)) {
-+                              netdev->stats.rx_dropped++;
-+                              skb_free_frag(data);
-+                              goto skip_rx;
-+                      }
--              if (ring->page_pool) {
--                      reserve_len = MTK_PP_HEADROOM;
--                      skb_mark_for_recycle(skb);
--              } else {
--                      reserve_len = NET_SKB_PAD + NET_IP_ALIGN;
-+                      skb_reserve(skb, NET_SKB_PAD + NET_IP_ALIGN);
-+                      skb_put(skb, pktlen);
-               }
--              skb_reserve(skb, reserve_len);
--              pktlen = RX_DMA_GET_PLEN0(trxd.rxd2);
-               skb->dev = netdev;
--              skb_put(skb, pktlen);
-+              bytes += skb->len;
-               if (MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2))
-                       rxdcsum = &trxd.rxd3;
-@@ -1559,7 +1632,6 @@ static int mtk_poll_rx(struct napi_struc
-               else
-                       skb_checksum_none_assert(skb);
-               skb->protocol = eth_type_trans(skb, netdev);
--              bytes += pktlen;
-               hash = trxd.rxd4 & MTK_RXD4_FOE_ENTRY;
-               if (hash != MTK_RXD4_FOE_ENTRY) {
-@@ -1622,6 +1694,9 @@ rx_done:
-                         &dim_sample);
-       net_dim(&eth->rx_dim, dim_sample);
-+      if (xdp_flush)
-+              xdp_do_flush_map();
-+
-       return done;
- }
-@@ -1967,7 +2042,7 @@ static int mtk_rx_alloc(struct mtk_eth *
-       if (!ring->data)
-               return -ENOMEM;
--      if (!eth->hwlro) {
-+      if (mtk_page_pool_enabled(eth)) {
-               struct page_pool *pp;
-               pp = mtk_create_page_pool(eth, &ring->xdp_q, ring_no,
-@@ -2712,6 +2787,48 @@ static int mtk_stop(struct net_device *d
-       return 0;
- }
-+static int mtk_xdp_setup(struct net_device *dev, struct bpf_prog *prog,
-+                       struct netlink_ext_ack *extack)
-+{
-+      struct mtk_mac *mac = netdev_priv(dev);
-+      struct mtk_eth *eth = mac->hw;
-+      struct bpf_prog *old_prog;
-+      bool need_update;
-+
-+      if (eth->hwlro) {
-+              NL_SET_ERR_MSG_MOD(extack, "XDP not supported with HWLRO");
-+              return -EOPNOTSUPP;
-+      }
-+
-+      if (dev->mtu > MTK_PP_MAX_BUF_SIZE) {
-+              NL_SET_ERR_MSG_MOD(extack, "MTU too large for XDP");
-+              return -EOPNOTSUPP;
-+      }
-+
-+      need_update = !!eth->prog != !!prog;
-+      if (netif_running(dev) && need_update)
-+              mtk_stop(dev);
-+
-+      old_prog = rcu_replace_pointer(eth->prog, prog, lockdep_rtnl_is_held());
-+      if (old_prog)
-+              bpf_prog_put(old_prog);
-+
-+      if (netif_running(dev) && need_update)
-+              return mtk_open(dev);
-+
-+      return 0;
-+}
-+
-+static int mtk_xdp(struct net_device *dev, struct netdev_bpf *xdp)
-+{
-+      switch (xdp->command) {
-+      case XDP_SETUP_PROG:
-+              return mtk_xdp_setup(dev, xdp->prog, xdp->extack);
-+      default:
-+              return -EINVAL;
-+      }
-+}
-+
- static void ethsys_reset(struct mtk_eth *eth, u32 reset_bits)
- {
-       regmap_update_bits(eth->ethsys, ETHSYS_RSTCTRL,
-@@ -2990,6 +3107,12 @@ static int mtk_change_mtu(struct net_dev
-       struct mtk_eth *eth = mac->hw;
-       u32 mcr_cur, mcr_new;
-+      if (rcu_access_pointer(eth->prog) &&
-+          length > MTK_PP_MAX_BUF_SIZE) {
-+              netdev_err(dev, "Invalid MTU for XDP mode\n");
-+              return -EINVAL;
-+      }
-+
-       if (!MTK_HAS_CAPS(eth->soc->caps, MTK_SOC_MT7628)) {
-               mcr_cur = mtk_r32(mac->hw, MTK_MAC_MCR(mac->id));
-               mcr_new = mcr_cur & ~MAC_MCR_MAX_RX_MASK;
-@@ -3316,6 +3439,7 @@ static const struct net_device_ops mtk_n
-       .ndo_poll_controller    = mtk_poll_controller,
- #endif
-       .ndo_setup_tc           = mtk_eth_setup_tc,
-+      .ndo_bpf                = mtk_xdp,
- };
- static int mtk_add_mac(struct mtk_eth *eth, struct device_node *np)
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-@@ -1086,6 +1086,8 @@ struct mtk_eth {
-       struct mtk_ppe                  *ppe;
-       struct rhashtable               flow_table;
-+
-+      struct bpf_prog                 __rcu *prog;
- };
- /* struct mtk_mac -   the structure that holds the info about the MACs of the
diff --git a/target/linux/generic/backport-5.15/706-02-v6.0-net-ethernet-mtk_eth_soc-introduce-xdp-ethtool-count.patch b/target/linux/generic/backport-5.15/706-02-v6.0-net-ethernet-mtk_eth_soc-introduce-xdp-ethtool-count.patch
deleted file mode 100644 (file)
index 7bb4222..0000000
+++ /dev/null
@@ -1,110 +0,0 @@
-From 916a6ee836d6b7b8ef1ed5f0515e256ca60e9968 Mon Sep 17 00:00:00 2001
-From: Lorenzo Bianconi <[email protected]>
-Date: Fri, 22 Jul 2022 09:19:38 +0200
-Subject: [PATCH] net: ethernet: mtk_eth_soc: introduce xdp ethtool counters
-
-Report xdp stats through ethtool
-
-Signed-off-by: Lorenzo Bianconi <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/ethernet/mediatek/mtk_eth_soc.c | 26 +++++++++++++++++++--
- drivers/net/ethernet/mediatek/mtk_eth_soc.h | 12 ++++++++++
- 2 files changed, 36 insertions(+), 2 deletions(-)
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-@@ -34,6 +34,10 @@ MODULE_PARM_DESC(msg_level, "Message lev
- #define MTK_ETHTOOL_STAT(x) { #x, \
-                             offsetof(struct mtk_hw_stats, x) / sizeof(u64) }
-+#define MTK_ETHTOOL_XDP_STAT(x) { #x, \
-+                                offsetof(struct mtk_hw_stats, xdp_stats.x) / \
-+                                sizeof(u64) }
-+
- static const struct mtk_reg_map mtk_reg_map = {
-       .tx_irq_mask            = 0x1a1c,
-       .tx_irq_status          = 0x1a18,
-@@ -141,6 +145,13 @@ static const struct mtk_ethtool_stats {
-       MTK_ETHTOOL_STAT(rx_long_errors),
-       MTK_ETHTOOL_STAT(rx_checksum_errors),
-       MTK_ETHTOOL_STAT(rx_flow_control_packets),
-+      MTK_ETHTOOL_XDP_STAT(rx_xdp_redirect),
-+      MTK_ETHTOOL_XDP_STAT(rx_xdp_pass),
-+      MTK_ETHTOOL_XDP_STAT(rx_xdp_drop),
-+      MTK_ETHTOOL_XDP_STAT(rx_xdp_tx),
-+      MTK_ETHTOOL_XDP_STAT(rx_xdp_tx_errors),
-+      MTK_ETHTOOL_XDP_STAT(tx_xdp_xmit),
-+      MTK_ETHTOOL_XDP_STAT(tx_xdp_xmit_errors),
- };
- static const char * const mtk_clks_source_name[] = {
-@@ -1458,6 +1469,9 @@ static void mtk_rx_put_buff(struct mtk_r
- static u32 mtk_xdp_run(struct mtk_eth *eth, struct mtk_rx_ring *ring,
-                      struct xdp_buff *xdp, struct net_device *dev)
- {
-+      struct mtk_mac *mac = netdev_priv(dev);
-+      struct mtk_hw_stats *hw_stats = mac->hw_stats;
-+      u64 *count = &hw_stats->xdp_stats.rx_xdp_drop;
-       struct bpf_prog *prog;
-       u32 act = XDP_PASS;
-@@ -1470,13 +1484,16 @@ static u32 mtk_xdp_run(struct mtk_eth *e
-       act = bpf_prog_run_xdp(prog, xdp);
-       switch (act) {
-       case XDP_PASS:
--              goto out;
-+              count = &hw_stats->xdp_stats.rx_xdp_pass;
-+              goto update_stats;
-       case XDP_REDIRECT:
-               if (unlikely(xdp_do_redirect(dev, xdp, prog))) {
-                       act = XDP_DROP;
-                       break;
-               }
--              goto out;
-+
-+              count = &hw_stats->xdp_stats.rx_xdp_redirect;
-+              goto update_stats;
-       default:
-               bpf_warn_invalid_xdp_action(act);
-               fallthrough;
-@@ -1489,6 +1506,11 @@ static u32 mtk_xdp_run(struct mtk_eth *e
-       page_pool_put_full_page(ring->page_pool,
-                               virt_to_head_page(xdp->data), true);
-+
-+update_stats:
-+      u64_stats_update_begin(&hw_stats->syncp);
-+      *count = *count + 1;
-+      u64_stats_update_end(&hw_stats->syncp);
- out:
-       rcu_read_unlock();
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-@@ -568,6 +568,16 @@ struct mtk_tx_dma_v2 {
- struct mtk_eth;
- struct mtk_mac;
-+struct mtk_xdp_stats {
-+      u64 rx_xdp_redirect;
-+      u64 rx_xdp_pass;
-+      u64 rx_xdp_drop;
-+      u64 rx_xdp_tx;
-+      u64 rx_xdp_tx_errors;
-+      u64 tx_xdp_xmit;
-+      u64 tx_xdp_xmit_errors;
-+};
-+
- /* struct mtk_hw_stats - the structure that holds the traffic statistics.
-  * @stats_lock:               make sure that stats operations are atomic
-  * @reg_offset:               the status register offset of the SoC
-@@ -591,6 +601,8 @@ struct mtk_hw_stats {
-       u64 rx_checksum_errors;
-       u64 rx_flow_control_packets;
-+      struct mtk_xdp_stats    xdp_stats;
-+
-       spinlock_t              stats_lock;
-       u32                     reg_offset;
-       struct u64_stats_sync   syncp;
diff --git a/target/linux/generic/backport-5.15/706-03-v6.0-net-ethernet-mtk_eth_soc-add-xmit-XDP-support.patch b/target/linux/generic/backport-5.15/706-03-v6.0-net-ethernet-mtk_eth_soc-add-xmit-XDP-support.patch
deleted file mode 100644 (file)
index deb06d4..0000000
+++ /dev/null
@@ -1,340 +0,0 @@
-From 5886d26fd25bbe26130e3e5f7474b9b3e98a3469 Mon Sep 17 00:00:00 2001
-From: Lorenzo Bianconi <[email protected]>
-Date: Fri, 22 Jul 2022 09:19:39 +0200
-Subject: [PATCH] net: ethernet: mtk_eth_soc: add xmit XDP support
-
-Introduce XDP support for XDP_TX verdict and ndo_xdp_xmit function
-pointer.
-
-Signed-off-by: Lorenzo Bianconi <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/ethernet/mediatek/mtk_eth_soc.c | 192 +++++++++++++++++---
- drivers/net/ethernet/mediatek/mtk_eth_soc.h |  10 +-
- 2 files changed, 180 insertions(+), 22 deletions(-)
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-@@ -987,15 +987,26 @@ static void mtk_tx_unmap(struct mtk_eth
-               }
-       }
--      tx_buf->flags = 0;
--      if (tx_buf->skb &&
--          (tx_buf->skb != (struct sk_buff *)MTK_DMA_DUMMY_DESC)) {
--              if (napi)
--                      napi_consume_skb(tx_buf->skb, napi);
-+      if (tx_buf->type == MTK_TYPE_SKB) {
-+              if (tx_buf->data &&
-+                  tx_buf->data != (void *)MTK_DMA_DUMMY_DESC) {
-+                      struct sk_buff *skb = tx_buf->data;
-+
-+                      if (napi)
-+                              napi_consume_skb(skb, napi);
-+                      else
-+                              dev_kfree_skb_any(skb);
-+              }
-+      } else if (tx_buf->data) {
-+              struct xdp_frame *xdpf = tx_buf->data;
-+
-+              if (napi && tx_buf->type == MTK_TYPE_XDP_TX)
-+                      xdp_return_frame_rx_napi(xdpf);
-               else
--                      dev_kfree_skb_any(tx_buf->skb);
-+                      xdp_return_frame(xdpf);
-       }
--      tx_buf->skb = NULL;
-+      tx_buf->flags = 0;
-+      tx_buf->data = NULL;
- }
- static void setup_tx_buf(struct mtk_eth *eth, struct mtk_tx_buf *tx_buf,
-@@ -1012,7 +1023,7 @@ static void setup_tx_buf(struct mtk_eth
-                       dma_unmap_addr_set(tx_buf, dma_addr1, mapped_addr);
-                       dma_unmap_len_set(tx_buf, dma_len1, size);
-               } else {
--                      tx_buf->skb = (struct sk_buff *)MTK_DMA_DUMMY_DESC;
-+                      tx_buf->data = (void *)MTK_DMA_DUMMY_DESC;
-                       txd->txd1 = mapped_addr;
-                       txd->txd2 = TX_DMA_PLEN0(size);
-                       dma_unmap_addr_set(tx_buf, dma_addr0, mapped_addr);
-@@ -1188,7 +1199,7 @@ static int mtk_tx_map(struct sk_buff *sk
-                                                   soc->txrx.txd_size);
-                       if (new_desc)
-                               memset(tx_buf, 0, sizeof(*tx_buf));
--                      tx_buf->skb = (struct sk_buff *)MTK_DMA_DUMMY_DESC;
-+                      tx_buf->data = (void *)MTK_DMA_DUMMY_DESC;
-                       tx_buf->flags |= MTK_TX_FLAGS_PAGE0;
-                       tx_buf->flags |= (!mac->id) ? MTK_TX_FLAGS_FPORT0 :
-                                        MTK_TX_FLAGS_FPORT1;
-@@ -1202,7 +1213,8 @@ static int mtk_tx_map(struct sk_buff *sk
-       }
-       /* store skb to cleanup */
--      itx_buf->skb = skb;
-+      itx_buf->type = MTK_TYPE_SKB;
-+      itx_buf->data = skb;
-       if (!MTK_HAS_CAPS(soc->caps, MTK_QDMA)) {
-               if (k & 0x1)
-@@ -1414,13 +1426,14 @@ static struct page_pool *mtk_create_page
-               .pool_size = size,
-               .nid = NUMA_NO_NODE,
-               .dev = eth->dma_dev,
--              .dma_dir = DMA_FROM_DEVICE,
-               .offset = MTK_PP_HEADROOM,
-               .max_len = MTK_PP_MAX_BUF_SIZE,
-       };
-       struct page_pool *pp;
-       int err;
-+      pp_params.dma_dir = rcu_access_pointer(eth->prog) ? DMA_BIDIRECTIONAL
-+                                                        : DMA_FROM_DEVICE;
-       pp = page_pool_create(&pp_params);
-       if (IS_ERR(pp))
-               return pp;
-@@ -1466,6 +1479,122 @@ static void mtk_rx_put_buff(struct mtk_r
-               skb_free_frag(data);
- }
-+static int mtk_xdp_submit_frame(struct mtk_eth *eth, struct xdp_frame *xdpf,
-+                              struct net_device *dev, bool dma_map)
-+{
-+      const struct mtk_soc_data *soc = eth->soc;
-+      struct mtk_tx_ring *ring = &eth->tx_ring;
-+      struct mtk_tx_dma_desc_info txd_info = {
-+              .size   = xdpf->len,
-+              .first  = true,
-+              .last   = true,
-+      };
-+      struct mtk_mac *mac = netdev_priv(dev);
-+      struct mtk_tx_dma *txd, *txd_pdma;
-+      int err = 0, index = 0, n_desc = 1;
-+      struct mtk_tx_buf *tx_buf;
-+
-+      if (unlikely(test_bit(MTK_RESETTING, &eth->state)))
-+              return -EBUSY;
-+
-+      if (unlikely(atomic_read(&ring->free_count) <= 1))
-+              return -EBUSY;
-+
-+      spin_lock(&eth->page_lock);
-+
-+      txd = ring->next_free;
-+      if (txd == ring->last_free) {
-+              err = -ENOMEM;
-+              goto out;
-+      }
-+
-+      tx_buf = mtk_desc_to_tx_buf(ring, txd, soc->txrx.txd_size);
-+      memset(tx_buf, 0, sizeof(*tx_buf));
-+
-+      if (dma_map) {  /* ndo_xdp_xmit */
-+              txd_info.addr = dma_map_single(eth->dma_dev, xdpf->data,
-+                                             txd_info.size, DMA_TO_DEVICE);
-+              if (unlikely(dma_mapping_error(eth->dma_dev, txd_info.addr))) {
-+                      err = -ENOMEM;
-+                      goto out;
-+              }
-+              tx_buf->flags |= MTK_TX_FLAGS_SINGLE0;
-+      } else {
-+              struct page *page = virt_to_head_page(xdpf->data);
-+
-+              txd_info.addr = page_pool_get_dma_addr(page) +
-+                              sizeof(*xdpf) + xdpf->headroom;
-+              dma_sync_single_for_device(eth->dma_dev, txd_info.addr,
-+                                         txd_info.size,
-+                                         DMA_BIDIRECTIONAL);
-+      }
-+      mtk_tx_set_dma_desc(dev, txd, &txd_info);
-+
-+      tx_buf->flags |= !mac->id ? MTK_TX_FLAGS_FPORT0 : MTK_TX_FLAGS_FPORT1;
-+
-+      txd_pdma = qdma_to_pdma(ring, txd);
-+      setup_tx_buf(eth, tx_buf, txd_pdma, txd_info.addr, txd_info.size,
-+                   index++);
-+
-+      /* store xdpf for cleanup */
-+      tx_buf->type = dma_map ? MTK_TYPE_XDP_NDO : MTK_TYPE_XDP_TX;
-+      tx_buf->data = xdpf;
-+
-+      if (!MTK_HAS_CAPS(soc->caps, MTK_QDMA)) {
-+              if (index & 1)
-+                      txd_pdma->txd2 |= TX_DMA_LS0;
-+              else
-+                      txd_pdma->txd2 |= TX_DMA_LS1;
-+      }
-+
-+      ring->next_free = mtk_qdma_phys_to_virt(ring, txd->txd2);
-+      atomic_sub(n_desc, &ring->free_count);
-+
-+      /* make sure that all changes to the dma ring are flushed before we
-+       * continue
-+       */
-+      wmb();
-+
-+      if (MTK_HAS_CAPS(soc->caps, MTK_QDMA)) {
-+              mtk_w32(eth, txd->txd2, soc->reg_map->qdma.ctx_ptr);
-+      } else {
-+              int idx;
-+
-+              idx = txd_to_idx(ring, txd, soc->txrx.txd_size);
-+              mtk_w32(eth, NEXT_DESP_IDX(idx, ring->dma_size),
-+                      MT7628_TX_CTX_IDX0);
-+      }
-+out:
-+      spin_unlock(&eth->page_lock);
-+
-+      return err;
-+}
-+
-+static int mtk_xdp_xmit(struct net_device *dev, int num_frame,
-+                      struct xdp_frame **frames, u32 flags)
-+{
-+      struct mtk_mac *mac = netdev_priv(dev);
-+      struct mtk_hw_stats *hw_stats = mac->hw_stats;
-+      struct mtk_eth *eth = mac->hw;
-+      int i, nxmit = 0;
-+
-+      if (unlikely(flags & ~XDP_XMIT_FLAGS_MASK))
-+              return -EINVAL;
-+
-+      for (i = 0; i < num_frame; i++) {
-+              if (mtk_xdp_submit_frame(eth, frames[i], dev, true))
-+                      break;
-+              nxmit++;
-+      }
-+
-+      u64_stats_update_begin(&hw_stats->syncp);
-+      hw_stats->xdp_stats.tx_xdp_xmit += nxmit;
-+      hw_stats->xdp_stats.tx_xdp_xmit_errors += num_frame - nxmit;
-+      u64_stats_update_end(&hw_stats->syncp);
-+
-+      return nxmit;
-+}
-+
- static u32 mtk_xdp_run(struct mtk_eth *eth, struct mtk_rx_ring *ring,
-                      struct xdp_buff *xdp, struct net_device *dev)
- {
-@@ -1494,6 +1623,18 @@ static u32 mtk_xdp_run(struct mtk_eth *e
-               count = &hw_stats->xdp_stats.rx_xdp_redirect;
-               goto update_stats;
-+      case XDP_TX: {
-+              struct xdp_frame *xdpf = xdp_convert_buff_to_frame(xdp);
-+
-+              if (mtk_xdp_submit_frame(eth, xdpf, dev, false)) {
-+                      count = &hw_stats->xdp_stats.rx_xdp_tx_errors;
-+                      act = XDP_DROP;
-+                      break;
-+              }
-+
-+              count = &hw_stats->xdp_stats.rx_xdp_tx;
-+              goto update_stats;
-+      }
-       default:
-               bpf_warn_invalid_xdp_action(act);
-               fallthrough;
-@@ -1727,9 +1868,8 @@ static int mtk_poll_tx_qdma(struct mtk_e
- {
-       const struct mtk_reg_map *reg_map = eth->soc->reg_map;
-       struct mtk_tx_ring *ring = &eth->tx_ring;
--      struct mtk_tx_dma *desc;
--      struct sk_buff *skb;
-       struct mtk_tx_buf *tx_buf;
-+      struct mtk_tx_dma *desc;
-       u32 cpu, dma;
-       cpu = ring->last_free_ptr;
-@@ -1750,15 +1890,21 @@ static int mtk_poll_tx_qdma(struct mtk_e
-               if (tx_buf->flags & MTK_TX_FLAGS_FPORT1)
-                       mac = 1;
--              skb = tx_buf->skb;
--              if (!skb)
-+              if (!tx_buf->data)
-                       break;
--              if (skb != (struct sk_buff *)MTK_DMA_DUMMY_DESC) {
-+              if (tx_buf->type == MTK_TYPE_SKB &&
-+                  tx_buf->data != (void *)MTK_DMA_DUMMY_DESC) {
-+                      struct sk_buff *skb = tx_buf->data;
-+
-                       bytes[mac] += skb->len;
-                       done[mac]++;
-                       budget--;
-+              } else if (tx_buf->type == MTK_TYPE_XDP_TX ||
-+                         tx_buf->type == MTK_TYPE_XDP_NDO) {
-+                      budget--;
-               }
-+
-               mtk_tx_unmap(eth, tx_buf, true);
-               ring->last_free = desc;
-@@ -1777,9 +1923,8 @@ static int mtk_poll_tx_pdma(struct mtk_e
-                           unsigned int *done, unsigned int *bytes)
- {
-       struct mtk_tx_ring *ring = &eth->tx_ring;
--      struct mtk_tx_dma *desc;
--      struct sk_buff *skb;
-       struct mtk_tx_buf *tx_buf;
-+      struct mtk_tx_dma *desc;
-       u32 cpu, dma;
-       cpu = ring->cpu_idx;
-@@ -1787,14 +1932,18 @@ static int mtk_poll_tx_pdma(struct mtk_e
-       while ((cpu != dma) && budget) {
-               tx_buf = &ring->buf[cpu];
--              skb = tx_buf->skb;
--              if (!skb)
-+              if (!tx_buf->data)
-                       break;
--              if (skb != (struct sk_buff *)MTK_DMA_DUMMY_DESC) {
-+              if (tx_buf->type == MTK_TYPE_SKB &&
-+                  tx_buf->data != (void *)MTK_DMA_DUMMY_DESC) {
-+                      struct sk_buff *skb = tx_buf->data;
-                       bytes[0] += skb->len;
-                       done[0]++;
-                       budget--;
-+              } else if (tx_buf->type == MTK_TYPE_XDP_TX ||
-+                         tx_buf->type == MTK_TYPE_XDP_NDO) {
-+                      budget--;
-               }
-               mtk_tx_unmap(eth, tx_buf, true);
-@@ -3462,6 +3611,7 @@ static const struct net_device_ops mtk_n
- #endif
-       .ndo_setup_tc           = mtk_eth_setup_tc,
-       .ndo_bpf                = mtk_xdp,
-+      .ndo_xdp_xmit           = mtk_xdp_xmit,
- };
- static int mtk_add_mac(struct mtk_eth *eth, struct device_node *np)
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-@@ -694,6 +694,12 @@ enum mtk_dev_state {
-       MTK_RESETTING
- };
-+enum mtk_tx_buf_type {
-+      MTK_TYPE_SKB,
-+      MTK_TYPE_XDP_TX,
-+      MTK_TYPE_XDP_NDO,
-+};
-+
- /* struct mtk_tx_buf -        This struct holds the pointers to the memory pointed at
-  *                    by the TX descriptor    s
-  * @skb:              The SKB pointer of the packet being sent
-@@ -703,7 +709,9 @@ enum mtk_dev_state {
-  * @dma_len1:         The length of the second segment
-  */
- struct mtk_tx_buf {
--      struct sk_buff *skb;
-+      enum mtk_tx_buf_type type;
-+      void *data;
-+
-       u32 flags;
-       DEFINE_DMA_UNMAP_ADDR(dma_addr0);
-       DEFINE_DMA_UNMAP_LEN(dma_len0);
diff --git a/target/linux/generic/backport-5.15/706-04-v6.0-net-ethernet-mtk_eth_soc-add-support-for-page_pool_g.patch b/target/linux/generic/backport-5.15/706-04-v6.0-net-ethernet-mtk_eth_soc-add-support-for-page_pool_g.patch
deleted file mode 100644 (file)
index 4707aac..0000000
+++ /dev/null
@@ -1,95 +0,0 @@
-From 84b9cd389036d4a262d8cee794d56c04095358a7 Mon Sep 17 00:00:00 2001
-From: Lorenzo Bianconi <[email protected]>
-Date: Fri, 22 Jul 2022 09:19:40 +0200
-Subject: [PATCH] net: ethernet: mtk_eth_soc: add support for
- page_pool_get_stats
-
-Introduce support for the page_pool stats API into mtk_eth_soc driver.
-Report page_pool stats through ethtool.
-
-Signed-off-by: Lorenzo Bianconi <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/ethernet/mediatek/Kconfig       |  1 +
- drivers/net/ethernet/mediatek/mtk_eth_soc.c | 37 +++++++++++++++++++--
- 2 files changed, 35 insertions(+), 3 deletions(-)
-
---- a/drivers/net/ethernet/mediatek/Kconfig
-+++ b/drivers/net/ethernet/mediatek/Kconfig
-@@ -17,6 +17,7 @@ config NET_MEDIATEK_SOC
-       select PHYLINK
-       select DIMLIB
-       select PAGE_POOL
-+      select PAGE_POOL_STATS
-       help
-         This driver supports the gigabit ethernet MACs in the
-         MediaTek SoC family.
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-@@ -3473,11 +3473,18 @@ static void mtk_get_strings(struct net_d
-       int i;
-       switch (stringset) {
--      case ETH_SS_STATS:
-+      case ETH_SS_STATS: {
-+              struct mtk_mac *mac = netdev_priv(dev);
-+
-               for (i = 0; i < ARRAY_SIZE(mtk_ethtool_stats); i++) {
-                       memcpy(data, mtk_ethtool_stats[i].str, ETH_GSTRING_LEN);
-                       data += ETH_GSTRING_LEN;
-               }
-+              if (mtk_page_pool_enabled(mac->hw))
-+                      page_pool_ethtool_stats_get_strings(data);
-+              break;
-+      }
-+      default:
-               break;
-       }
- }
-@@ -3485,13 +3492,35 @@ static void mtk_get_strings(struct net_d
- static int mtk_get_sset_count(struct net_device *dev, int sset)
- {
-       switch (sset) {
--      case ETH_SS_STATS:
--              return ARRAY_SIZE(mtk_ethtool_stats);
-+      case ETH_SS_STATS: {
-+              int count = ARRAY_SIZE(mtk_ethtool_stats);
-+              struct mtk_mac *mac = netdev_priv(dev);
-+
-+              if (mtk_page_pool_enabled(mac->hw))
-+                      count += page_pool_ethtool_stats_get_count();
-+              return count;
-+      }
-       default:
-               return -EOPNOTSUPP;
-       }
- }
-+static void mtk_ethtool_pp_stats(struct mtk_eth *eth, u64 *data)
-+{
-+      struct page_pool_stats stats = {};
-+      int i;
-+
-+      for (i = 0; i < ARRAY_SIZE(eth->rx_ring); i++) {
-+              struct mtk_rx_ring *ring = &eth->rx_ring[i];
-+
-+              if (!ring->page_pool)
-+                      continue;
-+
-+              page_pool_get_stats(ring->page_pool, &stats);
-+      }
-+      page_pool_ethtool_stats_get(data, &stats);
-+}
-+
- static void mtk_get_ethtool_stats(struct net_device *dev,
-                                 struct ethtool_stats *stats, u64 *data)
- {
-@@ -3519,6 +3548,8 @@ static void mtk_get_ethtool_stats(struct
-               for (i = 0; i < ARRAY_SIZE(mtk_ethtool_stats); i++)
-                       *data_dst++ = *(data_src + mtk_ethtool_stats[i].offset);
-+              if (mtk_page_pool_enabled(mac->hw))
-+                      mtk_ethtool_pp_stats(mac->hw, data_dst);
-       } while (u64_stats_fetch_retry_irq(&hwstats->syncp, start));
- }
diff --git a/target/linux/generic/backport-5.15/706-05-v6.0-net-ethernet-mtk_eth_soc-introduce-mtk_xdp_frame_map.patch b/target/linux/generic/backport-5.15/706-05-v6.0-net-ethernet-mtk_eth_soc-introduce-mtk_xdp_frame_map.patch
deleted file mode 100644 (file)
index 33a7616..0000000
+++ /dev/null
@@ -1,113 +0,0 @@
-From b16fe6d82b71fa0dd5c957bc22d66a694976d6eb Mon Sep 17 00:00:00 2001
-From: Lorenzo Bianconi <[email protected]>
-Date: Wed, 27 Jul 2022 23:20:50 +0200
-Subject: [PATCH] net: ethernet: mtk_eth_soc: introduce mtk_xdp_frame_map
- utility routine
-
-This is a preliminary patch to add xdp multi-frag support to mtk_eth_soc
-driver
-
-Signed-off-by: Lorenzo Bianconi <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/ethernet/mediatek/mtk_eth_soc.c | 68 +++++++++++++--------
- 1 file changed, 42 insertions(+), 26 deletions(-)
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-@@ -1479,6 +1479,41 @@ static void mtk_rx_put_buff(struct mtk_r
-               skb_free_frag(data);
- }
-+static int mtk_xdp_frame_map(struct mtk_eth *eth, struct net_device *dev,
-+                           struct mtk_tx_dma_desc_info *txd_info,
-+                           struct mtk_tx_dma *txd, struct mtk_tx_buf *tx_buf,
-+                           void *data, u16 headroom, int index, bool dma_map)
-+{
-+      struct mtk_tx_ring *ring = &eth->tx_ring;
-+      struct mtk_mac *mac = netdev_priv(dev);
-+      struct mtk_tx_dma *txd_pdma;
-+
-+      if (dma_map) {  /* ndo_xdp_xmit */
-+              txd_info->addr = dma_map_single(eth->dma_dev, data,
-+                                              txd_info->size, DMA_TO_DEVICE);
-+              if (unlikely(dma_mapping_error(eth->dma_dev, txd_info->addr)))
-+                      return -ENOMEM;
-+
-+              tx_buf->flags |= MTK_TX_FLAGS_SINGLE0;
-+      } else {
-+              struct page *page = virt_to_head_page(data);
-+
-+              txd_info->addr = page_pool_get_dma_addr(page) +
-+                               sizeof(struct xdp_frame) + headroom;
-+              dma_sync_single_for_device(eth->dma_dev, txd_info->addr,
-+                                         txd_info->size, DMA_BIDIRECTIONAL);
-+      }
-+      mtk_tx_set_dma_desc(dev, txd, txd_info);
-+
-+      tx_buf->flags |= !mac->id ? MTK_TX_FLAGS_FPORT0 : MTK_TX_FLAGS_FPORT1;
-+
-+      txd_pdma = qdma_to_pdma(ring, txd);
-+      setup_tx_buf(eth, tx_buf, txd_pdma, txd_info->addr, txd_info->size,
-+                   index);
-+
-+      return 0;
-+}
-+
- static int mtk_xdp_submit_frame(struct mtk_eth *eth, struct xdp_frame *xdpf,
-                               struct net_device *dev, bool dma_map)
- {
-@@ -1489,9 +1524,8 @@ static int mtk_xdp_submit_frame(struct m
-               .first  = true,
-               .last   = true,
-       };
--      struct mtk_mac *mac = netdev_priv(dev);
--      struct mtk_tx_dma *txd, *txd_pdma;
-       int err = 0, index = 0, n_desc = 1;
-+      struct mtk_tx_dma *txd, *txd_pdma;
-       struct mtk_tx_buf *tx_buf;
-       if (unlikely(test_bit(MTK_RESETTING, &eth->state)))
-@@ -1511,36 +1545,18 @@ static int mtk_xdp_submit_frame(struct m
-       tx_buf = mtk_desc_to_tx_buf(ring, txd, soc->txrx.txd_size);
-       memset(tx_buf, 0, sizeof(*tx_buf));
--      if (dma_map) {  /* ndo_xdp_xmit */
--              txd_info.addr = dma_map_single(eth->dma_dev, xdpf->data,
--                                             txd_info.size, DMA_TO_DEVICE);
--              if (unlikely(dma_mapping_error(eth->dma_dev, txd_info.addr))) {
--                      err = -ENOMEM;
--                      goto out;
--              }
--              tx_buf->flags |= MTK_TX_FLAGS_SINGLE0;
--      } else {
--              struct page *page = virt_to_head_page(xdpf->data);
--
--              txd_info.addr = page_pool_get_dma_addr(page) +
--                              sizeof(*xdpf) + xdpf->headroom;
--              dma_sync_single_for_device(eth->dma_dev, txd_info.addr,
--                                         txd_info.size,
--                                         DMA_BIDIRECTIONAL);
--      }
--      mtk_tx_set_dma_desc(dev, txd, &txd_info);
--
--      tx_buf->flags |= !mac->id ? MTK_TX_FLAGS_FPORT0 : MTK_TX_FLAGS_FPORT1;
--
--      txd_pdma = qdma_to_pdma(ring, txd);
--      setup_tx_buf(eth, tx_buf, txd_pdma, txd_info.addr, txd_info.size,
--                   index++);
-+      err = mtk_xdp_frame_map(eth, dev, &txd_info, txd, tx_buf,
-+                              xdpf->data, xdpf->headroom, index,
-+                              dma_map);
-+      if (err < 0)
-+              goto out;
-       /* store xdpf for cleanup */
-       tx_buf->type = dma_map ? MTK_TYPE_XDP_NDO : MTK_TYPE_XDP_TX;
-       tx_buf->data = xdpf;
-       if (!MTK_HAS_CAPS(soc->caps, MTK_QDMA)) {
-+              txd_pdma = qdma_to_pdma(ring, txd);
-               if (index & 1)
-                       txd_pdma->txd2 |= TX_DMA_LS0;
-               else
diff --git a/target/linux/generic/backport-5.15/706-06-v6.0-net-ethernet-mtk_eth_soc-introduce-xdp-multi-frag-su.patch b/target/linux/generic/backport-5.15/706-06-v6.0-net-ethernet-mtk_eth_soc-introduce-xdp-multi-frag-su.patch
deleted file mode 100644 (file)
index e75861b..0000000
+++ /dev/null
@@ -1,218 +0,0 @@
-From 155738a4f319538a09f734ce1f5a2eac3ada1de2 Mon Sep 17 00:00:00 2001
-From: Lorenzo Bianconi <[email protected]>
-Date: Wed, 27 Jul 2022 23:20:51 +0200
-Subject: [PATCH] net: ethernet: mtk_eth_soc: introduce xdp multi-frag support
-
-Add the capability to map non-linear xdp frames in XDP_TX and
-ndo_xdp_xmit callback.
-
-Signed-off-by: Lorenzo Bianconi <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/ethernet/mediatek/mtk_eth_soc.c | 125 +++++++++++++-------
- 1 file changed, 82 insertions(+), 43 deletions(-)
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-@@ -987,23 +987,22 @@ static void mtk_tx_unmap(struct mtk_eth
-               }
-       }
--      if (tx_buf->type == MTK_TYPE_SKB) {
--              if (tx_buf->data &&
--                  tx_buf->data != (void *)MTK_DMA_DUMMY_DESC) {
-+      if (tx_buf->data && tx_buf->data != (void *)MTK_DMA_DUMMY_DESC) {
-+              if (tx_buf->type == MTK_TYPE_SKB) {
-                       struct sk_buff *skb = tx_buf->data;
-                       if (napi)
-                               napi_consume_skb(skb, napi);
-                       else
-                               dev_kfree_skb_any(skb);
--              }
--      } else if (tx_buf->data) {
--              struct xdp_frame *xdpf = tx_buf->data;
-+              } else {
-+                      struct xdp_frame *xdpf = tx_buf->data;
--              if (napi && tx_buf->type == MTK_TYPE_XDP_TX)
--                      xdp_return_frame_rx_napi(xdpf);
--              else
--                      xdp_return_frame(xdpf);
-+                      if (napi && tx_buf->type == MTK_TYPE_XDP_TX)
-+                              xdp_return_frame_rx_napi(xdpf);
-+                      else
-+                              xdp_return_frame(xdpf);
-+              }
-       }
-       tx_buf->flags = 0;
-       tx_buf->data = NULL;
-@@ -1506,6 +1505,8 @@ static int mtk_xdp_frame_map(struct mtk_
-       mtk_tx_set_dma_desc(dev, txd, txd_info);
-       tx_buf->flags |= !mac->id ? MTK_TX_FLAGS_FPORT0 : MTK_TX_FLAGS_FPORT1;
-+      tx_buf->type = dma_map ? MTK_TYPE_XDP_NDO : MTK_TYPE_XDP_TX;
-+      tx_buf->data = (void *)MTK_DMA_DUMMY_DESC;
-       txd_pdma = qdma_to_pdma(ring, txd);
-       setup_tx_buf(eth, tx_buf, txd_pdma, txd_info->addr, txd_info->size,
-@@ -1517,43 +1518,69 @@ static int mtk_xdp_frame_map(struct mtk_
- static int mtk_xdp_submit_frame(struct mtk_eth *eth, struct xdp_frame *xdpf,
-                               struct net_device *dev, bool dma_map)
- {
-+      struct skb_shared_info *sinfo = xdp_get_shared_info_from_frame(xdpf);
-       const struct mtk_soc_data *soc = eth->soc;
-       struct mtk_tx_ring *ring = &eth->tx_ring;
-       struct mtk_tx_dma_desc_info txd_info = {
-               .size   = xdpf->len,
-               .first  = true,
--              .last   = true,
-+              .last   = !xdp_frame_has_frags(xdpf),
-       };
--      int err = 0, index = 0, n_desc = 1;
--      struct mtk_tx_dma *txd, *txd_pdma;
--      struct mtk_tx_buf *tx_buf;
-+      int err, index = 0, n_desc = 1, nr_frags;
-+      struct mtk_tx_dma *htxd, *txd, *txd_pdma;
-+      struct mtk_tx_buf *htx_buf, *tx_buf;
-+      void *data = xdpf->data;
-       if (unlikely(test_bit(MTK_RESETTING, &eth->state)))
-               return -EBUSY;
--      if (unlikely(atomic_read(&ring->free_count) <= 1))
-+      nr_frags = unlikely(xdp_frame_has_frags(xdpf)) ? sinfo->nr_frags : 0;
-+      if (unlikely(atomic_read(&ring->free_count) <= 1 + nr_frags))
-               return -EBUSY;
-       spin_lock(&eth->page_lock);
-       txd = ring->next_free;
-       if (txd == ring->last_free) {
--              err = -ENOMEM;
--              goto out;
-+              spin_unlock(&eth->page_lock);
-+              return -ENOMEM;
-       }
-+      htxd = txd;
-       tx_buf = mtk_desc_to_tx_buf(ring, txd, soc->txrx.txd_size);
-       memset(tx_buf, 0, sizeof(*tx_buf));
-+      htx_buf = tx_buf;
--      err = mtk_xdp_frame_map(eth, dev, &txd_info, txd, tx_buf,
--                              xdpf->data, xdpf->headroom, index,
--                              dma_map);
--      if (err < 0)
--              goto out;
-+      for (;;) {
-+              err = mtk_xdp_frame_map(eth, dev, &txd_info, txd, tx_buf,
-+                                      data, xdpf->headroom, index, dma_map);
-+              if (err < 0)
-+                      goto unmap;
-+
-+              if (txd_info.last)
-+                      break;
-+              if (MTK_HAS_CAPS(soc->caps, MTK_QDMA) || (index & 0x1)) {
-+                      txd = mtk_qdma_phys_to_virt(ring, txd->txd2);
-+                      txd_pdma = qdma_to_pdma(ring, txd);
-+                      if (txd == ring->last_free)
-+                              goto unmap;
-+
-+                      tx_buf = mtk_desc_to_tx_buf(ring, txd,
-+                                                  soc->txrx.txd_size);
-+                      memset(tx_buf, 0, sizeof(*tx_buf));
-+                      n_desc++;
-+              }
-+
-+              memset(&txd_info, 0, sizeof(struct mtk_tx_dma_desc_info));
-+              txd_info.size = skb_frag_size(&sinfo->frags[index]);
-+              txd_info.last = index + 1 == nr_frags;
-+              data = skb_frag_address(&sinfo->frags[index]);
-+
-+              index++;
-+      }
-       /* store xdpf for cleanup */
--      tx_buf->type = dma_map ? MTK_TYPE_XDP_NDO : MTK_TYPE_XDP_TX;
--      tx_buf->data = xdpf;
-+      htx_buf->data = xdpf;
-       if (!MTK_HAS_CAPS(soc->caps, MTK_QDMA)) {
-               txd_pdma = qdma_to_pdma(ring, txd);
-@@ -1580,7 +1607,24 @@ static int mtk_xdp_submit_frame(struct m
-               mtk_w32(eth, NEXT_DESP_IDX(idx, ring->dma_size),
-                       MT7628_TX_CTX_IDX0);
-       }
--out:
-+
-+      spin_unlock(&eth->page_lock);
-+
-+      return 0;
-+
-+unmap:
-+      while (htxd != txd) {
-+              txd_pdma = qdma_to_pdma(ring, htxd);
-+              tx_buf = mtk_desc_to_tx_buf(ring, htxd, soc->txrx.txd_size);
-+              mtk_tx_unmap(eth, tx_buf, false);
-+
-+              htxd->txd3 = TX_DMA_LS0 | TX_DMA_OWNER_CPU;
-+              if (!MTK_HAS_CAPS(soc->caps, MTK_QDMA))
-+                      txd_pdma->txd2 = TX_DMA_DESP2_DEF;
-+
-+              htxd = mtk_qdma_phys_to_virt(ring, htxd->txd2);
-+      }
-+
-       spin_unlock(&eth->page_lock);
-       return err;
-@@ -1909,18 +1953,15 @@ static int mtk_poll_tx_qdma(struct mtk_e
-               if (!tx_buf->data)
-                       break;
--              if (tx_buf->type == MTK_TYPE_SKB &&
--                  tx_buf->data != (void *)MTK_DMA_DUMMY_DESC) {
--                      struct sk_buff *skb = tx_buf->data;
-+              if (tx_buf->data != (void *)MTK_DMA_DUMMY_DESC) {
-+                      if (tx_buf->type == MTK_TYPE_SKB) {
-+                              struct sk_buff *skb = tx_buf->data;
--                      bytes[mac] += skb->len;
--                      done[mac]++;
--                      budget--;
--              } else if (tx_buf->type == MTK_TYPE_XDP_TX ||
--                         tx_buf->type == MTK_TYPE_XDP_NDO) {
-+                              bytes[mac] += skb->len;
-+                              done[mac]++;
-+                      }
-                       budget--;
-               }
--
-               mtk_tx_unmap(eth, tx_buf, true);
-               ring->last_free = desc;
-@@ -1951,17 +1992,15 @@ static int mtk_poll_tx_pdma(struct mtk_e
-               if (!tx_buf->data)
-                       break;
--              if (tx_buf->type == MTK_TYPE_SKB &&
--                  tx_buf->data != (void *)MTK_DMA_DUMMY_DESC) {
--                      struct sk_buff *skb = tx_buf->data;
--                      bytes[0] += skb->len;
--                      done[0]++;
--                      budget--;
--              } else if (tx_buf->type == MTK_TYPE_XDP_TX ||
--                         tx_buf->type == MTK_TYPE_XDP_NDO) {
-+              if (tx_buf->data != (void *)MTK_DMA_DUMMY_DESC) {
-+                      if (tx_buf->type == MTK_TYPE_SKB) {
-+                              struct sk_buff *skb = tx_buf->data;
-+
-+                              bytes[0] += skb->len;
-+                              done[0]++;
-+                      }
-                       budget--;
-               }
--
-               mtk_tx_unmap(eth, tx_buf, true);
-               desc = ring->dma + cpu * eth->soc->txrx.txd_size;
diff --git a/target/linux/generic/backport-5.15/707-v6.3-net-pcs-add-driver-for-MediaTek-SGMII-PCS.patch b/target/linux/generic/backport-5.15/707-v6.3-net-pcs-add-driver-for-MediaTek-SGMII-PCS.patch
deleted file mode 100644 (file)
index 1f2a3ee..0000000
+++ /dev/null
@@ -1,394 +0,0 @@
-From 4765a9722e09765866e131ec31f7b9cf4c1f4854 Mon Sep 17 00:00:00 2001
-From: Daniel Golle <[email protected]>
-Date: Sun, 19 Mar 2023 12:57:50 +0000
-Subject: [PATCH] net: pcs: add driver for MediaTek SGMII PCS
-
-The SGMII core found in several MediaTek SoCs is identical to what can
-also be found in MediaTek's MT7531 Ethernet switch IC.
-As this has not always been clear, both drivers developed different
-implementations to deal with the PCS.
-Recently Alexander Couzens pointed out this fact which lead to the
-development of this shared driver.
-
-Add a dedicated driver, mostly by copying the code now found in the
-Ethernet driver. The now redundant code will be removed by a follow-up
-commit.
-
-Suggested-by: Alexander Couzens <[email protected]>
-Suggested-by: Russell King (Oracle) <[email protected]>
-Signed-off-by: Daniel Golle <[email protected]>
-Tested-by: Frank Wunderlich <[email protected]>
-Reviewed-by: Russell King (Oracle) <[email protected]>
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- MAINTAINERS                       |   8 +
- drivers/net/pcs/Kconfig           |   7 +
- drivers/net/pcs/Makefile          |   1 +
- drivers/net/pcs/pcs-mtk-lynxi.c   | 305 ++++++++++++++++++++++++++++++
- include/linux/pcs/pcs-mtk-lynxi.h |  13 ++
- 5 files changed, 334 insertions(+)
- create mode 100644 drivers/net/pcs/pcs-mtk-lynxi.c
- create mode 100644 include/linux/pcs/pcs-mtk-lynxi.h
-
---- a/MAINTAINERS
-+++ b/MAINTAINERS
-@@ -11790,6 +11790,14 @@ L:    [email protected]
- S:    Maintained
- F:    drivers/net/ethernet/mediatek/
-+MEDIATEK ETHERNET PCS DRIVER
-+M:    Alexander Couzens <[email protected]>
-+M:    Daniel Golle <[email protected]>
-+L:    [email protected]
-+S:    Maintained
-+F:    drivers/net/pcs/pcs-mtk-lynxi.c
-+F:    include/linux/pcs/pcs-mtk-lynxi.h
-+
- MEDIATEK I2C CONTROLLER DRIVER
- M:    Qii Wang <[email protected]>
- L:    [email protected]
---- a/drivers/net/pcs/Kconfig
-+++ b/drivers/net/pcs/Kconfig
-@@ -18,4 +18,11 @@ config PCS_LYNX
-         This module provides helpers to phylink for managing the Lynx PCS
-         which is part of the Layerscape and QorIQ Ethernet SERDES.
-+config PCS_MTK_LYNXI
-+      tristate
-+      select REGMAP
-+      help
-+        This module provides helpers to phylink for managing the LynxI PCS
-+        which is part of MediaTek's SoC and Ethernet switch ICs.
-+
- endmenu
---- a/drivers/net/pcs/Makefile
-+++ b/drivers/net/pcs/Makefile
-@@ -5,3 +5,4 @@ pcs_xpcs-$(CONFIG_PCS_XPCS)    := pcs-xpcs.
- obj-$(CONFIG_PCS_XPCS)                += pcs_xpcs.o
- obj-$(CONFIG_PCS_LYNX)                += pcs-lynx.o
-+obj-$(CONFIG_PCS_MTK_LYNXI)   += pcs-mtk-lynxi.o
---- /dev/null
-+++ b/drivers/net/pcs/pcs-mtk-lynxi.c
-@@ -0,0 +1,305 @@
-+// SPDX-License-Identifier: GPL-2.0
-+// Copyright (c) 2018-2019 MediaTek Inc.
-+/* A library for MediaTek SGMII circuit
-+ *
-+ * Author: Sean Wang <[email protected]>
-+ * Author: Alexander Couzens <[email protected]>
-+ * Author: Daniel Golle <[email protected]>
-+ *
-+ */
-+
-+#include <linux/mdio.h>
-+#include <linux/of.h>
-+#include <linux/pcs/pcs-mtk-lynxi.h>
-+#include <linux/phylink.h>
-+#include <linux/regmap.h>
-+
-+/* SGMII subsystem config registers */
-+/* BMCR (low 16) BMSR (high 16) */
-+#define SGMSYS_PCS_CONTROL_1          0x0
-+#define SGMII_BMCR                    GENMASK(15, 0)
-+#define SGMII_BMSR                    GENMASK(31, 16)
-+
-+#define SGMSYS_PCS_DEVICE_ID          0x4
-+#define SGMII_LYNXI_DEV_ID            0x4d544950
-+
-+#define SGMSYS_PCS_ADVERTISE          0x8
-+#define SGMII_ADVERTISE                       GENMASK(15, 0)
-+#define SGMII_LPA                     GENMASK(31, 16)
-+
-+#define SGMSYS_PCS_SCRATCH            0x14
-+#define SGMII_DEV_VERSION             GENMASK(31, 16)
-+
-+/* Register to programmable link timer, the unit in 2 * 8ns */
-+#define SGMSYS_PCS_LINK_TIMER         0x18
-+#define SGMII_LINK_TIMER_MASK         GENMASK(19, 0)
-+#define SGMII_LINK_TIMER_VAL(ns)      FIELD_PREP(SGMII_LINK_TIMER_MASK, \
-+                                                 ((ns) / 2 / 8))
-+
-+/* Register to control remote fault */
-+#define SGMSYS_SGMII_MODE             0x20
-+#define SGMII_IF_MODE_SGMII           BIT(0)
-+#define SGMII_SPEED_DUPLEX_AN         BIT(1)
-+#define SGMII_SPEED_MASK              GENMASK(3, 2)
-+#define SGMII_SPEED_10                        FIELD_PREP(SGMII_SPEED_MASK, 0)
-+#define SGMII_SPEED_100                       FIELD_PREP(SGMII_SPEED_MASK, 1)
-+#define SGMII_SPEED_1000              FIELD_PREP(SGMII_SPEED_MASK, 2)
-+#define SGMII_DUPLEX_HALF             BIT(4)
-+#define SGMII_REMOTE_FAULT_DIS                BIT(8)
-+
-+/* Register to reset SGMII design */
-+#define SGMSYS_RESERVED_0             0x34
-+#define SGMII_SW_RESET                        BIT(0)
-+
-+/* Register to set SGMII speed, ANA RG_ Control Signals III */
-+#define SGMII_PHY_SPEED_MASK          GENMASK(3, 2)
-+#define SGMII_PHY_SPEED_1_25G         FIELD_PREP(SGMII_PHY_SPEED_MASK, 0)
-+#define SGMII_PHY_SPEED_3_125G                FIELD_PREP(SGMII_PHY_SPEED_MASK, 1)
-+
-+/* Register to power up QPHY */
-+#define SGMSYS_QPHY_PWR_STATE_CTRL    0xe8
-+#define       SGMII_PHYA_PWD                  BIT(4)
-+
-+/* Register to QPHY wrapper control */
-+#define SGMSYS_QPHY_WRAP_CTRL         0xec
-+#define SGMII_PN_SWAP_MASK            GENMASK(1, 0)
-+#define SGMII_PN_SWAP_TX_RX           (BIT(0) | BIT(1))
-+
-+/* struct mtk_pcs_lynxi -  This structure holds each sgmii regmap andassociated
-+ *                         data
-+ * @regmap:                The register map pointing at the range used to setup
-+ *                         SGMII modes
-+ * @dev:                   Pointer to device owning the PCS
-+ * @ana_rgc3:              The offset of register ANA_RGC3 relative to regmap
-+ * @interface:             Currently configured interface mode
-+ * @pcs:                   Phylink PCS structure
-+ * @flags:                 Flags indicating hardware properties
-+ */
-+struct mtk_pcs_lynxi {
-+      struct regmap           *regmap;
-+      u32                     ana_rgc3;
-+      phy_interface_t         interface;
-+      struct                  phylink_pcs pcs;
-+      u32                     flags;
-+};
-+
-+static struct mtk_pcs_lynxi *pcs_to_mtk_pcs_lynxi(struct phylink_pcs *pcs)
-+{
-+      return container_of(pcs, struct mtk_pcs_lynxi, pcs);
-+}
-+
-+static void mtk_pcs_lynxi_get_state(struct phylink_pcs *pcs,
-+                                  struct phylink_link_state *state)
-+{
-+      struct mtk_pcs_lynxi *mpcs = pcs_to_mtk_pcs_lynxi(pcs);
-+      unsigned int bm, adv;
-+
-+      /* Read the BMSR and LPA */
-+      regmap_read(mpcs->regmap, SGMSYS_PCS_CONTROL_1, &bm);
-+      regmap_read(mpcs->regmap, SGMSYS_PCS_ADVERTISE, &adv);
-+
-+      phylink_mii_c22_pcs_decode_state(state, FIELD_GET(SGMII_BMSR, bm),
-+                                       FIELD_GET(SGMII_LPA, adv));
-+}
-+
-+static int mtk_pcs_lynxi_config(struct phylink_pcs *pcs, unsigned int mode,
-+                              phy_interface_t interface,
-+                              const unsigned long *advertising,
-+                              bool permit_pause_to_mac)
-+{
-+      struct mtk_pcs_lynxi *mpcs = pcs_to_mtk_pcs_lynxi(pcs);
-+      bool mode_changed = false, changed, use_an;
-+      unsigned int rgc3, sgm_mode, bmcr;
-+      int advertise, link_timer;
-+
-+      advertise = phylink_mii_c22_pcs_encode_advertisement(interface,
-+                                                           advertising);
-+      if (advertise < 0)
-+              return advertise;
-+
-+      /* Clearing IF_MODE_BIT0 switches the PCS to BASE-X mode, and
-+       * we assume that fixes it's speed at bitrate = line rate (in
-+       * other words, 1000Mbps or 2500Mbps).
-+       */
-+      if (interface == PHY_INTERFACE_MODE_SGMII) {
-+              sgm_mode = SGMII_IF_MODE_SGMII;
-+              if (phylink_autoneg_inband(mode)) {
-+                      sgm_mode |= SGMII_REMOTE_FAULT_DIS |
-+                                  SGMII_SPEED_DUPLEX_AN;
-+                      use_an = true;
-+              } else {
-+                      use_an = false;
-+              }
-+      } else if (phylink_autoneg_inband(mode)) {
-+              /* 1000base-X or 2500base-X autoneg */
-+              sgm_mode = SGMII_REMOTE_FAULT_DIS;
-+              use_an = linkmode_test_bit(ETHTOOL_LINK_MODE_Autoneg_BIT,
-+                                         advertising);
-+      } else {
-+              /* 1000base-X or 2500base-X without autoneg */
-+              sgm_mode = 0;
-+              use_an = false;
-+      }
-+
-+      if (use_an)
-+              bmcr = BMCR_ANENABLE;
-+      else
-+              bmcr = 0;
-+
-+      if (mpcs->interface != interface) {
-+              link_timer = phylink_get_link_timer_ns(interface);
-+              if (link_timer < 0)
-+                      return link_timer;
-+
-+              /* PHYA power down */
-+              regmap_set_bits(mpcs->regmap, SGMSYS_QPHY_PWR_STATE_CTRL,
-+                              SGMII_PHYA_PWD);
-+
-+              /* Reset SGMII PCS state */
-+              regmap_set_bits(mpcs->regmap, SGMSYS_RESERVED_0,
-+                              SGMII_SW_RESET);
-+
-+              if (mpcs->flags & MTK_SGMII_FLAG_PN_SWAP)
-+                      regmap_update_bits(mpcs->regmap, SGMSYS_QPHY_WRAP_CTRL,
-+                                         SGMII_PN_SWAP_MASK,
-+                                         SGMII_PN_SWAP_TX_RX);
-+
-+              if (interface == PHY_INTERFACE_MODE_2500BASEX)
-+                      rgc3 = SGMII_PHY_SPEED_3_125G;
-+              else
-+                      rgc3 = SGMII_PHY_SPEED_1_25G;
-+
-+              /* Configure the underlying interface speed */
-+              regmap_update_bits(mpcs->regmap, mpcs->ana_rgc3,
-+                                 SGMII_PHY_SPEED_MASK, rgc3);
-+
-+              /* Setup the link timer */
-+              regmap_write(mpcs->regmap, SGMSYS_PCS_LINK_TIMER,
-+                           SGMII_LINK_TIMER_VAL(link_timer));
-+
-+              mpcs->interface = interface;
-+              mode_changed = true;
-+      }
-+
-+      /* Update the advertisement, noting whether it has changed */
-+      regmap_update_bits_check(mpcs->regmap, SGMSYS_PCS_ADVERTISE,
-+                               SGMII_ADVERTISE, advertise, &changed);
-+
-+      /* Update the sgmsys mode register */
-+      regmap_update_bits(mpcs->regmap, SGMSYS_SGMII_MODE,
-+                         SGMII_REMOTE_FAULT_DIS | SGMII_SPEED_DUPLEX_AN |
-+                         SGMII_IF_MODE_SGMII, sgm_mode);
-+
-+      /* Update the BMCR */
-+      regmap_update_bits(mpcs->regmap, SGMSYS_PCS_CONTROL_1,
-+                         BMCR_ANENABLE, bmcr);
-+
-+      /* Release PHYA power down state
-+       * Only removing bit SGMII_PHYA_PWD isn't enough.
-+       * There are cases when the SGMII_PHYA_PWD register contains 0x9 which
-+       * prevents SGMII from working. The SGMII still shows link but no traffic
-+       * can flow. Writing 0x0 to the PHYA_PWD register fix the issue. 0x0 was
-+       * taken from a good working state of the SGMII interface.
-+       * Unknown how much the QPHY needs but it is racy without a sleep.
-+       * Tested on mt7622 & mt7986.
-+       */
-+      usleep_range(50, 100);
-+      regmap_write(mpcs->regmap, SGMSYS_QPHY_PWR_STATE_CTRL, 0);
-+
-+      return changed || mode_changed;
-+}
-+
-+static void mtk_pcs_lynxi_restart_an(struct phylink_pcs *pcs)
-+{
-+      struct mtk_pcs_lynxi *mpcs = pcs_to_mtk_pcs_lynxi(pcs);
-+
-+      regmap_set_bits(mpcs->regmap, SGMSYS_PCS_CONTROL_1, BMCR_ANRESTART);
-+}
-+
-+static void mtk_pcs_lynxi_link_up(struct phylink_pcs *pcs, unsigned int mode,
-+                                phy_interface_t interface, int speed,
-+                                int duplex)
-+{
-+      struct mtk_pcs_lynxi *mpcs = pcs_to_mtk_pcs_lynxi(pcs);
-+      unsigned int sgm_mode;
-+
-+      if (!phylink_autoneg_inband(mode)) {
-+              /* Force the speed and duplex setting */
-+              if (speed == SPEED_10)
-+                      sgm_mode = SGMII_SPEED_10;
-+              else if (speed == SPEED_100)
-+                      sgm_mode = SGMII_SPEED_100;
-+              else
-+                      sgm_mode = SGMII_SPEED_1000;
-+
-+              if (duplex != DUPLEX_FULL)
-+                      sgm_mode |= SGMII_DUPLEX_HALF;
-+
-+              regmap_update_bits(mpcs->regmap, SGMSYS_SGMII_MODE,
-+                                 SGMII_DUPLEX_HALF | SGMII_SPEED_MASK,
-+                                 sgm_mode);
-+      }
-+}
-+
-+static const struct phylink_pcs_ops mtk_pcs_lynxi_ops = {
-+      .pcs_get_state = mtk_pcs_lynxi_get_state,
-+      .pcs_config = mtk_pcs_lynxi_config,
-+      .pcs_an_restart = mtk_pcs_lynxi_restart_an,
-+      .pcs_link_up = mtk_pcs_lynxi_link_up,
-+};
-+
-+struct phylink_pcs *mtk_pcs_lynxi_create(struct device *dev,
-+                                       struct regmap *regmap, u32 ana_rgc3,
-+                                       u32 flags)
-+{
-+      struct mtk_pcs_lynxi *mpcs;
-+      u32 id, ver;
-+      int ret;
-+
-+      ret = regmap_read(regmap, SGMSYS_PCS_DEVICE_ID, &id);
-+      if (ret < 0)
-+              return NULL;
-+
-+      if (id != SGMII_LYNXI_DEV_ID) {
-+              dev_err(dev, "unknown PCS device id %08x\n", id);
-+              return NULL;
-+      }
-+
-+      ret = regmap_read(regmap, SGMSYS_PCS_SCRATCH, &ver);
-+      if (ret < 0)
-+              return NULL;
-+
-+      ver = FIELD_GET(SGMII_DEV_VERSION, ver);
-+      if (ver != 0x1) {
-+              dev_err(dev, "unknown PCS device version %04x\n", ver);
-+              return NULL;
-+      }
-+
-+      dev_dbg(dev, "MediaTek LynxI SGMII PCS (id 0x%08x, ver 0x%04x)\n", id,
-+              ver);
-+
-+      mpcs = kzalloc(sizeof(*mpcs), GFP_KERNEL);
-+      if (!mpcs)
-+              return NULL;
-+
-+      mpcs->ana_rgc3 = ana_rgc3;
-+      mpcs->regmap = regmap;
-+      mpcs->flags = flags;
-+      mpcs->pcs.ops = &mtk_pcs_lynxi_ops;
-+      mpcs->pcs.poll = true;
-+      mpcs->interface = PHY_INTERFACE_MODE_NA;
-+
-+      return &mpcs->pcs;
-+}
-+EXPORT_SYMBOL(mtk_pcs_lynxi_create);
-+
-+void mtk_pcs_lynxi_destroy(struct phylink_pcs *pcs)
-+{
-+      if (!pcs)
-+              return;
-+
-+      kfree(pcs_to_mtk_pcs_lynxi(pcs));
-+}
-+EXPORT_SYMBOL(mtk_pcs_lynxi_destroy);
-+
-+MODULE_LICENSE("GPL");
---- /dev/null
-+++ b/include/linux/pcs/pcs-mtk-lynxi.h
-@@ -0,0 +1,13 @@
-+/* SPDX-License-Identifier: GPL-2.0 */
-+#ifndef __LINUX_PCS_MTK_LYNXI_H
-+#define __LINUX_PCS_MTK_LYNXI_H
-+
-+#include <linux/phylink.h>
-+#include <linux/regmap.h>
-+
-+#define MTK_SGMII_FLAG_PN_SWAP BIT(0)
-+struct phylink_pcs *mtk_pcs_lynxi_create(struct device *dev,
-+                                       struct regmap *regmap,
-+                                       u32 ana_rgc3, u32 flags);
-+void mtk_pcs_lynxi_destroy(struct phylink_pcs *pcs);
-+#endif
diff --git a/target/linux/generic/backport-5.15/708-01-v5.16-net-mvneta-Delete-unused-variable.patch b/target/linux/generic/backport-5.15/708-01-v5.16-net-mvneta-Delete-unused-variable.patch
deleted file mode 100644 (file)
index 421563e..0000000
+++ /dev/null
@@ -1,62 +0,0 @@
-From 43ed6fff01333868a1d0e19876f67c22d9939952 Mon Sep 17 00:00:00 2001
-From: Yuval Shaia <[email protected]>
-Date: Wed, 13 Oct 2021 09:49:21 +0300
-Subject: [PATCH] net: mvneta: Delete unused variable
-
-The variable pp is not in use - delete it.
-
-Signed-off-by: Yuval Shaia <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- drivers/net/ethernet/marvell/mvneta.c | 11 +++++------
- 1 file changed, 5 insertions(+), 6 deletions(-)
-
---- a/drivers/net/ethernet/marvell/mvneta.c
-+++ b/drivers/net/ethernet/marvell/mvneta.c
-@@ -1914,7 +1914,7 @@ static int mvneta_rx_refill(struct mvnet
- }
- /* Handle tx checksum */
--static u32 mvneta_skb_tx_csum(struct mvneta_port *pp, struct sk_buff *skb)
-+static u32 mvneta_skb_tx_csum(struct sk_buff *skb)
- {
-       if (skb->ip_summed == CHECKSUM_PARTIAL) {
-               int ip_hdr_len = 0;
-@@ -2595,8 +2595,7 @@ err_drop_frame:
- }
- static inline void
--mvneta_tso_put_hdr(struct sk_buff *skb,
--                 struct mvneta_port *pp, struct mvneta_tx_queue *txq)
-+mvneta_tso_put_hdr(struct sk_buff *skb, struct mvneta_tx_queue *txq)
- {
-       int hdr_len = skb_transport_offset(skb) + tcp_hdrlen(skb);
-       struct mvneta_tx_buf *buf = &txq->buf[txq->txq_put_index];
-@@ -2604,7 +2603,7 @@ mvneta_tso_put_hdr(struct sk_buff *skb,
-       tx_desc = mvneta_txq_next_desc_get(txq);
-       tx_desc->data_size = hdr_len;
--      tx_desc->command = mvneta_skb_tx_csum(pp, skb);
-+      tx_desc->command = mvneta_skb_tx_csum(skb);
-       tx_desc->command |= MVNETA_TXD_F_DESC;
-       tx_desc->buf_phys_addr = txq->tso_hdrs_phys +
-                                txq->txq_put_index * TSO_HEADER_SIZE;
-@@ -2681,7 +2680,7 @@ static int mvneta_tx_tso(struct sk_buff
-               hdr = txq->tso_hdrs + txq->txq_put_index * TSO_HEADER_SIZE;
-               tso_build_hdr(skb, hdr, &tso, data_left, total_len == 0);
--              mvneta_tso_put_hdr(skb, pp, txq);
-+              mvneta_tso_put_hdr(skb, txq);
-               while (data_left > 0) {
-                       int size;
-@@ -2799,7 +2798,7 @@ static netdev_tx_t mvneta_tx(struct sk_b
-       /* Get a descriptor for the first part of the packet */
-       tx_desc = mvneta_txq_next_desc_get(txq);
--      tx_cmd = mvneta_skb_tx_csum(pp, skb);
-+      tx_cmd = mvneta_skb_tx_csum(skb);
-       tx_desc->data_size = skb_headlen(skb);
diff --git a/target/linux/generic/backport-5.15/708-02-v6.3-net-mvneta-fix-potential-double-frees-in-mvneta_txq_.patch b/target/linux/generic/backport-5.15/708-02-v6.3-net-mvneta-fix-potential-double-frees-in-mvneta_txq_.patch
deleted file mode 100644 (file)
index a16e68e..0000000
+++ /dev/null
@@ -1,37 +0,0 @@
-From 0cf39c6543469aae4a30cba354243125514ed568 Mon Sep 17 00:00:00 2001
-From: "Russell King (Oracle)" <[email protected]>
-Date: Wed, 29 Mar 2023 13:11:17 +0100
-Subject: [PATCH] net: mvneta: fix potential double-frees in
- mvneta_txq_sw_deinit()
-
-Reported on the Turris forum, mvneta provokes kernel warnings in the
-architecture DMA mapping code when mvneta_setup_txqs() fails to
-allocate memory. This happens because when mvneta_cleanup_txqs() is
-called in the mvneta_stop() path, we leave pointers in the structure
-that have been freed.
-
-Then on mvneta_open(), we call mvneta_setup_txqs(), which starts
-allocating memory. On memory allocation failure, mvneta_cleanup_txqs()
-will walk all the queues freeing any non-NULL pointers - which includes
-pointers that were previously freed in mvneta_stop().
-
-Fix this by setting these pointers to NULL to prevent double-freeing
-of the same memory.
-
-Link: https://forum.turris.cz/t/random-kernel-exceptions-on-hbl-tos-7-0/18865/8
-Signed-off-by: Russell King (Oracle) <[email protected]>
----
- drivers/net/ethernet/marvell/mvneta.c | 2 ++
- 1 file changed, 2 insertions(+)
-
---- a/drivers/net/ethernet/marvell/mvneta.c
-+++ b/drivers/net/ethernet/marvell/mvneta.c
-@@ -3481,6 +3481,8 @@ static void mvneta_txq_sw_deinit(struct
-       netdev_tx_reset_queue(nq);
-+      txq->buf               = NULL;
-+      txq->tso_hdrs          = NULL;
-       txq->descs             = NULL;
-       txq->last_desc         = 0;
-       txq->next_desc_to_proc = 0;
diff --git a/target/linux/generic/backport-5.15/710-v6.0-net-ethernet-mtk_eth_soc-fix-hw-hash-reporting-for-M.patch b/target/linux/generic/backport-5.15/710-v6.0-net-ethernet-mtk_eth_soc-fix-hw-hash-reporting-for-M.patch
deleted file mode 100644 (file)
index a3842d3..0000000
+++ /dev/null
@@ -1,74 +0,0 @@
-From 0cf731f9ebb5bf6f252055bebf4463a5c0bd490b Mon Sep 17 00:00:00 2001
-From: Lorenzo Bianconi <[email protected]>
-Date: Tue, 23 Aug 2022 14:24:07 +0200
-Subject: [PATCH] net: ethernet: mtk_eth_soc: fix hw hash reporting for
- MTK_NETSYS_V2
-
-Properly report hw rx hash for mt7986 chipset accroding to the new dma
-descriptor layout.
-
-Fixes: 197c9e9b17b11 ("net: ethernet: mtk_eth_soc: introduce support for mt7986 chipset")
-Signed-off-by: Lorenzo Bianconi <[email protected]>
-Link: https://lore.kernel.org/r/091394ea4e705fbb35f828011d98d0ba33808f69.1661257293.git.lorenzo@kernel.org
-Signed-off-by: Paolo Abeni <[email protected]>
----
- drivers/net/ethernet/mediatek/mtk_eth_soc.c | 22 +++++++++++----------
- drivers/net/ethernet/mediatek/mtk_eth_soc.h |  5 +++++
- 2 files changed, 17 insertions(+), 10 deletions(-)
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-@@ -1845,10 +1845,19 @@ static int mtk_poll_rx(struct napi_struc
-               skb->dev = netdev;
-               bytes += skb->len;
--              if (MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2))
-+              if (MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2)) {
-+                      hash = trxd.rxd5 & MTK_RXD5_FOE_ENTRY;
-+                      if (hash != MTK_RXD5_FOE_ENTRY)
-+                              skb_set_hash(skb, jhash_1word(hash, 0),
-+                                           PKT_HASH_TYPE_L4);
-                       rxdcsum = &trxd.rxd3;
--              else
-+              } else {
-+                      hash = trxd.rxd4 & MTK_RXD4_FOE_ENTRY;
-+                      if (hash != MTK_RXD4_FOE_ENTRY)
-+                              skb_set_hash(skb, jhash_1word(hash, 0),
-+                                           PKT_HASH_TYPE_L4);
-                       rxdcsum = &trxd.rxd4;
-+              }
-               if (*rxdcsum & eth->soc->txrx.rx_dma_l4_valid)
-                       skb->ip_summed = CHECKSUM_UNNECESSARY;
-@@ -1856,16 +1865,9 @@ static int mtk_poll_rx(struct napi_struc
-                       skb_checksum_none_assert(skb);
-               skb->protocol = eth_type_trans(skb, netdev);
--              hash = trxd.rxd4 & MTK_RXD4_FOE_ENTRY;
--              if (hash != MTK_RXD4_FOE_ENTRY) {
--                      hash = jhash_1word(hash, 0);
--                      skb_set_hash(skb, hash, PKT_HASH_TYPE_L4);
--              }
--
-               reason = FIELD_GET(MTK_RXD4_PPE_CPU_REASON, trxd.rxd4);
-               if (reason == MTK_PPE_CPU_REASON_HIT_UNBIND_RATE_REACHED)
--                      mtk_ppe_check_skb(eth->ppe, skb,
--                                        trxd.rxd4 & MTK_RXD4_FOE_ENTRY);
-+                      mtk_ppe_check_skb(eth->ppe, skb, hash);
-               if (netdev->features & NETIF_F_HW_VLAN_CTAG_RX) {
-                       if (MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2)) {
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-@@ -314,6 +314,11 @@
- #define RX_DMA_L4_VALID_PDMA  BIT(30)         /* when PDMA is used */
- #define RX_DMA_SPECIAL_TAG    BIT(22)
-+/* PDMA descriptor rxd5 */
-+#define MTK_RXD5_FOE_ENTRY    GENMASK(14, 0)
-+#define MTK_RXD5_PPE_CPU_REASON       GENMASK(22, 18)
-+#define MTK_RXD5_SRC_PORT     GENMASK(29, 26)
-+
- #define RX_DMA_GET_SPORT(x)   (((x) >> 19) & 0xf)
- #define RX_DMA_GET_SPORT_V2(x)        (((x) >> 26) & 0x7)
diff --git a/target/linux/generic/backport-5.15/711-v6.0-01-net-ethernet-mtk_eth_soc-fix-off-by-one-check-of-ARR.patch b/target/linux/generic/backport-5.15/711-v6.0-01-net-ethernet-mtk_eth_soc-fix-off-by-one-check-of-ARR.patch
deleted file mode 100644 (file)
index 0de8ab4..0000000
+++ /dev/null
@@ -1,31 +0,0 @@
-From: Tom Rix <[email protected]>
-Date: Sat, 16 Jul 2022 17:46:54 -0400
-Subject: [PATCH] net: ethernet: mtk_eth_soc: fix off by one check of
- ARRAY_SIZE
-
-In mtk_wed_tx_ring_setup(.., int idx, ..), idx is used as an index here
-  struct mtk_wed_ring *ring = &dev->tx_ring[idx];
-
-The bounds of idx are checked here
-  BUG_ON(idx > ARRAY_SIZE(dev->tx_ring));
-
-If idx is the size of the array, it will pass this check and overflow.
-So change the check to >= .
-
-Fixes: 804775dfc288 ("net: ethernet: mtk_eth_soc: add support for Wireless Ethernet Dispatch (WED)")
-Signed-off-by: Tom Rix <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Jakub Kicinski <[email protected]>
----
-
---- a/drivers/net/ethernet/mediatek/mtk_wed.c
-+++ b/drivers/net/ethernet/mediatek/mtk_wed.c
-@@ -651,7 +651,7 @@ mtk_wed_tx_ring_setup(struct mtk_wed_dev
-        * WDMA RX.
-        */
--      BUG_ON(idx > ARRAY_SIZE(dev->tx_ring));
-+      BUG_ON(idx >= ARRAY_SIZE(dev->tx_ring));
-       if (mtk_wed_ring_alloc(dev, ring, MTK_WED_TX_RING_SIZE))
-               return -ENOMEM;
diff --git a/target/linux/generic/backport-5.15/711-v6.0-02-net-ethernet-mtk_ppe-fix-possible-NULL-pointer-deref.patch b/target/linux/generic/backport-5.15/711-v6.0-02-net-ethernet-mtk_ppe-fix-possible-NULL-pointer-deref.patch
deleted file mode 100644 (file)
index fc6e246..0000000
+++ /dev/null
@@ -1,27 +0,0 @@
-From: Lorenzo Bianconi <[email protected]>
-Date: Mon, 18 Jul 2022 11:51:53 +0200
-Subject: [PATCH] net: ethernet: mtk_ppe: fix possible NULL pointer dereference
- in mtk_flow_get_wdma_info
-
-odev pointer can be NULL in mtk_flow_offload_replace routine according
-to the flower action rules. Fix possible NULL pointer dereference in
-mtk_flow_get_wdma_info.
-
-Fixes: a333215e10cb5 ("net: ethernet: mtk_eth_soc: implement flow offloading to WED devices")
-Signed-off-by: Lorenzo Bianconi <[email protected]>
-Link: https://lore.kernel.org/r/4e1685bc4976e21e364055f6bee86261f8f9ee93.1658137753.git.lorenzo@kernel.org
-Signed-off-by: Jakub Kicinski <[email protected]>
----
-
---- a/drivers/net/ethernet/mediatek/mtk_ppe_offload.c
-+++ b/drivers/net/ethernet/mediatek/mtk_ppe_offload.c
-@@ -93,6 +93,9 @@ mtk_flow_get_wdma_info(struct net_device
-       };
-       struct net_device_path path = {};
-+      if (!ctx.dev)
-+              return -ENODEV;
-+
-       memcpy(ctx.daddr, addr, sizeof(ctx.daddr));
-       if (!IS_ENABLED(CONFIG_NET_MEDIATEK_SOC_WED))
diff --git a/target/linux/generic/backport-5.15/711-v6.0-03-net-ethernet-mtk-ppe-fix-traffic-offload-with-bridge.patch b/target/linux/generic/backport-5.15/711-v6.0-03-net-ethernet-mtk-ppe-fix-traffic-offload-with-bridge.patch
deleted file mode 100644 (file)
index c072015..0000000
+++ /dev/null
@@ -1,64 +0,0 @@
-From: Lorenzo Bianconi <[email protected]>
-Date: Fri, 22 Jul 2022 09:06:19 +0200
-Subject: [PATCH] net: ethernet: mtk-ppe: fix traffic offload with bridged wlan
-
-A typical flow offload scenario for OpenWrt users is routed traffic
-received by the wan interface that is redirected to a wlan device
-belonging to the lan bridge. Current implementation fails to
-fill wdma offload info in mtk_flow_get_wdma_info() since odev device is
-the local bridge. Fix the issue running dev_fill_forward_path routine in
-mtk_flow_get_wdma_info in order to identify the wlan device.
-
-Tested-by: Paolo Valerio <[email protected]>
-Signed-off-by: Lorenzo Bianconi <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
-
---- a/drivers/net/ethernet/mediatek/mtk_ppe_offload.c
-+++ b/drivers/net/ethernet/mediatek/mtk_ppe_offload.c
-@@ -88,32 +88,28 @@ mtk_flow_offload_mangle_eth(const struct
- static int
- mtk_flow_get_wdma_info(struct net_device *dev, const u8 *addr, struct mtk_wdma_info *info)
- {
--      struct net_device_path_ctx ctx = {
--              .dev = dev,
--      };
--      struct net_device_path path = {};
-+      struct net_device_path_stack stack;
-+      struct net_device_path *path;
-+      int err;
--      if (!ctx.dev)
-+      if (!dev)
-               return -ENODEV;
--      memcpy(ctx.daddr, addr, sizeof(ctx.daddr));
--
-       if (!IS_ENABLED(CONFIG_NET_MEDIATEK_SOC_WED))
-               return -1;
--      if (!dev->netdev_ops->ndo_fill_forward_path)
--              return -1;
--
--      if (dev->netdev_ops->ndo_fill_forward_path(&ctx, &path))
--              return -1;
-+      err = dev_fill_forward_path(dev, addr, &stack);
-+      if (err)
-+              return err;
--      if (path.type != DEV_PATH_MTK_WDMA)
-+      path = &stack.path[stack.num_paths - 1];
-+      if (path->type != DEV_PATH_MTK_WDMA)
-               return -1;
--      info->wdma_idx = path.mtk_wdma.wdma_idx;
--      info->queue = path.mtk_wdma.queue;
--      info->bss = path.mtk_wdma.bss;
--      info->wcid = path.mtk_wdma.wcid;
-+      info->wdma_idx = path->mtk_wdma.wdma_idx;
-+      info->queue = path->mtk_wdma.queue;
-+      info->bss = path->mtk_wdma.bss;
-+      info->wcid = path->mtk_wdma.wcid;
-       return 0;
- }
diff --git a/target/linux/generic/backport-5.15/711-v6.0-04-net-ethernet-mtk_eth_soc-remove-mtk_foe_entry_timest.patch b/target/linux/generic/backport-5.15/711-v6.0-04-net-ethernet-mtk_eth_soc-remove-mtk_foe_entry_timest.patch
deleted file mode 100644 (file)
index 3c28e83..0000000
+++ /dev/null
@@ -1,33 +0,0 @@
-From c9daab322313087afde8c46f41df3c628410ae20 Mon Sep 17 00:00:00 2001
-From: Lorenzo Bianconi <[email protected]>
-Date: Mon, 5 Sep 2022 14:46:01 +0200
-Subject: [PATCH] net: ethernet: mtk_eth_soc: remove mtk_foe_entry_timestamp
-
-Get rid of mtk_foe_entry_timestamp routine since it is no longer used.
-
-Signed-off-by: Lorenzo Bianconi <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/ethernet/mediatek/mtk_ppe.h | 11 -----------
- 1 file changed, 11 deletions(-)
-
---- a/drivers/net/ethernet/mediatek/mtk_ppe.h
-+++ b/drivers/net/ethernet/mediatek/mtk_ppe.h
-@@ -302,17 +302,6 @@ mtk_ppe_check_skb(struct mtk_ppe *ppe, s
-       __mtk_ppe_check_skb(ppe, skb, hash);
- }
--static inline int
--mtk_foe_entry_timestamp(struct mtk_ppe *ppe, u16 hash)
--{
--      u32 ib1 = READ_ONCE(ppe->foe_table[hash].ib1);
--
--      if (FIELD_GET(MTK_FOE_IB1_STATE, ib1) != MTK_FOE_STATE_BIND)
--              return -1;
--
--      return FIELD_GET(MTK_FOE_IB1_BIND_TIMESTAMP, ib1);
--}
--
- int mtk_foe_entry_prepare(struct mtk_foe_entry *entry, int type, int l4proto,
-                         u8 pse_port, u8 *src_mac, u8 *dest_mac);
- int mtk_foe_entry_set_pse_port(struct mtk_foe_entry *entry, u8 port);
diff --git a/target/linux/generic/backport-5.15/712-v6.0-net-ethernet-mtk_eth_soc-enable-XDP-support-just-for.patch b/target/linux/generic/backport-5.15/712-v6.0-net-ethernet-mtk_eth_soc-enable-XDP-support-just-for.patch
deleted file mode 100644 (file)
index f4eb030..0000000
+++ /dev/null
@@ -1,35 +0,0 @@
-From 5e69163d3b9931098922b3fc2f8e786af8c1f37e Mon Sep 17 00:00:00 2001
-From: Lorenzo Bianconi <[email protected]>
-Date: Tue, 13 Sep 2022 15:03:05 +0200
-Subject: [PATCH] net: ethernet: mtk_eth_soc: enable XDP support just for
- MT7986 SoC
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-Disable page_pool/XDP support for MT7621 SoC in order fix a regression
-introduce adding XDP for MT7986 SoC. There is no a real use case for XDP
-on MT7621 since it is a low-end cpu. Moreover this patch reduces the
-memory footprint.
-
-Tested-by: Sergio Paracuellos <[email protected]>
-Tested-by: Arınç ÜNAL <[email protected]>
-Fixes: 23233e577ef9 ("net: ethernet: mtk_eth_soc: rely on page_pool for single page buffers")
-Signed-off-by: Lorenzo Bianconi <[email protected]>
-Link: https://lore.kernel.org/r/2bf31e27b888c43228b0d84dd2ef5033338269e2.1663074002.git.lorenzo@kernel.org
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- drivers/net/ethernet/mediatek/mtk_eth_soc.c | 2 +-
- 1 file changed, 1 insertion(+), 1 deletion(-)
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-@@ -1412,7 +1412,7 @@ static void mtk_update_rx_cpu_idx(struct
- static bool mtk_page_pool_enabled(struct mtk_eth *eth)
- {
--      return !eth->hwlro;
-+      return MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2);
- }
- static struct page_pool *mtk_create_page_pool(struct mtk_eth *eth,
diff --git a/target/linux/generic/backport-5.15/713-v6.0-net-ethernet-mtk_eth_soc-move-gdma_to_ppe-and-ppe_ba.patch b/target/linux/generic/backport-5.15/713-v6.0-net-ethernet-mtk_eth_soc-move-gdma_to_ppe-and-ppe_ba.patch
deleted file mode 100644 (file)
index be6da9b..0000000
+++ /dev/null
@@ -1,127 +0,0 @@
-From patchwork Thu Sep  8 19:33:38 2022
-Content-Type: text/plain; charset="utf-8"
-MIME-Version: 1.0
-Content-Transfer-Encoding: 7bit
-X-Patchwork-Submitter: Lorenzo Bianconi <[email protected]>
-X-Patchwork-Id: 12970556
-X-Patchwork-Delegate: [email protected]
-From: Lorenzo Bianconi <[email protected]>
-Subject: [PATCH net-next 03/12] net: ethernet: mtk_eth_soc: move gdma_to_ppe
- and ppe_base definitions in mtk register map
-Date: Thu,  8 Sep 2022 21:33:37 +0200
-Message-Id: 
- <95938fc9cbe0223714be2658a49ca58e9baace00.1662661555.git.lorenzo@kernel.org>
-X-Mailer: git-send-email 2.37.3
-In-Reply-To: <[email protected]>
-References: <[email protected]>
-MIME-Version: 1.0
-Precedence: bulk
-List-ID: <netdev.vger.kernel.org>
-X-Mailing-List: [email protected]
-X-Patchwork-Delegate: [email protected]
-
-This is a preliminary patch to introduce mt7986 hw packet engine.
-
-Signed-off-by: Lorenzo Bianconi <[email protected]>
----
- drivers/net/ethernet/mediatek/mtk_eth_soc.c | 15 +++++++++++----
- drivers/net/ethernet/mediatek/mtk_eth_soc.h |  3 ++-
- drivers/net/ethernet/mediatek/mtk_ppe.h     |  2 --
- 3 files changed, 13 insertions(+), 7 deletions(-)
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-@@ -73,6 +73,8 @@ static const struct mtk_reg_map mtk_reg_
-               .fq_blen        = 0x1b2c,
-       },
-       .gdm1_cnt               = 0x2400,
-+      .gdma_to_ppe0           = 0x4444,
-+      .ppe_base               = 0x0c00,
- };
- static const struct mtk_reg_map mt7628_reg_map = {
-@@ -126,6 +128,8 @@ static const struct mtk_reg_map mt7986_r
-               .fq_blen        = 0x472c,
-       },
-       .gdm1_cnt               = 0x1c00,
-+      .gdma_to_ppe0           = 0x3333,
-+      .ppe_base               = 0x2000,
- };
- /* strings used by ethtool */
-@@ -2927,6 +2931,7 @@ static int mtk_open(struct net_device *d
-       /* we run 2 netdevs on the same dma ring so we only bring it up once */
-       if (!refcount_read(&eth->dma_refcnt)) {
-+              const struct mtk_soc_data *soc = eth->soc;
-               u32 gdm_config = MTK_GDMA_TO_PDMA;
-               int err;
-@@ -2936,15 +2941,15 @@ static int mtk_open(struct net_device *d
-                       return err;
-               }
--              if (eth->soc->offload_version && mtk_ppe_start(eth->ppe) == 0)
--                      gdm_config = MTK_GDMA_TO_PPE;
-+              if (soc->offload_version && mtk_ppe_start(eth->ppe) == 0)
-+                      gdm_config = soc->reg_map->gdma_to_ppe0;
-               mtk_gdm_config(eth, gdm_config);
-               napi_enable(&eth->tx_napi);
-               napi_enable(&eth->rx_napi);
-               mtk_tx_irq_enable(eth, MTK_TX_DONE_INT);
--              mtk_rx_irq_enable(eth, eth->soc->txrx.rx_irq_done_mask);
-+              mtk_rx_irq_enable(eth, soc->txrx.rx_irq_done_mask);
-               refcount_set(&eth->dma_refcnt, 1);
-       }
-       else
-@@ -4043,7 +4048,9 @@ static int mtk_probe(struct platform_dev
-       }
-       if (eth->soc->offload_version) {
--              eth->ppe = mtk_ppe_init(eth, eth->base + MTK_ETH_PPE_BASE, 2);
-+              u32 ppe_addr = eth->soc->reg_map->ppe_base;
-+
-+              eth->ppe = mtk_ppe_init(eth, eth->base + ppe_addr, 2);
-               if (!eth->ppe) {
-                       err = -ENOMEM;
-                       goto err_free_dev;
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-@@ -105,7 +105,6 @@
- #define MTK_GDMA_TCS_EN               BIT(21)
- #define MTK_GDMA_UCS_EN               BIT(20)
- #define MTK_GDMA_TO_PDMA      0x0
--#define MTK_GDMA_TO_PPE               0x4444
- #define MTK_GDMA_DROP_ALL       0x7777
- /* Unicast Filter MAC Address Register - Low */
-@@ -953,6 +952,8 @@ struct mtk_reg_map {
-               u32     fq_blen;        /* fq free page buffer length */
-       } qdma;
-       u32     gdm1_cnt;
-+      u32     gdma_to_ppe0;
-+      u32     ppe_base;
- };
- /* struct mtk_eth_data -      This is the structure holding all differences
---- a/drivers/net/ethernet/mediatek/mtk_ppe.h
-+++ b/drivers/net/ethernet/mediatek/mtk_ppe.h
-@@ -8,8 +8,6 @@
- #include <linux/bitfield.h>
- #include <linux/rhashtable.h>
--#define MTK_ETH_PPE_BASE              0xc00
--
- #define MTK_PPE_ENTRIES_SHIFT         3
- #define MTK_PPE_ENTRIES                       (1024 << MTK_PPE_ENTRIES_SHIFT)
- #define MTK_PPE_HASH_MASK             (MTK_PPE_ENTRIES - 1)
diff --git a/target/linux/generic/backport-5.15/714-v6.0-net-ethernet-mtk_eth_soc-move-ppe-table-hash-offset-.patch b/target/linux/generic/backport-5.15/714-v6.0-net-ethernet-mtk_eth_soc-move-ppe-table-hash-offset-.patch
deleted file mode 100644 (file)
index 76f954f..0000000
+++ /dev/null
@@ -1,199 +0,0 @@
-From patchwork Thu Sep  8 19:33:38 2022
-Content-Type: text/plain; charset="utf-8"
-MIME-Version: 1.0
-Content-Transfer-Encoding: 7bit
-X-Patchwork-Submitter: Lorenzo Bianconi <[email protected]>
-X-Patchwork-Id: 12970557
-X-Patchwork-Delegate: [email protected]
-From: Lorenzo Bianconi <[email protected]>
-Subject: [PATCH net-next 04/12] net: ethernet: mtk_eth_soc: move ppe table
- hash offset to mtk_soc_data structure
-Date: Thu,  8 Sep 2022 21:33:38 +0200
-Message-Id: 
- <cc263ffeaa3e1d7314e36a4f941e96d38e41a6bf.1662661555.git.lorenzo@kernel.org>
-X-Mailer: git-send-email 2.37.3
-In-Reply-To: <[email protected]>
-References: <[email protected]>
-MIME-Version: 1.0
-Precedence: bulk
-List-ID: <netdev.vger.kernel.org>
-X-Mailing-List: [email protected]
-X-Patchwork-Delegate: [email protected]
-
-This is a preliminary patch to introduce mt7986 hw packet engine.
-
-Co-developed-by: Bo Jiao <[email protected]>
-Signed-off-by: Bo Jiao <[email protected]>
-Co-developed-by: Sujuan Chen <[email protected]>
-Signed-off-by: Sujuan Chen <[email protected]>
-Signed-off-by: Lorenzo Bianconi <[email protected]>
----
- drivers/net/ethernet/mediatek/mtk_eth_soc.c |  4 ++++
- drivers/net/ethernet/mediatek/mtk_eth_soc.h |  2 ++
- drivers/net/ethernet/mediatek/mtk_ppe.c     | 24 +++++++++++++++------
- drivers/net/ethernet/mediatek/mtk_ppe.h     |  2 +-
- 4 files changed, 25 insertions(+), 7 deletions(-)
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-@@ -4146,6 +4146,7 @@ static const struct mtk_soc_data mt7621_
-       .required_clks = MT7621_CLKS_BITMAP,
-       .required_pctl = false,
-       .offload_version = 2,
-+      .hash_offset = 2,
-       .txrx = {
-               .txd_size = sizeof(struct mtk_tx_dma),
-               .rxd_size = sizeof(struct mtk_rx_dma),
-@@ -4164,6 +4165,7 @@ static const struct mtk_soc_data mt7622_
-       .required_clks = MT7622_CLKS_BITMAP,
-       .required_pctl = false,
-       .offload_version = 2,
-+      .hash_offset = 2,
-       .txrx = {
-               .txd_size = sizeof(struct mtk_tx_dma),
-               .rxd_size = sizeof(struct mtk_rx_dma),
-@@ -4181,6 +4183,7 @@ static const struct mtk_soc_data mt7623_
-       .required_clks = MT7623_CLKS_BITMAP,
-       .required_pctl = true,
-       .offload_version = 2,
-+      .hash_offset = 2,
-       .txrx = {
-               .txd_size = sizeof(struct mtk_tx_dma),
-               .rxd_size = sizeof(struct mtk_rx_dma),
-@@ -4214,6 +4217,7 @@ static const struct mtk_soc_data mt7986_
-       .caps = MT7986_CAPS,
-       .required_clks = MT7986_CLKS_BITMAP,
-       .required_pctl = false,
-+      .hash_offset = 4,
-       .txrx = {
-               .txd_size = sizeof(struct mtk_tx_dma_v2),
-               .rxd_size = sizeof(struct mtk_rx_dma_v2),
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-@@ -967,6 +967,7 @@ struct mtk_reg_map {
-  *                            the target SoC
-  * @required_pctl             A bool value to show whether the SoC requires
-  *                            the extra setup for those pins used by GMAC.
-+ * @hash_offset                       Flow table hash offset.
-  * @txd_size                  Tx DMA descriptor size.
-  * @rxd_size                  Rx DMA descriptor size.
-  * @rx_irq_done_mask          Rx irq done register mask.
-@@ -981,6 +982,7 @@ struct mtk_soc_data {
-       u32             required_clks;
-       bool            required_pctl;
-       u8              offload_version;
-+      u8              hash_offset;
-       netdev_features_t hw_features;
-       struct {
-               u32     txd_size;
---- a/drivers/net/ethernet/mediatek/mtk_ppe.c
-+++ b/drivers/net/ethernet/mediatek/mtk_ppe.c
-@@ -88,7 +88,7 @@ static void mtk_ppe_cache_enable(struct
-               enable * MTK_PPE_CACHE_CTL_EN);
- }
--static u32 mtk_ppe_hash_entry(struct mtk_foe_entry *e)
-+static u32 mtk_ppe_hash_entry(struct mtk_eth *eth, struct mtk_foe_entry *e)
- {
-       u32 hv1, hv2, hv3;
-       u32 hash;
-@@ -122,7 +122,7 @@ static u32 mtk_ppe_hash_entry(struct mtk
-       hash = (hash >> 24) | ((hash & 0xffffff) << 8);
-       hash ^= hv1 ^ hv2 ^ hv3;
-       hash ^= hash >> 16;
--      hash <<= 1;
-+      hash <<= (ffs(eth->soc->hash_offset) - 1);
-       hash &= MTK_PPE_ENTRIES - 1;
-       return hash;
-@@ -540,15 +540,16 @@ mtk_foe_entry_commit_l2(struct mtk_ppe *
- int mtk_foe_entry_commit(struct mtk_ppe *ppe, struct mtk_flow_entry *entry)
- {
-       int type = FIELD_GET(MTK_FOE_IB1_PACKET_TYPE, entry->data.ib1);
-+      const struct mtk_soc_data *soc = ppe->eth->soc;
-       u32 hash;
-       if (type == MTK_PPE_PKT_TYPE_BRIDGE)
-               return mtk_foe_entry_commit_l2(ppe, entry);
--      hash = mtk_ppe_hash_entry(&entry->data);
-+      hash = mtk_ppe_hash_entry(ppe->eth, &entry->data);
-       entry->hash = 0xffff;
-       spin_lock_bh(&ppe_lock);
--      hlist_add_head(&entry->list, &ppe->foe_flow[hash / 2]);
-+      hlist_add_head(&entry->list, &ppe->foe_flow[hash / soc->hash_offset]);
-       spin_unlock_bh(&ppe_lock);
-       return 0;
-@@ -558,6 +559,7 @@ static void
- mtk_foe_entry_commit_subflow(struct mtk_ppe *ppe, struct mtk_flow_entry *entry,
-                            u16 hash)
- {
-+      const struct mtk_soc_data *soc = ppe->eth->soc;
-       struct mtk_flow_entry *flow_info;
-       struct mtk_foe_entry foe, *hwe;
-       struct mtk_foe_mac_info *l2;
-@@ -572,7 +574,8 @@ mtk_foe_entry_commit_subflow(struct mtk_
-       flow_info->l2_data.base_flow = entry;
-       flow_info->type = MTK_FLOW_TYPE_L2_SUBFLOW;
-       flow_info->hash = hash;
--      hlist_add_head(&flow_info->list, &ppe->foe_flow[hash / 2]);
-+      hlist_add_head(&flow_info->list,
-+                     &ppe->foe_flow[hash / soc->hash_offset]);
-       hlist_add_head(&flow_info->l2_data.list, &entry->l2_flows);
-       hwe = &ppe->foe_table[hash];
-@@ -596,7 +599,8 @@ mtk_foe_entry_commit_subflow(struct mtk_
- void __mtk_ppe_check_skb(struct mtk_ppe *ppe, struct sk_buff *skb, u16 hash)
- {
--      struct hlist_head *head = &ppe->foe_flow[hash / 2];
-+      const struct mtk_soc_data *soc = ppe->eth->soc;
-+      struct hlist_head *head = &ppe->foe_flow[hash / soc->hash_offset];
-       struct mtk_foe_entry *hwe = &ppe->foe_table[hash];
-       struct mtk_flow_entry *entry;
-       struct mtk_foe_bridge key = {};
-@@ -680,9 +684,11 @@ int mtk_foe_entry_idle_time(struct mtk_p
- struct mtk_ppe *mtk_ppe_init(struct mtk_eth *eth, void __iomem *base,
-                int version)
- {
-+      const struct mtk_soc_data *soc = eth->soc;
-       struct device *dev = eth->dev;
-       struct mtk_foe_entry *foe;
-       struct mtk_ppe *ppe;
-+      u32 foe_flow_size;
-       ppe = devm_kzalloc(dev, sizeof(*ppe), GFP_KERNEL);
-       if (!ppe)
-@@ -705,6 +711,12 @@ struct mtk_ppe *mtk_ppe_init(struct mtk_
-       ppe->foe_table = foe;
-+      foe_flow_size = (MTK_PPE_ENTRIES / soc->hash_offset) *
-+                      sizeof(*ppe->foe_flow);
-+      ppe->foe_flow = devm_kzalloc(dev, foe_flow_size, GFP_KERNEL);
-+      if (!ppe->foe_flow)
-+              return NULL;
-+
-       mtk_ppe_debugfs_init(ppe);
-       return ppe;
---- a/drivers/net/ethernet/mediatek/mtk_ppe.h
-+++ b/drivers/net/ethernet/mediatek/mtk_ppe.h
-@@ -270,7 +270,7 @@ struct mtk_ppe {
-       dma_addr_t foe_phys;
-       u16 foe_check_time[MTK_PPE_ENTRIES];
--      struct hlist_head foe_flow[MTK_PPE_ENTRIES / 2];
-+      struct hlist_head *foe_flow;
-       struct rhashtable l2_flows;
diff --git a/target/linux/generic/backport-5.15/715-v6.0-net-ethernet-mtk_eth_soc-add-the-capability-to-run-m.patch b/target/linux/generic/backport-5.15/715-v6.0-net-ethernet-mtk_eth_soc-add-the-capability-to-run-m.patch
deleted file mode 100644 (file)
index fb64da3..0000000
+++ /dev/null
@@ -1,318 +0,0 @@
-From patchwork Thu Sep  8 19:33:39 2022
-Content-Type: text/plain; charset="utf-8"
-MIME-Version: 1.0
-Content-Transfer-Encoding: 7bit
-X-Patchwork-Submitter: Lorenzo Bianconi <[email protected]>
-X-Patchwork-Id: 12970559
-X-Patchwork-Delegate: [email protected]
-Return-Path: <[email protected]>
-From: Lorenzo Bianconi <[email protected]>
-Subject: [PATCH net-next 05/12] net: ethernet: mtk_eth_soc: add the capability
- to run multiple ppe
-Date: Thu,  8 Sep 2022 21:33:39 +0200
-Message-Id: 
- <dd0254775390eb031c67c448df8b19e87df58558.1662661555.git.lorenzo@kernel.org>
-X-Mailer: git-send-email 2.37.3
-In-Reply-To: <[email protected]>
-References: <[email protected]>
-MIME-Version: 1.0
-Precedence: bulk
-List-ID: <netdev.vger.kernel.org>
-X-Mailing-List: [email protected]
-X-Patchwork-Delegate: [email protected]
-
-mt7986 chipset support multiple packet engines for wlan <-> eth
-packet forwarding.
-
-Co-developed-by: Bo Jiao <[email protected]>
-Signed-off-by: Bo Jiao <[email protected]>
-Co-developed-by: Sujuan Chen <[email protected]>
-Signed-off-by: Sujuan Chen <[email protected]>
-Signed-off-by: Lorenzo Bianconi <[email protected]>
----
- drivers/net/ethernet/mediatek/mtk_eth_soc.c   | 35 ++++++++++++-------
- drivers/net/ethernet/mediatek/mtk_eth_soc.h   |  2 +-
- drivers/net/ethernet/mediatek/mtk_ppe.c       | 14 +++++---
- drivers/net/ethernet/mediatek/mtk_ppe.h       |  9 +++--
- .../net/ethernet/mediatek/mtk_ppe_debugfs.c   |  8 ++---
- .../net/ethernet/mediatek/mtk_ppe_offload.c   | 13 +++----
- 6 files changed, 48 insertions(+), 33 deletions(-)
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-@@ -1871,7 +1871,7 @@ static int mtk_poll_rx(struct napi_struc
-               reason = FIELD_GET(MTK_RXD4_PPE_CPU_REASON, trxd.rxd4);
-               if (reason == MTK_PPE_CPU_REASON_HIT_UNBIND_RATE_REACHED)
--                      mtk_ppe_check_skb(eth->ppe, skb, hash);
-+                      mtk_ppe_check_skb(eth->ppe[0], skb, hash);
-               if (netdev->features & NETIF_F_HW_VLAN_CTAG_RX) {
-                       if (MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2)) {
-@@ -2932,7 +2932,8 @@ static int mtk_open(struct net_device *d
-       /* we run 2 netdevs on the same dma ring so we only bring it up once */
-       if (!refcount_read(&eth->dma_refcnt)) {
-               const struct mtk_soc_data *soc = eth->soc;
--              u32 gdm_config = MTK_GDMA_TO_PDMA;
-+              u32 gdm_config;
-+              int i;
-               int err;
-               err = mtk_start_dma(eth);
-@@ -2941,8 +2942,11 @@ static int mtk_open(struct net_device *d
-                       return err;
-               }
--              if (soc->offload_version && mtk_ppe_start(eth->ppe) == 0)
--                      gdm_config = soc->reg_map->gdma_to_ppe0;
-+              for (i = 0; i < ARRAY_SIZE(eth->ppe); i++)
-+                      mtk_ppe_start(eth->ppe[i]);
-+
-+              gdm_config = soc->offload_version ? soc->reg_map->gdma_to_ppe0
-+                      : MTK_GDMA_TO_PDMA;
-               mtk_gdm_config(eth, gdm_config);
-@@ -2987,6 +2991,7 @@ static int mtk_stop(struct net_device *d
- {
-       struct mtk_mac *mac = netdev_priv(dev);
-       struct mtk_eth *eth = mac->hw;
-+      int i;
-       phylink_stop(mac->phylink);
-@@ -3014,8 +3019,8 @@ static int mtk_stop(struct net_device *d
-       mtk_dma_free(eth);
--      if (eth->soc->offload_version)
--              mtk_ppe_stop(eth->ppe);
-+      for (i = 0; i < ARRAY_SIZE(eth->ppe); i++)
-+              mtk_ppe_stop(eth->ppe[i]);
-       return 0;
- }
-@@ -4048,12 +4053,19 @@ static int mtk_probe(struct platform_dev
-       }
-       if (eth->soc->offload_version) {
--              u32 ppe_addr = eth->soc->reg_map->ppe_base;
-+              u32 num_ppe;
--              eth->ppe = mtk_ppe_init(eth, eth->base + ppe_addr, 2);
--              if (!eth->ppe) {
--                      err = -ENOMEM;
--                      goto err_free_dev;
-+              num_ppe = MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2) ? 2 : 1;
-+              num_ppe = min_t(u32, ARRAY_SIZE(eth->ppe), num_ppe);
-+              for (i = 0; i < num_ppe; i++) {
-+                      u32 ppe_addr = eth->soc->reg_map->ppe_base + i * 0x400;
-+
-+                      eth->ppe[i] = mtk_ppe_init(eth, eth->base + ppe_addr,
-+                                                 eth->soc->offload_version, i);
-+                      if (!eth->ppe[i]) {
-+                              err = -ENOMEM;
-+                              goto err_free_dev;
-+                      }
-               }
-               err = mtk_eth_offload_init(eth);
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-@@ -1112,7 +1112,7 @@ struct mtk_eth {
-       int                             ip_align;
--      struct mtk_ppe                  *ppe;
-+      struct mtk_ppe                  *ppe[2];
-       struct rhashtable               flow_table;
-       struct bpf_prog                 __rcu *prog;
---- a/drivers/net/ethernet/mediatek/mtk_ppe.c
-+++ b/drivers/net/ethernet/mediatek/mtk_ppe.c
-@@ -682,7 +682,7 @@ int mtk_foe_entry_idle_time(struct mtk_p
- }
- struct mtk_ppe *mtk_ppe_init(struct mtk_eth *eth, void __iomem *base,
--               int version)
-+                           int version, int index)
- {
-       const struct mtk_soc_data *soc = eth->soc;
-       struct device *dev = eth->dev;
-@@ -717,7 +717,7 @@ struct mtk_ppe *mtk_ppe_init(struct mtk_
-       if (!ppe->foe_flow)
-               return NULL;
--      mtk_ppe_debugfs_init(ppe);
-+      mtk_ppe_debugfs_init(ppe, index);
-       return ppe;
- }
-@@ -738,10 +738,13 @@ static void mtk_ppe_init_foe_table(struc
-                       ppe->foe_table[i + skip[k]].ib1 |= MTK_FOE_IB1_STATIC;
- }
--int mtk_ppe_start(struct mtk_ppe *ppe)
-+void mtk_ppe_start(struct mtk_ppe *ppe)
- {
-       u32 val;
-+      if (!ppe)
-+              return;
-+
-       mtk_ppe_init_foe_table(ppe);
-       ppe_w32(ppe, MTK_PPE_TB_BASE, ppe->foe_phys);
-@@ -809,8 +812,6 @@ int mtk_ppe_start(struct mtk_ppe *ppe)
-       ppe_w32(ppe, MTK_PPE_GLO_CFG, val);
-       ppe_w32(ppe, MTK_PPE_DEFAULT_CPU_PORT, 0);
--
--      return 0;
- }
- int mtk_ppe_stop(struct mtk_ppe *ppe)
-@@ -818,6 +819,9 @@ int mtk_ppe_stop(struct mtk_ppe *ppe)
-       u32 val;
-       int i;
-+      if (!ppe)
-+              return 0;
-+
-       for (i = 0; i < MTK_PPE_ENTRIES; i++)
-               ppe->foe_table[i].ib1 = FIELD_PREP(MTK_FOE_IB1_STATE,
-                                                  MTK_FOE_STATE_INVALID);
---- a/drivers/net/ethernet/mediatek/mtk_ppe.h
-+++ b/drivers/net/ethernet/mediatek/mtk_ppe.h
-@@ -247,6 +247,7 @@ struct mtk_flow_entry {
-       };
-       u8 type;
-       s8 wed_index;
-+      u8 ppe_index;
-       u16 hash;
-       union {
-               struct mtk_foe_entry data;
-@@ -265,6 +266,7 @@ struct mtk_ppe {
-       struct device *dev;
-       void __iomem *base;
-       int version;
-+      char dirname[5];
-       struct mtk_foe_entry *foe_table;
-       dma_addr_t foe_phys;
-@@ -277,8 +279,9 @@ struct mtk_ppe {
-       void *acct_table;
- };
--struct mtk_ppe *mtk_ppe_init(struct mtk_eth *eth, void __iomem *base, int version);
--int mtk_ppe_start(struct mtk_ppe *ppe);
-+struct mtk_ppe *mtk_ppe_init(struct mtk_eth *eth, void __iomem *base,
-+                           int version, int index);
-+void mtk_ppe_start(struct mtk_ppe *ppe);
- int mtk_ppe_stop(struct mtk_ppe *ppe);
- void __mtk_ppe_check_skb(struct mtk_ppe *ppe, struct sk_buff *skb, u16 hash);
-@@ -317,6 +320,6 @@ int mtk_foe_entry_set_wdma(struct mtk_fo
- int mtk_foe_entry_commit(struct mtk_ppe *ppe, struct mtk_flow_entry *entry);
- void mtk_foe_entry_clear(struct mtk_ppe *ppe, struct mtk_flow_entry *entry);
- int mtk_foe_entry_idle_time(struct mtk_ppe *ppe, struct mtk_flow_entry *entry);
--int mtk_ppe_debugfs_init(struct mtk_ppe *ppe);
-+int mtk_ppe_debugfs_init(struct mtk_ppe *ppe, int index);
- #endif
---- a/drivers/net/ethernet/mediatek/mtk_ppe_debugfs.c
-+++ b/drivers/net/ethernet/mediatek/mtk_ppe_debugfs.c
-@@ -187,7 +187,7 @@ mtk_ppe_debugfs_foe_open_bind(struct ino
-                          inode->i_private);
- }
--int mtk_ppe_debugfs_init(struct mtk_ppe *ppe)
-+int mtk_ppe_debugfs_init(struct mtk_ppe *ppe, int index)
- {
-       static const struct file_operations fops_all = {
-               .open = mtk_ppe_debugfs_foe_open_all,
-@@ -195,17 +195,17 @@ int mtk_ppe_debugfs_init(struct mtk_ppe
-               .llseek = seq_lseek,
-               .release = single_release,
-       };
--
-       static const struct file_operations fops_bind = {
-               .open = mtk_ppe_debugfs_foe_open_bind,
-               .read = seq_read,
-               .llseek = seq_lseek,
-               .release = single_release,
-       };
--
-       struct dentry *root;
--      root = debugfs_create_dir("mtk_ppe", NULL);
-+      snprintf(ppe->dirname, sizeof(ppe->dirname), "ppe%d", index);
-+
-+      root = debugfs_create_dir(ppe->dirname, NULL);
-       if (!root)
-               return -ENOMEM;
---- a/drivers/net/ethernet/mediatek/mtk_ppe_offload.c
-+++ b/drivers/net/ethernet/mediatek/mtk_ppe_offload.c
-@@ -434,7 +434,7 @@ mtk_flow_offload_replace(struct mtk_eth
-       memcpy(&entry->data, &foe, sizeof(entry->data));
-       entry->wed_index = wed_index;
--      err = mtk_foe_entry_commit(eth->ppe, entry);
-+      err = mtk_foe_entry_commit(eth->ppe[entry->ppe_index], entry);
-       if (err < 0)
-               goto free;
-@@ -446,7 +446,7 @@ mtk_flow_offload_replace(struct mtk_eth
-       return 0;
- clear:
--      mtk_foe_entry_clear(eth->ppe, entry);
-+      mtk_foe_entry_clear(eth->ppe[entry->ppe_index], entry);
- free:
-       kfree(entry);
-       if (wed_index >= 0)
-@@ -464,7 +464,7 @@ mtk_flow_offload_destroy(struct mtk_eth
-       if (!entry)
-               return -ENOENT;
--      mtk_foe_entry_clear(eth->ppe, entry);
-+      mtk_foe_entry_clear(eth->ppe[entry->ppe_index], entry);
-       rhashtable_remove_fast(&eth->flow_table, &entry->node,
-                              mtk_flow_ht_params);
-       if (entry->wed_index >= 0)
-@@ -485,7 +485,7 @@ mtk_flow_offload_stats(struct mtk_eth *e
-       if (!entry)
-               return -ENOENT;
--      idle = mtk_foe_entry_idle_time(eth->ppe, entry);
-+      idle = mtk_foe_entry_idle_time(eth->ppe[entry->ppe_index], entry);
-       f->stats.lastused = jiffies - idle * HZ;
-       return 0;
-@@ -537,7 +537,7 @@ mtk_eth_setup_tc_block(struct net_device
-       struct flow_block_cb *block_cb;
-       flow_setup_cb_t *cb;
--      if (!eth->ppe || !eth->ppe->foe_table)
-+      if (!eth->soc->offload_version)
-               return -EOPNOTSUPP;
-       if (f->binder_type != FLOW_BLOCK_BINDER_TYPE_CLSACT_INGRESS)
-@@ -590,8 +590,5 @@ int mtk_eth_setup_tc(struct net_device *
- int mtk_eth_offload_init(struct mtk_eth *eth)
- {
--      if (!eth->ppe || !eth->ppe->foe_table)
--              return 0;
--
-       return rhashtable_init(&eth->flow_table, &mtk_flow_ht_params);
- }
diff --git a/target/linux/generic/backport-5.15/716-v6.0-net-ethernet-mtk_eth_soc-move-wdma_base-definitions-.patch b/target/linux/generic/backport-5.15/716-v6.0-net-ethernet-mtk_eth_soc-move-wdma_base-definitions-.patch
deleted file mode 100644 (file)
index 6a58334..0000000
+++ /dev/null
@@ -1,80 +0,0 @@
-From 0dcbe607cec32ccae23b02a641b8bd6191a328ae Mon Sep 17 00:00:00 2001
-Message-Id: <0dcbe607cec32ccae23b02a641b8bd6191a328ae.1662243796.git.lorenzo@kernel.org>
-In-Reply-To: <43a21841ce0175d29f23c34a65ceaaf9dd7eb8b7.1662243796.git.lorenzo@kernel.org>
-References: <43a21841ce0175d29f23c34a65ceaaf9dd7eb8b7.1662243796.git.lorenzo@kernel.org>
-From: Lorenzo Bianconi <[email protected]>
-Date: Tue, 23 Aug 2022 23:09:05 +0200
-Subject: [PATCH net-next 2/4] net: ethernet: mtk_eth_soc: move wdma_base
- definitions in mtk register map
-
-This is a preliminary patch to introduce mt7986 wed support.
-
-Signed-off-by: Lorenzo Bianconi <[email protected]>
----
- drivers/net/ethernet/mediatek/mtk_eth_soc.c | 16 ++++++++++------
- drivers/net/ethernet/mediatek/mtk_eth_soc.h |  4 +---
- 2 files changed, 11 insertions(+), 9 deletions(-)
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-@@ -75,6 +75,10 @@ static const struct mtk_reg_map mtk_reg_
-       .gdm1_cnt               = 0x2400,
-       .gdma_to_ppe0           = 0x4444,
-       .ppe_base               = 0x0c00,
-+      .wdma_base = {
-+              [0]             = 0x2800,
-+              [1]             = 0x2c00,
-+      },
- };
- static const struct mtk_reg_map mt7628_reg_map = {
-@@ -130,6 +134,10 @@ static const struct mtk_reg_map mt7986_r
-       .gdm1_cnt               = 0x1c00,
-       .gdma_to_ppe0           = 0x3333,
-       .ppe_base               = 0x2000,
-+      .wdma_base = {
-+              [0]             = 0x4800,
-+              [1]             = 0x4c00,
-+      },
- };
- /* strings used by ethtool */
-@@ -3965,16 +3973,12 @@ static int mtk_probe(struct platform_dev
-       for (i = 0;; i++) {
-               struct device_node *np = of_parse_phandle(pdev->dev.of_node,
-                                                         "mediatek,wed", i);
--              static const u32 wdma_regs[] = {
--                      MTK_WDMA0_BASE,
--                      MTK_WDMA1_BASE
--              };
-               void __iomem *wdma;
--              if (!np || i >= ARRAY_SIZE(wdma_regs))
-+              if (!np || i >= ARRAY_SIZE(eth->soc->reg_map->wdma_base))
-                       break;
--              wdma = eth->base + wdma_regs[i];
-+              wdma = eth->base + eth->soc->reg_map->wdma_base[i];
-               mtk_wed_add_hw(np, eth, wdma, i);
-       }
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-@@ -268,9 +268,6 @@
- #define TX_DMA_FPORT_MASK_V2  0xf
- #define TX_DMA_SWC_V2         BIT(30)
--#define MTK_WDMA0_BASE                0x2800
--#define MTK_WDMA1_BASE                0x2c00
--
- /* QDMA descriptor txd4 */
- #define TX_DMA_CHKSUM         (0x7 << 29)
- #define TX_DMA_TSO            BIT(28)
-@@ -954,6 +951,7 @@ struct mtk_reg_map {
-       u32     gdm1_cnt;
-       u32     gdma_to_ppe0;
-       u32     ppe_base;
-+      u32     wdma_base[2];
- };
- /* struct mtk_eth_data -      This is the structure holding all differences
diff --git a/target/linux/generic/backport-5.15/717-v6.0-net-ethernet-mtk_eth_soc-add-foe_entry_size-to-mtk_e.patch b/target/linux/generic/backport-5.15/717-v6.0-net-ethernet-mtk_eth_soc-add-foe_entry_size-to-mtk_e.patch
deleted file mode 100644 (file)
index de1f217..0000000
+++ /dev/null
@@ -1,251 +0,0 @@
-From e3c27d869fccc1f2b8d0b4cde4763ab223874e8c Mon Sep 17 00:00:00 2001
-Message-Id: <e3c27d869fccc1f2b8d0b4cde4763ab223874e8c.1662243796.git.lorenzo@kernel.org>
-In-Reply-To: <43a21841ce0175d29f23c34a65ceaaf9dd7eb8b7.1662243796.git.lorenzo@kernel.org>
-References: <43a21841ce0175d29f23c34a65ceaaf9dd7eb8b7.1662243796.git.lorenzo@kernel.org>
-From: Lorenzo Bianconi <[email protected]>
-Date: Sun, 21 Aug 2022 17:51:17 +0200
-Subject: [PATCH net-next 3/4] net: ethernet: mtk_eth_soc: add foe_entry_size
- to mtk_eth_soc
-
-Introduce foe_entry_size to mtk_eth_soc data structure since mt7986
-relies on a bigger mtk_foe_entry data structure.
-
-Signed-off-by: Lorenzo Bianconi <[email protected]>
----
- drivers/net/ethernet/mediatek/mtk_eth_soc.c   |  3 +
- drivers/net/ethernet/mediatek/mtk_eth_soc.h   | 10 ++++
- drivers/net/ethernet/mediatek/mtk_ppe.c       | 55 +++++++++++--------
- drivers/net/ethernet/mediatek/mtk_ppe.h       |  2 +-
- .../net/ethernet/mediatek/mtk_ppe_debugfs.c   |  2 +-
- 5 files changed, 48 insertions(+), 24 deletions(-)
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-@@ -4163,6 +4163,7 @@ static const struct mtk_soc_data mt7621_
-       .required_pctl = false,
-       .offload_version = 2,
-       .hash_offset = 2,
-+      .foe_entry_size = sizeof(struct mtk_foe_entry),
-       .txrx = {
-               .txd_size = sizeof(struct mtk_tx_dma),
-               .rxd_size = sizeof(struct mtk_rx_dma),
-@@ -4182,6 +4183,7 @@ static const struct mtk_soc_data mt7622_
-       .required_pctl = false,
-       .offload_version = 2,
-       .hash_offset = 2,
-+      .foe_entry_size = sizeof(struct mtk_foe_entry),
-       .txrx = {
-               .txd_size = sizeof(struct mtk_tx_dma),
-               .rxd_size = sizeof(struct mtk_rx_dma),
-@@ -4200,6 +4202,7 @@ static const struct mtk_soc_data mt7623_
-       .required_pctl = true,
-       .offload_version = 2,
-       .hash_offset = 2,
-+      .foe_entry_size = sizeof(struct mtk_foe_entry),
-       .txrx = {
-               .txd_size = sizeof(struct mtk_tx_dma),
-               .rxd_size = sizeof(struct mtk_rx_dma),
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-@@ -966,6 +966,7 @@ struct mtk_reg_map {
-  * @required_pctl             A bool value to show whether the SoC requires
-  *                            the extra setup for those pins used by GMAC.
-  * @hash_offset                       Flow table hash offset.
-+ * @foe_entry_size            Foe table entry size.
-  * @txd_size                  Tx DMA descriptor size.
-  * @rxd_size                  Rx DMA descriptor size.
-  * @rx_irq_done_mask          Rx irq done register mask.
-@@ -981,6 +982,7 @@ struct mtk_soc_data {
-       bool            required_pctl;
-       u8              offload_version;
-       u8              hash_offset;
-+      u16             foe_entry_size;
-       netdev_features_t hw_features;
-       struct {
-               u32     txd_size;
-@@ -1141,6 +1143,14 @@ struct mtk_mac {
- /* the struct describing the SoC. these are declared in the soc_xyz.c files */
- extern const struct of_device_id of_mtk_match[];
-+static inline struct mtk_foe_entry *
-+mtk_foe_get_entry(struct mtk_ppe *ppe, u16 hash)
-+{
-+      const struct mtk_soc_data *soc = ppe->eth->soc;
-+
-+      return ppe->foe_table + hash * soc->foe_entry_size;
-+}
-+
- /* read the hardware status register */
- void mtk_stats_update_mac(struct mtk_mac *mac);
---- a/drivers/net/ethernet/mediatek/mtk_ppe.c
-+++ b/drivers/net/ethernet/mediatek/mtk_ppe.c
-@@ -410,9 +410,10 @@ __mtk_foe_entry_clear(struct mtk_ppe *pp
-       hlist_del_init(&entry->list);
-       if (entry->hash != 0xffff) {
--              ppe->foe_table[entry->hash].ib1 &= ~MTK_FOE_IB1_STATE;
--              ppe->foe_table[entry->hash].ib1 |= FIELD_PREP(MTK_FOE_IB1_STATE,
--                                                            MTK_FOE_STATE_BIND);
-+              struct mtk_foe_entry *hwe = mtk_foe_get_entry(ppe, entry->hash);
-+
-+              hwe->ib1 &= ~MTK_FOE_IB1_STATE;
-+              hwe->ib1 |= FIELD_PREP(MTK_FOE_IB1_STATE, MTK_FOE_STATE_BIND);
-               dma_wmb();
-       }
-       entry->hash = 0xffff;
-@@ -451,7 +452,7 @@ mtk_flow_entry_update_l2(struct mtk_ppe
-               int cur_idle;
-               u32 ib1;
--              hwe = &ppe->foe_table[cur->hash];
-+              hwe = mtk_foe_get_entry(ppe, cur->hash);
-               ib1 = READ_ONCE(hwe->ib1);
-               if (FIELD_GET(MTK_FOE_IB1_STATE, ib1) != MTK_FOE_STATE_BIND) {
-@@ -473,8 +474,8 @@ mtk_flow_entry_update_l2(struct mtk_ppe
- static void
- mtk_flow_entry_update(struct mtk_ppe *ppe, struct mtk_flow_entry *entry)
- {
-+      struct mtk_foe_entry foe = {};
-       struct mtk_foe_entry *hwe;
--      struct mtk_foe_entry foe;
-       spin_lock_bh(&ppe_lock);
-@@ -486,8 +487,8 @@ mtk_flow_entry_update(struct mtk_ppe *pp
-       if (entry->hash == 0xffff)
-               goto out;
--      hwe = &ppe->foe_table[entry->hash];
--      memcpy(&foe, hwe, sizeof(foe));
-+      hwe = mtk_foe_get_entry(ppe, entry->hash);
-+      memcpy(&foe, hwe, ppe->eth->soc->foe_entry_size);
-       if (!mtk_flow_entry_match(entry, &foe)) {
-               entry->hash = 0xffff;
-               goto out;
-@@ -511,8 +512,8 @@ __mtk_foe_entry_commit(struct mtk_ppe *p
-       entry->ib1 &= ~MTK_FOE_IB1_BIND_TIMESTAMP;
-       entry->ib1 |= FIELD_PREP(MTK_FOE_IB1_BIND_TIMESTAMP, timestamp);
--      hwe = &ppe->foe_table[hash];
--      memcpy(&hwe->data, &entry->data, sizeof(hwe->data));
-+      hwe = mtk_foe_get_entry(ppe, hash);
-+      memcpy(&hwe->data, &entry->data, ppe->eth->soc->foe_entry_size);
-       wmb();
-       hwe->ib1 = entry->ib1;
-@@ -561,7 +562,7 @@ mtk_foe_entry_commit_subflow(struct mtk_
- {
-       const struct mtk_soc_data *soc = ppe->eth->soc;
-       struct mtk_flow_entry *flow_info;
--      struct mtk_foe_entry foe, *hwe;
-+      struct mtk_foe_entry foe = {}, *hwe;
-       struct mtk_foe_mac_info *l2;
-       u32 ib1_mask = MTK_FOE_IB1_PACKET_TYPE | MTK_FOE_IB1_UDP;
-       int type;
-@@ -578,8 +579,8 @@ mtk_foe_entry_commit_subflow(struct mtk_
-                      &ppe->foe_flow[hash / soc->hash_offset]);
-       hlist_add_head(&flow_info->l2_data.list, &entry->l2_flows);
--      hwe = &ppe->foe_table[hash];
--      memcpy(&foe, hwe, sizeof(foe));
-+      hwe = mtk_foe_get_entry(ppe, hash);
-+      memcpy(&foe, hwe, soc->foe_entry_size);
-       foe.ib1 &= ib1_mask;
-       foe.ib1 |= entry->data.ib1 & ~ib1_mask;
-@@ -601,7 +602,7 @@ void __mtk_ppe_check_skb(struct mtk_ppe
- {
-       const struct mtk_soc_data *soc = ppe->eth->soc;
-       struct hlist_head *head = &ppe->foe_flow[hash / soc->hash_offset];
--      struct mtk_foe_entry *hwe = &ppe->foe_table[hash];
-+      struct mtk_foe_entry *hwe = mtk_foe_get_entry(ppe, hash);
-       struct mtk_flow_entry *entry;
-       struct mtk_foe_bridge key = {};
-       struct hlist_node *n;
-@@ -686,9 +687,9 @@ struct mtk_ppe *mtk_ppe_init(struct mtk_
- {
-       const struct mtk_soc_data *soc = eth->soc;
-       struct device *dev = eth->dev;
--      struct mtk_foe_entry *foe;
-       struct mtk_ppe *ppe;
-       u32 foe_flow_size;
-+      void *foe;
-       ppe = devm_kzalloc(dev, sizeof(*ppe), GFP_KERNEL);
-       if (!ppe)
-@@ -704,7 +705,8 @@ struct mtk_ppe *mtk_ppe_init(struct mtk_
-       ppe->dev = dev;
-       ppe->version = version;
--      foe = dmam_alloc_coherent(ppe->dev, MTK_PPE_ENTRIES * sizeof(*foe),
-+      foe = dmam_alloc_coherent(ppe->dev,
-+                                MTK_PPE_ENTRIES * soc->foe_entry_size,
-                                 &ppe->foe_phys, GFP_KERNEL);
-       if (!foe)
-               return NULL;
-@@ -727,15 +729,21 @@ static void mtk_ppe_init_foe_table(struc
-       static const u8 skip[] = { 12, 25, 38, 51, 76, 89, 102 };
-       int i, k;
--      memset(ppe->foe_table, 0, MTK_PPE_ENTRIES * sizeof(*ppe->foe_table));
-+      memset(ppe->foe_table, 0,
-+             MTK_PPE_ENTRIES * ppe->eth->soc->foe_entry_size);
-       if (!IS_ENABLED(CONFIG_SOC_MT7621))
-               return;
-       /* skip all entries that cross the 1024 byte boundary */
--      for (i = 0; i < MTK_PPE_ENTRIES; i += 128)
--              for (k = 0; k < ARRAY_SIZE(skip); k++)
--                      ppe->foe_table[i + skip[k]].ib1 |= MTK_FOE_IB1_STATIC;
-+      for (i = 0; i < MTK_PPE_ENTRIES; i += 128) {
-+              for (k = 0; k < ARRAY_SIZE(skip); k++) {
-+                      struct mtk_foe_entry *hwe;
-+
-+                      hwe = mtk_foe_get_entry(ppe, i + skip[k]);
-+                      hwe->ib1 |= MTK_FOE_IB1_STATIC;
-+              }
-+      }
- }
- void mtk_ppe_start(struct mtk_ppe *ppe)
-@@ -822,9 +830,12 @@ int mtk_ppe_stop(struct mtk_ppe *ppe)
-       if (!ppe)
-               return 0;
--      for (i = 0; i < MTK_PPE_ENTRIES; i++)
--              ppe->foe_table[i].ib1 = FIELD_PREP(MTK_FOE_IB1_STATE,
--                                                 MTK_FOE_STATE_INVALID);
-+      for (i = 0; i < MTK_PPE_ENTRIES; i++) {
-+              struct mtk_foe_entry *hwe = mtk_foe_get_entry(ppe, i);
-+
-+              hwe->ib1 = FIELD_PREP(MTK_FOE_IB1_STATE,
-+                                    MTK_FOE_STATE_INVALID);
-+      }
-       mtk_ppe_cache_enable(ppe, false);
---- a/drivers/net/ethernet/mediatek/mtk_ppe.h
-+++ b/drivers/net/ethernet/mediatek/mtk_ppe.h
-@@ -268,7 +268,7 @@ struct mtk_ppe {
-       int version;
-       char dirname[5];
--      struct mtk_foe_entry *foe_table;
-+      void *foe_table;
-       dma_addr_t foe_phys;
-       u16 foe_check_time[MTK_PPE_ENTRIES];
---- a/drivers/net/ethernet/mediatek/mtk_ppe_debugfs.c
-+++ b/drivers/net/ethernet/mediatek/mtk_ppe_debugfs.c
-@@ -79,7 +79,7 @@ mtk_ppe_debugfs_foe_show(struct seq_file
-       int i;
-       for (i = 0; i < MTK_PPE_ENTRIES; i++) {
--              struct mtk_foe_entry *entry = &ppe->foe_table[i];
-+              struct mtk_foe_entry *entry = mtk_foe_get_entry(ppe, i);
-               struct mtk_foe_mac_info *l2;
-               struct mtk_flow_addr_info ai = {};
-               unsigned char h_source[ETH_ALEN];
diff --git a/target/linux/generic/backport-5.15/718-v6.0-net-ethernet-mtk_eth_soc-fix-typo-in-__mtk_foe_entry.patch b/target/linux/generic/backport-5.15/718-v6.0-net-ethernet-mtk_eth_soc-fix-typo-in-__mtk_foe_entry.patch
deleted file mode 100644 (file)
index 77daf6c..0000000
+++ /dev/null
@@ -1,27 +0,0 @@
-From 12ff69304c83c679ca01ef3db963ab0db9de19fb Mon Sep 17 00:00:00 2001
-Message-Id: <12ff69304c83c679ca01ef3db963ab0db9de19fb.1662332102.git.lorenzo@kernel.org>
-In-Reply-To: <2a60545635c2705312299384f4e9fec2f2a3acd6.1662332102.git.lorenzo@kernel.org>
-References: <2a60545635c2705312299384f4e9fec2f2a3acd6.1662332102.git.lorenzo@kernel.org>
-From: Lorenzo Bianconi <[email protected]>
-Date: Mon, 5 Sep 2022 00:43:43 +0200
-Subject: [PATCH net-next 2/6] net: ethernet: mtk_eth_soc: fix typo in
- __mtk_foe_entry_clear
-
-Set ib1 state to MTK_FOE_STATE_UNBIND in __mtk_foe_entry_clear routine.
-
-Signed-off-by: Lorenzo Bianconi <[email protected]>
----
- drivers/net/ethernet/mediatek/mtk_ppe.c | 2 +-
- 1 file changed, 1 insertion(+), 1 deletion(-)
-
---- a/drivers/net/ethernet/mediatek/mtk_ppe.c
-+++ b/drivers/net/ethernet/mediatek/mtk_ppe.c
-@@ -413,7 +413,7 @@ __mtk_foe_entry_clear(struct mtk_ppe *pp
-               struct mtk_foe_entry *hwe = mtk_foe_get_entry(ppe, entry->hash);
-               hwe->ib1 &= ~MTK_FOE_IB1_STATE;
--              hwe->ib1 |= FIELD_PREP(MTK_FOE_IB1_STATE, MTK_FOE_STATE_BIND);
-+              hwe->ib1 |= FIELD_PREP(MTK_FOE_IB1_STATE, MTK_FOE_STATE_UNBIND);
-               dma_wmb();
-       }
-       entry->hash = 0xffff;
diff --git a/target/linux/generic/backport-5.15/719-v6.0-net-ethernet-mtk_eth_soc-check-max-allowed-value-in-.patch b/target/linux/generic/backport-5.15/719-v6.0-net-ethernet-mtk_eth_soc-check-max-allowed-value-in-.patch
deleted file mode 100644 (file)
index 7ab6d48..0000000
+++ /dev/null
@@ -1,28 +0,0 @@
-From 4253e6e2b795a18ab534adcd5c313d3fc4150975 Mon Sep 17 00:00:00 2001
-Message-Id: <4253e6e2b795a18ab534adcd5c313d3fc4150975.1662332102.git.lorenzo@kernel.org>
-In-Reply-To: <2a60545635c2705312299384f4e9fec2f2a3acd6.1662332102.git.lorenzo@kernel.org>
-References: <2a60545635c2705312299384f4e9fec2f2a3acd6.1662332102.git.lorenzo@kernel.org>
-From: Lorenzo Bianconi <[email protected]>
-Date: Mon, 5 Sep 2022 00:48:52 +0200
-Subject: [PATCH net-next 3/6] net: ethernet: mtk_eth_soc: check max allowed
- value in mtk_ppe_check_skb
-
-Check theoretical OOB accesses in mtk_ppe_check_skb routine
-
-Signed-off-by: Lorenzo Bianconi <[email protected]>
----
- drivers/net/ethernet/mediatek/mtk_ppe.h | 3 +++
- 1 file changed, 3 insertions(+)
-
---- a/drivers/net/ethernet/mediatek/mtk_ppe.h
-+++ b/drivers/net/ethernet/mediatek/mtk_ppe.h
-@@ -294,6 +294,9 @@ mtk_ppe_check_skb(struct mtk_ppe *ppe, s
-       if (!ppe)
-               return;
-+      if (hash > MTK_PPE_HASH_MASK)
-+              return;
-+
-       now = (u16)jiffies;
-       diff = now - ppe->foe_check_time[hash];
-       if (diff < HZ / 10)
diff --git a/target/linux/generic/backport-5.15/720-v6.0-net-ethernet-mtk_eth_wed-add-mtk_wed_configure_irq-a.patch b/target/linux/generic/backport-5.15/720-v6.0-net-ethernet-mtk_eth_wed-add-mtk_wed_configure_irq-a.patch
deleted file mode 100644 (file)
index a8c88da..0000000
+++ /dev/null
@@ -1,189 +0,0 @@
-From e5ecb4f619197b93fa682d722452dc8412864cdb Mon Sep 17 00:00:00 2001
-Message-Id: <e5ecb4f619197b93fa682d722452dc8412864cdb.1662886033.git.lorenzo@kernel.org>
-From: Lorenzo Bianconi <[email protected]>
-Date: Fri, 26 Aug 2022 01:12:57 +0200
-Subject: [PATCH net-next 1/5] net: ethernet: mtk_eth_wed: add
- mtk_wed_configure_irq and mtk_wed_dma_{enable/disable}
-
-Introduce mtk_wed_configure_irq, mtk_wed_dma_enable and mtk_wed_dma_disable
-utility routines.
-This is a preliminary patch to introduce mt7986 wed support.
-
-Co-developed-by: Bo Jiao <[email protected]>
-Signed-off-by: Bo Jiao <[email protected]>
-Co-developed-by: Sujuan Chen <[email protected]>
-Signed-off-by: Sujuan Chen <[email protected]>
-Signed-off-by: Lorenzo Bianconi <[email protected]>
----
- drivers/net/ethernet/mediatek/mtk_wed.c      | 87 +++++++++++++-------
- drivers/net/ethernet/mediatek/mtk_wed_regs.h |  6 +-
- 2 files changed, 64 insertions(+), 29 deletions(-)
-
---- a/drivers/net/ethernet/mediatek/mtk_wed.c
-+++ b/drivers/net/ethernet/mediatek/mtk_wed.c
-@@ -237,9 +237,30 @@ mtk_wed_set_ext_int(struct mtk_wed_devic
- }
- static void
--mtk_wed_stop(struct mtk_wed_device *dev)
-+mtk_wed_dma_disable(struct mtk_wed_device *dev)
- {
-+      wed_clr(dev, MTK_WED_WPDMA_GLO_CFG,
-+              MTK_WED_WPDMA_GLO_CFG_TX_DRV_EN |
-+              MTK_WED_WPDMA_GLO_CFG_RX_DRV_EN);
-+
-+      wed_clr(dev, MTK_WED_WDMA_GLO_CFG, MTK_WED_WDMA_GLO_CFG_RX_DRV_EN);
-+
-+      wed_clr(dev, MTK_WED_GLO_CFG,
-+              MTK_WED_GLO_CFG_TX_DMA_EN |
-+              MTK_WED_GLO_CFG_RX_DMA_EN);
-+
-       regmap_write(dev->hw->mirror, dev->hw->index * 4, 0);
-+      wdma_m32(dev, MTK_WDMA_GLO_CFG,
-+               MTK_WDMA_GLO_CFG_TX_DMA_EN |
-+               MTK_WDMA_GLO_CFG_RX_INFO1_PRERES |
-+               MTK_WDMA_GLO_CFG_RX_INFO2_PRERES |
-+               MTK_WDMA_GLO_CFG_RX_INFO3_PRERES, 0);
-+}
-+
-+static void
-+mtk_wed_stop(struct mtk_wed_device *dev)
-+{
-+      mtk_wed_dma_disable(dev);
-       mtk_wed_set_ext_int(dev, false);
-       wed_clr(dev, MTK_WED_CTRL,
-@@ -252,15 +273,6 @@ mtk_wed_stop(struct mtk_wed_device *dev)
-       wdma_w32(dev, MTK_WDMA_INT_MASK, 0);
-       wdma_w32(dev, MTK_WDMA_INT_GRP2, 0);
-       wed_w32(dev, MTK_WED_WPDMA_INT_MASK, 0);
--
--      wed_clr(dev, MTK_WED_GLO_CFG,
--              MTK_WED_GLO_CFG_TX_DMA_EN |
--              MTK_WED_GLO_CFG_RX_DMA_EN);
--      wed_clr(dev, MTK_WED_WPDMA_GLO_CFG,
--              MTK_WED_WPDMA_GLO_CFG_TX_DRV_EN |
--              MTK_WED_WPDMA_GLO_CFG_RX_DRV_EN);
--      wed_clr(dev, MTK_WED_WDMA_GLO_CFG,
--              MTK_WED_WDMA_GLO_CFG_RX_DRV_EN);
- }
- static void
-@@ -313,7 +325,10 @@ mtk_wed_hw_init_early(struct mtk_wed_dev
-             MTK_WED_WDMA_GLO_CFG_IDLE_DMAD_SUPPLY;
-       wed_m32(dev, MTK_WED_WDMA_GLO_CFG, mask, set);
--      wdma_set(dev, MTK_WDMA_GLO_CFG, MTK_WDMA_GLO_CFG_RX_INFO_PRERES);
-+      wdma_set(dev, MTK_WDMA_GLO_CFG,
-+               MTK_WDMA_GLO_CFG_RX_INFO1_PRERES |
-+               MTK_WDMA_GLO_CFG_RX_INFO2_PRERES |
-+               MTK_WDMA_GLO_CFG_RX_INFO3_PRERES);
-       offset = dev->hw->index ? 0x04000400 : 0;
-       wed_w32(dev, MTK_WED_WDMA_OFFSET0, 0x2a042a20 + offset);
-@@ -520,43 +535,38 @@ mtk_wed_wdma_ring_setup(struct mtk_wed_d
- }
- static void
--mtk_wed_start(struct mtk_wed_device *dev, u32 irq_mask)
-+mtk_wed_configure_irq(struct mtk_wed_device *dev, u32 irq_mask)
- {
--      u32 wdma_mask;
--      u32 val;
--      int i;
--
--      for (i = 0; i < ARRAY_SIZE(dev->tx_wdma); i++)
--              if (!dev->tx_wdma[i].desc)
--                      mtk_wed_wdma_ring_setup(dev, i, 16);
--
--      wdma_mask = FIELD_PREP(MTK_WDMA_INT_MASK_RX_DONE, GENMASK(1, 0));
--
--      mtk_wed_hw_init(dev);
-+      u32 wdma_mask = FIELD_PREP(MTK_WDMA_INT_MASK_RX_DONE, GENMASK(1, 0));
-+      /* wed control cr set */
-       wed_set(dev, MTK_WED_CTRL,
-               MTK_WED_CTRL_WDMA_INT_AGENT_EN |
-               MTK_WED_CTRL_WPDMA_INT_AGENT_EN |
-               MTK_WED_CTRL_WED_TX_BM_EN |
-               MTK_WED_CTRL_WED_TX_FREE_AGENT_EN);
--      wed_w32(dev, MTK_WED_PCIE_INT_TRIGGER, MTK_WED_PCIE_INT_TRIGGER_STATUS);
-+      wed_w32(dev, MTK_WED_PCIE_INT_TRIGGER,
-+              MTK_WED_PCIE_INT_TRIGGER_STATUS);
-       wed_w32(dev, MTK_WED_WPDMA_INT_TRIGGER,
-               MTK_WED_WPDMA_INT_TRIGGER_RX_DONE |
-               MTK_WED_WPDMA_INT_TRIGGER_TX_DONE);
--      wed_set(dev, MTK_WED_WPDMA_INT_CTRL,
--              MTK_WED_WPDMA_INT_CTRL_SUBRT_ADV);
--
-+      /* initail wdma interrupt agent */
-       wed_w32(dev, MTK_WED_WDMA_INT_TRIGGER, wdma_mask);
-       wed_clr(dev, MTK_WED_WDMA_INT_CTRL, wdma_mask);
-       wdma_w32(dev, MTK_WDMA_INT_MASK, wdma_mask);
-       wdma_w32(dev, MTK_WDMA_INT_GRP2, wdma_mask);
--
-       wed_w32(dev, MTK_WED_WPDMA_INT_MASK, irq_mask);
-       wed_w32(dev, MTK_WED_INT_MASK, irq_mask);
-+}
-+
-+static void
-+mtk_wed_dma_enable(struct mtk_wed_device *dev)
-+{
-+      wed_set(dev, MTK_WED_WPDMA_INT_CTRL, MTK_WED_WPDMA_INT_CTRL_SUBRT_ADV);
-       wed_set(dev, MTK_WED_GLO_CFG,
-               MTK_WED_GLO_CFG_TX_DMA_EN |
-@@ -567,6 +577,26 @@ mtk_wed_start(struct mtk_wed_device *dev
-       wed_set(dev, MTK_WED_WDMA_GLO_CFG,
-               MTK_WED_WDMA_GLO_CFG_RX_DRV_EN);
-+      wdma_set(dev, MTK_WDMA_GLO_CFG,
-+               MTK_WDMA_GLO_CFG_TX_DMA_EN |
-+               MTK_WDMA_GLO_CFG_RX_INFO1_PRERES |
-+               MTK_WDMA_GLO_CFG_RX_INFO2_PRERES |
-+               MTK_WDMA_GLO_CFG_RX_INFO3_PRERES);
-+}
-+
-+static void
-+mtk_wed_start(struct mtk_wed_device *dev, u32 irq_mask)
-+{
-+      u32 val;
-+      int i;
-+
-+      for (i = 0; i < ARRAY_SIZE(dev->tx_wdma); i++)
-+              if (!dev->tx_wdma[i].desc)
-+                      mtk_wed_wdma_ring_setup(dev, i, 16);
-+
-+      mtk_wed_hw_init(dev);
-+      mtk_wed_configure_irq(dev, irq_mask);
-+
-       mtk_wed_set_ext_int(dev, true);
-       val = dev->wlan.wpdma_phys |
-             MTK_PCIE_MIRROR_MAP_EN |
-@@ -577,6 +607,7 @@ mtk_wed_start(struct mtk_wed_device *dev
-       val |= BIT(0);
-       regmap_write(dev->hw->mirror, dev->hw->index * 4, val);
-+      mtk_wed_dma_enable(dev);
-       dev->running = true;
- }
---- a/drivers/net/ethernet/mediatek/mtk_wed_regs.h
-+++ b/drivers/net/ethernet/mediatek/mtk_wed_regs.h
-@@ -224,7 +224,11 @@ struct mtk_wdma_desc {
- #define MTK_WDMA_RING_RX(_n)                          (0x100 + (_n) * 0x10)
- #define MTK_WDMA_GLO_CFG                              0x204
--#define MTK_WDMA_GLO_CFG_RX_INFO_PRERES                       GENMASK(28, 26)
-+#define MTK_WDMA_GLO_CFG_TX_DMA_EN                    BIT(0)
-+#define MTK_WDMA_GLO_CFG_RX_DMA_EN                    BIT(2)
-+#define MTK_WDMA_GLO_CFG_RX_INFO3_PRERES              BIT(26)
-+#define MTK_WDMA_GLO_CFG_RX_INFO2_PRERES              BIT(27)
-+#define MTK_WDMA_GLO_CFG_RX_INFO1_PRERES              BIT(28)
- #define MTK_WDMA_RESET_IDX                            0x208
- #define MTK_WDMA_RESET_IDX_TX                         GENMASK(3, 0)
diff --git a/target/linux/generic/backport-5.15/721-v6.0-net-ethernet-mtk_eth_wed-add-wed-support-for-mt7986-.patch b/target/linux/generic/backport-5.15/721-v6.0-net-ethernet-mtk_eth_wed-add-wed-support-for-mt7986-.patch
deleted file mode 100644 (file)
index 00255cd..0000000
+++ /dev/null
@@ -1,942 +0,0 @@
-From 463a71af080fbc77339bee2037fb1e081e3824f7 Mon Sep 17 00:00:00 2001
-Message-Id: <463a71af080fbc77339bee2037fb1e081e3824f7.1662886034.git.lorenzo@kernel.org>
-In-Reply-To: <e5ecb4f619197b93fa682d722452dc8412864cdb.1662886033.git.lorenzo@kernel.org>
-References: <e5ecb4f619197b93fa682d722452dc8412864cdb.1662886033.git.lorenzo@kernel.org>
-From: Lorenzo Bianconi <[email protected]>
-Date: Sat, 27 Aug 2022 16:15:14 +0200
-Subject: [PATCH net-next 2/5] net: ethernet: mtk_eth_wed: add wed support for
- mt7986 chipset
-
-Introduce Wireless Etherne Dispatcher support on transmission side
-for mt7986 chipset
-
-Co-developed-by: Bo Jiao <[email protected]>
-Signed-off-by: Bo Jiao <[email protected]>
-Co-developed-by: Sujuan Chen <[email protected]>
-Signed-off-by: Sujuan Chen <[email protected]>
-Signed-off-by: Lorenzo Bianconi <[email protected]>
----
- drivers/net/ethernet/mediatek/mtk_eth_soc.c   |  34 +-
- drivers/net/ethernet/mediatek/mtk_wed.c       | 371 ++++++++++++++----
- drivers/net/ethernet/mediatek/mtk_wed.h       |   8 +-
- .../net/ethernet/mediatek/mtk_wed_debugfs.c   |   3 +
- drivers/net/ethernet/mediatek/mtk_wed_regs.h  |  81 +++-
- include/linux/soc/mediatek/mtk_wed.h          |   8 +
- 6 files changed, 408 insertions(+), 97 deletions(-)
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-@@ -3890,6 +3890,7 @@ void mtk_eth_set_dma_device(struct mtk_e
- static int mtk_probe(struct platform_device *pdev)
- {
-+      struct resource *res = NULL;
-       struct device_node *mac_np;
-       struct mtk_eth *eth;
-       int err, i;
-@@ -3970,16 +3971,31 @@ static int mtk_probe(struct platform_dev
-               }
-       }
--      for (i = 0;; i++) {
--              struct device_node *np = of_parse_phandle(pdev->dev.of_node,
--                                                        "mediatek,wed", i);
--              void __iomem *wdma;
--
--              if (!np || i >= ARRAY_SIZE(eth->soc->reg_map->wdma_base))
--                      break;
--
--              wdma = eth->base + eth->soc->reg_map->wdma_base[i];
--              mtk_wed_add_hw(np, eth, wdma, i);
-+      if (MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2)) {
-+              res = platform_get_resource(pdev, IORESOURCE_MEM, 0);
-+              if (!res)
-+                      return -EINVAL;
-+      }
-+
-+      if (eth->soc->offload_version) {
-+              for (i = 0;; i++) {
-+                      struct device_node *np;
-+                      phys_addr_t wdma_phy;
-+                      u32 wdma_base;
-+
-+                      if (i >= ARRAY_SIZE(eth->soc->reg_map->wdma_base))
-+                              break;
-+
-+                      np = of_parse_phandle(pdev->dev.of_node,
-+                                            "mediatek,wed", i);
-+                      if (!np)
-+                              break;
-+
-+                      wdma_base = eth->soc->reg_map->wdma_base[i];
-+                      wdma_phy = res ? res->start + wdma_base : 0;
-+                      mtk_wed_add_hw(np, eth, eth->base + wdma_base,
-+                                     wdma_phy, i);
-+              }
-       }
-       for (i = 0; i < 3; i++) {
---- a/drivers/net/ethernet/mediatek/mtk_wed.c
-+++ b/drivers/net/ethernet/mediatek/mtk_wed.c
-@@ -25,6 +25,11 @@
- #define MTK_WED_TX_RING_SIZE          2048
- #define MTK_WED_WDMA_RING_SIZE                1024
-+#define MTK_WED_MAX_GROUP_SIZE                0x100
-+#define MTK_WED_VLD_GROUP_SIZE                0x40
-+#define MTK_WED_PER_GROUP_PKT         128
-+
-+#define MTK_WED_FBUF_SIZE             128
- static struct mtk_wed_hw *hw_list[2];
- static DEFINE_MUTEX(hw_lock);
-@@ -150,10 +155,17 @@ mtk_wed_buffer_alloc(struct mtk_wed_devi
-                       desc->buf0 = cpu_to_le32(buf_phys);
-                       desc->buf1 = cpu_to_le32(buf_phys + txd_size);
--                      ctrl = FIELD_PREP(MTK_WDMA_DESC_CTRL_LEN0, txd_size) |
--                             FIELD_PREP(MTK_WDMA_DESC_CTRL_LEN1,
--                                        MTK_WED_BUF_SIZE - txd_size) |
--                             MTK_WDMA_DESC_CTRL_LAST_SEG1;
-+
-+                      if (dev->hw->version == 1)
-+                              ctrl = FIELD_PREP(MTK_WDMA_DESC_CTRL_LEN0, txd_size) |
-+                                     FIELD_PREP(MTK_WDMA_DESC_CTRL_LEN1,
-+                                                MTK_WED_BUF_SIZE - txd_size) |
-+                                     MTK_WDMA_DESC_CTRL_LAST_SEG1;
-+                      else
-+                              ctrl = FIELD_PREP(MTK_WDMA_DESC_CTRL_LEN0, txd_size) |
-+                                     FIELD_PREP(MTK_WDMA_DESC_CTRL_LEN1_V2,
-+                                                MTK_WED_BUF_SIZE - txd_size) |
-+                                     MTK_WDMA_DESC_CTRL_LAST_SEG0;
-                       desc->ctrl = cpu_to_le32(ctrl);
-                       desc->info = 0;
-                       desc++;
-@@ -209,7 +221,7 @@ mtk_wed_free_ring(struct mtk_wed_device
-       if (!ring->desc)
-               return;
--      dma_free_coherent(dev->hw->dev, ring->size * sizeof(*ring->desc),
-+      dma_free_coherent(dev->hw->dev, ring->size * ring->desc_size,
-                         ring->desc, ring->desc_phys);
- }
-@@ -229,6 +241,14 @@ mtk_wed_set_ext_int(struct mtk_wed_devic
- {
-       u32 mask = MTK_WED_EXT_INT_STATUS_ERROR_MASK;
-+      if (dev->hw->version == 1)
-+              mask |= MTK_WED_EXT_INT_STATUS_TX_DRV_R_RESP_ERR;
-+      else
-+              mask |= MTK_WED_EXT_INT_STATUS_RX_FBUF_LO_TH |
-+                      MTK_WED_EXT_INT_STATUS_RX_FBUF_HI_TH |
-+                      MTK_WED_EXT_INT_STATUS_RX_DRV_COHERENT |
-+                      MTK_WED_EXT_INT_STATUS_TX_DMA_W_RESP_ERR;
-+
-       if (!dev->hw->num_flows)
-               mask &= ~MTK_WED_EXT_INT_STATUS_TKID_WO_PYLD;
-@@ -237,6 +257,20 @@ mtk_wed_set_ext_int(struct mtk_wed_devic
- }
- static void
-+mtk_wed_set_512_support(struct mtk_wed_device *dev, bool enable)
-+{
-+      if (enable) {
-+              wed_w32(dev, MTK_WED_TXDP_CTRL, MTK_WED_TXDP_DW9_OVERWR);
-+              wed_w32(dev, MTK_WED_TXP_DW1,
-+                      FIELD_PREP(MTK_WED_WPDMA_WRITE_TXP, 0x0103));
-+      } else {
-+              wed_w32(dev, MTK_WED_TXP_DW1,
-+                      FIELD_PREP(MTK_WED_WPDMA_WRITE_TXP, 0x0100));
-+              wed_clr(dev, MTK_WED_TXDP_CTRL, MTK_WED_TXDP_DW9_OVERWR);
-+      }
-+}
-+
-+static void
- mtk_wed_dma_disable(struct mtk_wed_device *dev)
- {
-       wed_clr(dev, MTK_WED_WPDMA_GLO_CFG,
-@@ -249,12 +283,22 @@ mtk_wed_dma_disable(struct mtk_wed_devic
-               MTK_WED_GLO_CFG_TX_DMA_EN |
-               MTK_WED_GLO_CFG_RX_DMA_EN);
--      regmap_write(dev->hw->mirror, dev->hw->index * 4, 0);
-       wdma_m32(dev, MTK_WDMA_GLO_CFG,
-                MTK_WDMA_GLO_CFG_TX_DMA_EN |
-                MTK_WDMA_GLO_CFG_RX_INFO1_PRERES |
--               MTK_WDMA_GLO_CFG_RX_INFO2_PRERES |
--               MTK_WDMA_GLO_CFG_RX_INFO3_PRERES, 0);
-+               MTK_WDMA_GLO_CFG_RX_INFO2_PRERES, 0);
-+
-+      if (dev->hw->version == 1) {
-+              regmap_write(dev->hw->mirror, dev->hw->index * 4, 0);
-+              wdma_m32(dev, MTK_WDMA_GLO_CFG,
-+                       MTK_WDMA_GLO_CFG_RX_INFO3_PRERES, 0);
-+      } else {
-+              wed_clr(dev, MTK_WED_WPDMA_GLO_CFG,
-+                      MTK_WED_WPDMA_GLO_CFG_RX_DRV_R0_PKT_PROC |
-+                      MTK_WED_WPDMA_GLO_CFG_RX_DRV_R0_CRX_SYNC);
-+
-+              mtk_wed_set_512_support(dev, false);
-+      }
- }
- static void
-@@ -293,7 +337,7 @@ mtk_wed_detach(struct mtk_wed_device *de
-       mtk_wed_free_buffer(dev);
-       mtk_wed_free_tx_rings(dev);
--      if (of_dma_is_coherent(wlan_node))
-+      if (of_dma_is_coherent(wlan_node) && hw->hifsys)
-               regmap_update_bits(hw->hifsys, HIFSYS_DMA_AG_MAP,
-                                  BIT(hw->index), BIT(hw->index));
-@@ -308,14 +352,69 @@ mtk_wed_detach(struct mtk_wed_device *de
-       mutex_unlock(&hw_lock);
- }
-+#define PCIE_BASE_ADDR0               0x11280000
-+static void
-+mtk_wed_bus_init(struct mtk_wed_device *dev)
-+{
-+      struct device_node *np = dev->hw->eth->dev->of_node;
-+      struct regmap *regs;
-+      u32 val;
-+
-+      regs = syscon_regmap_lookup_by_phandle(np, "mediatek,wed-pcie");
-+      if (IS_ERR(regs))
-+              return;
-+
-+      regmap_update_bits(regs, 0, BIT(0), BIT(0));
-+
-+      wed_w32(dev, MTK_WED_PCIE_INT_CTRL,
-+              FIELD_PREP(MTK_WED_PCIE_INT_CTRL_POLL_EN, 2));
-+
-+      /* pcie interrupt control: pola/source selection */
-+      wed_set(dev, MTK_WED_PCIE_INT_CTRL,
-+              MTK_WED_PCIE_INT_CTRL_MSK_EN_POLA |
-+              FIELD_PREP(MTK_WED_PCIE_INT_CTRL_SRC_SEL, 1));
-+      wed_r32(dev, MTK_WED_PCIE_INT_CTRL);
-+
-+      val = wed_r32(dev, MTK_WED_PCIE_CFG_INTM);
-+      val = wed_r32(dev, MTK_WED_PCIE_CFG_BASE);
-+      wed_w32(dev, MTK_WED_PCIE_CFG_INTM, PCIE_BASE_ADDR0 | 0x180);
-+      wed_w32(dev, MTK_WED_PCIE_CFG_BASE, PCIE_BASE_ADDR0 | 0x184);
-+
-+      val = wed_r32(dev, MTK_WED_PCIE_CFG_INTM);
-+      val = wed_r32(dev, MTK_WED_PCIE_CFG_BASE);
-+
-+      /* pcie interrupt status trigger register */
-+      wed_w32(dev, MTK_WED_PCIE_INT_TRIGGER, BIT(24));
-+      wed_r32(dev, MTK_WED_PCIE_INT_TRIGGER);
-+
-+      /* pola setting */
-+      val = wed_r32(dev, MTK_WED_PCIE_INT_CTRL);
-+      wed_set(dev, MTK_WED_PCIE_INT_CTRL, MTK_WED_PCIE_INT_CTRL_MSK_EN_POLA);
-+}
-+
-+static void
-+mtk_wed_set_wpdma(struct mtk_wed_device *dev)
-+{
-+      if (dev->hw->version == 1) {
-+              wed_w32(dev, MTK_WED_WPDMA_CFG_BASE,  dev->wlan.wpdma_phys);
-+      } else {
-+              mtk_wed_bus_init(dev);
-+
-+              wed_w32(dev, MTK_WED_WPDMA_CFG_BASE,  dev->wlan.wpdma_int);
-+              wed_w32(dev, MTK_WED_WPDMA_CFG_INT_MASK,  dev->wlan.wpdma_mask);
-+              wed_w32(dev, MTK_WED_WPDMA_CFG_TX,  dev->wlan.wpdma_tx);
-+              wed_w32(dev, MTK_WED_WPDMA_CFG_TX_FREE,  dev->wlan.wpdma_txfree);
-+      }
-+}
-+
- static void
- mtk_wed_hw_init_early(struct mtk_wed_device *dev)
- {
-       u32 mask, set;
--      u32 offset;
-       mtk_wed_stop(dev);
-       mtk_wed_reset(dev, MTK_WED_RESET_WED);
-+      mtk_wed_set_wpdma(dev);
-       mask = MTK_WED_WDMA_GLO_CFG_BT_SIZE |
-              MTK_WED_WDMA_GLO_CFG_DYNAMIC_DMAD_RECYCLE |
-@@ -325,17 +424,33 @@ mtk_wed_hw_init_early(struct mtk_wed_dev
-             MTK_WED_WDMA_GLO_CFG_IDLE_DMAD_SUPPLY;
-       wed_m32(dev, MTK_WED_WDMA_GLO_CFG, mask, set);
--      wdma_set(dev, MTK_WDMA_GLO_CFG,
--               MTK_WDMA_GLO_CFG_RX_INFO1_PRERES |
--               MTK_WDMA_GLO_CFG_RX_INFO2_PRERES |
--               MTK_WDMA_GLO_CFG_RX_INFO3_PRERES);
--
--      offset = dev->hw->index ? 0x04000400 : 0;
--      wed_w32(dev, MTK_WED_WDMA_OFFSET0, 0x2a042a20 + offset);
--      wed_w32(dev, MTK_WED_WDMA_OFFSET1, 0x29002800 + offset);
-+      if (dev->hw->version == 1) {
-+              u32 offset = dev->hw->index ? 0x04000400 : 0;
--      wed_w32(dev, MTK_WED_PCIE_CFG_BASE, MTK_PCIE_BASE(dev->hw->index));
--      wed_w32(dev, MTK_WED_WPDMA_CFG_BASE, dev->wlan.wpdma_phys);
-+              wdma_set(dev, MTK_WDMA_GLO_CFG,
-+                       MTK_WDMA_GLO_CFG_RX_INFO1_PRERES |
-+                       MTK_WDMA_GLO_CFG_RX_INFO2_PRERES |
-+                       MTK_WDMA_GLO_CFG_RX_INFO3_PRERES);
-+
-+              wed_w32(dev, MTK_WED_WDMA_OFFSET0, 0x2a042a20 + offset);
-+              wed_w32(dev, MTK_WED_WDMA_OFFSET1, 0x29002800 + offset);
-+              wed_w32(dev, MTK_WED_PCIE_CFG_BASE,
-+                      MTK_PCIE_BASE(dev->hw->index));
-+      } else {
-+              wed_w32(dev, MTK_WED_WDMA_CFG_BASE, dev->hw->wdma_phy);
-+              wed_set(dev, MTK_WED_CTRL, MTK_WED_CTRL_ETH_DMAD_FMT);
-+              wed_w32(dev, MTK_WED_WDMA_OFFSET0,
-+                      FIELD_PREP(MTK_WED_WDMA_OFST0_GLO_INTS,
-+                                 MTK_WDMA_INT_STATUS) |
-+                      FIELD_PREP(MTK_WED_WDMA_OFST0_GLO_CFG,
-+                                 MTK_WDMA_GLO_CFG));
-+
-+              wed_w32(dev, MTK_WED_WDMA_OFFSET1,
-+                      FIELD_PREP(MTK_WED_WDMA_OFST1_TX_CTRL,
-+                                 MTK_WDMA_RING_TX(0)) |
-+                      FIELD_PREP(MTK_WED_WDMA_OFST1_RX_CTRL,
-+                                 MTK_WDMA_RING_RX(0)));
-+      }
- }
- static void
-@@ -355,37 +470,65 @@ mtk_wed_hw_init(struct mtk_wed_device *d
-       wed_w32(dev, MTK_WED_TX_BM_BASE, dev->buf_ring.desc_phys);
--      wed_w32(dev, MTK_WED_TX_BM_TKID,
--              FIELD_PREP(MTK_WED_TX_BM_TKID_START,
--                         dev->wlan.token_start) |
--              FIELD_PREP(MTK_WED_TX_BM_TKID_END,
--                         dev->wlan.token_start + dev->wlan.nbuf - 1));
--
-       wed_w32(dev, MTK_WED_TX_BM_BUF_LEN, MTK_WED_PKT_SIZE);
--      wed_w32(dev, MTK_WED_TX_BM_DYN_THR,
--              FIELD_PREP(MTK_WED_TX_BM_DYN_THR_LO, 1) |
--              MTK_WED_TX_BM_DYN_THR_HI);
-+      if (dev->hw->version == 1) {
-+              wed_w32(dev, MTK_WED_TX_BM_TKID,
-+                      FIELD_PREP(MTK_WED_TX_BM_TKID_START,
-+                                 dev->wlan.token_start) |
-+                      FIELD_PREP(MTK_WED_TX_BM_TKID_END,
-+                                 dev->wlan.token_start +
-+                                 dev->wlan.nbuf - 1));
-+              wed_w32(dev, MTK_WED_TX_BM_DYN_THR,
-+                      FIELD_PREP(MTK_WED_TX_BM_DYN_THR_LO, 1) |
-+                      MTK_WED_TX_BM_DYN_THR_HI);
-+      } else {
-+              wed_w32(dev, MTK_WED_TX_BM_TKID_V2,
-+                      FIELD_PREP(MTK_WED_TX_BM_TKID_START,
-+                                 dev->wlan.token_start) |
-+                      FIELD_PREP(MTK_WED_TX_BM_TKID_END,
-+                                 dev->wlan.token_start +
-+                                 dev->wlan.nbuf - 1));
-+              wed_w32(dev, MTK_WED_TX_BM_DYN_THR,
-+                      FIELD_PREP(MTK_WED_TX_BM_DYN_THR_LO_V2, 0) |
-+                      MTK_WED_TX_BM_DYN_THR_HI_V2);
-+              wed_w32(dev, MTK_WED_TX_TKID_CTRL,
-+                      MTK_WED_TX_TKID_CTRL_PAUSE |
-+                      FIELD_PREP(MTK_WED_TX_TKID_CTRL_VLD_GRP_NUM,
-+                                 dev->buf_ring.size / 128) |
-+                      FIELD_PREP(MTK_WED_TX_TKID_CTRL_RSV_GRP_NUM,
-+                                 dev->buf_ring.size / 128));
-+              wed_w32(dev, MTK_WED_TX_TKID_DYN_THR,
-+                      FIELD_PREP(MTK_WED_TX_TKID_DYN_THR_LO, 0) |
-+                      MTK_WED_TX_TKID_DYN_THR_HI);
-+      }
-       mtk_wed_reset(dev, MTK_WED_RESET_TX_BM);
--      wed_set(dev, MTK_WED_CTRL,
--              MTK_WED_CTRL_WED_TX_BM_EN |
--              MTK_WED_CTRL_WED_TX_FREE_AGENT_EN);
-+      if (dev->hw->version == 1)
-+              wed_set(dev, MTK_WED_CTRL,
-+                      MTK_WED_CTRL_WED_TX_BM_EN |
-+                      MTK_WED_CTRL_WED_TX_FREE_AGENT_EN);
-+      else
-+              wed_clr(dev, MTK_WED_TX_TKID_CTRL, MTK_WED_TX_TKID_CTRL_PAUSE);
-       wed_clr(dev, MTK_WED_TX_BM_CTRL, MTK_WED_TX_BM_CTRL_PAUSE);
- }
- static void
--mtk_wed_ring_reset(struct mtk_wdma_desc *desc, int size)
-+mtk_wed_ring_reset(struct mtk_wed_ring *ring, int size)
- {
-+      void *head = (void *)ring->desc;
-       int i;
-       for (i = 0; i < size; i++) {
--              desc[i].buf0 = 0;
--              desc[i].ctrl = cpu_to_le32(MTK_WDMA_DESC_CTRL_DMA_DONE);
--              desc[i].buf1 = 0;
--              desc[i].info = 0;
-+              struct mtk_wdma_desc *desc;
-+
-+              desc = (struct mtk_wdma_desc *)(head + i * ring->desc_size);
-+              desc->buf0 = 0;
-+              desc->ctrl = cpu_to_le32(MTK_WDMA_DESC_CTRL_DMA_DONE);
-+              desc->buf1 = 0;
-+              desc->info = 0;
-       }
- }
-@@ -436,12 +579,10 @@ mtk_wed_reset_dma(struct mtk_wed_device
-       int i;
-       for (i = 0; i < ARRAY_SIZE(dev->tx_ring); i++) {
--              struct mtk_wdma_desc *desc = dev->tx_ring[i].desc;
--
--              if (!desc)
-+              if (!dev->tx_ring[i].desc)
-                       continue;
--              mtk_wed_ring_reset(desc, MTK_WED_TX_RING_SIZE);
-+              mtk_wed_ring_reset(&dev->tx_ring[i], MTK_WED_TX_RING_SIZE);
-       }
-       if (mtk_wed_poll_busy(dev))
-@@ -498,16 +639,16 @@ mtk_wed_reset_dma(struct mtk_wed_device
- static int
- mtk_wed_ring_alloc(struct mtk_wed_device *dev, struct mtk_wed_ring *ring,
--                 int size)
-+                 int size, u32 desc_size)
- {
--      ring->desc = dma_alloc_coherent(dev->hw->dev,
--                                      size * sizeof(*ring->desc),
-+      ring->desc = dma_alloc_coherent(dev->hw->dev, size * desc_size,
-                                       &ring->desc_phys, GFP_KERNEL);
-       if (!ring->desc)
-               return -ENOMEM;
-+      ring->desc_size = desc_size;
-       ring->size = size;
--      mtk_wed_ring_reset(ring->desc, size);
-+      mtk_wed_ring_reset(ring, size);
-       return 0;
- }
-@@ -515,9 +656,10 @@ mtk_wed_ring_alloc(struct mtk_wed_device
- static int
- mtk_wed_wdma_ring_setup(struct mtk_wed_device *dev, int idx, int size)
- {
-+      u32 desc_size = sizeof(struct mtk_wdma_desc) * dev->hw->version;
-       struct mtk_wed_ring *wdma = &dev->tx_wdma[idx];
--      if (mtk_wed_ring_alloc(dev, wdma, MTK_WED_WDMA_RING_SIZE))
-+      if (mtk_wed_ring_alloc(dev, wdma, MTK_WED_WDMA_RING_SIZE, desc_size))
-               return -ENOMEM;
-       wdma_w32(dev, MTK_WDMA_RING_RX(idx) + MTK_WED_RING_OFS_BASE,
-@@ -546,16 +688,41 @@ mtk_wed_configure_irq(struct mtk_wed_dev
-               MTK_WED_CTRL_WED_TX_BM_EN |
-               MTK_WED_CTRL_WED_TX_FREE_AGENT_EN);
--      wed_w32(dev, MTK_WED_PCIE_INT_TRIGGER,
--              MTK_WED_PCIE_INT_TRIGGER_STATUS);
-+      if (dev->hw->version == 1) {
-+              wed_w32(dev, MTK_WED_PCIE_INT_TRIGGER,
-+                      MTK_WED_PCIE_INT_TRIGGER_STATUS);
-+
-+              wed_w32(dev, MTK_WED_WPDMA_INT_TRIGGER,
-+                      MTK_WED_WPDMA_INT_TRIGGER_RX_DONE |
-+                      MTK_WED_WPDMA_INT_TRIGGER_TX_DONE);
--      wed_w32(dev, MTK_WED_WPDMA_INT_TRIGGER,
--              MTK_WED_WPDMA_INT_TRIGGER_RX_DONE |
--              MTK_WED_WPDMA_INT_TRIGGER_TX_DONE);
-+              wed_clr(dev, MTK_WED_WDMA_INT_CTRL, wdma_mask);
-+      } else {
-+              /* initail tx interrupt trigger */
-+              wed_w32(dev, MTK_WED_WPDMA_INT_CTRL_TX,
-+                      MTK_WED_WPDMA_INT_CTRL_TX0_DONE_EN |
-+                      MTK_WED_WPDMA_INT_CTRL_TX0_DONE_CLR |
-+                      MTK_WED_WPDMA_INT_CTRL_TX1_DONE_EN |
-+                      MTK_WED_WPDMA_INT_CTRL_TX1_DONE_CLR |
-+                      FIELD_PREP(MTK_WED_WPDMA_INT_CTRL_TX0_DONE_TRIG,
-+                                 dev->wlan.tx_tbit[0]) |
-+                      FIELD_PREP(MTK_WED_WPDMA_INT_CTRL_TX1_DONE_TRIG,
-+                                 dev->wlan.tx_tbit[1]));
-+
-+              /* initail txfree interrupt trigger */
-+              wed_w32(dev, MTK_WED_WPDMA_INT_CTRL_TX_FREE,
-+                      MTK_WED_WPDMA_INT_CTRL_TX_FREE_DONE_EN |
-+                      MTK_WED_WPDMA_INT_CTRL_TX_FREE_DONE_CLR |
-+                      FIELD_PREP(MTK_WED_WPDMA_INT_CTRL_TX_FREE_DONE_TRIG,
-+                                 dev->wlan.txfree_tbit));
-+
-+              wed_w32(dev, MTK_WED_WDMA_INT_CLR, wdma_mask);
-+              wed_set(dev, MTK_WED_WDMA_INT_CTRL,
-+                      FIELD_PREP(MTK_WED_WDMA_INT_CTRL_POLL_SRC_SEL,
-+                                 dev->wdma_idx));
-+      }
--      /* initail wdma interrupt agent */
-       wed_w32(dev, MTK_WED_WDMA_INT_TRIGGER, wdma_mask);
--      wed_clr(dev, MTK_WED_WDMA_INT_CTRL, wdma_mask);
-       wdma_w32(dev, MTK_WDMA_INT_MASK, wdma_mask);
-       wdma_w32(dev, MTK_WDMA_INT_GRP2, wdma_mask);
-@@ -580,14 +747,28 @@ mtk_wed_dma_enable(struct mtk_wed_device
-       wdma_set(dev, MTK_WDMA_GLO_CFG,
-                MTK_WDMA_GLO_CFG_TX_DMA_EN |
-                MTK_WDMA_GLO_CFG_RX_INFO1_PRERES |
--               MTK_WDMA_GLO_CFG_RX_INFO2_PRERES |
--               MTK_WDMA_GLO_CFG_RX_INFO3_PRERES);
-+               MTK_WDMA_GLO_CFG_RX_INFO2_PRERES);
-+
-+      if (dev->hw->version == 1) {
-+              wdma_set(dev, MTK_WDMA_GLO_CFG,
-+                       MTK_WDMA_GLO_CFG_RX_INFO3_PRERES);
-+      } else {
-+              wed_set(dev, MTK_WED_WPDMA_CTRL,
-+                      MTK_WED_WPDMA_CTRL_SDL1_FIXED);
-+
-+              wed_set(dev, MTK_WED_WPDMA_GLO_CFG,
-+                      MTK_WED_WPDMA_GLO_CFG_RX_DRV_R0_PKT_PROC |
-+                      MTK_WED_WPDMA_GLO_CFG_RX_DRV_R0_CRX_SYNC);
-+
-+              wed_clr(dev, MTK_WED_WPDMA_GLO_CFG,
-+                      MTK_WED_WPDMA_GLO_CFG_TX_TKID_KEEP |
-+                      MTK_WED_WPDMA_GLO_CFG_TX_DMAD_DW3_PREV);
-+      }
- }
- static void
- mtk_wed_start(struct mtk_wed_device *dev, u32 irq_mask)
- {
--      u32 val;
-       int i;
-       for (i = 0; i < ARRAY_SIZE(dev->tx_wdma); i++)
-@@ -598,14 +779,17 @@ mtk_wed_start(struct mtk_wed_device *dev
-       mtk_wed_configure_irq(dev, irq_mask);
-       mtk_wed_set_ext_int(dev, true);
--      val = dev->wlan.wpdma_phys |
--            MTK_PCIE_MIRROR_MAP_EN |
--            FIELD_PREP(MTK_PCIE_MIRROR_MAP_WED_ID, dev->hw->index);
--
--      if (dev->hw->index)
--              val |= BIT(1);
--      val |= BIT(0);
--      regmap_write(dev->hw->mirror, dev->hw->index * 4, val);
-+
-+      if (dev->hw->version == 1) {
-+              u32 val = dev->wlan.wpdma_phys | MTK_PCIE_MIRROR_MAP_EN |
-+                        FIELD_PREP(MTK_PCIE_MIRROR_MAP_WED_ID,
-+                                   dev->hw->index);
-+
-+              val |= BIT(0) | (BIT(1) * !!dev->hw->index);
-+              regmap_write(dev->hw->mirror, dev->hw->index * 4, val);
-+      } else {
-+              mtk_wed_set_512_support(dev, true);
-+      }
-       mtk_wed_dma_enable(dev);
-       dev->running = true;
-@@ -639,7 +823,9 @@ mtk_wed_attach(struct mtk_wed_device *de
-               goto out;
-       }
--      dev_info(&dev->wlan.pci_dev->dev, "attaching wed device %d\n", hw->index);
-+      dev_info(&dev->wlan.pci_dev->dev,
-+               "attaching wed device %d version %d\n",
-+               hw->index, hw->version);
-       dev->hw = hw;
-       dev->dev = hw->dev;
-@@ -657,7 +843,9 @@ mtk_wed_attach(struct mtk_wed_device *de
-       }
-       mtk_wed_hw_init_early(dev);
--      regmap_update_bits(hw->hifsys, HIFSYS_DMA_AG_MAP, BIT(hw->index), 0);
-+      if (hw->hifsys)
-+              regmap_update_bits(hw->hifsys, HIFSYS_DMA_AG_MAP,
-+                                 BIT(hw->index), 0);
- out:
-       mutex_unlock(&hw_lock);
-@@ -684,7 +872,8 @@ mtk_wed_tx_ring_setup(struct mtk_wed_dev
-       BUG_ON(idx >= ARRAY_SIZE(dev->tx_ring));
--      if (mtk_wed_ring_alloc(dev, ring, MTK_WED_TX_RING_SIZE))
-+      if (mtk_wed_ring_alloc(dev, ring, MTK_WED_TX_RING_SIZE,
-+                             sizeof(*ring->desc)))
-               return -ENOMEM;
-       if (mtk_wed_wdma_ring_setup(dev, idx, MTK_WED_WDMA_RING_SIZE))
-@@ -711,21 +900,21 @@ static int
- mtk_wed_txfree_ring_setup(struct mtk_wed_device *dev, void __iomem *regs)
- {
-       struct mtk_wed_ring *ring = &dev->txfree_ring;
--      int i;
-+      int i, index = dev->hw->version == 1;
-       /*
-        * For txfree event handling, the same DMA ring is shared between WED
-        * and WLAN. The WLAN driver accesses the ring index registers through
-        * WED
-        */
--      ring->reg_base = MTK_WED_RING_RX(1);
-+      ring->reg_base = MTK_WED_RING_RX(index);
-       ring->wpdma = regs;
-       for (i = 0; i < 12; i += 4) {
-               u32 val = readl(regs + i);
--              wed_w32(dev, MTK_WED_RING_RX(1) + i, val);
--              wed_w32(dev, MTK_WED_WPDMA_RING_RX(1) + i, val);
-+              wed_w32(dev, MTK_WED_RING_RX(index) + i, val);
-+              wed_w32(dev, MTK_WED_WPDMA_RING_RX(index) + i, val);
-       }
-       return 0;
-@@ -734,11 +923,19 @@ mtk_wed_txfree_ring_setup(struct mtk_wed
- static u32
- mtk_wed_irq_get(struct mtk_wed_device *dev, u32 mask)
- {
--      u32 val;
-+      u32 val, ext_mask = MTK_WED_EXT_INT_STATUS_ERROR_MASK;
-+
-+      if (dev->hw->version == 1)
-+              ext_mask |= MTK_WED_EXT_INT_STATUS_TX_DRV_R_RESP_ERR;
-+      else
-+              ext_mask |= MTK_WED_EXT_INT_STATUS_RX_FBUF_LO_TH |
-+                          MTK_WED_EXT_INT_STATUS_RX_FBUF_HI_TH |
-+                          MTK_WED_EXT_INT_STATUS_RX_DRV_COHERENT |
-+                          MTK_WED_EXT_INT_STATUS_TX_DMA_W_RESP_ERR;
-       val = wed_r32(dev, MTK_WED_EXT_INT_STATUS);
-       wed_w32(dev, MTK_WED_EXT_INT_STATUS, val);
--      val &= MTK_WED_EXT_INT_STATUS_ERROR_MASK;
-+      val &= ext_mask;
-       if (!dev->hw->num_flows)
-               val &= ~MTK_WED_EXT_INT_STATUS_TKID_WO_PYLD;
-       if (val && net_ratelimit())
-@@ -813,7 +1010,8 @@ out:
- }
- void mtk_wed_add_hw(struct device_node *np, struct mtk_eth *eth,
--                  void __iomem *wdma, int index)
-+                  void __iomem *wdma, phys_addr_t wdma_phy,
-+                  int index)
- {
-       static const struct mtk_wed_ops wed_ops = {
-               .attach = mtk_wed_attach,
-@@ -860,26 +1058,33 @@ void mtk_wed_add_hw(struct device_node *
-       hw = kzalloc(sizeof(*hw), GFP_KERNEL);
-       if (!hw)
-               goto unlock;
-+
-       hw->node = np;
-       hw->regs = regs;
-       hw->eth = eth;
-       hw->dev = &pdev->dev;
-+      hw->wdma_phy = wdma_phy;
-       hw->wdma = wdma;
-       hw->index = index;
-       hw->irq = irq;
--      hw->mirror = syscon_regmap_lookup_by_phandle(eth_np,
--                                                   "mediatek,pcie-mirror");
--      hw->hifsys = syscon_regmap_lookup_by_phandle(eth_np,
--                                                   "mediatek,hifsys");
--      if (IS_ERR(hw->mirror) || IS_ERR(hw->hifsys)) {
--              kfree(hw);
--              goto unlock;
--      }
-+      hw->version = MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2) ? 2 : 1;
--      if (!index) {
--              regmap_write(hw->mirror, 0, 0);
--              regmap_write(hw->mirror, 4, 0);
-+      if (hw->version == 1) {
-+              hw->mirror = syscon_regmap_lookup_by_phandle(eth_np,
-+                              "mediatek,pcie-mirror");
-+              hw->hifsys = syscon_regmap_lookup_by_phandle(eth_np,
-+                              "mediatek,hifsys");
-+              if (IS_ERR(hw->mirror) || IS_ERR(hw->hifsys)) {
-+                      kfree(hw);
-+                      goto unlock;
-+              }
-+
-+              if (!index) {
-+                      regmap_write(hw->mirror, 0, 0);
-+                      regmap_write(hw->mirror, 4, 0);
-+              }
-       }
-+
-       mtk_wed_hw_add_debugfs(hw);
-       hw_list[index] = hw;
---- a/drivers/net/ethernet/mediatek/mtk_wed.h
-+++ b/drivers/net/ethernet/mediatek/mtk_wed.h
-@@ -18,11 +18,13 @@ struct mtk_wed_hw {
-       struct regmap *hifsys;
-       struct device *dev;
-       void __iomem *wdma;
-+      phys_addr_t wdma_phy;
-       struct regmap *mirror;
-       struct dentry *debugfs_dir;
-       struct mtk_wed_device *wed_dev;
-       u32 debugfs_reg;
-       u32 num_flows;
-+      u8 version;
-       char dirname[5];
-       int irq;
-       int index;
-@@ -101,14 +103,16 @@ wpdma_txfree_w32(struct mtk_wed_device *
- }
- void mtk_wed_add_hw(struct device_node *np, struct mtk_eth *eth,
--                  void __iomem *wdma, int index);
-+                  void __iomem *wdma, phys_addr_t wdma_phy,
-+                  int index);
- void mtk_wed_exit(void);
- int mtk_wed_flow_add(int index);
- void mtk_wed_flow_remove(int index);
- #else
- static inline void
- mtk_wed_add_hw(struct device_node *np, struct mtk_eth *eth,
--             void __iomem *wdma, int index)
-+             void __iomem *wdma, phys_addr_t wdma_phy,
-+             int index)
- {
- }
- static inline void
---- a/drivers/net/ethernet/mediatek/mtk_wed_debugfs.c
-+++ b/drivers/net/ethernet/mediatek/mtk_wed_debugfs.c
-@@ -116,6 +116,9 @@ wed_txinfo_show(struct seq_file *s, void
-               DUMP_WDMA(WDMA_GLO_CFG),
-               DUMP_WDMA_RING(WDMA_RING_RX(0)),
-               DUMP_WDMA_RING(WDMA_RING_RX(1)),
-+
-+              DUMP_STR("TX FREE"),
-+              DUMP_WED(WED_RX_MIB(0)),
-       };
-       struct mtk_wed_hw *hw = s->private;
-       struct mtk_wed_device *dev = hw->wed_dev;
---- a/drivers/net/ethernet/mediatek/mtk_wed_regs.h
-+++ b/drivers/net/ethernet/mediatek/mtk_wed_regs.h
-@@ -5,6 +5,7 @@
- #define __MTK_WED_REGS_H
- #define MTK_WDMA_DESC_CTRL_LEN1                       GENMASK(14, 0)
-+#define MTK_WDMA_DESC_CTRL_LEN1_V2            GENMASK(13, 0)
- #define MTK_WDMA_DESC_CTRL_LAST_SEG1          BIT(15)
- #define MTK_WDMA_DESC_CTRL_BURST              BIT(16)
- #define MTK_WDMA_DESC_CTRL_LEN0                       GENMASK(29, 16)
-@@ -41,6 +42,7 @@ struct mtk_wdma_desc {
- #define MTK_WED_CTRL_RESERVE_EN                               BIT(12)
- #define MTK_WED_CTRL_RESERVE_BUSY                     BIT(13)
- #define MTK_WED_CTRL_FINAL_DIDX_READ                  BIT(24)
-+#define MTK_WED_CTRL_ETH_DMAD_FMT                     BIT(25)
- #define MTK_WED_CTRL_MIB_READ_CLEAR                   BIT(28)
- #define MTK_WED_EXT_INT_STATUS                                0x020
-@@ -57,7 +59,8 @@ struct mtk_wdma_desc {
- #define MTK_WED_EXT_INT_STATUS_RX_DRV_INIT_WDMA_EN    BIT(19)
- #define MTK_WED_EXT_INT_STATUS_RX_DRV_BM_DMAD_COHERENT        BIT(20)
- #define MTK_WED_EXT_INT_STATUS_TX_DRV_R_RESP_ERR      BIT(21)
--#define MTK_WED_EXT_INT_STATUS_TX_DRV_W_RESP_ERR      BIT(22)
-+#define MTK_WED_EXT_INT_STATUS_TX_DMA_R_RESP_ERR      BIT(22)
-+#define MTK_WED_EXT_INT_STATUS_TX_DMA_W_RESP_ERR      BIT(23)
- #define MTK_WED_EXT_INT_STATUS_RX_DRV_DMA_RECYCLE     BIT(24)
- #define MTK_WED_EXT_INT_STATUS_ERROR_MASK             (MTK_WED_EXT_INT_STATUS_TF_LEN_ERR | \
-                                                        MTK_WED_EXT_INT_STATUS_TKID_WO_PYLD | \
-@@ -65,8 +68,7 @@ struct mtk_wdma_desc {
-                                                        MTK_WED_EXT_INT_STATUS_RX_DRV_R_RESP_ERR | \
-                                                        MTK_WED_EXT_INT_STATUS_RX_DRV_W_RESP_ERR | \
-                                                        MTK_WED_EXT_INT_STATUS_RX_DRV_INIT_WDMA_EN | \
--                                                       MTK_WED_EXT_INT_STATUS_TX_DRV_R_RESP_ERR | \
--                                                       MTK_WED_EXT_INT_STATUS_TX_DRV_W_RESP_ERR)
-+                                                       MTK_WED_EXT_INT_STATUS_TX_DMA_R_RESP_ERR)
- #define MTK_WED_EXT_INT_MASK                          0x028
-@@ -81,6 +83,7 @@ struct mtk_wdma_desc {
- #define MTK_WED_TX_BM_BASE                            0x084
- #define MTK_WED_TX_BM_TKID                            0x088
-+#define MTK_WED_TX_BM_TKID_V2                         0x0c8
- #define MTK_WED_TX_BM_TKID_START                      GENMASK(15, 0)
- #define MTK_WED_TX_BM_TKID_END                                GENMASK(31, 16)
-@@ -94,7 +97,25 @@ struct mtk_wdma_desc {
- #define MTK_WED_TX_BM_DYN_THR                         0x0a0
- #define MTK_WED_TX_BM_DYN_THR_LO                      GENMASK(6, 0)
-+#define MTK_WED_TX_BM_DYN_THR_LO_V2                   GENMASK(8, 0)
- #define MTK_WED_TX_BM_DYN_THR_HI                      GENMASK(22, 16)
-+#define MTK_WED_TX_BM_DYN_THR_HI_V2                   GENMASK(24, 16)
-+
-+#define MTK_WED_TX_TKID_CTRL                          0x0c0
-+#define MTK_WED_TX_TKID_CTRL_VLD_GRP_NUM              GENMASK(6, 0)
-+#define MTK_WED_TX_TKID_CTRL_RSV_GRP_NUM              GENMASK(22, 16)
-+#define MTK_WED_TX_TKID_CTRL_PAUSE                    BIT(28)
-+
-+#define MTK_WED_TX_TKID_DYN_THR                               0x0e0
-+#define MTK_WED_TX_TKID_DYN_THR_LO                    GENMASK(6, 0)
-+#define MTK_WED_TX_TKID_DYN_THR_HI                    GENMASK(22, 16)
-+
-+#define MTK_WED_TXP_DW0                                       0x120
-+#define MTK_WED_TXP_DW1                                       0x124
-+#define MTK_WED_WPDMA_WRITE_TXP                               GENMASK(31, 16)
-+#define MTK_WED_TXDP_CTRL                             0x130
-+#define MTK_WED_TXDP_DW9_OVERWR                               BIT(9)
-+#define MTK_WED_RX_BM_TKID_MIB                                0x1cc
- #define MTK_WED_INT_STATUS                            0x200
- #define MTK_WED_INT_MASK                              0x204
-@@ -125,6 +146,7 @@ struct mtk_wdma_desc {
- #define MTK_WED_RESET_IDX_RX                          GENMASK(17, 16)
- #define MTK_WED_TX_MIB(_n)                            (0x2a0 + (_n) * 4)
-+#define MTK_WED_RX_MIB(_n)                            (0x2e0 + (_n) * 4)
- #define MTK_WED_RING_TX(_n)                           (0x300 + (_n) * 0x10)
-@@ -155,21 +177,62 @@ struct mtk_wdma_desc {
- #define MTK_WED_WPDMA_GLO_CFG_BYTE_SWAP                       BIT(29)
- #define MTK_WED_WPDMA_GLO_CFG_RX_2B_OFFSET            BIT(31)
-+/* CONFIG_MEDIATEK_NETSYS_V2 */
-+#define MTK_WED_WPDMA_GLO_CFG_RX_DRV_R0_PKT_PROC      BIT(4)
-+#define MTK_WED_WPDMA_GLO_CFG_RX_DRV_R1_PKT_PROC      BIT(5)
-+#define MTK_WED_WPDMA_GLO_CFG_RX_DRV_R0_CRX_SYNC      BIT(6)
-+#define MTK_WED_WPDMA_GLO_CFG_RX_DRV_R1_CRX_SYNC      BIT(7)
-+#define MTK_WED_WPDMA_GLO_CFG_RX_DRV_EVENT_PKT_FMT_VER        GENMASK(18, 16)
-+#define MTK_WED_WPDMA_GLO_CFG_RX_DRV_UNSUPPORT_FMT    BIT(19)
-+#define MTK_WED_WPDMA_GLO_CFG_RX_DRV_UEVENT_PKT_FMT_CHK BIT(20)
-+#define MTK_WED_WPDMA_GLO_CFG_RX_DDONE2_WR            BIT(21)
-+#define MTK_WED_WPDMA_GLO_CFG_TX_TKID_KEEP            BIT(24)
-+#define MTK_WED_WPDMA_GLO_CFG_TX_DMAD_DW3_PREV                BIT(28)
-+
- #define MTK_WED_WPDMA_RESET_IDX                               0x50c
- #define MTK_WED_WPDMA_RESET_IDX_TX                    GENMASK(3, 0)
- #define MTK_WED_WPDMA_RESET_IDX_RX                    GENMASK(17, 16)
-+#define MTK_WED_WPDMA_CTRL                            0x518
-+#define MTK_WED_WPDMA_CTRL_SDL1_FIXED                 BIT(31)
-+
- #define MTK_WED_WPDMA_INT_CTRL                                0x520
- #define MTK_WED_WPDMA_INT_CTRL_SUBRT_ADV              BIT(21)
- #define MTK_WED_WPDMA_INT_MASK                                0x524
-+#define MTK_WED_WPDMA_INT_CTRL_TX                     0x530
-+#define MTK_WED_WPDMA_INT_CTRL_TX0_DONE_EN            BIT(0)
-+#define MTK_WED_WPDMA_INT_CTRL_TX0_DONE_CLR           BIT(1)
-+#define MTK_WED_WPDMA_INT_CTRL_TX0_DONE_TRIG          GENMASK(6, 2)
-+#define MTK_WED_WPDMA_INT_CTRL_TX1_DONE_EN            BIT(8)
-+#define MTK_WED_WPDMA_INT_CTRL_TX1_DONE_CLR           BIT(9)
-+#define MTK_WED_WPDMA_INT_CTRL_TX1_DONE_TRIG          GENMASK(14, 10)
-+
-+#define MTK_WED_WPDMA_INT_CTRL_RX                     0x534
-+
-+#define MTK_WED_WPDMA_INT_CTRL_TX_FREE                        0x538
-+#define MTK_WED_WPDMA_INT_CTRL_TX_FREE_DONE_EN                BIT(0)
-+#define MTK_WED_WPDMA_INT_CTRL_TX_FREE_DONE_CLR               BIT(1)
-+#define MTK_WED_WPDMA_INT_CTRL_TX_FREE_DONE_TRIG      GENMASK(6, 2)
-+
- #define MTK_WED_PCIE_CFG_BASE                         0x560
-+#define MTK_WED_PCIE_CFG_BASE                         0x560
-+#define MTK_WED_PCIE_CFG_INTM                         0x564
-+#define MTK_WED_PCIE_CFG_MSIS                         0x568
- #define MTK_WED_PCIE_INT_TRIGGER                      0x570
- #define MTK_WED_PCIE_INT_TRIGGER_STATUS                       BIT(16)
-+#define MTK_WED_PCIE_INT_CTRL                         0x57c
-+#define MTK_WED_PCIE_INT_CTRL_MSK_EN_POLA             BIT(20)
-+#define MTK_WED_PCIE_INT_CTRL_SRC_SEL                 GENMASK(17, 16)
-+#define MTK_WED_PCIE_INT_CTRL_POLL_EN                 GENMASK(13, 12)
-+
- #define MTK_WED_WPDMA_CFG_BASE                                0x580
-+#define MTK_WED_WPDMA_CFG_INT_MASK                    0x584
-+#define MTK_WED_WPDMA_CFG_TX                          0x588
-+#define MTK_WED_WPDMA_CFG_TX_FREE                     0x58c
- #define MTK_WED_WPDMA_TX_MIB(_n)                      (0x5a0 + (_n) * 4)
- #define MTK_WED_WPDMA_TX_COHERENT_MIB(_n)             (0x5d0 + (_n) * 4)
-@@ -203,15 +266,24 @@ struct mtk_wdma_desc {
- #define MTK_WED_WDMA_RESET_IDX_RX                     GENMASK(17, 16)
- #define MTK_WED_WDMA_RESET_IDX_DRV                    GENMASK(25, 24)
-+#define MTK_WED_WDMA_INT_CLR                          0xa24
-+#define MTK_WED_WDMA_INT_CLR_RX_DONE                  GENMASK(17, 16)
-+
- #define MTK_WED_WDMA_INT_TRIGGER                      0xa28
- #define MTK_WED_WDMA_INT_TRIGGER_RX_DONE              GENMASK(17, 16)
- #define MTK_WED_WDMA_INT_CTRL                         0xa2c
- #define MTK_WED_WDMA_INT_CTRL_POLL_SRC_SEL            GENMASK(17, 16)
-+#define MTK_WED_WDMA_CFG_BASE                         0xaa0
- #define MTK_WED_WDMA_OFFSET0                          0xaa4
- #define MTK_WED_WDMA_OFFSET1                          0xaa8
-+#define MTK_WED_WDMA_OFST0_GLO_INTS                   GENMASK(15, 0)
-+#define MTK_WED_WDMA_OFST0_GLO_CFG                    GENMASK(31, 16)
-+#define MTK_WED_WDMA_OFST1_TX_CTRL                    GENMASK(15, 0)
-+#define MTK_WED_WDMA_OFST1_RX_CTRL                    GENMASK(31, 16)
-+
- #define MTK_WED_WDMA_RX_MIB(_n)                               (0xae0 + (_n) * 4)
- #define MTK_WED_WDMA_RX_RECYCLE_MIB(_n)                       (0xae8 + (_n) * 4)
- #define MTK_WED_WDMA_RX_PROCESSED_MIB(_n)             (0xaf0 + (_n) * 4)
-@@ -221,6 +293,7 @@ struct mtk_wdma_desc {
- #define MTK_WED_RING_OFS_CPU_IDX                      0x08
- #define MTK_WED_RING_OFS_DMA_IDX                      0x0c
-+#define MTK_WDMA_RING_TX(_n)                          (0x000 + (_n) * 0x10)
- #define MTK_WDMA_RING_RX(_n)                          (0x100 + (_n) * 0x10)
- #define MTK_WDMA_GLO_CFG                              0x204
-@@ -234,6 +307,8 @@ struct mtk_wdma_desc {
- #define MTK_WDMA_RESET_IDX_TX                         GENMASK(3, 0)
- #define MTK_WDMA_RESET_IDX_RX                         GENMASK(17, 16)
-+#define MTK_WDMA_INT_STATUS                           0x220
-+
- #define MTK_WDMA_INT_MASK                             0x228
- #define MTK_WDMA_INT_MASK_TX_DONE                     GENMASK(3, 0)
- #define MTK_WDMA_INT_MASK_RX_DONE                     GENMASK(17, 16)
---- a/include/linux/soc/mediatek/mtk_wed.h
-+++ b/include/linux/soc/mediatek/mtk_wed.h
-@@ -14,6 +14,7 @@ struct mtk_wdma_desc;
- struct mtk_wed_ring {
-       struct mtk_wdma_desc *desc;
-       dma_addr_t desc_phys;
-+      u32 desc_size;
-       int size;
-       u32 reg_base;
-@@ -45,10 +46,17 @@ struct mtk_wed_device {
-               struct pci_dev *pci_dev;
-               u32 wpdma_phys;
-+              u32 wpdma_int;
-+              u32 wpdma_mask;
-+              u32 wpdma_tx;
-+              u32 wpdma_txfree;
-               u16 token_start;
-               unsigned int nbuf;
-+              u8 tx_tbit[MTK_WED_TX_QUEUES];
-+              u8 txfree_tbit;
-+
-               u32 (*init_buf)(void *ptr, dma_addr_t phys, int token_id);
-               int (*offload_enable)(struct mtk_wed_device *wed);
-               void (*offload_disable)(struct mtk_wed_device *wed);
diff --git a/target/linux/generic/backport-5.15/722-v6.0-net-ethernet-mtk_eth_wed-add-axi-bus-support.patch b/target/linux/generic/backport-5.15/722-v6.0-net-ethernet-mtk_eth_wed-add-axi-bus-support.patch
deleted file mode 100644 (file)
index f4b78a2..0000000
+++ /dev/null
@@ -1,230 +0,0 @@
-From 6e1df49f330dce7c58a39d6772f1385b6887bb03 Mon Sep 17 00:00:00 2001
-Message-Id: <6e1df49f330dce7c58a39d6772f1385b6887bb03.1662990860.git.lorenzo@kernel.org>
-From: Lorenzo Bianconi <[email protected]>
-Date: Thu, 8 Sep 2022 11:26:10 +0200
-Subject: [PATCH net-next] net: ethernet: mtk_eth_wed: add axi bus support
-
-Other than pcie bus, introduce support for axi bus to mtk wed driver.
-Axi bus is used to connect mt7986-wmac soc chip available on mt7986
-device.
-
-Co-developed-by: Bo Jiao <[email protected]>
-Signed-off-by: Bo Jiao <[email protected]>
-Co-developed-by: Sujuan Chen <[email protected]>
-Signed-off-by: Sujuan Chen <[email protected]>
-Signed-off-by: Lorenzo Bianconi <[email protected]>
----
- drivers/net/ethernet/mediatek/mtk_wed.c      | 116 +++++++++++++------
- drivers/net/ethernet/mediatek/mtk_wed_regs.h |   2 +
- include/linux/soc/mediatek/mtk_wed.h         |  11 +-
- 3 files changed, 91 insertions(+), 38 deletions(-)
-
---- a/drivers/net/ethernet/mediatek/mtk_wed.c
-+++ b/drivers/net/ethernet/mediatek/mtk_wed.c
-@@ -85,11 +85,31 @@ static struct mtk_wed_hw *
- mtk_wed_assign(struct mtk_wed_device *dev)
- {
-       struct mtk_wed_hw *hw;
-+      int i;
-+
-+      if (dev->wlan.bus_type == MTK_WED_BUS_PCIE) {
-+              hw = hw_list[pci_domain_nr(dev->wlan.pci_dev->bus)];
-+              if (!hw)
-+                      return NULL;
-+
-+              if (!hw->wed_dev)
-+                      goto out;
-+
-+              if (hw->version == 1)
-+                      return NULL;
-+
-+              /* MT7986 WED devices do not have any pcie slot restrictions */
-+      }
-+      /* MT7986 PCIE or AXI */
-+      for (i = 0; i < ARRAY_SIZE(hw_list); i++) {
-+              hw = hw_list[i];
-+              if (hw && !hw->wed_dev)
-+                      goto out;
-+      }
--      hw = hw_list[pci_domain_nr(dev->wlan.pci_dev->bus)];
--      if (!hw || hw->wed_dev)
--              return NULL;
-+      return NULL;
-+out:
-       hw->wed_dev = dev;
-       return hw;
- }
-@@ -322,7 +342,6 @@ mtk_wed_stop(struct mtk_wed_device *dev)
- static void
- mtk_wed_detach(struct mtk_wed_device *dev)
- {
--      struct device_node *wlan_node = dev->wlan.pci_dev->dev.of_node;
-       struct mtk_wed_hw *hw = dev->hw;
-       mutex_lock(&hw_lock);
-@@ -337,9 +356,14 @@ mtk_wed_detach(struct mtk_wed_device *de
-       mtk_wed_free_buffer(dev);
-       mtk_wed_free_tx_rings(dev);
--      if (of_dma_is_coherent(wlan_node) && hw->hifsys)
--              regmap_update_bits(hw->hifsys, HIFSYS_DMA_AG_MAP,
--                                 BIT(hw->index), BIT(hw->index));
-+      if (dev->wlan.bus_type == MTK_WED_BUS_PCIE) {
-+              struct device_node *wlan_node;
-+
-+              wlan_node = dev->wlan.pci_dev->dev.of_node;
-+              if (of_dma_is_coherent(wlan_node) && hw->hifsys)
-+                      regmap_update_bits(hw->hifsys, HIFSYS_DMA_AG_MAP,
-+                                         BIT(hw->index), BIT(hw->index));
-+      }
-       if (!hw_list[!hw->index]->wed_dev &&
-           hw->eth->dma_dev != hw->eth->dev)
-@@ -356,40 +380,47 @@ mtk_wed_detach(struct mtk_wed_device *de
- static void
- mtk_wed_bus_init(struct mtk_wed_device *dev)
- {
--      struct device_node *np = dev->hw->eth->dev->of_node;
--      struct regmap *regs;
--      u32 val;
--
--      regs = syscon_regmap_lookup_by_phandle(np, "mediatek,wed-pcie");
--      if (IS_ERR(regs))
--              return;
-+      switch (dev->wlan.bus_type) {
-+      case MTK_WED_BUS_PCIE: {
-+              struct device_node *np = dev->hw->eth->dev->of_node;
-+              struct regmap *regs;
-+
-+              regs = syscon_regmap_lookup_by_phandle(np,
-+                                                     "mediatek,wed-pcie");
-+              if (IS_ERR(regs))
-+                      break;
--      regmap_update_bits(regs, 0, BIT(0), BIT(0));
-+              regmap_update_bits(regs, 0, BIT(0), BIT(0));
--      wed_w32(dev, MTK_WED_PCIE_INT_CTRL,
--              FIELD_PREP(MTK_WED_PCIE_INT_CTRL_POLL_EN, 2));
-+              wed_w32(dev, MTK_WED_PCIE_INT_CTRL,
-+                      FIELD_PREP(MTK_WED_PCIE_INT_CTRL_POLL_EN, 2));
--      /* pcie interrupt control: pola/source selection */
--      wed_set(dev, MTK_WED_PCIE_INT_CTRL,
--              MTK_WED_PCIE_INT_CTRL_MSK_EN_POLA |
--              FIELD_PREP(MTK_WED_PCIE_INT_CTRL_SRC_SEL, 1));
--      wed_r32(dev, MTK_WED_PCIE_INT_CTRL);
--
--      val = wed_r32(dev, MTK_WED_PCIE_CFG_INTM);
--      val = wed_r32(dev, MTK_WED_PCIE_CFG_BASE);
--      wed_w32(dev, MTK_WED_PCIE_CFG_INTM, PCIE_BASE_ADDR0 | 0x180);
--      wed_w32(dev, MTK_WED_PCIE_CFG_BASE, PCIE_BASE_ADDR0 | 0x184);
--
--      val = wed_r32(dev, MTK_WED_PCIE_CFG_INTM);
--      val = wed_r32(dev, MTK_WED_PCIE_CFG_BASE);
--
--      /* pcie interrupt status trigger register */
--      wed_w32(dev, MTK_WED_PCIE_INT_TRIGGER, BIT(24));
--      wed_r32(dev, MTK_WED_PCIE_INT_TRIGGER);
--
--      /* pola setting */
--      val = wed_r32(dev, MTK_WED_PCIE_INT_CTRL);
--      wed_set(dev, MTK_WED_PCIE_INT_CTRL, MTK_WED_PCIE_INT_CTRL_MSK_EN_POLA);
-+              /* pcie interrupt control: pola/source selection */
-+              wed_set(dev, MTK_WED_PCIE_INT_CTRL,
-+                      MTK_WED_PCIE_INT_CTRL_MSK_EN_POLA |
-+                      FIELD_PREP(MTK_WED_PCIE_INT_CTRL_SRC_SEL, 1));
-+              wed_r32(dev, MTK_WED_PCIE_INT_CTRL);
-+
-+              wed_w32(dev, MTK_WED_PCIE_CFG_INTM, PCIE_BASE_ADDR0 | 0x180);
-+              wed_w32(dev, MTK_WED_PCIE_CFG_BASE, PCIE_BASE_ADDR0 | 0x184);
-+
-+              /* pcie interrupt status trigger register */
-+              wed_w32(dev, MTK_WED_PCIE_INT_TRIGGER, BIT(24));
-+              wed_r32(dev, MTK_WED_PCIE_INT_TRIGGER);
-+
-+              /* pola setting */
-+              wed_set(dev, MTK_WED_PCIE_INT_CTRL,
-+                      MTK_WED_PCIE_INT_CTRL_MSK_EN_POLA);
-+              break;
-+      }
-+      case MTK_WED_BUS_AXI:
-+              wed_set(dev, MTK_WED_WPDMA_INT_CTRL,
-+                      MTK_WED_WPDMA_INT_CTRL_SIG_SRC |
-+                      FIELD_PREP(MTK_WED_WPDMA_INT_CTRL_SRC_SEL, 0));
-+              break;
-+      default:
-+              break;
-+      }
- }
- static void
-@@ -800,12 +831,14 @@ mtk_wed_attach(struct mtk_wed_device *de
-       __releases(RCU)
- {
-       struct mtk_wed_hw *hw;
-+      struct device *device;
-       int ret = 0;
-       RCU_LOCKDEP_WARN(!rcu_read_lock_held(),
-                        "mtk_wed_attach without holding the RCU read lock");
--      if (pci_domain_nr(dev->wlan.pci_dev->bus) > 1 ||
-+      if ((dev->wlan.bus_type == MTK_WED_BUS_PCIE &&
-+           pci_domain_nr(dev->wlan.pci_dev->bus) > 1) ||
-           !try_module_get(THIS_MODULE))
-               ret = -ENODEV;
-@@ -823,8 +856,10 @@ mtk_wed_attach(struct mtk_wed_device *de
-               goto out;
-       }
--      dev_info(&dev->wlan.pci_dev->dev,
--               "attaching wed device %d version %d\n",
-+      device = dev->wlan.bus_type == MTK_WED_BUS_PCIE
-+              ? &dev->wlan.pci_dev->dev
-+              : &dev->wlan.platform_dev->dev;
-+      dev_info(device, "attaching wed device %d version %d\n",
-                hw->index, hw->version);
-       dev->hw = hw;
---- a/drivers/net/ethernet/mediatek/mtk_wed_regs.h
-+++ b/drivers/net/ethernet/mediatek/mtk_wed_regs.h
-@@ -198,6 +198,8 @@ struct mtk_wdma_desc {
- #define MTK_WED_WPDMA_INT_CTRL                                0x520
- #define MTK_WED_WPDMA_INT_CTRL_SUBRT_ADV              BIT(21)
-+#define MTK_WED_WPDMA_INT_CTRL_SIG_SRC                        BIT(22)
-+#define MTK_WED_WPDMA_INT_CTRL_SRC_SEL                        GENMASK(17, 16)
- #define MTK_WED_WPDMA_INT_MASK                                0x524
---- a/include/linux/soc/mediatek/mtk_wed.h
-+++ b/include/linux/soc/mediatek/mtk_wed.h
-@@ -11,6 +11,11 @@
- struct mtk_wed_hw;
- struct mtk_wdma_desc;
-+enum mtk_wed_bus_tye {
-+      MTK_WED_BUS_PCIE,
-+      MTK_WED_BUS_AXI,
-+};
-+
- struct mtk_wed_ring {
-       struct mtk_wdma_desc *desc;
-       dma_addr_t desc_phys;
-@@ -43,7 +48,11 @@ struct mtk_wed_device {
-       /* filled by driver: */
-       struct {
--              struct pci_dev *pci_dev;
-+              union {
-+                      struct platform_device *platform_dev;
-+                      struct pci_dev *pci_dev;
-+              };
-+              enum mtk_wed_bus_tye bus_type;
-               u32 wpdma_phys;
-               u32 wpdma_int;
diff --git a/target/linux/generic/backport-5.15/723-v6.0-net-ethernet-mtk_eth_soc-introduce-flow-offloading-s.patch b/target/linux/generic/backport-5.15/723-v6.0-net-ethernet-mtk_eth_soc-introduce-flow-offloading-s.patch
deleted file mode 100644 (file)
index 56d63b1..0000000
+++ /dev/null
@@ -1,882 +0,0 @@
-From 93408c858e5dc01d97c55efa721268f63fde2ae5 Mon Sep 17 00:00:00 2001
-Message-Id: <93408c858e5dc01d97c55efa721268f63fde2ae5.1662886034.git.lorenzo@kernel.org>
-In-Reply-To: <e5ecb4f619197b93fa682d722452dc8412864cdb.1662886033.git.lorenzo@kernel.org>
-References: <e5ecb4f619197b93fa682d722452dc8412864cdb.1662886033.git.lorenzo@kernel.org>
-From: Lorenzo Bianconi <[email protected]>
-Date: Sat, 3 Sep 2022 18:34:09 +0200
-Subject: [PATCH net-next 4/5] net: ethernet: mtk_eth_soc: introduce flow
- offloading support for mt7986
-
-Introduce hw flow offload support for mt7986 chipset. PPE is not enabled
-yet in mt7986 since mt76 support is not available yet.
-
-Co-developed-by: Bo Jiao <[email protected]>
-Signed-off-by: Bo Jiao <[email protected]>
-Co-developed-by: Sujuan Chen <[email protected]>
-Signed-off-by: Sujuan Chen <[email protected]>
-Signed-off-by: Lorenzo Bianconi <[email protected]>
----
- drivers/net/ethernet/mediatek/mtk_eth_soc.c   |  11 +-
- drivers/net/ethernet/mediatek/mtk_eth_soc.h   |  72 ++++++
- drivers/net/ethernet/mediatek/mtk_ppe.c       | 213 +++++++++++-------
- drivers/net/ethernet/mediatek/mtk_ppe.h       |  52 ++++-
- .../net/ethernet/mediatek/mtk_ppe_offload.c   |  49 ++--
- drivers/net/ethernet/mediatek/mtk_ppe_regs.h  |   8 +
- 6 files changed, 289 insertions(+), 116 deletions(-)
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-@@ -1858,12 +1858,14 @@ static int mtk_poll_rx(struct napi_struc
-               bytes += skb->len;
-               if (MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2)) {
-+                      reason = FIELD_GET(MTK_RXD5_PPE_CPU_REASON, trxd.rxd5);
-                       hash = trxd.rxd5 & MTK_RXD5_FOE_ENTRY;
-                       if (hash != MTK_RXD5_FOE_ENTRY)
-                               skb_set_hash(skb, jhash_1word(hash, 0),
-                                            PKT_HASH_TYPE_L4);
-                       rxdcsum = &trxd.rxd3;
-               } else {
-+                      reason = FIELD_GET(MTK_RXD4_PPE_CPU_REASON, trxd.rxd4);
-                       hash = trxd.rxd4 & MTK_RXD4_FOE_ENTRY;
-                       if (hash != MTK_RXD4_FOE_ENTRY)
-                               skb_set_hash(skb, jhash_1word(hash, 0),
-@@ -1877,7 +1879,6 @@ static int mtk_poll_rx(struct napi_struc
-                       skb_checksum_none_assert(skb);
-               skb->protocol = eth_type_trans(skb, netdev);
--              reason = FIELD_GET(MTK_RXD4_PPE_CPU_REASON, trxd.rxd4);
-               if (reason == MTK_PPE_CPU_REASON_HIT_UNBIND_RATE_REACHED)
-                       mtk_ppe_check_skb(eth->ppe[0], skb, hash);
-@@ -4179,7 +4180,7 @@ static const struct mtk_soc_data mt7621_
-       .required_pctl = false,
-       .offload_version = 2,
-       .hash_offset = 2,
--      .foe_entry_size = sizeof(struct mtk_foe_entry),
-+      .foe_entry_size = sizeof(struct mtk_foe_entry) - 16,
-       .txrx = {
-               .txd_size = sizeof(struct mtk_tx_dma),
-               .rxd_size = sizeof(struct mtk_rx_dma),
-@@ -4199,7 +4200,7 @@ static const struct mtk_soc_data mt7622_
-       .required_pctl = false,
-       .offload_version = 2,
-       .hash_offset = 2,
--      .foe_entry_size = sizeof(struct mtk_foe_entry),
-+      .foe_entry_size = sizeof(struct mtk_foe_entry) - 16,
-       .txrx = {
-               .txd_size = sizeof(struct mtk_tx_dma),
-               .rxd_size = sizeof(struct mtk_rx_dma),
-@@ -4218,7 +4219,7 @@ static const struct mtk_soc_data mt7623_
-       .required_pctl = true,
-       .offload_version = 2,
-       .hash_offset = 2,
--      .foe_entry_size = sizeof(struct mtk_foe_entry),
-+      .foe_entry_size = sizeof(struct mtk_foe_entry) - 16,
-       .txrx = {
-               .txd_size = sizeof(struct mtk_tx_dma),
-               .rxd_size = sizeof(struct mtk_rx_dma),
-@@ -4250,9 +4251,11 @@ static const struct mtk_soc_data mt7986_
-       .reg_map = &mt7986_reg_map,
-       .ana_rgc3 = 0x128,
-       .caps = MT7986_CAPS,
-+      .hw_features = MTK_HW_FEATURES,
-       .required_clks = MT7986_CLKS_BITMAP,
-       .required_pctl = false,
-       .hash_offset = 4,
-+      .foe_entry_size = sizeof(struct mtk_foe_entry),
-       .txrx = {
-               .txd_size = sizeof(struct mtk_tx_dma_v2),
-               .rxd_size = sizeof(struct mtk_rx_dma_v2),
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-@@ -1151,6 +1151,78 @@ mtk_foe_get_entry(struct mtk_ppe *ppe, u
-       return ppe->foe_table + hash * soc->foe_entry_size;
- }
-+static inline u32 mtk_get_ib1_ts_mask(struct mtk_eth *eth)
-+{
-+      if (MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2))
-+              return MTK_FOE_IB1_BIND_TIMESTAMP_V2;
-+
-+      return MTK_FOE_IB1_BIND_TIMESTAMP;
-+}
-+
-+static inline u32 mtk_get_ib1_ppoe_mask(struct mtk_eth *eth)
-+{
-+      if (MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2))
-+              return MTK_FOE_IB1_BIND_PPPOE_V2;
-+
-+      return MTK_FOE_IB1_BIND_PPPOE;
-+}
-+
-+static inline u32 mtk_get_ib1_vlan_tag_mask(struct mtk_eth *eth)
-+{
-+      if (MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2))
-+              return MTK_FOE_IB1_BIND_VLAN_TAG_V2;
-+
-+      return MTK_FOE_IB1_BIND_VLAN_TAG;
-+}
-+
-+static inline u32 mtk_get_ib1_vlan_layer_mask(struct mtk_eth *eth)
-+{
-+      if (MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2))
-+              return MTK_FOE_IB1_BIND_VLAN_LAYER_V2;
-+
-+      return MTK_FOE_IB1_BIND_VLAN_LAYER;
-+}
-+
-+static inline u32 mtk_prep_ib1_vlan_layer(struct mtk_eth *eth, u32 val)
-+{
-+      if (MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2))
-+              return FIELD_PREP(MTK_FOE_IB1_BIND_VLAN_LAYER_V2, val);
-+
-+      return FIELD_PREP(MTK_FOE_IB1_BIND_VLAN_LAYER, val);
-+}
-+
-+static inline u32 mtk_get_ib1_vlan_layer(struct mtk_eth *eth, u32 val)
-+{
-+      if (MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2))
-+              return FIELD_GET(MTK_FOE_IB1_BIND_VLAN_LAYER_V2, val);
-+
-+      return FIELD_GET(MTK_FOE_IB1_BIND_VLAN_LAYER, val);
-+}
-+
-+static inline u32 mtk_get_ib1_pkt_type_mask(struct mtk_eth *eth)
-+{
-+      if (MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2))
-+              return MTK_FOE_IB1_PACKET_TYPE_V2;
-+
-+      return MTK_FOE_IB1_PACKET_TYPE;
-+}
-+
-+static inline u32 mtk_get_ib1_pkt_type(struct mtk_eth *eth, u32 val)
-+{
-+      if (MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2))
-+              return FIELD_GET(MTK_FOE_IB1_PACKET_TYPE_V2, val);
-+
-+      return FIELD_GET(MTK_FOE_IB1_PACKET_TYPE, val);
-+}
-+
-+static inline u32 mtk_get_ib2_multicast_mask(struct mtk_eth *eth)
-+{
-+      if (MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2))
-+              return MTK_FOE_IB2_MULTICAST_V2;
-+
-+      return MTK_FOE_IB2_MULTICAST;
-+}
-+
- /* read the hardware status register */
- void mtk_stats_update_mac(struct mtk_mac *mac);
---- a/drivers/net/ethernet/mediatek/mtk_ppe.c
-+++ b/drivers/net/ethernet/mediatek/mtk_ppe.c
-@@ -56,7 +56,7 @@ static u32 ppe_clear(struct mtk_ppe *ppe
- static u32 mtk_eth_timestamp(struct mtk_eth *eth)
- {
--      return mtk_r32(eth, 0x0010) & MTK_FOE_IB1_BIND_TIMESTAMP;
-+      return mtk_r32(eth, 0x0010) & mtk_get_ib1_ts_mask(eth);
- }
- static int mtk_ppe_wait_busy(struct mtk_ppe *ppe)
-@@ -93,7 +93,7 @@ static u32 mtk_ppe_hash_entry(struct mtk
-       u32 hv1, hv2, hv3;
-       u32 hash;
--      switch (FIELD_GET(MTK_FOE_IB1_PACKET_TYPE, e->ib1)) {
-+      switch (mtk_get_ib1_pkt_type(eth, e->ib1)) {
-               case MTK_PPE_PKT_TYPE_IPV4_ROUTE:
-               case MTK_PPE_PKT_TYPE_IPV4_HNAPT:
-                       hv1 = e->ipv4.orig.ports;
-@@ -129,9 +129,9 @@ static u32 mtk_ppe_hash_entry(struct mtk
- }
- static inline struct mtk_foe_mac_info *
--mtk_foe_entry_l2(struct mtk_foe_entry *entry)
-+mtk_foe_entry_l2(struct mtk_eth *eth, struct mtk_foe_entry *entry)
- {
--      int type = FIELD_GET(MTK_FOE_IB1_PACKET_TYPE, entry->ib1);
-+      int type = mtk_get_ib1_pkt_type(eth, entry->ib1);
-       if (type == MTK_PPE_PKT_TYPE_BRIDGE)
-               return &entry->bridge.l2;
-@@ -143,9 +143,9 @@ mtk_foe_entry_l2(struct mtk_foe_entry *e
- }
- static inline u32 *
--mtk_foe_entry_ib2(struct mtk_foe_entry *entry)
-+mtk_foe_entry_ib2(struct mtk_eth *eth, struct mtk_foe_entry *entry)
- {
--      int type = FIELD_GET(MTK_FOE_IB1_PACKET_TYPE, entry->ib1);
-+      int type = mtk_get_ib1_pkt_type(eth, entry->ib1);
-       if (type == MTK_PPE_PKT_TYPE_BRIDGE)
-               return &entry->bridge.ib2;
-@@ -156,27 +156,38 @@ mtk_foe_entry_ib2(struct mtk_foe_entry *
-       return &entry->ipv4.ib2;
- }
--int mtk_foe_entry_prepare(struct mtk_foe_entry *entry, int type, int l4proto,
--                        u8 pse_port, u8 *src_mac, u8 *dest_mac)
-+int mtk_foe_entry_prepare(struct mtk_eth *eth, struct mtk_foe_entry *entry,
-+                        int type, int l4proto, u8 pse_port, u8 *src_mac,
-+                        u8 *dest_mac)
- {
-       struct mtk_foe_mac_info *l2;
-       u32 ports_pad, val;
-       memset(entry, 0, sizeof(*entry));
--      val = FIELD_PREP(MTK_FOE_IB1_STATE, MTK_FOE_STATE_BIND) |
--            FIELD_PREP(MTK_FOE_IB1_PACKET_TYPE, type) |
--            FIELD_PREP(MTK_FOE_IB1_UDP, l4proto == IPPROTO_UDP) |
--            MTK_FOE_IB1_BIND_TTL |
--            MTK_FOE_IB1_BIND_CACHE;
--      entry->ib1 = val;
--
--      val = FIELD_PREP(MTK_FOE_IB2_PORT_MG, 0x3f) |
--            FIELD_PREP(MTK_FOE_IB2_PORT_AG, 0x1f) |
--            FIELD_PREP(MTK_FOE_IB2_DEST_PORT, pse_port);
-+      if (MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2)) {
-+              val = FIELD_PREP(MTK_FOE_IB1_STATE, MTK_FOE_STATE_BIND) |
-+                    FIELD_PREP(MTK_FOE_IB1_PACKET_TYPE_V2, type) |
-+                    FIELD_PREP(MTK_FOE_IB1_UDP, l4proto == IPPROTO_UDP) |
-+                    MTK_FOE_IB1_BIND_CACHE_V2 | MTK_FOE_IB1_BIND_TTL_V2;
-+              entry->ib1 = val;
-+
-+              val = FIELD_PREP(MTK_FOE_IB2_DEST_PORT_V2, pse_port) |
-+                    FIELD_PREP(MTK_FOE_IB2_PORT_AG_V2, 0xf);
-+      } else {
-+              val = FIELD_PREP(MTK_FOE_IB1_STATE, MTK_FOE_STATE_BIND) |
-+                    FIELD_PREP(MTK_FOE_IB1_PACKET_TYPE, type) |
-+                    FIELD_PREP(MTK_FOE_IB1_UDP, l4proto == IPPROTO_UDP) |
-+                    MTK_FOE_IB1_BIND_CACHE | MTK_FOE_IB1_BIND_TTL;
-+              entry->ib1 = val;
-+
-+              val = FIELD_PREP(MTK_FOE_IB2_DEST_PORT, pse_port) |
-+                    FIELD_PREP(MTK_FOE_IB2_PORT_MG, 0x3f) |
-+                    FIELD_PREP(MTK_FOE_IB2_PORT_AG, 0x1f);
-+      }
-       if (is_multicast_ether_addr(dest_mac))
--              val |= MTK_FOE_IB2_MULTICAST;
-+              val |= mtk_get_ib2_multicast_mask(eth);
-       ports_pad = 0xa5a5a500 | (l4proto & 0xff);
-       if (type == MTK_PPE_PKT_TYPE_IPV4_ROUTE)
-@@ -210,24 +221,30 @@ int mtk_foe_entry_prepare(struct mtk_foe
-       return 0;
- }
--int mtk_foe_entry_set_pse_port(struct mtk_foe_entry *entry, u8 port)
-+int mtk_foe_entry_set_pse_port(struct mtk_eth *eth,
-+                             struct mtk_foe_entry *entry, u8 port)
- {
--      u32 *ib2 = mtk_foe_entry_ib2(entry);
--      u32 val;
-+      u32 *ib2 = mtk_foe_entry_ib2(eth, entry);
-+      u32 val = *ib2;
--      val = *ib2;
--      val &= ~MTK_FOE_IB2_DEST_PORT;
--      val |= FIELD_PREP(MTK_FOE_IB2_DEST_PORT, port);
-+      if (MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2)) {
-+              val &= ~MTK_FOE_IB2_DEST_PORT_V2;
-+              val |= FIELD_PREP(MTK_FOE_IB2_DEST_PORT_V2, port);
-+      } else {
-+              val &= ~MTK_FOE_IB2_DEST_PORT;
-+              val |= FIELD_PREP(MTK_FOE_IB2_DEST_PORT, port);
-+      }
-       *ib2 = val;
-       return 0;
- }
--int mtk_foe_entry_set_ipv4_tuple(struct mtk_foe_entry *entry, bool egress,
-+int mtk_foe_entry_set_ipv4_tuple(struct mtk_eth *eth,
-+                               struct mtk_foe_entry *entry, bool egress,
-                                __be32 src_addr, __be16 src_port,
-                                __be32 dest_addr, __be16 dest_port)
- {
--      int type = FIELD_GET(MTK_FOE_IB1_PACKET_TYPE, entry->ib1);
-+      int type = mtk_get_ib1_pkt_type(eth, entry->ib1);
-       struct mtk_ipv4_tuple *t;
-       switch (type) {
-@@ -262,11 +279,12 @@ int mtk_foe_entry_set_ipv4_tuple(struct
-       return 0;
- }
--int mtk_foe_entry_set_ipv6_tuple(struct mtk_foe_entry *entry,
-+int mtk_foe_entry_set_ipv6_tuple(struct mtk_eth *eth,
-+                               struct mtk_foe_entry *entry,
-                                __be32 *src_addr, __be16 src_port,
-                                __be32 *dest_addr, __be16 dest_port)
- {
--      int type = FIELD_GET(MTK_FOE_IB1_PACKET_TYPE, entry->ib1);
-+      int type = mtk_get_ib1_pkt_type(eth, entry->ib1);
-       u32 *src, *dest;
-       int i;
-@@ -297,39 +315,41 @@ int mtk_foe_entry_set_ipv6_tuple(struct
-       return 0;
- }
--int mtk_foe_entry_set_dsa(struct mtk_foe_entry *entry, int port)
-+int mtk_foe_entry_set_dsa(struct mtk_eth *eth, struct mtk_foe_entry *entry,
-+                        int port)
- {
--      struct mtk_foe_mac_info *l2 = mtk_foe_entry_l2(entry);
-+      struct mtk_foe_mac_info *l2 = mtk_foe_entry_l2(eth, entry);
-       l2->etype = BIT(port);
--      if (!(entry->ib1 & MTK_FOE_IB1_BIND_VLAN_LAYER))
--              entry->ib1 |= FIELD_PREP(MTK_FOE_IB1_BIND_VLAN_LAYER, 1);
-+      if (!(entry->ib1 & mtk_get_ib1_vlan_layer_mask(eth)))
-+              entry->ib1 |= mtk_prep_ib1_vlan_layer(eth, 1);
-       else
-               l2->etype |= BIT(8);
--      entry->ib1 &= ~MTK_FOE_IB1_BIND_VLAN_TAG;
-+      entry->ib1 &= ~mtk_get_ib1_vlan_tag_mask(eth);
-       return 0;
- }
--int mtk_foe_entry_set_vlan(struct mtk_foe_entry *entry, int vid)
-+int mtk_foe_entry_set_vlan(struct mtk_eth *eth, struct mtk_foe_entry *entry,
-+                         int vid)
- {
--      struct mtk_foe_mac_info *l2 = mtk_foe_entry_l2(entry);
-+      struct mtk_foe_mac_info *l2 = mtk_foe_entry_l2(eth, entry);
--      switch (FIELD_GET(MTK_FOE_IB1_BIND_VLAN_LAYER, entry->ib1)) {
-+      switch (mtk_prep_ib1_vlan_layer(eth, entry->ib1)) {
-       case 0:
--              entry->ib1 |= MTK_FOE_IB1_BIND_VLAN_TAG |
--                            FIELD_PREP(MTK_FOE_IB1_BIND_VLAN_LAYER, 1);
-+              entry->ib1 |= mtk_get_ib1_vlan_tag_mask(eth) |
-+                            mtk_prep_ib1_vlan_layer(eth, 1);
-               l2->vlan1 = vid;
-               return 0;
-       case 1:
--              if (!(entry->ib1 & MTK_FOE_IB1_BIND_VLAN_TAG)) {
-+              if (!(entry->ib1 & mtk_get_ib1_vlan_tag_mask(eth))) {
-                       l2->vlan1 = vid;
-                       l2->etype |= BIT(8);
-               } else {
-                       l2->vlan2 = vid;
--                      entry->ib1 += FIELD_PREP(MTK_FOE_IB1_BIND_VLAN_LAYER, 1);
-+                      entry->ib1 += mtk_prep_ib1_vlan_layer(eth, 1);
-               }
-               return 0;
-       default:
-@@ -337,34 +357,42 @@ int mtk_foe_entry_set_vlan(struct mtk_fo
-       }
- }
--int mtk_foe_entry_set_pppoe(struct mtk_foe_entry *entry, int sid)
-+int mtk_foe_entry_set_pppoe(struct mtk_eth *eth, struct mtk_foe_entry *entry,
-+                          int sid)
- {
--      struct mtk_foe_mac_info *l2 = mtk_foe_entry_l2(entry);
-+      struct mtk_foe_mac_info *l2 = mtk_foe_entry_l2(eth, entry);
--      if (!(entry->ib1 & MTK_FOE_IB1_BIND_VLAN_LAYER) ||
--          (entry->ib1 & MTK_FOE_IB1_BIND_VLAN_TAG))
-+      if (!(entry->ib1 & mtk_get_ib1_vlan_layer_mask(eth)) ||
-+          (entry->ib1 & mtk_get_ib1_vlan_tag_mask(eth)))
-               l2->etype = ETH_P_PPP_SES;
--      entry->ib1 |= MTK_FOE_IB1_BIND_PPPOE;
-+      entry->ib1 |= mtk_get_ib1_ppoe_mask(eth);
-       l2->pppoe_id = sid;
-       return 0;
- }
--int mtk_foe_entry_set_wdma(struct mtk_foe_entry *entry, int wdma_idx, int txq,
--                         int bss, int wcid)
-+int mtk_foe_entry_set_wdma(struct mtk_eth *eth, struct mtk_foe_entry *entry,
-+                         int wdma_idx, int txq, int bss, int wcid)
- {
--      struct mtk_foe_mac_info *l2 = mtk_foe_entry_l2(entry);
--      u32 *ib2 = mtk_foe_entry_ib2(entry);
-+      struct mtk_foe_mac_info *l2 = mtk_foe_entry_l2(eth, entry);
-+      u32 *ib2 = mtk_foe_entry_ib2(eth, entry);
--      *ib2 &= ~MTK_FOE_IB2_PORT_MG;
--      *ib2 |= MTK_FOE_IB2_WDMA_WINFO;
--      if (wdma_idx)
--              *ib2 |= MTK_FOE_IB2_WDMA_DEVIDX;
--
--      l2->vlan2 = FIELD_PREP(MTK_FOE_VLAN2_WINFO_BSS, bss) |
--                  FIELD_PREP(MTK_FOE_VLAN2_WINFO_WCID, wcid) |
--                  FIELD_PREP(MTK_FOE_VLAN2_WINFO_RING, txq);
-+      if (MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2)) {
-+              *ib2 &= ~MTK_FOE_IB2_PORT_MG_V2;
-+              *ib2 |=  FIELD_PREP(MTK_FOE_IB2_RX_IDX, txq) |
-+                       MTK_FOE_IB2_WDMA_WINFO_V2;
-+              l2->winfo = FIELD_PREP(MTK_FOE_WINFO_WCID, wcid) |
-+                          FIELD_PREP(MTK_FOE_WINFO_BSS, bss);
-+      } else {
-+              *ib2 &= ~MTK_FOE_IB2_PORT_MG;
-+              *ib2 |= MTK_FOE_IB2_WDMA_WINFO;
-+              if (wdma_idx)
-+                      *ib2 |= MTK_FOE_IB2_WDMA_DEVIDX;
-+              l2->vlan2 = FIELD_PREP(MTK_FOE_VLAN2_WINFO_BSS, bss) |
-+                          FIELD_PREP(MTK_FOE_VLAN2_WINFO_WCID, wcid) |
-+                          FIELD_PREP(MTK_FOE_VLAN2_WINFO_RING, txq);
-+      }
-       return 0;
- }
-@@ -376,14 +404,15 @@ static inline bool mtk_foe_entry_usable(
- }
- static bool
--mtk_flow_entry_match(struct mtk_flow_entry *entry, struct mtk_foe_entry *data)
-+mtk_flow_entry_match(struct mtk_eth *eth, struct mtk_flow_entry *entry,
-+                   struct mtk_foe_entry *data)
- {
-       int type, len;
-       if ((data->ib1 ^ entry->data.ib1) & MTK_FOE_IB1_UDP)
-               return false;
--      type = FIELD_GET(MTK_FOE_IB1_PACKET_TYPE, entry->data.ib1);
-+      type = mtk_get_ib1_pkt_type(eth, entry->data.ib1);
-       if (type > MTK_PPE_PKT_TYPE_IPV4_DSLITE)
-               len = offsetof(struct mtk_foe_entry, ipv6._rsv);
-       else
-@@ -427,14 +456,12 @@ __mtk_foe_entry_clear(struct mtk_ppe *pp
- static int __mtk_foe_entry_idle_time(struct mtk_ppe *ppe, u32 ib1)
- {
--      u16 timestamp;
--      u16 now;
--
--      now = mtk_eth_timestamp(ppe->eth) & MTK_FOE_IB1_BIND_TIMESTAMP;
--      timestamp = ib1 & MTK_FOE_IB1_BIND_TIMESTAMP;
-+      u32 ib1_ts_mask = mtk_get_ib1_ts_mask(ppe->eth);
-+      u16 now = mtk_eth_timestamp(ppe->eth);
-+      u16 timestamp = ib1 & ib1_ts_mask;
-       if (timestamp > now)
--              return MTK_FOE_IB1_BIND_TIMESTAMP + 1 - timestamp + now;
-+              return ib1_ts_mask + 1 - timestamp + now;
-       else
-               return now - timestamp;
- }
-@@ -442,6 +469,7 @@ static int __mtk_foe_entry_idle_time(str
- static void
- mtk_flow_entry_update_l2(struct mtk_ppe *ppe, struct mtk_flow_entry *entry)
- {
-+      u32 ib1_ts_mask = mtk_get_ib1_ts_mask(ppe->eth);
-       struct mtk_flow_entry *cur;
-       struct mtk_foe_entry *hwe;
-       struct hlist_node *tmp;
-@@ -466,8 +494,8 @@ mtk_flow_entry_update_l2(struct mtk_ppe
-                       continue;
-               idle = cur_idle;
--              entry->data.ib1 &= ~MTK_FOE_IB1_BIND_TIMESTAMP;
--              entry->data.ib1 |= hwe->ib1 & MTK_FOE_IB1_BIND_TIMESTAMP;
-+              entry->data.ib1 &= ~ib1_ts_mask;
-+              entry->data.ib1 |= hwe->ib1 & ib1_ts_mask;
-       }
- }
-@@ -489,7 +517,7 @@ mtk_flow_entry_update(struct mtk_ppe *pp
-       hwe = mtk_foe_get_entry(ppe, entry->hash);
-       memcpy(&foe, hwe, ppe->eth->soc->foe_entry_size);
--      if (!mtk_flow_entry_match(entry, &foe)) {
-+      if (!mtk_flow_entry_match(ppe->eth, entry, &foe)) {
-               entry->hash = 0xffff;
-               goto out;
-       }
-@@ -504,16 +532,22 @@ static void
- __mtk_foe_entry_commit(struct mtk_ppe *ppe, struct mtk_foe_entry *entry,
-                      u16 hash)
- {
-+      struct mtk_eth *eth = ppe->eth;
-+      u16 timestamp = mtk_eth_timestamp(eth);
-       struct mtk_foe_entry *hwe;
--      u16 timestamp;
--      timestamp = mtk_eth_timestamp(ppe->eth);
--      timestamp &= MTK_FOE_IB1_BIND_TIMESTAMP;
--      entry->ib1 &= ~MTK_FOE_IB1_BIND_TIMESTAMP;
--      entry->ib1 |= FIELD_PREP(MTK_FOE_IB1_BIND_TIMESTAMP, timestamp);
-+      if (MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2)) {
-+              entry->ib1 &= ~MTK_FOE_IB1_BIND_TIMESTAMP_V2;
-+              entry->ib1 |= FIELD_PREP(MTK_FOE_IB1_BIND_TIMESTAMP_V2,
-+                                       timestamp);
-+      } else {
-+              entry->ib1 &= ~MTK_FOE_IB1_BIND_TIMESTAMP;
-+              entry->ib1 |= FIELD_PREP(MTK_FOE_IB1_BIND_TIMESTAMP,
-+                                       timestamp);
-+      }
-       hwe = mtk_foe_get_entry(ppe, hash);
--      memcpy(&hwe->data, &entry->data, ppe->eth->soc->foe_entry_size);
-+      memcpy(&hwe->data, &entry->data, eth->soc->foe_entry_size);
-       wmb();
-       hwe->ib1 = entry->ib1;
-@@ -540,8 +574,8 @@ mtk_foe_entry_commit_l2(struct mtk_ppe *
- int mtk_foe_entry_commit(struct mtk_ppe *ppe, struct mtk_flow_entry *entry)
- {
--      int type = FIELD_GET(MTK_FOE_IB1_PACKET_TYPE, entry->data.ib1);
-       const struct mtk_soc_data *soc = ppe->eth->soc;
-+      int type = mtk_get_ib1_pkt_type(ppe->eth, entry->data.ib1);
-       u32 hash;
-       if (type == MTK_PPE_PKT_TYPE_BRIDGE)
-@@ -564,7 +598,7 @@ mtk_foe_entry_commit_subflow(struct mtk_
-       struct mtk_flow_entry *flow_info;
-       struct mtk_foe_entry foe = {}, *hwe;
-       struct mtk_foe_mac_info *l2;
--      u32 ib1_mask = MTK_FOE_IB1_PACKET_TYPE | MTK_FOE_IB1_UDP;
-+      u32 ib1_mask = mtk_get_ib1_pkt_type_mask(ppe->eth) | MTK_FOE_IB1_UDP;
-       int type;
-       flow_info = kzalloc(offsetof(struct mtk_flow_entry, l2_data.end),
-@@ -584,16 +618,16 @@ mtk_foe_entry_commit_subflow(struct mtk_
-       foe.ib1 &= ib1_mask;
-       foe.ib1 |= entry->data.ib1 & ~ib1_mask;
--      l2 = mtk_foe_entry_l2(&foe);
-+      l2 = mtk_foe_entry_l2(ppe->eth, &foe);
-       memcpy(l2, &entry->data.bridge.l2, sizeof(*l2));
--      type = FIELD_GET(MTK_FOE_IB1_PACKET_TYPE, foe.ib1);
-+      type = mtk_get_ib1_pkt_type(ppe->eth, foe.ib1);
-       if (type == MTK_PPE_PKT_TYPE_IPV4_HNAPT)
-               memcpy(&foe.ipv4.new, &foe.ipv4.orig, sizeof(foe.ipv4.new));
-       else if (type >= MTK_PPE_PKT_TYPE_IPV6_ROUTE_3T && l2->etype == ETH_P_IP)
-               l2->etype = ETH_P_IPV6;
--      *mtk_foe_entry_ib2(&foe) = entry->data.bridge.ib2;
-+      *mtk_foe_entry_ib2(ppe->eth, &foe) = entry->data.bridge.ib2;
-       __mtk_foe_entry_commit(ppe, &foe, hash);
- }
-@@ -626,7 +660,7 @@ void __mtk_ppe_check_skb(struct mtk_ppe
-                       continue;
-               }
--              if (found || !mtk_flow_entry_match(entry, hwe)) {
-+              if (found || !mtk_flow_entry_match(ppe->eth, entry, hwe)) {
-                       if (entry->hash != 0xffff)
-                               entry->hash = 0xffff;
-                       continue;
-@@ -771,6 +805,8 @@ void mtk_ppe_start(struct mtk_ppe *ppe)
-                        MTK_PPE_SCAN_MODE_CHECK_AGE) |
-             FIELD_PREP(MTK_PPE_TB_CFG_ENTRY_NUM,
-                        MTK_PPE_ENTRIES_SHIFT);
-+      if (MTK_HAS_CAPS(ppe->eth->soc->caps, MTK_NETSYS_V2))
-+              val |= MTK_PPE_TB_CFG_INFO_SEL;
-       ppe_w32(ppe, MTK_PPE_TB_CFG, val);
-       ppe_w32(ppe, MTK_PPE_IP_PROTO_CHK,
-@@ -778,15 +814,21 @@ void mtk_ppe_start(struct mtk_ppe *ppe)
-       mtk_ppe_cache_enable(ppe, true);
--      val = MTK_PPE_FLOW_CFG_IP4_TCP_FRAG |
--            MTK_PPE_FLOW_CFG_IP4_UDP_FRAG |
--            MTK_PPE_FLOW_CFG_IP6_3T_ROUTE |
-+      val = MTK_PPE_FLOW_CFG_IP6_3T_ROUTE |
-             MTK_PPE_FLOW_CFG_IP6_5T_ROUTE |
-             MTK_PPE_FLOW_CFG_IP6_6RD |
-             MTK_PPE_FLOW_CFG_IP4_NAT |
-             MTK_PPE_FLOW_CFG_IP4_NAPT |
-             MTK_PPE_FLOW_CFG_IP4_DSLITE |
-             MTK_PPE_FLOW_CFG_IP4_NAT_FRAG;
-+      if (MTK_HAS_CAPS(ppe->eth->soc->caps, MTK_NETSYS_V2))
-+              val |= MTK_PPE_MD_TOAP_BYP_CRSN0 |
-+                     MTK_PPE_MD_TOAP_BYP_CRSN1 |
-+                     MTK_PPE_MD_TOAP_BYP_CRSN2 |
-+                     MTK_PPE_FLOW_CFG_IP4_HASH_GRE_KEY;
-+      else
-+              val |= MTK_PPE_FLOW_CFG_IP4_TCP_FRAG |
-+                     MTK_PPE_FLOW_CFG_IP4_UDP_FRAG;
-       ppe_w32(ppe, MTK_PPE_FLOW_CFG, val);
-       val = FIELD_PREP(MTK_PPE_UNBIND_AGE_MIN_PACKETS, 1000) |
-@@ -820,6 +862,11 @@ void mtk_ppe_start(struct mtk_ppe *ppe)
-       ppe_w32(ppe, MTK_PPE_GLO_CFG, val);
-       ppe_w32(ppe, MTK_PPE_DEFAULT_CPU_PORT, 0);
-+
-+      if (MTK_HAS_CAPS(ppe->eth->soc->caps, MTK_NETSYS_V2)) {
-+              ppe_w32(ppe, MTK_PPE_DEFAULT_CPU_PORT1, 0xcb777);
-+              ppe_w32(ppe, MTK_PPE_SBW_CTRL, 0x7f);
-+      }
- }
- int mtk_ppe_stop(struct mtk_ppe *ppe)
---- a/drivers/net/ethernet/mediatek/mtk_ppe.h
-+++ b/drivers/net/ethernet/mediatek/mtk_ppe.h
-@@ -32,6 +32,15 @@
- #define MTK_FOE_IB1_UDP                       BIT(30)
- #define MTK_FOE_IB1_STATIC            BIT(31)
-+/* CONFIG_MEDIATEK_NETSYS_V2 */
-+#define MTK_FOE_IB1_BIND_TIMESTAMP_V2 GENMASK(7, 0)
-+#define MTK_FOE_IB1_BIND_VLAN_LAYER_V2        GENMASK(16, 14)
-+#define MTK_FOE_IB1_BIND_PPPOE_V2     BIT(17)
-+#define MTK_FOE_IB1_BIND_VLAN_TAG_V2  BIT(18)
-+#define MTK_FOE_IB1_BIND_CACHE_V2     BIT(20)
-+#define MTK_FOE_IB1_BIND_TTL_V2               BIT(22)
-+#define MTK_FOE_IB1_PACKET_TYPE_V2    GENMASK(27, 23)
-+
- enum {
-       MTK_PPE_PKT_TYPE_IPV4_HNAPT = 0,
-       MTK_PPE_PKT_TYPE_IPV4_ROUTE = 1,
-@@ -53,14 +62,25 @@ enum {
- #define MTK_FOE_IB2_PORT_MG           GENMASK(17, 12)
-+#define MTK_FOE_IB2_RX_IDX            GENMASK(18, 17)
- #define MTK_FOE_IB2_PORT_AG           GENMASK(23, 18)
- #define MTK_FOE_IB2_DSCP              GENMASK(31, 24)
-+/* CONFIG_MEDIATEK_NETSYS_V2 */
-+#define MTK_FOE_IB2_PORT_MG_V2                BIT(7)
-+#define MTK_FOE_IB2_DEST_PORT_V2      GENMASK(12, 9)
-+#define MTK_FOE_IB2_MULTICAST_V2      BIT(13)
-+#define MTK_FOE_IB2_WDMA_WINFO_V2     BIT(19)
-+#define MTK_FOE_IB2_PORT_AG_V2                GENMASK(23, 20)
-+
- #define MTK_FOE_VLAN2_WINFO_BSS               GENMASK(5, 0)
- #define MTK_FOE_VLAN2_WINFO_WCID      GENMASK(13, 6)
- #define MTK_FOE_VLAN2_WINFO_RING      GENMASK(15, 14)
-+#define MTK_FOE_WINFO_BSS             GENMASK(5, 0)
-+#define MTK_FOE_WINFO_WCID            GENMASK(15, 6)
-+
- enum {
-       MTK_FOE_STATE_INVALID,
-       MTK_FOE_STATE_UNBIND,
-@@ -81,6 +101,9 @@ struct mtk_foe_mac_info {
-       u16 pppoe_id;
-       u16 src_mac_lo;
-+
-+      u16 minfo;
-+      u16 winfo;
- };
- /* software-only entry type */
-@@ -198,7 +221,7 @@ struct mtk_foe_entry {
-               struct mtk_foe_ipv4_dslite dslite;
-               struct mtk_foe_ipv6 ipv6;
-               struct mtk_foe_ipv6_6rd ipv6_6rd;
--              u32 data[19];
-+              u32 data[23];
-       };
- };
-@@ -306,20 +329,27 @@ mtk_ppe_check_skb(struct mtk_ppe *ppe, s
-       __mtk_ppe_check_skb(ppe, skb, hash);
- }
--int mtk_foe_entry_prepare(struct mtk_foe_entry *entry, int type, int l4proto,
--                        u8 pse_port, u8 *src_mac, u8 *dest_mac);
--int mtk_foe_entry_set_pse_port(struct mtk_foe_entry *entry, u8 port);
--int mtk_foe_entry_set_ipv4_tuple(struct mtk_foe_entry *entry, bool orig,
-+int mtk_foe_entry_prepare(struct mtk_eth *eth, struct mtk_foe_entry *entry,
-+                        int type, int l4proto, u8 pse_port, u8 *src_mac,
-+                        u8 *dest_mac);
-+int mtk_foe_entry_set_pse_port(struct mtk_eth *eth,
-+                             struct mtk_foe_entry *entry, u8 port);
-+int mtk_foe_entry_set_ipv4_tuple(struct mtk_eth *eth,
-+                               struct mtk_foe_entry *entry, bool orig,
-                                __be32 src_addr, __be16 src_port,
-                                __be32 dest_addr, __be16 dest_port);
--int mtk_foe_entry_set_ipv6_tuple(struct mtk_foe_entry *entry,
-+int mtk_foe_entry_set_ipv6_tuple(struct mtk_eth *eth,
-+                               struct mtk_foe_entry *entry,
-                                __be32 *src_addr, __be16 src_port,
-                                __be32 *dest_addr, __be16 dest_port);
--int mtk_foe_entry_set_dsa(struct mtk_foe_entry *entry, int port);
--int mtk_foe_entry_set_vlan(struct mtk_foe_entry *entry, int vid);
--int mtk_foe_entry_set_pppoe(struct mtk_foe_entry *entry, int sid);
--int mtk_foe_entry_set_wdma(struct mtk_foe_entry *entry, int wdma_idx, int txq,
--                         int bss, int wcid);
-+int mtk_foe_entry_set_dsa(struct mtk_eth *eth, struct mtk_foe_entry *entry,
-+                        int port);
-+int mtk_foe_entry_set_vlan(struct mtk_eth *eth, struct mtk_foe_entry *entry,
-+                         int vid);
-+int mtk_foe_entry_set_pppoe(struct mtk_eth *eth, struct mtk_foe_entry *entry,
-+                          int sid);
-+int mtk_foe_entry_set_wdma(struct mtk_eth *eth, struct mtk_foe_entry *entry,
-+                         int wdma_idx, int txq, int bss, int wcid);
- int mtk_foe_entry_commit(struct mtk_ppe *ppe, struct mtk_flow_entry *entry);
- void mtk_foe_entry_clear(struct mtk_ppe *ppe, struct mtk_flow_entry *entry);
- int mtk_foe_entry_idle_time(struct mtk_ppe *ppe, struct mtk_flow_entry *entry);
---- a/drivers/net/ethernet/mediatek/mtk_ppe_offload.c
-+++ b/drivers/net/ethernet/mediatek/mtk_ppe_offload.c
-@@ -52,18 +52,19 @@ static const struct rhashtable_params mt
- };
- static int
--mtk_flow_set_ipv4_addr(struct mtk_foe_entry *foe, struct mtk_flow_data *data,
--                     bool egress)
-+mtk_flow_set_ipv4_addr(struct mtk_eth *eth, struct mtk_foe_entry *foe,
-+                     struct mtk_flow_data *data, bool egress)
- {
--      return mtk_foe_entry_set_ipv4_tuple(foe, egress,
-+      return mtk_foe_entry_set_ipv4_tuple(eth, foe, egress,
-                                           data->v4.src_addr, data->src_port,
-                                           data->v4.dst_addr, data->dst_port);
- }
- static int
--mtk_flow_set_ipv6_addr(struct mtk_foe_entry *foe, struct mtk_flow_data *data)
-+mtk_flow_set_ipv6_addr(struct mtk_eth *eth, struct mtk_foe_entry *foe,
-+                     struct mtk_flow_data *data)
- {
--      return mtk_foe_entry_set_ipv6_tuple(foe,
-+      return mtk_foe_entry_set_ipv6_tuple(eth, foe,
-                                           data->v6.src_addr.s6_addr32, data->src_port,
-                                           data->v6.dst_addr.s6_addr32, data->dst_port);
- }
-@@ -190,16 +191,29 @@ mtk_flow_set_output_device(struct mtk_et
-       int pse_port, dsa_port;
-       if (mtk_flow_get_wdma_info(dev, dest_mac, &info) == 0) {
--              mtk_foe_entry_set_wdma(foe, info.wdma_idx, info.queue, info.bss,
--                                     info.wcid);
--              pse_port = 3;
-+              mtk_foe_entry_set_wdma(eth, foe, info.wdma_idx, info.queue,
-+                                     info.bss, info.wcid);
-+              if (MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2)) {
-+                      switch (info.wdma_idx) {
-+                      case 0:
-+                              pse_port = 8;
-+                              break;
-+                      case 1:
-+                              pse_port = 9;
-+                              break;
-+                      default:
-+                              return -EINVAL;
-+                      }
-+              } else {
-+                      pse_port = 3;
-+              }
-               *wed_index = info.wdma_idx;
-               goto out;
-       }
-       dsa_port = mtk_flow_get_dsa_port(&dev);
-       if (dsa_port >= 0)
--              mtk_foe_entry_set_dsa(foe, dsa_port);
-+              mtk_foe_entry_set_dsa(eth, foe, dsa_port);
-       if (dev == eth->netdev[0])
-               pse_port = 1;
-@@ -209,7 +223,7 @@ mtk_flow_set_output_device(struct mtk_et
-               return -EOPNOTSUPP;
- out:
--      mtk_foe_entry_set_pse_port(foe, pse_port);
-+      mtk_foe_entry_set_pse_port(eth, foe, pse_port);
-       return 0;
- }
-@@ -333,9 +347,8 @@ mtk_flow_offload_replace(struct mtk_eth
-           !is_valid_ether_addr(data.eth.h_dest))
-               return -EINVAL;
--      err = mtk_foe_entry_prepare(&foe, offload_type, l4proto, 0,
--                                  data.eth.h_source,
--                                  data.eth.h_dest);
-+      err = mtk_foe_entry_prepare(eth, &foe, offload_type, l4proto, 0,
-+                                  data.eth.h_source, data.eth.h_dest);
-       if (err)
-               return err;
-@@ -360,7 +373,7 @@ mtk_flow_offload_replace(struct mtk_eth
-               data.v4.src_addr = addrs.key->src;
-               data.v4.dst_addr = addrs.key->dst;
--              mtk_flow_set_ipv4_addr(&foe, &data, false);
-+              mtk_flow_set_ipv4_addr(eth, &foe, &data, false);
-       }
-       if (addr_type == FLOW_DISSECTOR_KEY_IPV6_ADDRS) {
-@@ -371,7 +384,7 @@ mtk_flow_offload_replace(struct mtk_eth
-               data.v6.src_addr = addrs.key->src;
-               data.v6.dst_addr = addrs.key->dst;
--              mtk_flow_set_ipv6_addr(&foe, &data);
-+              mtk_flow_set_ipv6_addr(eth, &foe, &data);
-       }
-       flow_action_for_each(i, act, &rule->action) {
-@@ -401,7 +414,7 @@ mtk_flow_offload_replace(struct mtk_eth
-       }
-       if (addr_type == FLOW_DISSECTOR_KEY_IPV4_ADDRS) {
--              err = mtk_flow_set_ipv4_addr(&foe, &data, true);
-+              err = mtk_flow_set_ipv4_addr(eth, &foe, &data, true);
-               if (err)
-                       return err;
-       }
-@@ -413,10 +426,10 @@ mtk_flow_offload_replace(struct mtk_eth
-               if (data.vlan.proto != htons(ETH_P_8021Q))
-                       return -EOPNOTSUPP;
--              mtk_foe_entry_set_vlan(&foe, data.vlan.id);
-+              mtk_foe_entry_set_vlan(eth, &foe, data.vlan.id);
-       }
-       if (data.pppoe.num == 1)
--              mtk_foe_entry_set_pppoe(&foe, data.pppoe.sid);
-+              mtk_foe_entry_set_pppoe(eth, &foe, data.pppoe.sid);
-       err = mtk_flow_set_output_device(eth, &foe, odev, data.eth.h_dest,
-                                        &wed_index);
---- a/drivers/net/ethernet/mediatek/mtk_ppe_regs.h
-+++ b/drivers/net/ethernet/mediatek/mtk_ppe_regs.h
-@@ -21,6 +21,9 @@
- #define MTK_PPE_GLO_CFG_BUSY                  BIT(31)
- #define MTK_PPE_FLOW_CFG                      0x204
-+#define MTK_PPE_MD_TOAP_BYP_CRSN0             BIT(1)
-+#define MTK_PPE_MD_TOAP_BYP_CRSN1             BIT(2)
-+#define MTK_PPE_MD_TOAP_BYP_CRSN2             BIT(3)
- #define MTK_PPE_FLOW_CFG_IP4_TCP_FRAG         BIT(6)
- #define MTK_PPE_FLOW_CFG_IP4_UDP_FRAG         BIT(7)
- #define MTK_PPE_FLOW_CFG_IP6_3T_ROUTE         BIT(8)
-@@ -54,6 +57,7 @@
- #define MTK_PPE_TB_CFG_HASH_MODE              GENMASK(15, 14)
- #define MTK_PPE_TB_CFG_SCAN_MODE              GENMASK(17, 16)
- #define MTK_PPE_TB_CFG_HASH_DEBUG             GENMASK(19, 18)
-+#define MTK_PPE_TB_CFG_INFO_SEL                       BIT(20)
- enum {
-       MTK_PPE_SCAN_MODE_DISABLED,
-@@ -112,6 +116,8 @@ enum {
- #define MTK_PPE_DEFAULT_CPU_PORT              0x248
- #define MTK_PPE_DEFAULT_CPU_PORT_MASK(_n)     (GENMASK(2, 0) << ((_n) * 4))
-+#define MTK_PPE_DEFAULT_CPU_PORT1             0x24c
-+
- #define MTK_PPE_MTU_DROP                      0x308
- #define MTK_PPE_VLAN_MTU0                     0x30c
-@@ -141,4 +147,6 @@ enum {
- #define MTK_PPE_MIB_CACHE_CTL_EN              BIT(0)
- #define MTK_PPE_MIB_CACHE_CTL_FLUSH           BIT(2)
-+#define MTK_PPE_SBW_CTRL                      0x374
-+
- #endif
diff --git a/target/linux/generic/backport-5.15/724-v6.0-net-ethernet-mtk_eth_soc-fix-wrong-use-of-new-helper.patch b/target/linux/generic/backport-5.15/724-v6.0-net-ethernet-mtk_eth_soc-fix-wrong-use-of-new-helper.patch
deleted file mode 100644 (file)
index c4bd293..0000000
+++ /dev/null
@@ -1,46 +0,0 @@
-From 40350ce3ae8701146aafd79c5f7b5582d9955e58 Mon Sep 17 00:00:00 2001
-From: Daniel Golle <[email protected]>
-Date: Sun, 25 Sep 2022 15:12:35 +0100
-Subject: [PATCH 1/2] net: ethernet: mtk_eth_soc: fix wrong use of new helper
- function
-    Lorenzo Bianconi <[email protected]>
-Cc: Sujuan Chen <[email protected]>,
-    Bo Jiao <[email protected]>,
-    Felix Fietkau <[email protected]>,
-    John Crispin <[email protected]>,
-    Sean Wang <[email protected]>,
-    Mark Lee <[email protected]>,
-    David S. Miller <[email protected]>,
-    Eric Dumazet <[email protected]>,
-    Jakub Kicinski <[email protected]>,
-    Paolo Abeni <[email protected]>,
-    Matthias Brugger <[email protected]>,
-    Chen Minqiang <[email protected]>
-
-In function mtk_foe_entry_set_vlan() the call to field accessor macro
-FIELD_GET(MTK_FOE_IB1_BIND_VLAN_LAYER, entry->ib1)
-has been wrongly replaced by
-mtk_prep_ib1_vlan_layer(eth, entry->ib1)
-
-Use correct helper function mtk_get_ib1_vlan_layer instead.
-
-Reported-by: Chen Minqiang <[email protected]>
-Fixes: 03a3180e5c09e1 ("net: ethernet: mtk_eth_soc: introduce flow offloading support for mt7986")
-Signed-off-by: Daniel Golle <[email protected]>
----
- drivers/net/ethernet/mediatek/mtk_ppe.c | 2 +-
- 1 file changed, 1 insertion(+), 1 deletion(-)
-
---- a/drivers/net/ethernet/mediatek/mtk_ppe.c
-+++ b/drivers/net/ethernet/mediatek/mtk_ppe.c
-@@ -337,7 +337,7 @@ int mtk_foe_entry_set_vlan(struct mtk_et
- {
-       struct mtk_foe_mac_info *l2 = mtk_foe_entry_l2(eth, entry);
--      switch (mtk_prep_ib1_vlan_layer(eth, entry->ib1)) {
-+      switch (mtk_get_ib1_vlan_layer(eth, entry->ib1)) {
-       case 0:
-               entry->ib1 |= mtk_get_ib1_vlan_tag_mask(eth) |
-                             mtk_prep_ib1_vlan_layer(eth, 1);
diff --git a/target/linux/generic/backport-5.15/724-v6.2-net-ethernet-mtk_eth_soc-enable-flow-offloading-supp.patch b/target/linux/generic/backport-5.15/724-v6.2-net-ethernet-mtk_eth_soc-enable-flow-offloading-supp.patch
deleted file mode 100644 (file)
index 58314a8..0000000
+++ /dev/null
@@ -1,26 +0,0 @@
-From b94b02a270471337bef73c44fa3493a521e31a61 Mon Sep 17 00:00:00 2001
-Message-Id: <b94b02a270471337bef73c44fa3493a521e31a61.1662886034.git.lorenzo@kernel.org>
-In-Reply-To: <e5ecb4f619197b93fa682d722452dc8412864cdb.1662886033.git.lorenzo@kernel.org>
-References: <e5ecb4f619197b93fa682d722452dc8412864cdb.1662886033.git.lorenzo@kernel.org>
-From: Lorenzo Bianconi <[email protected]>
-Date: Mon, 5 Sep 2022 13:56:13 +0200
-Subject: [PATCH net-next 5/5] net: ethernet: mtk_eth_soc: enable flow
- offloading support for mt7986
-
-Enable hw packet engine and wireless packet dispatcher for mt7986
-
-Signed-off-by: Lorenzo Bianconi <[email protected]>
----
- drivers/net/ethernet/mediatek/mtk_eth_soc.c | 1 +
- 1 file changed, 1 insertion(+)
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-@@ -4254,6 +4254,7 @@ static const struct mtk_soc_data mt7986_
-       .hw_features = MTK_HW_FEATURES,
-       .required_clks = MT7986_CLKS_BITMAP,
-       .required_pctl = false,
-+      .offload_version = 2,
-       .hash_offset = 4,
-       .foe_entry_size = sizeof(struct mtk_foe_entry),
-       .txrx = {
diff --git a/target/linux/generic/backport-5.15/725-v6.0-net-ethernet-mtk_eth_soc-fix-usage-of-foe_entry_size.patch b/target/linux/generic/backport-5.15/725-v6.0-net-ethernet-mtk_eth_soc-fix-usage-of-foe_entry_size.patch
deleted file mode 100644 (file)
index bb02f40..0000000
+++ /dev/null
@@ -1,49 +0,0 @@
-From fcf14c2c5deae8f8c3d25530bab10856f63f8a63 Mon Sep 17 00:00:00 2001
-From: Daniel Golle <[email protected]>
-Date: Sun, 25 Sep 2022 15:18:54 +0100
-Subject: [PATCH 2/2] net: ethernet: mtk_eth_soc: fix usage of foe_entry_size
-    Lorenzo Bianconi <[email protected]>
-Cc: Sujuan Chen <[email protected]>,
-    Bo Jiao <[email protected]>,
-    Felix Fietkau <[email protected]>,
-    John Crispin <[email protected]>,
-    Sean Wang <[email protected]>,
-    Mark Lee <[email protected]>,
-    David S. Miller <[email protected]>,
-    Eric Dumazet <[email protected]>,
-    Jakub Kicinski <[email protected]>,
-    Paolo Abeni <[email protected]>,
-    Matthias Brugger <[email protected]>,
-    Chen Minqiang <[email protected]>
-
-As sizeof(hwe->data) can now longer be used as the actual size depends
-on foe_entry_size, in commit 9d8cb4c096ab02
-("net: ethernet: mtk_eth_soc: add foe_entry_size to mtk_eth_soc") the
-use of sizeof(hwe->data) is hence replaced.
-However, replacing it with ppe->eth->soc->foe_entry_size is wrong as
-foe_entry_size represents the size of the whole descriptor and not just
-the 'data' field.
-Fix this by subtracing the size of the only other field in the struct
-'ib1', so we actually end up with the correct size to be copied to the
-data field.
-
-Reported-by: Chen Minqiang <[email protected]>
-Fixes: 9d8cb4c096ab02 ("net: ethernet: mtk_eth_soc: add foe_entry_size to mtk_eth_soc")
-Signed-off-by: Daniel Golle <[email protected]>
----
- drivers/net/ethernet/mediatek/mtk_ppe.c | 2 +-
- 1 file changed, 1 insertion(+), 1 deletion(-)
-
---- a/drivers/net/ethernet/mediatek/mtk_ppe.c
-+++ b/drivers/net/ethernet/mediatek/mtk_ppe.c
-@@ -547,7 +547,7 @@ __mtk_foe_entry_commit(struct mtk_ppe *p
-       }
-       hwe = mtk_foe_get_entry(ppe, hash);
--      memcpy(&hwe->data, &entry->data, eth->soc->foe_entry_size);
-+      memcpy(&hwe->data, &entry->data, eth->soc->foe_entry_size - sizeof(hwe->ib1));
-       wmb();
-       hwe->ib1 = entry->ib1;
diff --git a/target/linux/generic/backport-5.15/726-v6.0-net-ethernet-mtk_eth_soc-fix-mask-of-RX_DMA_GET_SPOR.patch b/target/linux/generic/backport-5.15/726-v6.0-net-ethernet-mtk_eth_soc-fix-mask-of-RX_DMA_GET_SPOR.patch
deleted file mode 100644 (file)
index 27c719b..0000000
+++ /dev/null
@@ -1,32 +0,0 @@
-From c9da02bfb1112461e048d3b736afb1873f6f4ccf Mon Sep 17 00:00:00 2001
-From: Daniel Golle <[email protected]>
-Date: Tue, 27 Sep 2022 16:30:02 +0100
-Subject: [PATCH 1/1] net: ethernet: mtk_eth_soc: fix mask of
- RX_DMA_GET_SPORT{,_V2}
-
-The bitmasks applied in RX_DMA_GET_SPORT and RX_DMA_GET_SPORT_V2 macros
-were swapped. Fix that.
-
-Reported-by: Chen Minqiang <[email protected]>
-Fixes: 160d3a9b192985 ("net: ethernet: mtk_eth_soc: introduce MTK_NETSYS_V2 support")
-Acked-by: Lorenzo Bianconi <[email protected]>
-Signed-off-by: Daniel Golle <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- drivers/net/ethernet/mediatek/mtk_eth_soc.h | 4 ++--
- 1 file changed, 2 insertions(+), 2 deletions(-)
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-@@ -315,8 +315,8 @@
- #define MTK_RXD5_PPE_CPU_REASON       GENMASK(22, 18)
- #define MTK_RXD5_SRC_PORT     GENMASK(29, 26)
--#define RX_DMA_GET_SPORT(x)   (((x) >> 19) & 0xf)
--#define RX_DMA_GET_SPORT_V2(x)        (((x) >> 26) & 0x7)
-+#define RX_DMA_GET_SPORT(x)   (((x) >> 19) & 0x7)
-+#define RX_DMA_GET_SPORT_V2(x)        (((x) >> 26) & 0xf)
- /* PDMA V2 descriptor rxd3 */
- #define RX_DMA_VTAG_V2                BIT(0)
diff --git a/target/linux/generic/backport-5.15/727-v6.1-net-ethernet-mtk_eth_soc-fix-state-in-__mtk_foe_entr.patch b/target/linux/generic/backport-5.15/727-v6.1-net-ethernet-mtk_eth_soc-fix-state-in-__mtk_foe_entr.patch
deleted file mode 100644 (file)
index 11465c1..0000000
+++ /dev/null
@@ -1,37 +0,0 @@
-From ae3ed15da5889263de372ff9df2e83e16acca4cb Mon Sep 17 00:00:00 2001
-From: Daniel Golle <[email protected]>
-Date: Fri, 30 Sep 2022 01:56:53 +0100
-Subject: [PATCH 1/1] net: ethernet: mtk_eth_soc: fix state in
- __mtk_foe_entry_clear
-
-Setting ib1 state to MTK_FOE_STATE_UNBIND in __mtk_foe_entry_clear
-routine as done by commit 0e80707d94e4c8 ("net: ethernet: mtk_eth_soc:
-fix typo in __mtk_foe_entry_clear") breaks flow offloading, at least
-on older MTK_NETSYS_V1 SoCs, OpenWrt users have confirmed the bug on
-MT7622 and MT7621 systems.
-Felix Fietkau suggested to use MTK_FOE_STATE_INVALID instead which
-works well on both, MTK_NETSYS_V1 and MTK_NETSYS_V2.
-
-Tested on MT7622 (Linksys E8450) and MT7986 (BananaPi BPI-R3).
-
-Suggested-by: Felix Fietkau <[email protected]>
-Fixes: 0e80707d94e4c8 ("net: ethernet: mtk_eth_soc: fix typo in __mtk_foe_entry_clear")
-Fixes: 33fc42de33278b ("net: ethernet: mtk_eth_soc: support creating mac address based offload entries")
-Signed-off-by: Daniel Golle <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- drivers/net/ethernet/mediatek/mtk_ppe.c | 2 +-
- 1 file changed, 1 insertion(+), 1 deletion(-)
-
---- a/drivers/net/ethernet/mediatek/mtk_ppe.c
-+++ b/drivers/net/ethernet/mediatek/mtk_ppe.c
-@@ -442,7 +442,7 @@ __mtk_foe_entry_clear(struct mtk_ppe *pp
-               struct mtk_foe_entry *hwe = mtk_foe_get_entry(ppe, entry->hash);
-               hwe->ib1 &= ~MTK_FOE_IB1_STATE;
--              hwe->ib1 |= FIELD_PREP(MTK_FOE_IB1_STATE, MTK_FOE_STATE_UNBIND);
-+              hwe->ib1 |= FIELD_PREP(MTK_FOE_IB1_STATE, MTK_FOE_STATE_INVALID);
-               dma_wmb();
-       }
-       entry->hash = 0xffff;
diff --git a/target/linux/generic/backport-5.15/728-v6.1-01-net-ethernet-mtk_eth_soc-fix-possible-memory-leak-in.patch b/target/linux/generic/backport-5.15/728-v6.1-01-net-ethernet-mtk_eth_soc-fix-possible-memory-leak-in.patch
deleted file mode 100644 (file)
index cad3204..0000000
+++ /dev/null
@@ -1,73 +0,0 @@
-From b3d0d98179d62f9d55635a600679c4fa362baf8d Mon Sep 17 00:00:00 2001
-From: Yang Yingliang <[email protected]>
-Date: Mon, 17 Oct 2022 11:51:54 +0800
-Subject: [PATCH 1/3] net: ethernet: mtk_eth_soc: fix possible memory leak in
- mtk_probe()
-
-If mtk_wed_add_hw() has been called, mtk_wed_exit() needs be called
-in error path or removing module to free the memory allocated in
-mtk_wed_add_hw().
-
-Fixes: 804775dfc288 ("net: ethernet: mtk_eth_soc: add support for Wireless Ethernet Dispatch (WED)")
-Signed-off-by: Yang Yingliang <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/ethernet/mediatek/mtk_eth_soc.c | 17 ++++++++++++-----
- 1 file changed, 12 insertions(+), 5 deletions(-)
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-@@ -4006,19 +4006,23 @@ static int mtk_probe(struct platform_dev
-                       eth->irq[i] = platform_get_irq(pdev, i);
-               if (eth->irq[i] < 0) {
-                       dev_err(&pdev->dev, "no IRQ%d resource found\n", i);
--                      return -ENXIO;
-+                      err = -ENXIO;
-+                      goto err_wed_exit;
-               }
-       }
-       for (i = 0; i < ARRAY_SIZE(eth->clks); i++) {
-               eth->clks[i] = devm_clk_get(eth->dev,
-                                           mtk_clks_source_name[i]);
-               if (IS_ERR(eth->clks[i])) {
--                      if (PTR_ERR(eth->clks[i]) == -EPROBE_DEFER)
--                              return -EPROBE_DEFER;
-+                      if (PTR_ERR(eth->clks[i]) == -EPROBE_DEFER) {
-+                              err = -EPROBE_DEFER;
-+                              goto err_wed_exit;
-+                      }
-                       if (eth->soc->required_clks & BIT(i)) {
-                               dev_err(&pdev->dev, "clock %s not found\n",
-                                       mtk_clks_source_name[i]);
--                              return -EINVAL;
-+                              err = -EINVAL;
-+                              goto err_wed_exit;
-                       }
-                       eth->clks[i] = NULL;
-               }
-@@ -4029,7 +4033,7 @@ static int mtk_probe(struct platform_dev
-       err = mtk_hw_init(eth);
-       if (err)
--              return err;
-+              goto err_wed_exit;
-       eth->hwlro = MTK_HAS_CAPS(eth->soc->caps, MTK_HWLRO);
-@@ -4127,6 +4131,8 @@ err_free_dev:
-       mtk_free_dev(eth);
- err_deinit_hw:
-       mtk_hw_deinit(eth);
-+err_wed_exit:
-+      mtk_wed_exit();
-       return err;
- }
-@@ -4146,6 +4152,7 @@ static int mtk_remove(struct platform_de
-               phylink_disconnect_phy(mac->phylink);
-       }
-+      mtk_wed_exit();
-       mtk_hw_deinit(eth);
-       netif_napi_del(&eth->tx_napi);
diff --git a/target/linux/generic/backport-5.15/728-v6.1-02-net-ethernet-mtk_eth_wed-add-missing-put_device-in-m.patch b/target/linux/generic/backport-5.15/728-v6.1-02-net-ethernet-mtk_eth_wed-add-missing-put_device-in-m.patch
deleted file mode 100644 (file)
index 4f0b78f..0000000
+++ /dev/null
@@ -1,47 +0,0 @@
-From 9d4f20a476ca57e4c9246eb1fa2a61bea2354720 Mon Sep 17 00:00:00 2001
-From: Yang Yingliang <[email protected]>
-Date: Mon, 17 Oct 2022 11:51:55 +0800
-Subject: [PATCH 2/3] net: ethernet: mtk_eth_wed: add missing put_device() in
- mtk_wed_add_hw()
-
-After calling get_device() in mtk_wed_add_hw(), in error path, put_device()
-needs be called.
-
-Fixes: 804775dfc288 ("net: ethernet: mtk_eth_soc: add support for Wireless Ethernet Dispatch (WED)")
-Signed-off-by: Yang Yingliang <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/ethernet/mediatek/mtk_wed.c | 10 ++++++++--
- 1 file changed, 8 insertions(+), 2 deletions(-)
-
---- a/drivers/net/ethernet/mediatek/mtk_wed.c
-+++ b/drivers/net/ethernet/mediatek/mtk_wed.c
-@@ -1077,11 +1077,11 @@ void mtk_wed_add_hw(struct device_node *
-       get_device(&pdev->dev);
-       irq = platform_get_irq(pdev, 0);
-       if (irq < 0)
--              return;
-+              goto err_put_device;
-       regs = syscon_regmap_lookup_by_phandle(np, NULL);
-       if (IS_ERR(regs))
--              return;
-+              goto err_put_device;
-       rcu_assign_pointer(mtk_soc_wed_ops, &wed_ops);
-@@ -1124,8 +1124,14 @@ void mtk_wed_add_hw(struct device_node *
-       hw_list[index] = hw;
-+      mutex_unlock(&hw_lock);
-+
-+      return;
-+
- unlock:
-       mutex_unlock(&hw_lock);
-+err_put_device:
-+      put_device(&pdev->dev);
- }
- void mtk_wed_exit(void)
diff --git a/target/linux/generic/backport-5.15/728-v6.1-03-net-ethernet-mtk_eth_wed-add-missing-of_node_put.patch b/target/linux/generic/backport-5.15/728-v6.1-03-net-ethernet-mtk_eth_wed-add-missing-of_node_put.patch
deleted file mode 100644 (file)
index 32f62aa..0000000
+++ /dev/null
@@ -1,43 +0,0 @@
-From e0bb4659e235770e6f53b3692e958591f49448f5 Mon Sep 17 00:00:00 2001
-From: Yang Yingliang <[email protected]>
-Date: Mon, 17 Oct 2022 11:51:56 +0800
-Subject: [PATCH 3/3] net: ethernet: mtk_eth_wed: add missing of_node_put()
-
-The device_node pointer returned by of_parse_phandle() with refcount
-incremented, when finish using it, the refcount need be decreased.
-
-Fixes: 804775dfc288 ("net: ethernet: mtk_eth_soc: add support for Wireless Ethernet Dispatch (WED)")
-Signed-off-by: Yang Yingliang <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/ethernet/mediatek/mtk_wed.c | 5 ++++-
- 1 file changed, 4 insertions(+), 1 deletion(-)
-
---- a/drivers/net/ethernet/mediatek/mtk_wed.c
-+++ b/drivers/net/ethernet/mediatek/mtk_wed.c
-@@ -1072,7 +1072,7 @@ void mtk_wed_add_hw(struct device_node *
-       pdev = of_find_device_by_node(np);
-       if (!pdev)
--              return;
-+              goto err_of_node_put;
-       get_device(&pdev->dev);
-       irq = platform_get_irq(pdev, 0);
-@@ -1132,6 +1132,8 @@ unlock:
-       mutex_unlock(&hw_lock);
- err_put_device:
-       put_device(&pdev->dev);
-+err_of_node_put:
-+      of_node_put(np);
- }
- void mtk_wed_exit(void)
-@@ -1152,6 +1154,7 @@ void mtk_wed_exit(void)
-               hw_list[i] = NULL;
-               debugfs_remove(hw->debugfs_dir);
-               put_device(hw->dev);
-+              of_node_put(hw->node);
-               kfree(hw);
-       }
- }
diff --git a/target/linux/generic/backport-5.15/728-v6.1-04-net-ethernet-mtk_eth_soc-fix-resource-leak-in-error-.patch b/target/linux/generic/backport-5.15/728-v6.1-04-net-ethernet-mtk_eth_soc-fix-resource-leak-in-error-.patch
deleted file mode 100644 (file)
index e2a2046..0000000
+++ /dev/null
@@ -1,35 +0,0 @@
-From 8110437e59616293228cd781c486d8495a61e36a Mon Sep 17 00:00:00 2001
-From: Yan Cangang <[email protected]>
-Date: Sun, 20 Nov 2022 13:52:58 +0800
-Subject: [PATCH] net: ethernet: mtk_eth_soc: fix resource leak in error path
-
-In mtk_probe(), when mtk_ppe_init() or mtk_eth_offload_init() failed,
-mtk_mdio_cleanup() isn't called. Fix it.
-
-Fixes: ba37b7caf1ed ("net: ethernet: mtk_eth_soc: add support for initializing the PPE")
-Fixes: 502e84e2382d ("net: ethernet: mtk_eth_soc: add flow offloading support")
-Signed-off-by: Yan Cangang <[email protected]>
-Reviewed-by: Leon Romanovsky <[email protected]>
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- drivers/net/ethernet/mediatek/mtk_eth_soc.c | 4 ++--
- 1 file changed, 2 insertions(+), 2 deletions(-)
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-@@ -4089,13 +4089,13 @@ static int mtk_probe(struct platform_dev
-                                                  eth->soc->offload_version, i);
-                       if (!eth->ppe[i]) {
-                               err = -ENOMEM;
--                              goto err_free_dev;
-+                              goto err_deinit_mdio;
-                       }
-               }
-               err = mtk_eth_offload_init(eth);
-               if (err)
--                      goto err_free_dev;
-+                      goto err_deinit_mdio;
-       }
-       for (i = 0; i < MTK_MAX_DEVS; i++) {
diff --git a/target/linux/generic/backport-5.15/728-v6.1-05-net-ethernet-mtk_eth_soc-fix-memory-leak-in-error-pa.patch b/target/linux/generic/backport-5.15/728-v6.1-05-net-ethernet-mtk_eth_soc-fix-memory-leak-in-error-pa.patch
deleted file mode 100644 (file)
index 13f0ed5..0000000
+++ /dev/null
@@ -1,107 +0,0 @@
-From 603ea5e7ffa73c7fac07d8713d97285990695213 Mon Sep 17 00:00:00 2001
-From: Yan Cangang <[email protected]>
-Date: Sun, 20 Nov 2022 13:52:59 +0800
-Subject: [PATCH] net: ethernet: mtk_eth_soc: fix memory leak in error path
-
-In mtk_ppe_init(), when dmam_alloc_coherent() or devm_kzalloc() failed,
-the rhashtable ppe->l2_flows isn't destroyed. Fix it.
-
-In mtk_probe(), when mtk_ppe_init() or mtk_eth_offload_init() or
-register_netdev() failed, have the same problem. Fix it.
-
-Fixes: 33fc42de3327 ("net: ethernet: mtk_eth_soc: support creating mac address based offload entries")
-Signed-off-by: Yan Cangang <[email protected]>
-Reviewed-by: Leon Romanovsky <[email protected]>
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- drivers/net/ethernet/mediatek/mtk_eth_soc.c |  9 +++++----
- drivers/net/ethernet/mediatek/mtk_ppe.c     | 19 +++++++++++++++++--
- drivers/net/ethernet/mediatek/mtk_ppe.h     |  1 +
- 3 files changed, 23 insertions(+), 6 deletions(-)
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-@@ -4089,13 +4089,13 @@ static int mtk_probe(struct platform_dev
-                                                  eth->soc->offload_version, i);
-                       if (!eth->ppe[i]) {
-                               err = -ENOMEM;
--                              goto err_deinit_mdio;
-+                              goto err_deinit_ppe;
-                       }
-               }
-               err = mtk_eth_offload_init(eth);
-               if (err)
--                      goto err_deinit_mdio;
-+                      goto err_deinit_ppe;
-       }
-       for (i = 0; i < MTK_MAX_DEVS; i++) {
-@@ -4105,7 +4105,7 @@ static int mtk_probe(struct platform_dev
-               err = register_netdev(eth->netdev[i]);
-               if (err) {
-                       dev_err(eth->dev, "error bringing up device\n");
--                      goto err_deinit_mdio;
-+                      goto err_deinit_ppe;
-               } else
-                       netif_info(eth, probe, eth->netdev[i],
-                                  "mediatek frame engine at 0x%08lx, irq %d\n",
-@@ -4125,7 +4125,8 @@ static int mtk_probe(struct platform_dev
-       return 0;
--err_deinit_mdio:
-+err_deinit_ppe:
-+      mtk_ppe_deinit(eth);
-       mtk_mdio_cleanup(eth);
- err_free_dev:
-       mtk_free_dev(eth);
---- a/drivers/net/ethernet/mediatek/mtk_ppe.c
-+++ b/drivers/net/ethernet/mediatek/mtk_ppe.c
-@@ -743,7 +743,7 @@ struct mtk_ppe *mtk_ppe_init(struct mtk_
-                                 MTK_PPE_ENTRIES * soc->foe_entry_size,
-                                 &ppe->foe_phys, GFP_KERNEL);
-       if (!foe)
--              return NULL;
-+              goto err_free_l2_flows;
-       ppe->foe_table = foe;
-@@ -751,11 +751,26 @@ struct mtk_ppe *mtk_ppe_init(struct mtk_
-                       sizeof(*ppe->foe_flow);
-       ppe->foe_flow = devm_kzalloc(dev, foe_flow_size, GFP_KERNEL);
-       if (!ppe->foe_flow)
--              return NULL;
-+              goto err_free_l2_flows;
-       mtk_ppe_debugfs_init(ppe, index);
-       return ppe;
-+
-+err_free_l2_flows:
-+      rhashtable_destroy(&ppe->l2_flows);
-+      return NULL;
-+}
-+
-+void mtk_ppe_deinit(struct mtk_eth *eth)
-+{
-+      int i;
-+
-+      for (i = 0; i < ARRAY_SIZE(eth->ppe); i++) {
-+              if (!eth->ppe[i])
-+                      return;
-+              rhashtable_destroy(&eth->ppe[i]->l2_flows);
-+      }
- }
- static void mtk_ppe_init_foe_table(struct mtk_ppe *ppe)
---- a/drivers/net/ethernet/mediatek/mtk_ppe.h
-+++ b/drivers/net/ethernet/mediatek/mtk_ppe.h
-@@ -304,6 +304,7 @@ struct mtk_ppe {
- struct mtk_ppe *mtk_ppe_init(struct mtk_eth *eth, void __iomem *base,
-                            int version, int index);
-+void mtk_ppe_deinit(struct mtk_eth *eth);
- void mtk_ppe_start(struct mtk_ppe *ppe);
- int mtk_ppe_stop(struct mtk_ppe *ppe);
diff --git a/target/linux/generic/backport-5.15/729-01-v6.1-net-ethernet-mtk_wed-introduce-wed-mcu-support.patch b/target/linux/generic/backport-5.15/729-01-v6.1-net-ethernet-mtk_wed-introduce-wed-mcu-support.patch
deleted file mode 100644 (file)
index c486139..0000000
+++ /dev/null
@@ -1,591 +0,0 @@
-From: Sujuan Chen <[email protected]>
-Date: Sat, 5 Nov 2022 23:36:18 +0100
-Subject: [PATCH] net: ethernet: mtk_wed: introduce wed mcu support
-
-Introduce WED mcu support used to configure WED WO chip.
-This is a preliminary patch in order to add RX Wireless
-Ethernet Dispatch available on MT7986 SoC.
-
-Tested-by: Daniel Golle <[email protected]>
-Co-developed-by: Lorenzo Bianconi <[email protected]>
-Signed-off-by: Lorenzo Bianconi <[email protected]>
-Signed-off-by: Sujuan Chen <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- create mode 100644 drivers/net/ethernet/mediatek/mtk_wed_mcu.c
- create mode 100644 drivers/net/ethernet/mediatek/mtk_wed_wo.h
-
---- a/drivers/net/ethernet/mediatek/Makefile
-+++ b/drivers/net/ethernet/mediatek/Makefile
-@@ -5,7 +5,7 @@
- obj-$(CONFIG_NET_MEDIATEK_SOC) += mtk_eth.o
- mtk_eth-y := mtk_eth_soc.o mtk_sgmii.o mtk_eth_path.o mtk_ppe.o mtk_ppe_debugfs.o mtk_ppe_offload.o
--mtk_eth-$(CONFIG_NET_MEDIATEK_SOC_WED) += mtk_wed.o
-+mtk_eth-$(CONFIG_NET_MEDIATEK_SOC_WED) += mtk_wed.o mtk_wed_mcu.o
- ifdef CONFIG_DEBUG_FS
- mtk_eth-$(CONFIG_NET_MEDIATEK_SOC_WED) += mtk_wed_debugfs.o
- endif
---- /dev/null
-+++ b/drivers/net/ethernet/mediatek/mtk_wed_mcu.c
-@@ -0,0 +1,359 @@
-+// SPDX-License-Identifier: GPL-2.0-only
-+/* Copyright (C) 2022 MediaTek Inc.
-+ *
-+ * Author: Lorenzo Bianconi <[email protected]>
-+ *       Sujuan Chen <[email protected]>
-+ */
-+
-+#include <linux/firmware.h>
-+#include <linux/of_address.h>
-+#include <linux/of_reserved_mem.h>
-+#include <linux/mfd/syscon.h>
-+#include <linux/soc/mediatek/mtk_wed.h>
-+
-+#include "mtk_wed_regs.h"
-+#include "mtk_wed_wo.h"
-+#include "mtk_wed.h"
-+
-+static u32 wo_r32(struct mtk_wed_wo *wo, u32 reg)
-+{
-+      return readl(wo->boot.addr + reg);
-+}
-+
-+static void wo_w32(struct mtk_wed_wo *wo, u32 reg, u32 val)
-+{
-+      writel(val, wo->boot.addr + reg);
-+}
-+
-+static struct sk_buff *
-+mtk_wed_mcu_msg_alloc(const void *data, int data_len)
-+{
-+      int length = sizeof(struct mtk_wed_mcu_hdr) + data_len;
-+      struct sk_buff *skb;
-+
-+      skb = alloc_skb(length, GFP_KERNEL);
-+      if (!skb)
-+              return NULL;
-+
-+      memset(skb->head, 0, length);
-+      skb_reserve(skb, sizeof(struct mtk_wed_mcu_hdr));
-+      if (data && data_len)
-+              skb_put_data(skb, data, data_len);
-+
-+      return skb;
-+}
-+
-+static struct sk_buff *
-+mtk_wed_mcu_get_response(struct mtk_wed_wo *wo, unsigned long expires)
-+{
-+      if (!time_is_after_jiffies(expires))
-+              return NULL;
-+
-+      wait_event_timeout(wo->mcu.wait, !skb_queue_empty(&wo->mcu.res_q),
-+                         expires - jiffies);
-+      return skb_dequeue(&wo->mcu.res_q);
-+}
-+
-+void mtk_wed_mcu_rx_event(struct mtk_wed_wo *wo, struct sk_buff *skb)
-+{
-+      skb_queue_tail(&wo->mcu.res_q, skb);
-+      wake_up(&wo->mcu.wait);
-+}
-+
-+void mtk_wed_mcu_rx_unsolicited_event(struct mtk_wed_wo *wo,
-+                                    struct sk_buff *skb)
-+{
-+      struct mtk_wed_mcu_hdr *hdr = (struct mtk_wed_mcu_hdr *)skb->data;
-+
-+      switch (hdr->cmd) {
-+      case MTK_WED_WO_EVT_LOG_DUMP: {
-+              const char *msg = (const char *)(skb->data + sizeof(*hdr));
-+
-+              dev_notice(wo->hw->dev, "%s\n", msg);
-+              break;
-+      }
-+      case MTK_WED_WO_EVT_PROFILING: {
-+              struct mtk_wed_wo_log_info *info;
-+              u32 count = (skb->len - sizeof(*hdr)) / sizeof(*info);
-+              int i;
-+
-+              info = (struct mtk_wed_wo_log_info *)(skb->data + sizeof(*hdr));
-+              for (i = 0 ; i < count ; i++)
-+                      dev_notice(wo->hw->dev,
-+                                 "SN:%u latency: total=%u, rro:%u, mod:%u\n",
-+                                 le32_to_cpu(info[i].sn),
-+                                 le32_to_cpu(info[i].total),
-+                                 le32_to_cpu(info[i].rro),
-+                                 le32_to_cpu(info[i].mod));
-+              break;
-+      }
-+      case MTK_WED_WO_EVT_RXCNT_INFO:
-+              break;
-+      default:
-+              break;
-+      }
-+
-+      dev_kfree_skb(skb);
-+}
-+
-+static int
-+mtk_wed_mcu_skb_send_msg(struct mtk_wed_wo *wo, struct sk_buff *skb,
-+                       int id, int cmd, u16 *wait_seq, bool wait_resp)
-+{
-+      struct mtk_wed_mcu_hdr *hdr;
-+
-+      /* TODO: make it dynamic based on cmd */
-+      wo->mcu.timeout = 20 * HZ;
-+
-+      hdr = (struct mtk_wed_mcu_hdr *)skb_push(skb, sizeof(*hdr));
-+      hdr->cmd = cmd;
-+      hdr->length = cpu_to_le16(skb->len);
-+
-+      if (wait_resp && wait_seq) {
-+              u16 seq = ++wo->mcu.seq;
-+
-+              if (!seq)
-+                      seq = ++wo->mcu.seq;
-+              *wait_seq = seq;
-+
-+              hdr->flag |= cpu_to_le16(MTK_WED_WARP_CMD_FLAG_NEED_RSP);
-+              hdr->seq = cpu_to_le16(seq);
-+      }
-+      if (id == MTK_WED_MODULE_ID_WO)
-+              hdr->flag |= cpu_to_le16(MTK_WED_WARP_CMD_FLAG_FROM_TO_WO);
-+
-+      dev_kfree_skb(skb);
-+      return 0;
-+}
-+
-+static int
-+mtk_wed_mcu_parse_response(struct mtk_wed_wo *wo, struct sk_buff *skb,
-+                         int cmd, int seq)
-+{
-+      struct mtk_wed_mcu_hdr *hdr;
-+
-+      if (!skb) {
-+              dev_err(wo->hw->dev, "Message %08x (seq %d) timeout\n",
-+                      cmd, seq);
-+              return -ETIMEDOUT;
-+      }
-+
-+      hdr = (struct mtk_wed_mcu_hdr *)skb->data;
-+      if (le16_to_cpu(hdr->seq) != seq)
-+              return -EAGAIN;
-+
-+      skb_pull(skb, sizeof(*hdr));
-+      switch (cmd) {
-+      case MTK_WED_WO_CMD_RXCNT_INFO:
-+      default:
-+              break;
-+      }
-+
-+      return 0;
-+}
-+
-+int mtk_wed_mcu_send_msg(struct mtk_wed_wo *wo, int id, int cmd,
-+                       const void *data, int len, bool wait_resp)
-+{
-+      unsigned long expires;
-+      struct sk_buff *skb;
-+      u16 seq;
-+      int ret;
-+
-+      skb = mtk_wed_mcu_msg_alloc(data, len);
-+      if (!skb)
-+              return -ENOMEM;
-+
-+      mutex_lock(&wo->mcu.mutex);
-+
-+      ret = mtk_wed_mcu_skb_send_msg(wo, skb, id, cmd, &seq, wait_resp);
-+      if (ret || !wait_resp)
-+              goto unlock;
-+
-+      expires = jiffies + wo->mcu.timeout;
-+      do {
-+              skb = mtk_wed_mcu_get_response(wo, expires);
-+              ret = mtk_wed_mcu_parse_response(wo, skb, cmd, seq);
-+              dev_kfree_skb(skb);
-+      } while (ret == -EAGAIN);
-+
-+unlock:
-+      mutex_unlock(&wo->mcu.mutex);
-+
-+      return ret;
-+}
-+
-+static int
-+mtk_wed_get_memory_region(struct mtk_wed_wo *wo,
-+                        struct mtk_wed_wo_memory_region *region)
-+{
-+      struct reserved_mem *rmem;
-+      struct device_node *np;
-+      int index;
-+
-+      index = of_property_match_string(wo->hw->node, "memory-region-names",
-+                                       region->name);
-+      if (index < 0)
-+              return index;
-+
-+      np = of_parse_phandle(wo->hw->node, "memory-region", index);
-+      if (!np)
-+              return -ENODEV;
-+
-+      rmem = of_reserved_mem_lookup(np);
-+      of_node_put(np);
-+
-+      if (!rmem)
-+              return -ENODEV;
-+
-+      region->phy_addr = rmem->base;
-+      region->size = rmem->size;
-+      region->addr = devm_ioremap(wo->hw->dev, region->phy_addr, region->size);
-+
-+      return !region->addr ? -EINVAL : 0;
-+}
-+
-+static int
-+mtk_wed_mcu_run_firmware(struct mtk_wed_wo *wo, const struct firmware *fw,
-+                       struct mtk_wed_wo_memory_region *region)
-+{
-+      const u8 *first_region_ptr, *region_ptr, *trailer_ptr, *ptr = fw->data;
-+      const struct mtk_wed_fw_trailer *trailer;
-+      const struct mtk_wed_fw_region *fw_region;
-+
-+      trailer_ptr = fw->data + fw->size - sizeof(*trailer);
-+      trailer = (const struct mtk_wed_fw_trailer *)trailer_ptr;
-+      region_ptr = trailer_ptr - trailer->num_region * sizeof(*fw_region);
-+      first_region_ptr = region_ptr;
-+
-+      while (region_ptr < trailer_ptr) {
-+              u32 length;
-+
-+              fw_region = (const struct mtk_wed_fw_region *)region_ptr;
-+              length = le32_to_cpu(fw_region->len);
-+
-+              if (region->phy_addr != le32_to_cpu(fw_region->addr))
-+                      goto next;
-+
-+              if (region->size < length)
-+                      goto next;
-+
-+              if (first_region_ptr < ptr + length)
-+                      goto next;
-+
-+              if (region->shared && region->consumed)
-+                      return 0;
-+
-+              if (!region->shared || !region->consumed) {
-+                      memcpy_toio(region->addr, ptr, length);
-+                      region->consumed = true;
-+                      return 0;
-+              }
-+next:
-+              region_ptr += sizeof(*fw_region);
-+              ptr += length;
-+      }
-+
-+      return -EINVAL;
-+}
-+
-+static int
-+mtk_wed_mcu_load_firmware(struct mtk_wed_wo *wo)
-+{
-+      static struct mtk_wed_wo_memory_region mem_region[] = {
-+              [MTK_WED_WO_REGION_EMI] = {
-+                      .name = "wo-emi",
-+              },
-+              [MTK_WED_WO_REGION_ILM] = {
-+                      .name = "wo-ilm",
-+              },
-+              [MTK_WED_WO_REGION_DATA] = {
-+                      .name = "wo-data",
-+                      .shared = true,
-+              },
-+      };
-+      const struct mtk_wed_fw_trailer *trailer;
-+      const struct firmware *fw;
-+      const char *fw_name;
-+      u32 val, boot_cr;
-+      int ret, i;
-+
-+      /* load firmware region metadata */
-+      for (i = 0; i < ARRAY_SIZE(mem_region); i++) {
-+              ret = mtk_wed_get_memory_region(wo, &mem_region[i]);
-+              if (ret)
-+                      return ret;
-+      }
-+
-+      wo->boot.name = "wo-boot";
-+      ret = mtk_wed_get_memory_region(wo, &wo->boot);
-+      if (ret)
-+              return ret;
-+
-+      /* set dummy cr */
-+      wed_w32(wo->hw->wed_dev, MTK_WED_SCR0 + 4 * MTK_WED_DUMMY_CR_FWDL,
-+              wo->hw->index + 1);
-+
-+      /* load firmware */
-+      fw_name = wo->hw->index ? MT7986_FIRMWARE_WO1 : MT7986_FIRMWARE_WO0;
-+      ret = request_firmware(&fw, fw_name, wo->hw->dev);
-+      if (ret)
-+              return ret;
-+
-+      trailer = (void *)(fw->data + fw->size -
-+                         sizeof(struct mtk_wed_fw_trailer));
-+      dev_info(wo->hw->dev,
-+               "MTK WED WO Firmware Version: %.10s, Build Time: %.15s\n",
-+               trailer->fw_ver, trailer->build_date);
-+      dev_info(wo->hw->dev, "MTK WED WO Chip ID %02x Region %d\n",
-+               trailer->chip_id, trailer->num_region);
-+
-+      for (i = 0; i < ARRAY_SIZE(mem_region); i++) {
-+              ret = mtk_wed_mcu_run_firmware(wo, fw, &mem_region[i]);
-+              if (ret)
-+                      goto out;
-+      }
-+
-+      /* set the start address */
-+      boot_cr = wo->hw->index ? MTK_WO_MCU_CFG_LS_WA_BOOT_ADDR_ADDR
-+                              : MTK_WO_MCU_CFG_LS_WM_BOOT_ADDR_ADDR;
-+      wo_w32(wo, boot_cr, mem_region[MTK_WED_WO_REGION_EMI].phy_addr >> 16);
-+      /* wo firmware reset */
-+      wo_w32(wo, MTK_WO_MCU_CFG_LS_WF_MCCR_CLR_ADDR, 0xc00);
-+
-+      val = wo_r32(wo, MTK_WO_MCU_CFG_LS_WF_MCU_CFG_WM_WA_ADDR);
-+      val |= wo->hw->index ? MTK_WO_MCU_CFG_LS_WF_WM_WA_WA_CPU_RSTB_MASK
-+                           : MTK_WO_MCU_CFG_LS_WF_WM_WA_WM_CPU_RSTB_MASK;
-+      wo_w32(wo, MTK_WO_MCU_CFG_LS_WF_MCU_CFG_WM_WA_ADDR, val);
-+out:
-+      release_firmware(fw);
-+
-+      return ret;
-+}
-+
-+static u32
-+mtk_wed_mcu_read_fw_dl(struct mtk_wed_wo *wo)
-+{
-+      return wed_r32(wo->hw->wed_dev,
-+                     MTK_WED_SCR0 + 4 * MTK_WED_DUMMY_CR_FWDL);
-+}
-+
-+int mtk_wed_mcu_init(struct mtk_wed_wo *wo)
-+{
-+      u32 val;
-+      int ret;
-+
-+      skb_queue_head_init(&wo->mcu.res_q);
-+      init_waitqueue_head(&wo->mcu.wait);
-+      mutex_init(&wo->mcu.mutex);
-+
-+      ret = mtk_wed_mcu_load_firmware(wo);
-+      if (ret)
-+              return ret;
-+
-+      return readx_poll_timeout(mtk_wed_mcu_read_fw_dl, wo, val, !val,
-+                                100, MTK_FW_DL_TIMEOUT);
-+}
-+
-+MODULE_FIRMWARE(MT7986_FIRMWARE_WO0);
-+MODULE_FIRMWARE(MT7986_FIRMWARE_WO1);
---- a/drivers/net/ethernet/mediatek/mtk_wed_regs.h
-+++ b/drivers/net/ethernet/mediatek/mtk_wed_regs.h
-@@ -152,6 +152,7 @@ struct mtk_wdma_desc {
- #define MTK_WED_RING_RX(_n)                           (0x400 + (_n) * 0x10)
-+#define MTK_WED_SCR0                                  0x3c0
- #define MTK_WED_WPDMA_INT_TRIGGER                     0x504
- #define MTK_WED_WPDMA_INT_TRIGGER_RX_DONE             BIT(1)
- #define MTK_WED_WPDMA_INT_TRIGGER_TX_DONE             GENMASK(5, 4)
---- /dev/null
-+++ b/drivers/net/ethernet/mediatek/mtk_wed_wo.h
-@@ -0,0 +1,150 @@
-+/* SPDX-License-Identifier: GPL-2.0-only */
-+/* Copyright (C) 2022 Lorenzo Bianconi <[email protected]>  */
-+
-+#ifndef __MTK_WED_WO_H
-+#define __MTK_WED_WO_H
-+
-+#include <linux/skbuff.h>
-+#include <linux/netdevice.h>
-+
-+struct mtk_wed_hw;
-+
-+struct mtk_wed_mcu_hdr {
-+      /* DW0 */
-+      u8 version;
-+      u8 cmd;
-+      __le16 length;
-+
-+      /* DW1 */
-+      __le16 seq;
-+      __le16 flag;
-+
-+      /* DW2 */
-+      __le32 status;
-+
-+      /* DW3 */
-+      u8 rsv[20];
-+};
-+
-+struct mtk_wed_wo_log_info {
-+      __le32 sn;
-+      __le32 total;
-+      __le32 rro;
-+      __le32 mod;
-+};
-+
-+enum mtk_wed_wo_event {
-+      MTK_WED_WO_EVT_LOG_DUMP         = 0x1,
-+      MTK_WED_WO_EVT_PROFILING        = 0x2,
-+      MTK_WED_WO_EVT_RXCNT_INFO       = 0x3,
-+};
-+
-+#define MTK_WED_MODULE_ID_WO          1
-+#define MTK_FW_DL_TIMEOUT             4000000 /* us */
-+#define MTK_WOCPU_TIMEOUT             2000000 /* us */
-+
-+enum {
-+      MTK_WED_WARP_CMD_FLAG_RSP               = BIT(0),
-+      MTK_WED_WARP_CMD_FLAG_NEED_RSP          = BIT(1),
-+      MTK_WED_WARP_CMD_FLAG_FROM_TO_WO        = BIT(2),
-+};
-+
-+enum {
-+      MTK_WED_WO_REGION_EMI,
-+      MTK_WED_WO_REGION_ILM,
-+      MTK_WED_WO_REGION_DATA,
-+      MTK_WED_WO_REGION_BOOT,
-+      __MTK_WED_WO_REGION_MAX,
-+};
-+
-+enum mtk_wed_dummy_cr_idx {
-+      MTK_WED_DUMMY_CR_FWDL,
-+      MTK_WED_DUMMY_CR_WO_STATUS,
-+};
-+
-+#define MT7986_FIRMWARE_WO0   "mediatek/mt7986_wo_0.bin"
-+#define MT7986_FIRMWARE_WO1   "mediatek/mt7986_wo_1.bin"
-+
-+#define MTK_WO_MCU_CFG_LS_BASE                                0
-+#define MTK_WO_MCU_CFG_LS_HW_VER_ADDR                 (MTK_WO_MCU_CFG_LS_BASE + 0x000)
-+#define MTK_WO_MCU_CFG_LS_FW_VER_ADDR                 (MTK_WO_MCU_CFG_LS_BASE + 0x004)
-+#define MTK_WO_MCU_CFG_LS_CFG_DBG1_ADDR                       (MTK_WO_MCU_CFG_LS_BASE + 0x00c)
-+#define MTK_WO_MCU_CFG_LS_CFG_DBG2_ADDR                       (MTK_WO_MCU_CFG_LS_BASE + 0x010)
-+#define MTK_WO_MCU_CFG_LS_WF_MCCR_ADDR                        (MTK_WO_MCU_CFG_LS_BASE + 0x014)
-+#define MTK_WO_MCU_CFG_LS_WF_MCCR_SET_ADDR            (MTK_WO_MCU_CFG_LS_BASE + 0x018)
-+#define MTK_WO_MCU_CFG_LS_WF_MCCR_CLR_ADDR            (MTK_WO_MCU_CFG_LS_BASE + 0x01c)
-+#define MTK_WO_MCU_CFG_LS_WF_MCU_CFG_WM_WA_ADDR               (MTK_WO_MCU_CFG_LS_BASE + 0x050)
-+#define MTK_WO_MCU_CFG_LS_WM_BOOT_ADDR_ADDR           (MTK_WO_MCU_CFG_LS_BASE + 0x060)
-+#define MTK_WO_MCU_CFG_LS_WA_BOOT_ADDR_ADDR           (MTK_WO_MCU_CFG_LS_BASE + 0x064)
-+
-+#define MTK_WO_MCU_CFG_LS_WF_WM_WA_WM_CPU_RSTB_MASK   BIT(5)
-+#define MTK_WO_MCU_CFG_LS_WF_WM_WA_WA_CPU_RSTB_MASK   BIT(0)
-+
-+struct mtk_wed_wo_memory_region {
-+      const char *name;
-+      void __iomem *addr;
-+      phys_addr_t phy_addr;
-+      u32 size;
-+      bool shared:1;
-+      bool consumed:1;
-+};
-+
-+struct mtk_wed_fw_region {
-+      __le32 decomp_crc;
-+      __le32 decomp_len;
-+      __le32 decomp_blk_sz;
-+      u8 rsv0[4];
-+      __le32 addr;
-+      __le32 len;
-+      u8 feature_set;
-+      u8 rsv1[15];
-+} __packed;
-+
-+struct mtk_wed_fw_trailer {
-+      u8 chip_id;
-+      u8 eco_code;
-+      u8 num_region;
-+      u8 format_ver;
-+      u8 format_flag;
-+      u8 rsv[2];
-+      char fw_ver[10];
-+      char build_date[15];
-+      u32 crc;
-+};
-+
-+struct mtk_wed_wo {
-+      struct mtk_wed_hw *hw;
-+      struct mtk_wed_wo_memory_region boot;
-+
-+      struct {
-+              struct mutex mutex;
-+              int timeout;
-+              u16 seq;
-+
-+              struct sk_buff_head res_q;
-+              wait_queue_head_t wait;
-+      } mcu;
-+};
-+
-+static inline int
-+mtk_wed_mcu_check_msg(struct mtk_wed_wo *wo, struct sk_buff *skb)
-+{
-+      struct mtk_wed_mcu_hdr *hdr = (struct mtk_wed_mcu_hdr *)skb->data;
-+
-+      if (hdr->version)
-+              return -EINVAL;
-+
-+      if (skb->len < sizeof(*hdr) || skb->len != le16_to_cpu(hdr->length))
-+              return -EINVAL;
-+
-+      return 0;
-+}
-+
-+void mtk_wed_mcu_rx_event(struct mtk_wed_wo *wo, struct sk_buff *skb);
-+void mtk_wed_mcu_rx_unsolicited_event(struct mtk_wed_wo *wo,
-+                                    struct sk_buff *skb);
-+int mtk_wed_mcu_send_msg(struct mtk_wed_wo *wo, int id, int cmd,
-+                       const void *data, int len, bool wait_resp);
-+int mtk_wed_mcu_init(struct mtk_wed_wo *wo);
-+
-+#endif /* __MTK_WED_WO_H */
---- a/include/linux/soc/mediatek/mtk_wed.h
-+++ b/include/linux/soc/mediatek/mtk_wed.h
-@@ -11,6 +11,35 @@
- struct mtk_wed_hw;
- struct mtk_wdma_desc;
-+enum mtk_wed_wo_cmd {
-+      MTK_WED_WO_CMD_WED_CFG,
-+      MTK_WED_WO_CMD_WED_RX_STAT,
-+      MTK_WED_WO_CMD_RRO_SER,
-+      MTK_WED_WO_CMD_DBG_INFO,
-+      MTK_WED_WO_CMD_DEV_INFO,
-+      MTK_WED_WO_CMD_BSS_INFO,
-+      MTK_WED_WO_CMD_STA_REC,
-+      MTK_WED_WO_CMD_DEV_INFO_DUMP,
-+      MTK_WED_WO_CMD_BSS_INFO_DUMP,
-+      MTK_WED_WO_CMD_STA_REC_DUMP,
-+      MTK_WED_WO_CMD_BA_INFO_DUMP,
-+      MTK_WED_WO_CMD_FBCMD_Q_DUMP,
-+      MTK_WED_WO_CMD_FW_LOG_CTRL,
-+      MTK_WED_WO_CMD_LOG_FLUSH,
-+      MTK_WED_WO_CMD_CHANGE_STATE,
-+      MTK_WED_WO_CMD_CPU_STATS_ENABLE,
-+      MTK_WED_WO_CMD_CPU_STATS_DUMP,
-+      MTK_WED_WO_CMD_EXCEPTION_INIT,
-+      MTK_WED_WO_CMD_PROF_CTRL,
-+      MTK_WED_WO_CMD_STA_BA_DUMP,
-+      MTK_WED_WO_CMD_BA_CTRL_DUMP,
-+      MTK_WED_WO_CMD_RXCNT_CTRL,
-+      MTK_WED_WO_CMD_RXCNT_INFO,
-+      MTK_WED_WO_CMD_SET_CAP,
-+      MTK_WED_WO_CMD_CCIF_RING_DUMP,
-+      MTK_WED_WO_CMD_WED_END
-+};
-+
- enum mtk_wed_bus_tye {
-       MTK_WED_BUS_PCIE,
-       MTK_WED_BUS_AXI,
diff --git a/target/linux/generic/backport-5.15/729-02-v6.1-net-ethernet-mtk_wed-introduce-wed-wo-support.patch b/target/linux/generic/backport-5.15/729-02-v6.1-net-ethernet-mtk_wed-introduce-wed-wo-support.patch
deleted file mode 100644 (file)
index fd5f45d..0000000
+++ /dev/null
@@ -1,737 +0,0 @@
-From: Lorenzo Bianconi <[email protected]>
-Date: Sat, 5 Nov 2022 23:36:19 +0100
-Subject: [PATCH] net: ethernet: mtk_wed: introduce wed wo support
-
-Introduce WO chip support to mtk wed driver. MTK WED WO is used to
-implement RX Wireless Ethernet Dispatch and offload traffic received by
-wlan nic to the wired interface.
-
-Tested-by: Daniel Golle <[email protected]>
-Co-developed-by: Sujuan Chen <[email protected]>
-Signed-off-by: Sujuan Chen <[email protected]>
-Signed-off-by: Lorenzo Bianconi <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- create mode 100644 drivers/net/ethernet/mediatek/mtk_wed_wo.c
-
---- a/drivers/net/ethernet/mediatek/Makefile
-+++ b/drivers/net/ethernet/mediatek/Makefile
-@@ -5,7 +5,7 @@
- obj-$(CONFIG_NET_MEDIATEK_SOC) += mtk_eth.o
- mtk_eth-y := mtk_eth_soc.o mtk_sgmii.o mtk_eth_path.o mtk_ppe.o mtk_ppe_debugfs.o mtk_ppe_offload.o
--mtk_eth-$(CONFIG_NET_MEDIATEK_SOC_WED) += mtk_wed.o mtk_wed_mcu.o
-+mtk_eth-$(CONFIG_NET_MEDIATEK_SOC_WED) += mtk_wed.o mtk_wed_mcu.o mtk_wed_wo.o
- ifdef CONFIG_DEBUG_FS
- mtk_eth-$(CONFIG_NET_MEDIATEK_SOC_WED) += mtk_wed_debugfs.o
- endif
---- a/drivers/net/ethernet/mediatek/mtk_wed.c
-+++ b/drivers/net/ethernet/mediatek/mtk_wed.c
-@@ -16,6 +16,7 @@
- #include "mtk_wed_regs.h"
- #include "mtk_wed.h"
- #include "mtk_ppe.h"
-+#include "mtk_wed_wo.h"
- #define MTK_PCIE_BASE(n)              (0x1a143000 + (n) * 0x2000)
-@@ -355,6 +356,8 @@ mtk_wed_detach(struct mtk_wed_device *de
-       mtk_wed_free_buffer(dev);
-       mtk_wed_free_tx_rings(dev);
-+      if (hw->version != 1)
-+              mtk_wed_wo_deinit(hw);
-       if (dev->wlan.bus_type == MTK_WED_BUS_PCIE) {
-               struct device_node *wlan_node;
-@@ -878,9 +881,11 @@ mtk_wed_attach(struct mtk_wed_device *de
-       }
-       mtk_wed_hw_init_early(dev);
--      if (hw->hifsys)
-+      if (hw->version == 1)
-               regmap_update_bits(hw->hifsys, HIFSYS_DMA_AG_MAP,
-                                  BIT(hw->index), 0);
-+      else
-+              ret = mtk_wed_wo_init(hw);
- out:
-       mutex_unlock(&hw_lock);
---- a/drivers/net/ethernet/mediatek/mtk_wed.h
-+++ b/drivers/net/ethernet/mediatek/mtk_wed.h
-@@ -10,6 +10,7 @@
- #include <linux/netdevice.h>
- struct mtk_eth;
-+struct mtk_wed_wo;
- struct mtk_wed_hw {
-       struct device_node *node;
-@@ -22,6 +23,7 @@ struct mtk_wed_hw {
-       struct regmap *mirror;
-       struct dentry *debugfs_dir;
-       struct mtk_wed_device *wed_dev;
-+      struct mtk_wed_wo *wed_wo;
-       u32 debugfs_reg;
-       u32 num_flows;
-       u8 version;
---- a/drivers/net/ethernet/mediatek/mtk_wed_mcu.c
-+++ b/drivers/net/ethernet/mediatek/mtk_wed_mcu.c
-@@ -122,8 +122,7 @@ mtk_wed_mcu_skb_send_msg(struct mtk_wed_
-       if (id == MTK_WED_MODULE_ID_WO)
-               hdr->flag |= cpu_to_le16(MTK_WED_WARP_CMD_FLAG_FROM_TO_WO);
--      dev_kfree_skb(skb);
--      return 0;
-+      return mtk_wed_wo_queue_tx_skb(wo, &wo->q_tx, skb);
- }
- static int
---- /dev/null
-+++ b/drivers/net/ethernet/mediatek/mtk_wed_wo.c
-@@ -0,0 +1,508 @@
-+// SPDX-License-Identifier: GPL-2.0-only
-+/* Copyright (C) 2022 MediaTek Inc.
-+ *
-+ * Author: Lorenzo Bianconi <[email protected]>
-+ *       Sujuan Chen <[email protected]>
-+ */
-+
-+#include <linux/kernel.h>
-+#include <linux/dma-mapping.h>
-+#include <linux/of_platform.h>
-+#include <linux/interrupt.h>
-+#include <linux/of_address.h>
-+#include <linux/mfd/syscon.h>
-+#include <linux/of_irq.h>
-+#include <linux/bitfield.h>
-+
-+#include "mtk_wed.h"
-+#include "mtk_wed_regs.h"
-+#include "mtk_wed_wo.h"
-+
-+static u32
-+mtk_wed_mmio_r32(struct mtk_wed_wo *wo, u32 reg)
-+{
-+      u32 val;
-+
-+      if (regmap_read(wo->mmio.regs, reg, &val))
-+              val = ~0;
-+
-+      return val;
-+}
-+
-+static void
-+mtk_wed_mmio_w32(struct mtk_wed_wo *wo, u32 reg, u32 val)
-+{
-+      regmap_write(wo->mmio.regs, reg, val);
-+}
-+
-+static u32
-+mtk_wed_wo_get_isr(struct mtk_wed_wo *wo)
-+{
-+      u32 val = mtk_wed_mmio_r32(wo, MTK_WED_WO_CCIF_RCHNUM);
-+
-+      return val & MTK_WED_WO_CCIF_RCHNUM_MASK;
-+}
-+
-+static void
-+mtk_wed_wo_set_isr(struct mtk_wed_wo *wo, u32 mask)
-+{
-+      mtk_wed_mmio_w32(wo, MTK_WED_WO_CCIF_IRQ0_MASK, mask);
-+}
-+
-+static void
-+mtk_wed_wo_set_ack(struct mtk_wed_wo *wo, u32 mask)
-+{
-+      mtk_wed_mmio_w32(wo, MTK_WED_WO_CCIF_ACK, mask);
-+}
-+
-+static void
-+mtk_wed_wo_set_isr_mask(struct mtk_wed_wo *wo, u32 mask, u32 val, bool set)
-+{
-+      unsigned long flags;
-+
-+      spin_lock_irqsave(&wo->mmio.lock, flags);
-+      wo->mmio.irq_mask &= ~mask;
-+      wo->mmio.irq_mask |= val;
-+      if (set)
-+              mtk_wed_wo_set_isr(wo, wo->mmio.irq_mask);
-+      spin_unlock_irqrestore(&wo->mmio.lock, flags);
-+}
-+
-+static void
-+mtk_wed_wo_irq_enable(struct mtk_wed_wo *wo, u32 mask)
-+{
-+      mtk_wed_wo_set_isr_mask(wo, 0, mask, false);
-+      tasklet_schedule(&wo->mmio.irq_tasklet);
-+}
-+
-+static void
-+mtk_wed_wo_irq_disable(struct mtk_wed_wo *wo, u32 mask)
-+{
-+      mtk_wed_wo_set_isr_mask(wo, mask, 0, true);
-+}
-+
-+static void
-+mtk_wed_wo_kickout(struct mtk_wed_wo *wo)
-+{
-+      mtk_wed_mmio_w32(wo, MTK_WED_WO_CCIF_BUSY, 1 << MTK_WED_WO_TXCH_NUM);
-+      mtk_wed_mmio_w32(wo, MTK_WED_WO_CCIF_TCHNUM, MTK_WED_WO_TXCH_NUM);
-+}
-+
-+static void
-+mtk_wed_wo_queue_kick(struct mtk_wed_wo *wo, struct mtk_wed_wo_queue *q,
-+                    u32 val)
-+{
-+      wmb();
-+      mtk_wed_mmio_w32(wo, q->regs.cpu_idx, val);
-+}
-+
-+static void *
-+mtk_wed_wo_dequeue(struct mtk_wed_wo *wo, struct mtk_wed_wo_queue *q, u32 *len,
-+                 bool flush)
-+{
-+      int buf_len = SKB_WITH_OVERHEAD(q->buf_size);
-+      int index = (q->tail + 1) % q->n_desc;
-+      struct mtk_wed_wo_queue_entry *entry;
-+      struct mtk_wed_wo_queue_desc *desc;
-+      void *buf;
-+
-+      if (!q->queued)
-+              return NULL;
-+
-+      if (flush)
-+              q->desc[index].ctrl |= cpu_to_le32(MTK_WED_WO_CTL_DMA_DONE);
-+      else if (!(q->desc[index].ctrl & cpu_to_le32(MTK_WED_WO_CTL_DMA_DONE)))
-+              return NULL;
-+
-+      q->tail = index;
-+      q->queued--;
-+
-+      desc = &q->desc[index];
-+      entry = &q->entry[index];
-+      buf = entry->buf;
-+      if (len)
-+              *len = FIELD_GET(MTK_WED_WO_CTL_SD_LEN0,
-+                               le32_to_cpu(READ_ONCE(desc->ctrl)));
-+      if (buf)
-+              dma_unmap_single(wo->hw->dev, entry->addr, buf_len,
-+                               DMA_FROM_DEVICE);
-+      entry->buf = NULL;
-+
-+      return buf;
-+}
-+
-+static int
-+mtk_wed_wo_queue_refill(struct mtk_wed_wo *wo, struct mtk_wed_wo_queue *q,
-+                      gfp_t gfp, bool rx)
-+{
-+      enum dma_data_direction dir = rx ? DMA_FROM_DEVICE : DMA_TO_DEVICE;
-+      int n_buf = 0;
-+
-+      spin_lock_bh(&q->lock);
-+      while (q->queued < q->n_desc) {
-+              void *buf = page_frag_alloc(&q->cache, q->buf_size, gfp);
-+              struct mtk_wed_wo_queue_entry *entry;
-+              dma_addr_t addr;
-+
-+              if (!buf)
-+                      break;
-+
-+              addr = dma_map_single(wo->hw->dev, buf, q->buf_size, dir);
-+              if (unlikely(dma_mapping_error(wo->hw->dev, addr))) {
-+                      skb_free_frag(buf);
-+                      break;
-+              }
-+
-+              q->head = (q->head + 1) % q->n_desc;
-+              entry = &q->entry[q->head];
-+              entry->addr = addr;
-+              entry->len = q->buf_size;
-+              q->entry[q->head].buf = buf;
-+
-+              if (rx) {
-+                      struct mtk_wed_wo_queue_desc *desc = &q->desc[q->head];
-+                      u32 ctrl = MTK_WED_WO_CTL_LAST_SEC0 |
-+                                 FIELD_PREP(MTK_WED_WO_CTL_SD_LEN0,
-+                                            entry->len);
-+
-+                      WRITE_ONCE(desc->buf0, cpu_to_le32(addr));
-+                      WRITE_ONCE(desc->ctrl, cpu_to_le32(ctrl));
-+              }
-+              q->queued++;
-+              n_buf++;
-+      }
-+      spin_unlock_bh(&q->lock);
-+
-+      return n_buf;
-+}
-+
-+static void
-+mtk_wed_wo_rx_complete(struct mtk_wed_wo *wo)
-+{
-+      mtk_wed_wo_set_ack(wo, MTK_WED_WO_RXCH_INT_MASK);
-+      mtk_wed_wo_irq_enable(wo, MTK_WED_WO_RXCH_INT_MASK);
-+}
-+
-+static void
-+mtk_wed_wo_rx_run_queue(struct mtk_wed_wo *wo, struct mtk_wed_wo_queue *q)
-+{
-+      for (;;) {
-+              struct mtk_wed_mcu_hdr *hdr;
-+              struct sk_buff *skb;
-+              void *data;
-+              u32 len;
-+
-+              data = mtk_wed_wo_dequeue(wo, q, &len, false);
-+              if (!data)
-+                      break;
-+
-+              skb = build_skb(data, q->buf_size);
-+              if (!skb) {
-+                      skb_free_frag(data);
-+                      continue;
-+              }
-+
-+              __skb_put(skb, len);
-+              if (mtk_wed_mcu_check_msg(wo, skb)) {
-+                      dev_kfree_skb(skb);
-+                      continue;
-+              }
-+
-+              hdr = (struct mtk_wed_mcu_hdr *)skb->data;
-+              if (hdr->flag & cpu_to_le16(MTK_WED_WARP_CMD_FLAG_RSP))
-+                      mtk_wed_mcu_rx_event(wo, skb);
-+              else
-+                      mtk_wed_mcu_rx_unsolicited_event(wo, skb);
-+      }
-+
-+      if (mtk_wed_wo_queue_refill(wo, q, GFP_ATOMIC, true)) {
-+              u32 index = (q->head - 1) % q->n_desc;
-+
-+              mtk_wed_wo_queue_kick(wo, q, index);
-+      }
-+}
-+
-+static irqreturn_t
-+mtk_wed_wo_irq_handler(int irq, void *data)
-+{
-+      struct mtk_wed_wo *wo = data;
-+
-+      mtk_wed_wo_set_isr(wo, 0);
-+      tasklet_schedule(&wo->mmio.irq_tasklet);
-+
-+      return IRQ_HANDLED;
-+}
-+
-+static void mtk_wed_wo_irq_tasklet(struct tasklet_struct *t)
-+{
-+      struct mtk_wed_wo *wo = from_tasklet(wo, t, mmio.irq_tasklet);
-+      u32 intr, mask;
-+
-+      /* disable interrupts */
-+      mtk_wed_wo_set_isr(wo, 0);
-+
-+      intr = mtk_wed_wo_get_isr(wo);
-+      intr &= wo->mmio.irq_mask;
-+      mask = intr & (MTK_WED_WO_RXCH_INT_MASK | MTK_WED_WO_EXCEPTION_INT_MASK);
-+      mtk_wed_wo_irq_disable(wo, mask);
-+
-+      if (intr & MTK_WED_WO_RXCH_INT_MASK) {
-+              mtk_wed_wo_rx_run_queue(wo, &wo->q_rx);
-+              mtk_wed_wo_rx_complete(wo);
-+      }
-+}
-+
-+/* mtk wed wo hw queues */
-+
-+static int
-+mtk_wed_wo_queue_alloc(struct mtk_wed_wo *wo, struct mtk_wed_wo_queue *q,
-+                     int n_desc, int buf_size, int index,
-+                     struct mtk_wed_wo_queue_regs *regs)
-+{
-+      spin_lock_init(&q->lock);
-+      q->regs = *regs;
-+      q->n_desc = n_desc;
-+      q->buf_size = buf_size;
-+
-+      q->desc = dmam_alloc_coherent(wo->hw->dev, n_desc * sizeof(*q->desc),
-+                                    &q->desc_dma, GFP_KERNEL);
-+      if (!q->desc)
-+              return -ENOMEM;
-+
-+      q->entry = devm_kzalloc(wo->hw->dev, n_desc * sizeof(*q->entry),
-+                              GFP_KERNEL);
-+      if (!q->entry)
-+              return -ENOMEM;
-+
-+      return 0;
-+}
-+
-+static void
-+mtk_wed_wo_queue_free(struct mtk_wed_wo *wo, struct mtk_wed_wo_queue *q)
-+{
-+      mtk_wed_mmio_w32(wo, q->regs.cpu_idx, 0);
-+      dma_free_coherent(wo->hw->dev, q->n_desc * sizeof(*q->desc), q->desc,
-+                        q->desc_dma);
-+}
-+
-+static void
-+mtk_wed_wo_queue_tx_clean(struct mtk_wed_wo *wo, struct mtk_wed_wo_queue *q)
-+{
-+      struct page *page;
-+      int i;
-+
-+      spin_lock_bh(&q->lock);
-+      for (i = 0; i < q->n_desc; i++) {
-+              struct mtk_wed_wo_queue_entry *entry = &q->entry[i];
-+
-+              dma_unmap_single(wo->hw->dev, entry->addr, entry->len,
-+                               DMA_TO_DEVICE);
-+              skb_free_frag(entry->buf);
-+              entry->buf = NULL;
-+      }
-+      spin_unlock_bh(&q->lock);
-+
-+      if (!q->cache.va)
-+              return;
-+
-+      page = virt_to_page(q->cache.va);
-+      __page_frag_cache_drain(page, q->cache.pagecnt_bias);
-+      memset(&q->cache, 0, sizeof(q->cache));
-+}
-+
-+static void
-+mtk_wed_wo_queue_rx_clean(struct mtk_wed_wo *wo, struct mtk_wed_wo_queue *q)
-+{
-+      struct page *page;
-+
-+      spin_lock_bh(&q->lock);
-+      for (;;) {
-+              void *buf = mtk_wed_wo_dequeue(wo, q, NULL, true);
-+
-+              if (!buf)
-+                      break;
-+
-+              skb_free_frag(buf);
-+      }
-+      spin_unlock_bh(&q->lock);
-+
-+      if (!q->cache.va)
-+              return;
-+
-+      page = virt_to_page(q->cache.va);
-+      __page_frag_cache_drain(page, q->cache.pagecnt_bias);
-+      memset(&q->cache, 0, sizeof(q->cache));
-+}
-+
-+static void
-+mtk_wed_wo_queue_reset(struct mtk_wed_wo *wo, struct mtk_wed_wo_queue *q)
-+{
-+      mtk_wed_mmio_w32(wo, q->regs.cpu_idx, 0);
-+      mtk_wed_mmio_w32(wo, q->regs.desc_base, q->desc_dma);
-+      mtk_wed_mmio_w32(wo, q->regs.ring_size, q->n_desc);
-+}
-+
-+int mtk_wed_wo_queue_tx_skb(struct mtk_wed_wo *wo, struct mtk_wed_wo_queue *q,
-+                          struct sk_buff *skb)
-+{
-+      struct mtk_wed_wo_queue_entry *entry;
-+      struct mtk_wed_wo_queue_desc *desc;
-+      int ret = 0, index;
-+      u32 ctrl;
-+
-+      spin_lock_bh(&q->lock);
-+
-+      q->tail = mtk_wed_mmio_r32(wo, q->regs.dma_idx);
-+      index = (q->head + 1) % q->n_desc;
-+      if (q->tail == index) {
-+              ret = -ENOMEM;
-+              goto out;
-+      }
-+
-+      entry = &q->entry[index];
-+      if (skb->len > entry->len) {
-+              ret = -ENOMEM;
-+              goto out;
-+      }
-+
-+      desc = &q->desc[index];
-+      q->head = index;
-+
-+      dma_sync_single_for_cpu(wo->hw->dev, entry->addr, skb->len,
-+                              DMA_TO_DEVICE);
-+      memcpy(entry->buf, skb->data, skb->len);
-+      dma_sync_single_for_device(wo->hw->dev, entry->addr, skb->len,
-+                                 DMA_TO_DEVICE);
-+
-+      ctrl = FIELD_PREP(MTK_WED_WO_CTL_SD_LEN0, skb->len) |
-+             MTK_WED_WO_CTL_LAST_SEC0 | MTK_WED_WO_CTL_DMA_DONE;
-+      WRITE_ONCE(desc->buf0, cpu_to_le32(entry->addr));
-+      WRITE_ONCE(desc->ctrl, cpu_to_le32(ctrl));
-+
-+      mtk_wed_wo_queue_kick(wo, q, q->head);
-+      mtk_wed_wo_kickout(wo);
-+out:
-+      spin_unlock_bh(&q->lock);
-+
-+      dev_kfree_skb(skb);
-+
-+      return ret;
-+}
-+
-+static int
-+mtk_wed_wo_exception_init(struct mtk_wed_wo *wo)
-+{
-+      return 0;
-+}
-+
-+static int
-+mtk_wed_wo_hardware_init(struct mtk_wed_wo *wo)
-+{
-+      struct mtk_wed_wo_queue_regs regs;
-+      struct device_node *np;
-+      int ret;
-+
-+      np = of_parse_phandle(wo->hw->node, "mediatek,wo-ccif", 0);
-+      if (!np)
-+              return -ENODEV;
-+
-+      wo->mmio.regs = syscon_regmap_lookup_by_phandle(np, NULL);
-+      if (IS_ERR_OR_NULL(wo->mmio.regs))
-+              return PTR_ERR(wo->mmio.regs);
-+
-+      wo->mmio.irq = irq_of_parse_and_map(np, 0);
-+      wo->mmio.irq_mask = MTK_WED_WO_ALL_INT_MASK;
-+      spin_lock_init(&wo->mmio.lock);
-+      tasklet_setup(&wo->mmio.irq_tasklet, mtk_wed_wo_irq_tasklet);
-+
-+      ret = devm_request_irq(wo->hw->dev, wo->mmio.irq,
-+                             mtk_wed_wo_irq_handler, IRQF_TRIGGER_HIGH,
-+                             KBUILD_MODNAME, wo);
-+      if (ret)
-+              goto error;
-+
-+      regs.desc_base = MTK_WED_WO_CCIF_DUMMY1;
-+      regs.ring_size = MTK_WED_WO_CCIF_DUMMY2;
-+      regs.dma_idx = MTK_WED_WO_CCIF_SHADOW4;
-+      regs.cpu_idx = MTK_WED_WO_CCIF_DUMMY3;
-+
-+      ret = mtk_wed_wo_queue_alloc(wo, &wo->q_tx, MTK_WED_WO_RING_SIZE,
-+                                   MTK_WED_WO_CMD_LEN, MTK_WED_WO_TXCH_NUM,
-+                                   &regs);
-+      if (ret)
-+              goto error;
-+
-+      mtk_wed_wo_queue_refill(wo, &wo->q_tx, GFP_KERNEL, false);
-+      mtk_wed_wo_queue_reset(wo, &wo->q_tx);
-+
-+      regs.desc_base = MTK_WED_WO_CCIF_DUMMY5;
-+      regs.ring_size = MTK_WED_WO_CCIF_DUMMY6;
-+      regs.dma_idx = MTK_WED_WO_CCIF_SHADOW8;
-+      regs.cpu_idx = MTK_WED_WO_CCIF_DUMMY7;
-+
-+      ret = mtk_wed_wo_queue_alloc(wo, &wo->q_rx, MTK_WED_WO_RING_SIZE,
-+                                   MTK_WED_WO_CMD_LEN, MTK_WED_WO_RXCH_NUM,
-+                                   &regs);
-+      if (ret)
-+              goto error;
-+
-+      mtk_wed_wo_queue_refill(wo, &wo->q_rx, GFP_KERNEL, true);
-+      mtk_wed_wo_queue_reset(wo, &wo->q_rx);
-+
-+      /* rx queue irqmask */
-+      mtk_wed_wo_set_isr(wo, wo->mmio.irq_mask);
-+
-+      return 0;
-+
-+error:
-+      devm_free_irq(wo->hw->dev, wo->mmio.irq, wo);
-+
-+      return ret;
-+}
-+
-+static void
-+mtk_wed_wo_hw_deinit(struct mtk_wed_wo *wo)
-+{
-+      /* disable interrupts */
-+      mtk_wed_wo_set_isr(wo, 0);
-+
-+      tasklet_disable(&wo->mmio.irq_tasklet);
-+
-+      disable_irq(wo->mmio.irq);
-+      devm_free_irq(wo->hw->dev, wo->mmio.irq, wo);
-+
-+      mtk_wed_wo_queue_tx_clean(wo, &wo->q_tx);
-+      mtk_wed_wo_queue_rx_clean(wo, &wo->q_rx);
-+      mtk_wed_wo_queue_free(wo, &wo->q_tx);
-+      mtk_wed_wo_queue_free(wo, &wo->q_rx);
-+}
-+
-+int mtk_wed_wo_init(struct mtk_wed_hw *hw)
-+{
-+      struct mtk_wed_wo *wo;
-+      int ret;
-+
-+      wo = devm_kzalloc(hw->dev, sizeof(*wo), GFP_KERNEL);
-+      if (!wo)
-+              return -ENOMEM;
-+
-+      hw->wed_wo = wo;
-+      wo->hw = hw;
-+
-+      ret = mtk_wed_wo_hardware_init(wo);
-+      if (ret)
-+              return ret;
-+
-+      ret = mtk_wed_mcu_init(wo);
-+      if (ret)
-+              return ret;
-+
-+      return mtk_wed_wo_exception_init(wo);
-+}
-+
-+void mtk_wed_wo_deinit(struct mtk_wed_hw *hw)
-+{
-+      struct mtk_wed_wo *wo = hw->wed_wo;
-+
-+      mtk_wed_wo_hw_deinit(wo);
-+}
---- a/drivers/net/ethernet/mediatek/mtk_wed_wo.h
-+++ b/drivers/net/ethernet/mediatek/mtk_wed_wo.h
-@@ -80,6 +80,54 @@ enum mtk_wed_dummy_cr_idx {
- #define MTK_WO_MCU_CFG_LS_WF_WM_WA_WM_CPU_RSTB_MASK   BIT(5)
- #define MTK_WO_MCU_CFG_LS_WF_WM_WA_WA_CPU_RSTB_MASK   BIT(0)
-+#define MTK_WED_WO_RING_SIZE  256
-+#define MTK_WED_WO_CMD_LEN    1504
-+
-+#define MTK_WED_WO_TXCH_NUM           0
-+#define MTK_WED_WO_RXCH_NUM           1
-+#define MTK_WED_WO_RXCH_WO_EXCEPTION  7
-+
-+#define MTK_WED_WO_TXCH_INT_MASK      BIT(0)
-+#define MTK_WED_WO_RXCH_INT_MASK      BIT(1)
-+#define MTK_WED_WO_EXCEPTION_INT_MASK BIT(7)
-+#define MTK_WED_WO_ALL_INT_MASK               (MTK_WED_WO_RXCH_INT_MASK | \
-+                                       MTK_WED_WO_EXCEPTION_INT_MASK)
-+
-+#define MTK_WED_WO_CCIF_BUSY          0x004
-+#define MTK_WED_WO_CCIF_START         0x008
-+#define MTK_WED_WO_CCIF_TCHNUM                0x00c
-+#define MTK_WED_WO_CCIF_RCHNUM                0x010
-+#define MTK_WED_WO_CCIF_RCHNUM_MASK   GENMASK(7, 0)
-+
-+#define MTK_WED_WO_CCIF_ACK           0x014
-+#define MTK_WED_WO_CCIF_IRQ0_MASK     0x018
-+#define MTK_WED_WO_CCIF_IRQ1_MASK     0x01c
-+#define MTK_WED_WO_CCIF_DUMMY1                0x020
-+#define MTK_WED_WO_CCIF_DUMMY2                0x024
-+#define MTK_WED_WO_CCIF_DUMMY3                0x028
-+#define MTK_WED_WO_CCIF_DUMMY4                0x02c
-+#define MTK_WED_WO_CCIF_SHADOW1               0x030
-+#define MTK_WED_WO_CCIF_SHADOW2               0x034
-+#define MTK_WED_WO_CCIF_SHADOW3               0x038
-+#define MTK_WED_WO_CCIF_SHADOW4               0x03c
-+#define MTK_WED_WO_CCIF_DUMMY5                0x050
-+#define MTK_WED_WO_CCIF_DUMMY6                0x054
-+#define MTK_WED_WO_CCIF_DUMMY7                0x058
-+#define MTK_WED_WO_CCIF_DUMMY8                0x05c
-+#define MTK_WED_WO_CCIF_SHADOW5               0x060
-+#define MTK_WED_WO_CCIF_SHADOW6               0x064
-+#define MTK_WED_WO_CCIF_SHADOW7               0x068
-+#define MTK_WED_WO_CCIF_SHADOW8               0x06c
-+
-+#define MTK_WED_WO_CTL_SD_LEN1                GENMASK(13, 0)
-+#define MTK_WED_WO_CTL_LAST_SEC1      BIT(14)
-+#define MTK_WED_WO_CTL_BURST          BIT(15)
-+#define MTK_WED_WO_CTL_SD_LEN0_SHIFT  16
-+#define MTK_WED_WO_CTL_SD_LEN0                GENMASK(29, 16)
-+#define MTK_WED_WO_CTL_LAST_SEC0      BIT(30)
-+#define MTK_WED_WO_CTL_DMA_DONE               BIT(31)
-+#define MTK_WED_WO_INFO_WINFO         GENMASK(15, 0)
-+
- struct mtk_wed_wo_memory_region {
-       const char *name;
-       void __iomem *addr;
-@@ -112,10 +160,53 @@ struct mtk_wed_fw_trailer {
-       u32 crc;
- };
-+struct mtk_wed_wo_queue_regs {
-+      u32 desc_base;
-+      u32 ring_size;
-+      u32 cpu_idx;
-+      u32 dma_idx;
-+};
-+
-+struct mtk_wed_wo_queue_desc {
-+      __le32 buf0;
-+      __le32 ctrl;
-+      __le32 buf1;
-+      __le32 info;
-+      __le32 reserved[4];
-+} __packed __aligned(32);
-+
-+struct mtk_wed_wo_queue_entry {
-+      dma_addr_t addr;
-+      void *buf;
-+      u32 len;
-+};
-+
-+struct mtk_wed_wo_queue {
-+      struct mtk_wed_wo_queue_regs regs;
-+
-+      struct page_frag_cache cache;
-+      spinlock_t lock;
-+
-+      struct mtk_wed_wo_queue_desc *desc;
-+      dma_addr_t desc_dma;
-+
-+      struct mtk_wed_wo_queue_entry *entry;
-+
-+      u16 head;
-+      u16 tail;
-+      int n_desc;
-+      int queued;
-+      int buf_size;
-+
-+};
-+
- struct mtk_wed_wo {
-       struct mtk_wed_hw *hw;
-       struct mtk_wed_wo_memory_region boot;
-+      struct mtk_wed_wo_queue q_tx;
-+      struct mtk_wed_wo_queue q_rx;
-+
-       struct {
-               struct mutex mutex;
-               int timeout;
-@@ -124,6 +215,15 @@ struct mtk_wed_wo {
-               struct sk_buff_head res_q;
-               wait_queue_head_t wait;
-       } mcu;
-+
-+      struct {
-+              struct regmap *regs;
-+
-+              spinlock_t lock;
-+              struct tasklet_struct irq_tasklet;
-+              int irq;
-+              u32 irq_mask;
-+      } mmio;
- };
- static inline int
-@@ -146,5 +246,9 @@ void mtk_wed_mcu_rx_unsolicited_event(st
- int mtk_wed_mcu_send_msg(struct mtk_wed_wo *wo, int id, int cmd,
-                        const void *data, int len, bool wait_resp);
- int mtk_wed_mcu_init(struct mtk_wed_wo *wo);
-+int mtk_wed_wo_init(struct mtk_wed_hw *hw);
-+void mtk_wed_wo_deinit(struct mtk_wed_hw *hw);
-+int mtk_wed_wo_queue_tx_skb(struct mtk_wed_wo *dev, struct mtk_wed_wo_queue *q,
-+                          struct sk_buff *skb);
- #endif /* __MTK_WED_WO_H */
diff --git a/target/linux/generic/backport-5.15/729-03-v6.1-net-ethernet-mtk_wed-rename-tx_wdma-array-in-rx_wdma.patch b/target/linux/generic/backport-5.15/729-03-v6.1-net-ethernet-mtk_wed-rename-tx_wdma-array-in-rx_wdma.patch
deleted file mode 100644 (file)
index a002a5f..0000000
+++ /dev/null
@@ -1,79 +0,0 @@
-From: Lorenzo Bianconi <[email protected]>
-Date: Sat, 5 Nov 2022 23:36:20 +0100
-Subject: [PATCH] net: ethernet: mtk_wed: rename tx_wdma array in rx_wdma
-
-Rename tx_wdma queue array in rx_wdma since this is rx side of wdma soc.
-Moreover rename mtk_wed_wdma_ring_setup routine in
-mtk_wed_wdma_rx_ring_setup()
-
-Signed-off-by: Lorenzo Bianconi <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
-
---- a/drivers/net/ethernet/mediatek/mtk_wed.c
-+++ b/drivers/net/ethernet/mediatek/mtk_wed.c
-@@ -253,8 +253,8 @@ mtk_wed_free_tx_rings(struct mtk_wed_dev
-       for (i = 0; i < ARRAY_SIZE(dev->tx_ring); i++)
-               mtk_wed_free_ring(dev, &dev->tx_ring[i]);
--      for (i = 0; i < ARRAY_SIZE(dev->tx_wdma); i++)
--              mtk_wed_free_ring(dev, &dev->tx_wdma[i]);
-+      for (i = 0; i < ARRAY_SIZE(dev->rx_wdma); i++)
-+              mtk_wed_free_ring(dev, &dev->rx_wdma[i]);
- }
- static void
-@@ -688,10 +688,10 @@ mtk_wed_ring_alloc(struct mtk_wed_device
- }
- static int
--mtk_wed_wdma_ring_setup(struct mtk_wed_device *dev, int idx, int size)
-+mtk_wed_wdma_rx_ring_setup(struct mtk_wed_device *dev, int idx, int size)
- {
-       u32 desc_size = sizeof(struct mtk_wdma_desc) * dev->hw->version;
--      struct mtk_wed_ring *wdma = &dev->tx_wdma[idx];
-+      struct mtk_wed_ring *wdma = &dev->rx_wdma[idx];
-       if (mtk_wed_ring_alloc(dev, wdma, MTK_WED_WDMA_RING_SIZE, desc_size))
-               return -ENOMEM;
-@@ -805,9 +805,9 @@ mtk_wed_start(struct mtk_wed_device *dev
- {
-       int i;
--      for (i = 0; i < ARRAY_SIZE(dev->tx_wdma); i++)
--              if (!dev->tx_wdma[i].desc)
--                      mtk_wed_wdma_ring_setup(dev, i, 16);
-+      for (i = 0; i < ARRAY_SIZE(dev->rx_wdma); i++)
-+              if (!dev->rx_wdma[i].desc)
-+                      mtk_wed_wdma_rx_ring_setup(dev, i, 16);
-       mtk_wed_hw_init(dev);
-       mtk_wed_configure_irq(dev, irq_mask);
-@@ -916,7 +916,7 @@ mtk_wed_tx_ring_setup(struct mtk_wed_dev
-                              sizeof(*ring->desc)))
-               return -ENOMEM;
--      if (mtk_wed_wdma_ring_setup(dev, idx, MTK_WED_WDMA_RING_SIZE))
-+      if (mtk_wed_wdma_rx_ring_setup(dev, idx, MTK_WED_WDMA_RING_SIZE))
-               return -ENOMEM;
-       ring->reg_base = MTK_WED_RING_TX(idx);
---- a/include/linux/soc/mediatek/mtk_wed.h
-+++ b/include/linux/soc/mediatek/mtk_wed.h
-@@ -7,6 +7,7 @@
- #include <linux/pci.h>
- #define MTK_WED_TX_QUEUES             2
-+#define MTK_WED_RX_QUEUES             2
- struct mtk_wed_hw;
- struct mtk_wdma_desc;
-@@ -66,7 +67,7 @@ struct mtk_wed_device {
-       struct mtk_wed_ring tx_ring[MTK_WED_TX_QUEUES];
-       struct mtk_wed_ring txfree_ring;
--      struct mtk_wed_ring tx_wdma[MTK_WED_TX_QUEUES];
-+      struct mtk_wed_ring rx_wdma[MTK_WED_RX_QUEUES];
-       struct {
-               int size;
diff --git a/target/linux/generic/backport-5.15/729-04-v6.1-net-ethernet-mtk_wed-add-configure-wed-wo-support.patch b/target/linux/generic/backport-5.15/729-04-v6.1-net-ethernet-mtk_wed-add-configure-wed-wo-support.patch
deleted file mode 100644 (file)
index eca2973..0000000
+++ /dev/null
@@ -1,1521 +0,0 @@
-From: Lorenzo Bianconi <[email protected]>
-Date: Sat, 5 Nov 2022 23:36:21 +0100
-Subject: [PATCH] net: ethernet: mtk_wed: add configure wed wo support
-
-Enable RX Wireless Ethernet Dispatch available on MT7986 Soc.
-
-Tested-by: Daniel Golle <[email protected]>
-Co-developed-by: Sujuan Chen <[email protected]>
-Signed-off-by: Sujuan Chen <[email protected]>
-Signed-off-by: Lorenzo Bianconi <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
-
---- a/drivers/net/ethernet/mediatek/mtk_wed.c
-+++ b/drivers/net/ethernet/mediatek/mtk_wed.c
-@@ -9,6 +9,7 @@
- #include <linux/skbuff.h>
- #include <linux/of_platform.h>
- #include <linux/of_address.h>
-+#include <linux/of_reserved_mem.h>
- #include <linux/mfd/syscon.h>
- #include <linux/debugfs.h>
- #include <linux/soc/mediatek/mtk_wed.h>
-@@ -23,6 +24,7 @@
- #define MTK_WED_PKT_SIZE              1900
- #define MTK_WED_BUF_SIZE              2048
- #define MTK_WED_BUF_PER_PAGE          (PAGE_SIZE / 2048)
-+#define MTK_WED_RX_RING_SIZE          1536
- #define MTK_WED_TX_RING_SIZE          2048
- #define MTK_WED_WDMA_RING_SIZE                1024
-@@ -31,6 +33,10 @@
- #define MTK_WED_PER_GROUP_PKT         128
- #define MTK_WED_FBUF_SIZE             128
-+#define MTK_WED_MIOD_CNT              16
-+#define MTK_WED_FB_CMD_CNT            1024
-+#define MTK_WED_RRO_QUE_CNT           8192
-+#define MTK_WED_MIOD_ENTRY_CNT                128
- static struct mtk_wed_hw *hw_list[2];
- static DEFINE_MUTEX(hw_lock);
-@@ -65,12 +71,76 @@ wdma_set(struct mtk_wed_device *dev, u32
-       wdma_m32(dev, reg, 0, mask);
- }
-+static void
-+wdma_clr(struct mtk_wed_device *dev, u32 reg, u32 mask)
-+{
-+      wdma_m32(dev, reg, mask, 0);
-+}
-+
-+static u32
-+wifi_r32(struct mtk_wed_device *dev, u32 reg)
-+{
-+      return readl(dev->wlan.base + reg);
-+}
-+
-+static void
-+wifi_w32(struct mtk_wed_device *dev, u32 reg, u32 val)
-+{
-+      writel(val, dev->wlan.base + reg);
-+}
-+
- static u32
- mtk_wed_read_reset(struct mtk_wed_device *dev)
- {
-       return wed_r32(dev, MTK_WED_RESET);
- }
-+static u32
-+mtk_wdma_read_reset(struct mtk_wed_device *dev)
-+{
-+      return wdma_r32(dev, MTK_WDMA_GLO_CFG);
-+}
-+
-+static void
-+mtk_wdma_rx_reset(struct mtk_wed_device *dev)
-+{
-+      u32 status, mask = MTK_WDMA_GLO_CFG_RX_DMA_BUSY;
-+      int i;
-+
-+      wdma_clr(dev, MTK_WDMA_GLO_CFG, MTK_WDMA_GLO_CFG_RX_DMA_EN);
-+      if (readx_poll_timeout(mtk_wdma_read_reset, dev, status,
-+                             !(status & mask), 0, 1000))
-+              dev_err(dev->hw->dev, "rx reset failed\n");
-+
-+      for (i = 0; i < ARRAY_SIZE(dev->rx_wdma); i++) {
-+              if (dev->rx_wdma[i].desc)
-+                      continue;
-+
-+              wdma_w32(dev,
-+                       MTK_WDMA_RING_RX(i) + MTK_WED_RING_OFS_CPU_IDX, 0);
-+      }
-+}
-+
-+static void
-+mtk_wdma_tx_reset(struct mtk_wed_device *dev)
-+{
-+      u32 status, mask = MTK_WDMA_GLO_CFG_TX_DMA_BUSY;
-+      int i;
-+
-+      wdma_clr(dev, MTK_WDMA_GLO_CFG, MTK_WDMA_GLO_CFG_TX_DMA_EN);
-+      if (readx_poll_timeout(mtk_wdma_read_reset, dev, status,
-+                             !(status & mask), 0, 1000))
-+              dev_err(dev->hw->dev, "tx reset failed\n");
-+
-+      for (i = 0; i < ARRAY_SIZE(dev->tx_wdma); i++) {
-+              if (dev->tx_wdma[i].desc)
-+                      continue;
-+
-+              wdma_w32(dev,
-+                       MTK_WDMA_RING_TX(i) + MTK_WED_RING_OFS_CPU_IDX, 0);
-+      }
-+}
-+
- static void
- mtk_wed_reset(struct mtk_wed_device *dev, u32 mask)
- {
-@@ -82,6 +152,54 @@ mtk_wed_reset(struct mtk_wed_device *dev
-               WARN_ON_ONCE(1);
- }
-+static u32
-+mtk_wed_wo_read_status(struct mtk_wed_device *dev)
-+{
-+      return wed_r32(dev, MTK_WED_SCR0 + 4 * MTK_WED_DUMMY_CR_WO_STATUS);
-+}
-+
-+static void
-+mtk_wed_wo_reset(struct mtk_wed_device *dev)
-+{
-+      struct mtk_wed_wo *wo = dev->hw->wed_wo;
-+      u8 state = MTK_WED_WO_STATE_DISABLE;
-+      void __iomem *reg;
-+      u32 val;
-+
-+      mtk_wdma_tx_reset(dev);
-+      mtk_wed_reset(dev, MTK_WED_RESET_WED);
-+
-+      mtk_wed_mcu_send_msg(wo, MTK_WED_MODULE_ID_WO,
-+                           MTK_WED_WO_CMD_CHANGE_STATE, &state,
-+                           sizeof(state), false);
-+
-+      if (readx_poll_timeout(mtk_wed_wo_read_status, dev, val,
-+                             val == MTK_WED_WOIF_DISABLE_DONE,
-+                             100, MTK_WOCPU_TIMEOUT))
-+              dev_err(dev->hw->dev, "failed to disable wed-wo\n");
-+
-+      reg = ioremap(MTK_WED_WO_CPU_MCUSYS_RESET_ADDR, 4);
-+
-+      val = readl(reg);
-+      switch (dev->hw->index) {
-+      case 0:
-+              val |= MTK_WED_WO_CPU_WO0_MCUSYS_RESET_MASK;
-+              writel(val, reg);
-+              val &= ~MTK_WED_WO_CPU_WO0_MCUSYS_RESET_MASK;
-+              writel(val, reg);
-+              break;
-+      case 1:
-+              val |= MTK_WED_WO_CPU_WO1_MCUSYS_RESET_MASK;
-+              writel(val, reg);
-+              val &= ~MTK_WED_WO_CPU_WO1_MCUSYS_RESET_MASK;
-+              writel(val, reg);
-+              break;
-+      default:
-+              break;
-+      }
-+      iounmap(reg);
-+}
-+
- static struct mtk_wed_hw *
- mtk_wed_assign(struct mtk_wed_device *dev)
- {
-@@ -116,7 +234,7 @@ out:
- }
- static int
--mtk_wed_buffer_alloc(struct mtk_wed_device *dev)
-+mtk_wed_tx_buffer_alloc(struct mtk_wed_device *dev)
- {
-       struct mtk_wdma_desc *desc;
-       dma_addr_t desc_phys;
-@@ -133,16 +251,16 @@ mtk_wed_buffer_alloc(struct mtk_wed_devi
-       if (!page_list)
-               return -ENOMEM;
--      dev->buf_ring.size = ring_size;
--      dev->buf_ring.pages = page_list;
-+      dev->tx_buf_ring.size = ring_size;
-+      dev->tx_buf_ring.pages = page_list;
-       desc = dma_alloc_coherent(dev->hw->dev, ring_size * sizeof(*desc),
-                                 &desc_phys, GFP_KERNEL);
-       if (!desc)
-               return -ENOMEM;
--      dev->buf_ring.desc = desc;
--      dev->buf_ring.desc_phys = desc_phys;
-+      dev->tx_buf_ring.desc = desc;
-+      dev->tx_buf_ring.desc_phys = desc_phys;
-       for (i = 0, page_idx = 0; i < ring_size; i += MTK_WED_BUF_PER_PAGE) {
-               dma_addr_t page_phys, buf_phys;
-@@ -203,10 +321,10 @@ mtk_wed_buffer_alloc(struct mtk_wed_devi
- }
- static void
--mtk_wed_free_buffer(struct mtk_wed_device *dev)
-+mtk_wed_free_tx_buffer(struct mtk_wed_device *dev)
- {
--      struct mtk_wdma_desc *desc = dev->buf_ring.desc;
--      void **page_list = dev->buf_ring.pages;
-+      struct mtk_wdma_desc *desc = dev->tx_buf_ring.desc;
-+      void **page_list = dev->tx_buf_ring.pages;
-       int page_idx;
-       int i;
-@@ -216,7 +334,8 @@ mtk_wed_free_buffer(struct mtk_wed_devic
-       if (!desc)
-               goto free_pagelist;
--      for (i = 0, page_idx = 0; i < dev->buf_ring.size; i += MTK_WED_BUF_PER_PAGE) {
-+      for (i = 0, page_idx = 0; i < dev->tx_buf_ring.size;
-+           i += MTK_WED_BUF_PER_PAGE) {
-               void *page = page_list[page_idx++];
-               dma_addr_t buf_addr;
-@@ -229,13 +348,59 @@ mtk_wed_free_buffer(struct mtk_wed_devic
-               __free_page(page);
-       }
--      dma_free_coherent(dev->hw->dev, dev->buf_ring.size * sizeof(*desc),
--                        desc, dev->buf_ring.desc_phys);
-+      dma_free_coherent(dev->hw->dev, dev->tx_buf_ring.size * sizeof(*desc),
-+                        desc, dev->tx_buf_ring.desc_phys);
- free_pagelist:
-       kfree(page_list);
- }
-+static int
-+mtk_wed_rx_buffer_alloc(struct mtk_wed_device *dev)
-+{
-+      struct mtk_rxbm_desc *desc;
-+      dma_addr_t desc_phys;
-+
-+      dev->rx_buf_ring.size = dev->wlan.rx_nbuf;
-+      desc = dma_alloc_coherent(dev->hw->dev,
-+                                dev->wlan.rx_nbuf * sizeof(*desc),
-+                                &desc_phys, GFP_KERNEL);
-+      if (!desc)
-+              return -ENOMEM;
-+
-+      dev->rx_buf_ring.desc = desc;
-+      dev->rx_buf_ring.desc_phys = desc_phys;
-+      dev->wlan.init_rx_buf(dev, dev->wlan.rx_npkt);
-+
-+      return 0;
-+}
-+
-+static void
-+mtk_wed_free_rx_buffer(struct mtk_wed_device *dev)
-+{
-+      struct mtk_rxbm_desc *desc = dev->rx_buf_ring.desc;
-+
-+      if (!desc)
-+              return;
-+
-+      dev->wlan.release_rx_buf(dev);
-+      dma_free_coherent(dev->hw->dev, dev->rx_buf_ring.size * sizeof(*desc),
-+                        desc, dev->rx_buf_ring.desc_phys);
-+}
-+
-+static void
-+mtk_wed_rx_buffer_hw_init(struct mtk_wed_device *dev)
-+{
-+      wed_w32(dev, MTK_WED_RX_BM_RX_DMAD,
-+              FIELD_PREP(MTK_WED_RX_BM_RX_DMAD_SDL0, dev->wlan.rx_size));
-+      wed_w32(dev, MTK_WED_RX_BM_BASE, dev->rx_buf_ring.desc_phys);
-+      wed_w32(dev, MTK_WED_RX_BM_INIT_PTR, MTK_WED_RX_BM_INIT_SW_TAIL |
-+              FIELD_PREP(MTK_WED_RX_BM_SW_TAIL, dev->wlan.rx_npkt));
-+      wed_w32(dev, MTK_WED_RX_BM_DYN_ALLOC_TH,
-+              FIELD_PREP(MTK_WED_RX_BM_DYN_ALLOC_TH_H, 0xffff));
-+      wed_set(dev, MTK_WED_CTRL, MTK_WED_CTRL_WED_RX_BM_EN);
-+}
-+
- static void
- mtk_wed_free_ring(struct mtk_wed_device *dev, struct mtk_wed_ring *ring)
- {
-@@ -247,6 +412,13 @@ mtk_wed_free_ring(struct mtk_wed_device
- }
- static void
-+mtk_wed_free_rx_rings(struct mtk_wed_device *dev)
-+{
-+      mtk_wed_free_rx_buffer(dev);
-+      mtk_wed_free_ring(dev, &dev->rro.ring);
-+}
-+
-+static void
- mtk_wed_free_tx_rings(struct mtk_wed_device *dev)
- {
-       int i;
-@@ -291,6 +463,38 @@ mtk_wed_set_512_support(struct mtk_wed_d
-       }
- }
-+#define MTK_WFMDA_RX_DMA_EN   BIT(2)
-+static void
-+mtk_wed_check_wfdma_rx_fill(struct mtk_wed_device *dev, int idx)
-+{
-+      u32 val;
-+      int i;
-+
-+      if (!(dev->rx_ring[idx].flags & MTK_WED_RING_CONFIGURED))
-+              return; /* queue is not configured by mt76 */
-+
-+      for (i = 0; i < 3; i++) {
-+              u32 cur_idx;
-+
-+              cur_idx = wed_r32(dev,
-+                                MTK_WED_WPDMA_RING_RX_DATA(idx) +
-+                                MTK_WED_RING_OFS_CPU_IDX);
-+              if (cur_idx == MTK_WED_RX_RING_SIZE - 1)
-+                      break;
-+
-+              usleep_range(100000, 200000);
-+      }
-+
-+      if (i == 3) {
-+              dev_err(dev->hw->dev, "rx dma enable failed\n");
-+              return;
-+      }
-+
-+      val = wifi_r32(dev, dev->wlan.wpdma_rx_glo - dev->wlan.phy_base) |
-+            MTK_WFMDA_RX_DMA_EN;
-+      wifi_w32(dev, dev->wlan.wpdma_rx_glo - dev->wlan.phy_base, val);
-+}
-+
- static void
- mtk_wed_dma_disable(struct mtk_wed_device *dev)
- {
-@@ -304,20 +508,25 @@ mtk_wed_dma_disable(struct mtk_wed_devic
-               MTK_WED_GLO_CFG_TX_DMA_EN |
-               MTK_WED_GLO_CFG_RX_DMA_EN);
--      wdma_m32(dev, MTK_WDMA_GLO_CFG,
-+      wdma_clr(dev, MTK_WDMA_GLO_CFG,
-                MTK_WDMA_GLO_CFG_TX_DMA_EN |
-                MTK_WDMA_GLO_CFG_RX_INFO1_PRERES |
--               MTK_WDMA_GLO_CFG_RX_INFO2_PRERES, 0);
-+               MTK_WDMA_GLO_CFG_RX_INFO2_PRERES);
-       if (dev->hw->version == 1) {
-               regmap_write(dev->hw->mirror, dev->hw->index * 4, 0);
--              wdma_m32(dev, MTK_WDMA_GLO_CFG,
--                       MTK_WDMA_GLO_CFG_RX_INFO3_PRERES, 0);
-+              wdma_clr(dev, MTK_WDMA_GLO_CFG,
-+                       MTK_WDMA_GLO_CFG_RX_INFO3_PRERES);
-       } else {
-               wed_clr(dev, MTK_WED_WPDMA_GLO_CFG,
-                       MTK_WED_WPDMA_GLO_CFG_RX_DRV_R0_PKT_PROC |
-                       MTK_WED_WPDMA_GLO_CFG_RX_DRV_R0_CRX_SYNC);
-+              wed_clr(dev, MTK_WED_WPDMA_RX_D_GLO_CFG,
-+                      MTK_WED_WPDMA_RX_D_RX_DRV_EN);
-+              wed_clr(dev, MTK_WED_WDMA_GLO_CFG,
-+                      MTK_WED_WDMA_GLO_CFG_TX_DDONE_CHK);
-+
-               mtk_wed_set_512_support(dev, false);
-       }
- }
-@@ -338,6 +547,13 @@ mtk_wed_stop(struct mtk_wed_device *dev)
-       wdma_w32(dev, MTK_WDMA_INT_MASK, 0);
-       wdma_w32(dev, MTK_WDMA_INT_GRP2, 0);
-       wed_w32(dev, MTK_WED_WPDMA_INT_MASK, 0);
-+
-+      if (dev->hw->version == 1)
-+              return;
-+
-+      wed_w32(dev, MTK_WED_EXT_INT_MASK1, 0);
-+      wed_w32(dev, MTK_WED_EXT_INT_MASK2, 0);
-+      wed_clr(dev, MTK_WED_CTRL, MTK_WED_CTRL_WED_RX_BM_EN);
- }
- static void
-@@ -353,11 +569,21 @@ mtk_wed_detach(struct mtk_wed_device *de
-       wdma_w32(dev, MTK_WDMA_RESET_IDX, 0);
-       mtk_wed_reset(dev, MTK_WED_RESET_WED);
-+      if (mtk_wed_get_rx_capa(dev)) {
-+              wdma_clr(dev, MTK_WDMA_GLO_CFG, MTK_WDMA_GLO_CFG_TX_DMA_EN);
-+              wdma_w32(dev, MTK_WDMA_RESET_IDX, MTK_WDMA_RESET_IDX_TX);
-+              wdma_w32(dev, MTK_WDMA_RESET_IDX, 0);
-+      }
--      mtk_wed_free_buffer(dev);
-+      mtk_wed_free_tx_buffer(dev);
-       mtk_wed_free_tx_rings(dev);
--      if (hw->version != 1)
-+
-+      if (mtk_wed_get_rx_capa(dev)) {
-+              mtk_wed_wo_reset(dev);
-+              mtk_wed_free_rx_rings(dev);
-               mtk_wed_wo_deinit(hw);
-+              mtk_wdma_rx_reset(dev);
-+      }
-       if (dev->wlan.bus_type == MTK_WED_BUS_PCIE) {
-               struct device_node *wlan_node;
-@@ -434,10 +660,12 @@ mtk_wed_set_wpdma(struct mtk_wed_device
-       } else {
-               mtk_wed_bus_init(dev);
--              wed_w32(dev, MTK_WED_WPDMA_CFG_BASE,  dev->wlan.wpdma_int);
--              wed_w32(dev, MTK_WED_WPDMA_CFG_INT_MASK,  dev->wlan.wpdma_mask);
--              wed_w32(dev, MTK_WED_WPDMA_CFG_TX,  dev->wlan.wpdma_tx);
--              wed_w32(dev, MTK_WED_WPDMA_CFG_TX_FREE,  dev->wlan.wpdma_txfree);
-+              wed_w32(dev, MTK_WED_WPDMA_CFG_BASE, dev->wlan.wpdma_int);
-+              wed_w32(dev, MTK_WED_WPDMA_CFG_INT_MASK, dev->wlan.wpdma_mask);
-+              wed_w32(dev, MTK_WED_WPDMA_CFG_TX, dev->wlan.wpdma_tx);
-+              wed_w32(dev, MTK_WED_WPDMA_CFG_TX_FREE, dev->wlan.wpdma_txfree);
-+              wed_w32(dev, MTK_WED_WPDMA_RX_GLO_CFG, dev->wlan.wpdma_rx_glo);
-+              wed_w32(dev, MTK_WED_WPDMA_RX_RING, dev->wlan.wpdma_rx);
-       }
- }
-@@ -487,6 +715,132 @@ mtk_wed_hw_init_early(struct mtk_wed_dev
-       }
- }
-+static int
-+mtk_wed_rro_ring_alloc(struct mtk_wed_device *dev, struct mtk_wed_ring *ring,
-+                     int size)
-+{
-+      ring->desc = dma_alloc_coherent(dev->hw->dev,
-+                                      size * sizeof(*ring->desc),
-+                                      &ring->desc_phys, GFP_KERNEL);
-+      if (!ring->desc)
-+              return -ENOMEM;
-+
-+      ring->desc_size = sizeof(*ring->desc);
-+      ring->size = size;
-+      memset(ring->desc, 0, size);
-+
-+      return 0;
-+}
-+
-+#define MTK_WED_MIOD_COUNT    (MTK_WED_MIOD_ENTRY_CNT * MTK_WED_MIOD_CNT)
-+static int
-+mtk_wed_rro_alloc(struct mtk_wed_device *dev)
-+{
-+      struct reserved_mem *rmem;
-+      struct device_node *np;
-+      int index;
-+
-+      index = of_property_match_string(dev->hw->node, "memory-region-names",
-+                                       "wo-dlm");
-+      if (index < 0)
-+              return index;
-+
-+      np = of_parse_phandle(dev->hw->node, "memory-region", index);
-+      if (!np)
-+              return -ENODEV;
-+
-+      rmem = of_reserved_mem_lookup(np);
-+      of_node_put(np);
-+
-+      if (!rmem)
-+              return -ENODEV;
-+
-+      dev->rro.miod_phys = rmem->base;
-+      dev->rro.fdbk_phys = MTK_WED_MIOD_COUNT + dev->rro.miod_phys;
-+
-+      return mtk_wed_rro_ring_alloc(dev, &dev->rro.ring,
-+                                    MTK_WED_RRO_QUE_CNT);
-+}
-+
-+static int
-+mtk_wed_rro_cfg(struct mtk_wed_device *dev)
-+{
-+      struct mtk_wed_wo *wo = dev->hw->wed_wo;
-+      struct {
-+              struct {
-+                      __le32 base;
-+                      __le32 cnt;
-+                      __le32 unit;
-+              } ring[2];
-+              __le32 wed;
-+              u8 version;
-+      } req = {
-+              .ring[0] = {
-+                      .base = cpu_to_le32(MTK_WED_WOCPU_VIEW_MIOD_BASE),
-+                      .cnt = cpu_to_le32(MTK_WED_MIOD_CNT),
-+                      .unit = cpu_to_le32(MTK_WED_MIOD_ENTRY_CNT),
-+              },
-+              .ring[1] = {
-+                      .base = cpu_to_le32(MTK_WED_WOCPU_VIEW_MIOD_BASE +
-+                                          MTK_WED_MIOD_COUNT),
-+                      .cnt = cpu_to_le32(MTK_WED_FB_CMD_CNT),
-+                      .unit = cpu_to_le32(4),
-+              },
-+      };
-+
-+      return mtk_wed_mcu_send_msg(wo, MTK_WED_MODULE_ID_WO,
-+                                  MTK_WED_WO_CMD_WED_CFG,
-+                                  &req, sizeof(req), true);
-+}
-+
-+static void
-+mtk_wed_rro_hw_init(struct mtk_wed_device *dev)
-+{
-+      wed_w32(dev, MTK_WED_RROQM_MIOD_CFG,
-+              FIELD_PREP(MTK_WED_RROQM_MIOD_MID_DW, 0x70 >> 2) |
-+              FIELD_PREP(MTK_WED_RROQM_MIOD_MOD_DW, 0x10 >> 2) |
-+              FIELD_PREP(MTK_WED_RROQM_MIOD_ENTRY_DW,
-+                         MTK_WED_MIOD_ENTRY_CNT >> 2));
-+
-+      wed_w32(dev, MTK_WED_RROQM_MIOD_CTRL0, dev->rro.miod_phys);
-+      wed_w32(dev, MTK_WED_RROQM_MIOD_CTRL1,
-+              FIELD_PREP(MTK_WED_RROQM_MIOD_CNT, MTK_WED_MIOD_CNT));
-+      wed_w32(dev, MTK_WED_RROQM_FDBK_CTRL0, dev->rro.fdbk_phys);
-+      wed_w32(dev, MTK_WED_RROQM_FDBK_CTRL1,
-+              FIELD_PREP(MTK_WED_RROQM_FDBK_CNT, MTK_WED_FB_CMD_CNT));
-+      wed_w32(dev, MTK_WED_RROQM_FDBK_CTRL2, 0);
-+      wed_w32(dev, MTK_WED_RROQ_BASE_L, dev->rro.ring.desc_phys);
-+
-+      wed_set(dev, MTK_WED_RROQM_RST_IDX,
-+              MTK_WED_RROQM_RST_IDX_MIOD |
-+              MTK_WED_RROQM_RST_IDX_FDBK);
-+
-+      wed_w32(dev, MTK_WED_RROQM_RST_IDX, 0);
-+      wed_w32(dev, MTK_WED_RROQM_MIOD_CTRL2, MTK_WED_MIOD_CNT - 1);
-+      wed_set(dev, MTK_WED_CTRL, MTK_WED_CTRL_RX_RRO_QM_EN);
-+}
-+
-+static void
-+mtk_wed_route_qm_hw_init(struct mtk_wed_device *dev)
-+{
-+      wed_w32(dev, MTK_WED_RESET, MTK_WED_RESET_RX_ROUTE_QM);
-+
-+      for (;;) {
-+              usleep_range(100, 200);
-+              if (!(wed_r32(dev, MTK_WED_RESET) & MTK_WED_RESET_RX_ROUTE_QM))
-+                      break;
-+      }
-+
-+      /* configure RX_ROUTE_QM */
-+      wed_clr(dev, MTK_WED_RTQM_GLO_CFG, MTK_WED_RTQM_Q_RST);
-+      wed_clr(dev, MTK_WED_RTQM_GLO_CFG, MTK_WED_RTQM_TXDMAD_FPORT);
-+      wed_set(dev, MTK_WED_RTQM_GLO_CFG,
-+              FIELD_PREP(MTK_WED_RTQM_TXDMAD_FPORT, 0x3 + dev->hw->index));
-+      wed_clr(dev, MTK_WED_RTQM_GLO_CFG, MTK_WED_RTQM_Q_RST);
-+      /* enable RX_ROUTE_QM */
-+      wed_set(dev, MTK_WED_CTRL, MTK_WED_CTRL_RX_ROUTE_QM_EN);
-+}
-+
- static void
- mtk_wed_hw_init(struct mtk_wed_device *dev)
- {
-@@ -498,11 +852,11 @@ mtk_wed_hw_init(struct mtk_wed_device *d
-       wed_w32(dev, MTK_WED_TX_BM_CTRL,
-               MTK_WED_TX_BM_CTRL_PAUSE |
-               FIELD_PREP(MTK_WED_TX_BM_CTRL_VLD_GRP_NUM,
--                         dev->buf_ring.size / 128) |
-+                         dev->tx_buf_ring.size / 128) |
-               FIELD_PREP(MTK_WED_TX_BM_CTRL_RSV_GRP_NUM,
-                          MTK_WED_TX_RING_SIZE / 256));
--      wed_w32(dev, MTK_WED_TX_BM_BASE, dev->buf_ring.desc_phys);
-+      wed_w32(dev, MTK_WED_TX_BM_BASE, dev->tx_buf_ring.desc_phys);
-       wed_w32(dev, MTK_WED_TX_BM_BUF_LEN, MTK_WED_PKT_SIZE);
-@@ -529,9 +883,9 @@ mtk_wed_hw_init(struct mtk_wed_device *d
-               wed_w32(dev, MTK_WED_TX_TKID_CTRL,
-                       MTK_WED_TX_TKID_CTRL_PAUSE |
-                       FIELD_PREP(MTK_WED_TX_TKID_CTRL_VLD_GRP_NUM,
--                                 dev->buf_ring.size / 128) |
-+                                 dev->tx_buf_ring.size / 128) |
-                       FIELD_PREP(MTK_WED_TX_TKID_CTRL_RSV_GRP_NUM,
--                                 dev->buf_ring.size / 128));
-+                                 dev->tx_buf_ring.size / 128));
-               wed_w32(dev, MTK_WED_TX_TKID_DYN_THR,
-                       FIELD_PREP(MTK_WED_TX_TKID_DYN_THR_LO, 0) |
-                       MTK_WED_TX_TKID_DYN_THR_HI);
-@@ -539,18 +893,28 @@ mtk_wed_hw_init(struct mtk_wed_device *d
-       mtk_wed_reset(dev, MTK_WED_RESET_TX_BM);
--      if (dev->hw->version == 1)
-+      if (dev->hw->version == 1) {
-               wed_set(dev, MTK_WED_CTRL,
-                       MTK_WED_CTRL_WED_TX_BM_EN |
-                       MTK_WED_CTRL_WED_TX_FREE_AGENT_EN);
--      else
-+      } else {
-               wed_clr(dev, MTK_WED_TX_TKID_CTRL, MTK_WED_TX_TKID_CTRL_PAUSE);
-+              /* rx hw init */
-+              wed_w32(dev, MTK_WED_WPDMA_RX_D_RST_IDX,
-+                      MTK_WED_WPDMA_RX_D_RST_CRX_IDX |
-+                      MTK_WED_WPDMA_RX_D_RST_DRV_IDX);
-+              wed_w32(dev, MTK_WED_WPDMA_RX_D_RST_IDX, 0);
-+
-+              mtk_wed_rx_buffer_hw_init(dev);
-+              mtk_wed_rro_hw_init(dev);
-+              mtk_wed_route_qm_hw_init(dev);
-+      }
-       wed_clr(dev, MTK_WED_TX_BM_CTRL, MTK_WED_TX_BM_CTRL_PAUSE);
- }
- static void
--mtk_wed_ring_reset(struct mtk_wed_ring *ring, int size)
-+mtk_wed_ring_reset(struct mtk_wed_ring *ring, int size, bool tx)
- {
-       void *head = (void *)ring->desc;
-       int i;
-@@ -560,7 +924,10 @@ mtk_wed_ring_reset(struct mtk_wed_ring *
-               desc = (struct mtk_wdma_desc *)(head + i * ring->desc_size);
-               desc->buf0 = 0;
--              desc->ctrl = cpu_to_le32(MTK_WDMA_DESC_CTRL_DMA_DONE);
-+              if (tx)
-+                      desc->ctrl = cpu_to_le32(MTK_WDMA_DESC_CTRL_DMA_DONE);
-+              else
-+                      desc->ctrl = cpu_to_le32(MTK_WFDMA_DESC_CTRL_TO_HOST);
-               desc->buf1 = 0;
-               desc->info = 0;
-       }
-@@ -616,7 +983,8 @@ mtk_wed_reset_dma(struct mtk_wed_device
-               if (!dev->tx_ring[i].desc)
-                       continue;
--              mtk_wed_ring_reset(&dev->tx_ring[i], MTK_WED_TX_RING_SIZE);
-+              mtk_wed_ring_reset(&dev->tx_ring[i], MTK_WED_TX_RING_SIZE,
-+                                 true);
-       }
-       if (mtk_wed_poll_busy(dev))
-@@ -634,6 +1002,9 @@ mtk_wed_reset_dma(struct mtk_wed_device
-       wdma_w32(dev, MTK_WDMA_RESET_IDX, MTK_WDMA_RESET_IDX_RX);
-       wdma_w32(dev, MTK_WDMA_RESET_IDX, 0);
-+      if (mtk_wed_get_rx_capa(dev))
-+              mtk_wdma_rx_reset(dev);
-+
-       if (busy) {
-               mtk_wed_reset(dev, MTK_WED_RESET_WDMA_INT_AGENT);
-               mtk_wed_reset(dev, MTK_WED_RESET_WDMA_RX_DRV);
-@@ -668,12 +1039,11 @@ mtk_wed_reset_dma(struct mtk_wed_device
-                       MTK_WED_WPDMA_RESET_IDX_RX);
-               wed_w32(dev, MTK_WED_WPDMA_RESET_IDX, 0);
-       }
--
- }
- static int
- mtk_wed_ring_alloc(struct mtk_wed_device *dev, struct mtk_wed_ring *ring,
--                 int size, u32 desc_size)
-+                 int size, u32 desc_size, bool tx)
- {
-       ring->desc = dma_alloc_coherent(dev->hw->dev, size * desc_size,
-                                       &ring->desc_phys, GFP_KERNEL);
-@@ -682,7 +1052,7 @@ mtk_wed_ring_alloc(struct mtk_wed_device
-       ring->desc_size = desc_size;
-       ring->size = size;
--      mtk_wed_ring_reset(ring, size);
-+      mtk_wed_ring_reset(ring, size, tx);
-       return 0;
- }
-@@ -691,9 +1061,14 @@ static int
- mtk_wed_wdma_rx_ring_setup(struct mtk_wed_device *dev, int idx, int size)
- {
-       u32 desc_size = sizeof(struct mtk_wdma_desc) * dev->hw->version;
--      struct mtk_wed_ring *wdma = &dev->rx_wdma[idx];
-+      struct mtk_wed_ring *wdma;
--      if (mtk_wed_ring_alloc(dev, wdma, MTK_WED_WDMA_RING_SIZE, desc_size))
-+      if (idx >= ARRAY_SIZE(dev->rx_wdma))
-+              return -EINVAL;
-+
-+      wdma = &dev->rx_wdma[idx];
-+      if (mtk_wed_ring_alloc(dev, wdma, MTK_WED_WDMA_RING_SIZE, desc_size,
-+                             true))
-               return -ENOMEM;
-       wdma_w32(dev, MTK_WDMA_RING_RX(idx) + MTK_WED_RING_OFS_BASE,
-@@ -710,6 +1085,60 @@ mtk_wed_wdma_rx_ring_setup(struct mtk_we
-       return 0;
- }
-+static int
-+mtk_wed_wdma_tx_ring_setup(struct mtk_wed_device *dev, int idx, int size)
-+{
-+      u32 desc_size = sizeof(struct mtk_wdma_desc) * dev->hw->version;
-+      struct mtk_wed_ring *wdma;
-+
-+      if (idx >= ARRAY_SIZE(dev->tx_wdma))
-+              return -EINVAL;
-+
-+      wdma = &dev->tx_wdma[idx];
-+      if (mtk_wed_ring_alloc(dev, wdma, MTK_WED_WDMA_RING_SIZE, desc_size,
-+                             true))
-+              return -ENOMEM;
-+
-+      wdma_w32(dev, MTK_WDMA_RING_TX(idx) + MTK_WED_RING_OFS_BASE,
-+               wdma->desc_phys);
-+      wdma_w32(dev, MTK_WDMA_RING_TX(idx) + MTK_WED_RING_OFS_COUNT,
-+               size);
-+      wdma_w32(dev, MTK_WDMA_RING_TX(idx) + MTK_WED_RING_OFS_CPU_IDX, 0);
-+      wdma_w32(dev, MTK_WDMA_RING_TX(idx) + MTK_WED_RING_OFS_DMA_IDX, 0);
-+
-+      if (!idx)  {
-+              wed_w32(dev, MTK_WED_WDMA_RING_TX + MTK_WED_RING_OFS_BASE,
-+                      wdma->desc_phys);
-+              wed_w32(dev, MTK_WED_WDMA_RING_TX + MTK_WED_RING_OFS_COUNT,
-+                      size);
-+              wed_w32(dev, MTK_WED_WDMA_RING_TX + MTK_WED_RING_OFS_CPU_IDX,
-+                      0);
-+              wed_w32(dev, MTK_WED_WDMA_RING_TX + MTK_WED_RING_OFS_DMA_IDX,
-+                      0);
-+      }
-+
-+      return 0;
-+}
-+
-+static void
-+mtk_wed_ppe_check(struct mtk_wed_device *dev, struct sk_buff *skb,
-+                u32 reason, u32 hash)
-+{
-+      struct mtk_eth *eth = dev->hw->eth;
-+      struct ethhdr *eh;
-+
-+      if (!skb)
-+              return;
-+
-+      if (reason != MTK_PPE_CPU_REASON_HIT_UNBIND_RATE_REACHED)
-+              return;
-+
-+      skb_set_mac_header(skb, 0);
-+      eh = eth_hdr(skb);
-+      skb->protocol = eh->h_proto;
-+      mtk_ppe_check_skb(eth->ppe[dev->hw->index], skb, hash);
-+}
-+
- static void
- mtk_wed_configure_irq(struct mtk_wed_device *dev, u32 irq_mask)
- {
-@@ -732,6 +1161,8 @@ mtk_wed_configure_irq(struct mtk_wed_dev
-               wed_clr(dev, MTK_WED_WDMA_INT_CTRL, wdma_mask);
-       } else {
-+              wdma_mask |= FIELD_PREP(MTK_WDMA_INT_MASK_TX_DONE,
-+                                      GENMASK(1, 0));
-               /* initail tx interrupt trigger */
-               wed_w32(dev, MTK_WED_WPDMA_INT_CTRL_TX,
-                       MTK_WED_WPDMA_INT_CTRL_TX0_DONE_EN |
-@@ -750,6 +1181,16 @@ mtk_wed_configure_irq(struct mtk_wed_dev
-                       FIELD_PREP(MTK_WED_WPDMA_INT_CTRL_TX_FREE_DONE_TRIG,
-                                  dev->wlan.txfree_tbit));
-+              wed_w32(dev, MTK_WED_WPDMA_INT_CTRL_RX,
-+                      MTK_WED_WPDMA_INT_CTRL_RX0_EN |
-+                      MTK_WED_WPDMA_INT_CTRL_RX0_CLR |
-+                      MTK_WED_WPDMA_INT_CTRL_RX1_EN |
-+                      MTK_WED_WPDMA_INT_CTRL_RX1_CLR |
-+                      FIELD_PREP(MTK_WED_WPDMA_INT_CTRL_RX0_DONE_TRIG,
-+                                 dev->wlan.rx_tbit[0]) |
-+                      FIELD_PREP(MTK_WED_WPDMA_INT_CTRL_RX1_DONE_TRIG,
-+                                 dev->wlan.rx_tbit[1]));
-+
-               wed_w32(dev, MTK_WED_WDMA_INT_CLR, wdma_mask);
-               wed_set(dev, MTK_WED_WDMA_INT_CTRL,
-                       FIELD_PREP(MTK_WED_WDMA_INT_CTRL_POLL_SRC_SEL,
-@@ -787,9 +1228,15 @@ mtk_wed_dma_enable(struct mtk_wed_device
-               wdma_set(dev, MTK_WDMA_GLO_CFG,
-                        MTK_WDMA_GLO_CFG_RX_INFO3_PRERES);
-       } else {
-+              int i;
-+
-               wed_set(dev, MTK_WED_WPDMA_CTRL,
-                       MTK_WED_WPDMA_CTRL_SDL1_FIXED);
-+              wed_set(dev, MTK_WED_WDMA_GLO_CFG,
-+                      MTK_WED_WDMA_GLO_CFG_TX_DRV_EN |
-+                      MTK_WED_WDMA_GLO_CFG_TX_DDONE_CHK);
-+
-               wed_set(dev, MTK_WED_WPDMA_GLO_CFG,
-                       MTK_WED_WPDMA_GLO_CFG_RX_DRV_R0_PKT_PROC |
-                       MTK_WED_WPDMA_GLO_CFG_RX_DRV_R0_CRX_SYNC);
-@@ -797,6 +1244,15 @@ mtk_wed_dma_enable(struct mtk_wed_device
-               wed_clr(dev, MTK_WED_WPDMA_GLO_CFG,
-                       MTK_WED_WPDMA_GLO_CFG_TX_TKID_KEEP |
-                       MTK_WED_WPDMA_GLO_CFG_TX_DMAD_DW3_PREV);
-+
-+              wed_set(dev, MTK_WED_WPDMA_RX_D_GLO_CFG,
-+                      MTK_WED_WPDMA_RX_D_RX_DRV_EN |
-+                      FIELD_PREP(MTK_WED_WPDMA_RX_D_RXD_READ_LEN, 0x18) |
-+                      FIELD_PREP(MTK_WED_WPDMA_RX_D_INIT_PHASE_RXEN_SEL,
-+                                 0x2));
-+
-+              for (i = 0; i < MTK_WED_RX_QUEUES; i++)
-+                      mtk_wed_check_wfdma_rx_fill(dev, i);
-       }
- }
-@@ -822,7 +1278,19 @@ mtk_wed_start(struct mtk_wed_device *dev
-               val |= BIT(0) | (BIT(1) * !!dev->hw->index);
-               regmap_write(dev->hw->mirror, dev->hw->index * 4, val);
-       } else {
--              mtk_wed_set_512_support(dev, true);
-+              /* driver set mid ready and only once */
-+              wed_w32(dev, MTK_WED_EXT_INT_MASK1,
-+                      MTK_WED_EXT_INT_STATUS_WPDMA_MID_RDY);
-+              wed_w32(dev, MTK_WED_EXT_INT_MASK2,
-+                      MTK_WED_EXT_INT_STATUS_WPDMA_MID_RDY);
-+
-+              wed_r32(dev, MTK_WED_EXT_INT_MASK1);
-+              wed_r32(dev, MTK_WED_EXT_INT_MASK2);
-+
-+              if (mtk_wed_rro_cfg(dev))
-+                      return;
-+
-+              mtk_wed_set_512_support(dev, dev->wlan.wcid_512);
-       }
-       mtk_wed_dma_enable(dev);
-@@ -856,7 +1324,7 @@ mtk_wed_attach(struct mtk_wed_device *de
-       if (!hw) {
-               module_put(THIS_MODULE);
-               ret = -ENODEV;
--              goto out;
-+              goto unlock;
-       }
-       device = dev->wlan.bus_type == MTK_WED_BUS_PCIE
-@@ -869,15 +1337,24 @@ mtk_wed_attach(struct mtk_wed_device *de
-       dev->dev = hw->dev;
-       dev->irq = hw->irq;
-       dev->wdma_idx = hw->index;
-+      dev->version = hw->version;
-       if (hw->eth->dma_dev == hw->eth->dev &&
-           of_dma_is_coherent(hw->eth->dev->of_node))
-               mtk_eth_set_dma_device(hw->eth, hw->dev);
--      ret = mtk_wed_buffer_alloc(dev);
--      if (ret) {
--              mtk_wed_detach(dev);
-+      ret = mtk_wed_tx_buffer_alloc(dev);
-+      if (ret)
-               goto out;
-+
-+      if (mtk_wed_get_rx_capa(dev)) {
-+              ret = mtk_wed_rx_buffer_alloc(dev);
-+              if (ret)
-+                      goto out;
-+
-+              ret = mtk_wed_rro_alloc(dev);
-+              if (ret)
-+                      goto out;
-       }
-       mtk_wed_hw_init_early(dev);
-@@ -886,8 +1363,10 @@ mtk_wed_attach(struct mtk_wed_device *de
-                                  BIT(hw->index), 0);
-       else
-               ret = mtk_wed_wo_init(hw);
--
- out:
-+      if (ret)
-+              mtk_wed_detach(dev);
-+unlock:
-       mutex_unlock(&hw_lock);
-       return ret;
-@@ -910,10 +1389,11 @@ mtk_wed_tx_ring_setup(struct mtk_wed_dev
-        * WDMA RX.
-        */
--      BUG_ON(idx >= ARRAY_SIZE(dev->tx_ring));
-+      if (WARN_ON(idx >= ARRAY_SIZE(dev->tx_ring)))
-+              return -EINVAL;
-       if (mtk_wed_ring_alloc(dev, ring, MTK_WED_TX_RING_SIZE,
--                             sizeof(*ring->desc)))
-+                             sizeof(*ring->desc), true))
-               return -ENOMEM;
-       if (mtk_wed_wdma_rx_ring_setup(dev, idx, MTK_WED_WDMA_RING_SIZE))
-@@ -960,6 +1440,37 @@ mtk_wed_txfree_ring_setup(struct mtk_wed
-       return 0;
- }
-+static int
-+mtk_wed_rx_ring_setup(struct mtk_wed_device *dev, int idx, void __iomem *regs)
-+{
-+      struct mtk_wed_ring *ring = &dev->rx_ring[idx];
-+
-+      if (WARN_ON(idx >= ARRAY_SIZE(dev->rx_ring)))
-+              return -EINVAL;
-+
-+      if (mtk_wed_ring_alloc(dev, ring, MTK_WED_RX_RING_SIZE,
-+                             sizeof(*ring->desc), false))
-+              return -ENOMEM;
-+
-+      if (mtk_wed_wdma_tx_ring_setup(dev, idx, MTK_WED_WDMA_RING_SIZE))
-+              return -ENOMEM;
-+
-+      ring->reg_base = MTK_WED_RING_RX_DATA(idx);
-+      ring->wpdma = regs;
-+      ring->flags |= MTK_WED_RING_CONFIGURED;
-+
-+      /* WPDMA ->  WED */
-+      wpdma_rx_w32(dev, idx, MTK_WED_RING_OFS_BASE, ring->desc_phys);
-+      wpdma_rx_w32(dev, idx, MTK_WED_RING_OFS_COUNT, MTK_WED_RX_RING_SIZE);
-+
-+      wed_w32(dev, MTK_WED_WPDMA_RING_RX_DATA(idx) + MTK_WED_RING_OFS_BASE,
-+              ring->desc_phys);
-+      wed_w32(dev, MTK_WED_WPDMA_RING_RX_DATA(idx) + MTK_WED_RING_OFS_COUNT,
-+              MTK_WED_RX_RING_SIZE);
-+
-+      return 0;
-+}
-+
- static u32
- mtk_wed_irq_get(struct mtk_wed_device *dev, u32 mask)
- {
-@@ -1056,7 +1567,9 @@ void mtk_wed_add_hw(struct device_node *
-       static const struct mtk_wed_ops wed_ops = {
-               .attach = mtk_wed_attach,
-               .tx_ring_setup = mtk_wed_tx_ring_setup,
-+              .rx_ring_setup = mtk_wed_rx_ring_setup,
-               .txfree_ring_setup = mtk_wed_txfree_ring_setup,
-+              .msg_update = mtk_wed_mcu_msg_update,
-               .start = mtk_wed_start,
-               .stop = mtk_wed_stop,
-               .reset_dma = mtk_wed_reset_dma,
-@@ -1065,6 +1578,7 @@ void mtk_wed_add_hw(struct device_node *
-               .irq_get = mtk_wed_irq_get,
-               .irq_set_mask = mtk_wed_irq_set_mask,
-               .detach = mtk_wed_detach,
-+              .ppe_check = mtk_wed_ppe_check,
-       };
-       struct device_node *eth_np = eth->dev->of_node;
-       struct platform_device *pdev;
---- a/drivers/net/ethernet/mediatek/mtk_wed.h
-+++ b/drivers/net/ethernet/mediatek/mtk_wed.h
-@@ -87,6 +87,24 @@ wpdma_tx_w32(struct mtk_wed_device *dev,
- }
- static inline u32
-+wpdma_rx_r32(struct mtk_wed_device *dev, int ring, u32 reg)
-+{
-+      if (!dev->rx_ring[ring].wpdma)
-+              return 0;
-+
-+      return readl(dev->rx_ring[ring].wpdma + reg);
-+}
-+
-+static inline void
-+wpdma_rx_w32(struct mtk_wed_device *dev, int ring, u32 reg, u32 val)
-+{
-+      if (!dev->rx_ring[ring].wpdma)
-+              return;
-+
-+      writel(val, dev->rx_ring[ring].wpdma + reg);
-+}
-+
-+static inline u32
- wpdma_txfree_r32(struct mtk_wed_device *dev, u32 reg)
- {
-       if (!dev->txfree_ring.wpdma)
-@@ -128,6 +146,7 @@ static inline int mtk_wed_flow_add(int i
- static inline void mtk_wed_flow_remove(int index)
- {
- }
-+
- #endif
- #ifdef CONFIG_DEBUG_FS
---- a/drivers/net/ethernet/mediatek/mtk_wed_mcu.c
-+++ b/drivers/net/ethernet/mediatek/mtk_wed_mcu.c
-@@ -10,6 +10,7 @@
- #include <linux/of_reserved_mem.h>
- #include <linux/mfd/syscon.h>
- #include <linux/soc/mediatek/mtk_wed.h>
-+#include <asm/unaligned.h>
- #include "mtk_wed_regs.h"
- #include "mtk_wed_wo.h"
-@@ -60,24 +61,37 @@ void mtk_wed_mcu_rx_event(struct mtk_wed
-       wake_up(&wo->mcu.wait);
- }
-+static void
-+mtk_wed_update_rx_stats(struct mtk_wed_device *wed, struct sk_buff *skb)
-+{
-+      u32 count = get_unaligned_le32(skb->data);
-+      struct mtk_wed_wo_rx_stats *stats;
-+      int i;
-+
-+      if (count * sizeof(*stats) > skb->len - sizeof(u32))
-+              return;
-+
-+      stats = (struct mtk_wed_wo_rx_stats *)(skb->data + sizeof(u32));
-+      for (i = 0 ; i < count ; i++)
-+              wed->wlan.update_wo_rx_stats(wed, &stats[i]);
-+}
-+
- void mtk_wed_mcu_rx_unsolicited_event(struct mtk_wed_wo *wo,
-                                     struct sk_buff *skb)
- {
-       struct mtk_wed_mcu_hdr *hdr = (struct mtk_wed_mcu_hdr *)skb->data;
--      switch (hdr->cmd) {
--      case MTK_WED_WO_EVT_LOG_DUMP: {
--              const char *msg = (const char *)(skb->data + sizeof(*hdr));
-+      skb_pull(skb, sizeof(*hdr));
--              dev_notice(wo->hw->dev, "%s\n", msg);
-+      switch (hdr->cmd) {
-+      case MTK_WED_WO_EVT_LOG_DUMP:
-+              dev_notice(wo->hw->dev, "%s\n", skb->data);
-               break;
--      }
-       case MTK_WED_WO_EVT_PROFILING: {
--              struct mtk_wed_wo_log_info *info;
--              u32 count = (skb->len - sizeof(*hdr)) / sizeof(*info);
-+              struct mtk_wed_wo_log_info *info = (void *)skb->data;
-+              u32 count = skb->len / sizeof(*info);
-               int i;
--              info = (struct mtk_wed_wo_log_info *)(skb->data + sizeof(*hdr));
-               for (i = 0 ; i < count ; i++)
-                       dev_notice(wo->hw->dev,
-                                  "SN:%u latency: total=%u, rro:%u, mod:%u\n",
-@@ -88,6 +102,7 @@ void mtk_wed_mcu_rx_unsolicited_event(st
-               break;
-       }
-       case MTK_WED_WO_EVT_RXCNT_INFO:
-+              mtk_wed_update_rx_stats(wo->hw->wed_dev, skb);
-               break;
-       default:
-               break;
-@@ -144,6 +159,8 @@ mtk_wed_mcu_parse_response(struct mtk_we
-       skb_pull(skb, sizeof(*hdr));
-       switch (cmd) {
-       case MTK_WED_WO_CMD_RXCNT_INFO:
-+              mtk_wed_update_rx_stats(wo->hw->wed_dev, skb);
-+              break;
-       default:
-               break;
-       }
-@@ -182,6 +199,18 @@ unlock:
-       return ret;
- }
-+int mtk_wed_mcu_msg_update(struct mtk_wed_device *dev, int id, void *data,
-+                         int len)
-+{
-+      struct mtk_wed_wo *wo = dev->hw->wed_wo;
-+
-+      if (dev->hw->version == 1)
-+              return 0;
-+
-+      return mtk_wed_mcu_send_msg(wo, MTK_WED_MODULE_ID_WO, id, data, len,
-+                                  true);
-+}
-+
- static int
- mtk_wed_get_memory_region(struct mtk_wed_wo *wo,
-                         struct mtk_wed_wo_memory_region *region)
---- a/drivers/net/ethernet/mediatek/mtk_wed_regs.h
-+++ b/drivers/net/ethernet/mediatek/mtk_wed_regs.h
-@@ -4,6 +4,7 @@
- #ifndef __MTK_WED_REGS_H
- #define __MTK_WED_REGS_H
-+#define MTK_WFDMA_DESC_CTRL_TO_HOST           BIT(8)
- #define MTK_WDMA_DESC_CTRL_LEN1                       GENMASK(14, 0)
- #define MTK_WDMA_DESC_CTRL_LEN1_V2            GENMASK(13, 0)
- #define MTK_WDMA_DESC_CTRL_LAST_SEG1          BIT(15)
-@@ -28,6 +29,8 @@ struct mtk_wdma_desc {
- #define MTK_WED_RESET_WED_TX_DMA                      BIT(12)
- #define MTK_WED_RESET_WDMA_RX_DRV                     BIT(17)
- #define MTK_WED_RESET_WDMA_INT_AGENT                  BIT(19)
-+#define MTK_WED_RESET_RX_RRO_QM                               BIT(20)
-+#define MTK_WED_RESET_RX_ROUTE_QM                     BIT(21)
- #define MTK_WED_RESET_WED                             BIT(31)
- #define MTK_WED_CTRL                                  0x00c
-@@ -39,8 +42,12 @@ struct mtk_wdma_desc {
- #define MTK_WED_CTRL_WED_TX_BM_BUSY                   BIT(9)
- #define MTK_WED_CTRL_WED_TX_FREE_AGENT_EN             BIT(10)
- #define MTK_WED_CTRL_WED_TX_FREE_AGENT_BUSY           BIT(11)
--#define MTK_WED_CTRL_RESERVE_EN                               BIT(12)
--#define MTK_WED_CTRL_RESERVE_BUSY                     BIT(13)
-+#define MTK_WED_CTRL_WED_RX_BM_EN                     BIT(12)
-+#define MTK_WED_CTRL_WED_RX_BM_BUSY                   BIT(13)
-+#define MTK_WED_CTRL_RX_RRO_QM_EN                     BIT(14)
-+#define MTK_WED_CTRL_RX_RRO_QM_BUSY                   BIT(15)
-+#define MTK_WED_CTRL_RX_ROUTE_QM_EN                   BIT(16)
-+#define MTK_WED_CTRL_RX_ROUTE_QM_BUSY                 BIT(17)
- #define MTK_WED_CTRL_FINAL_DIDX_READ                  BIT(24)
- #define MTK_WED_CTRL_ETH_DMAD_FMT                     BIT(25)
- #define MTK_WED_CTRL_MIB_READ_CLEAR                   BIT(28)
-@@ -62,6 +69,9 @@ struct mtk_wdma_desc {
- #define MTK_WED_EXT_INT_STATUS_TX_DMA_R_RESP_ERR      BIT(22)
- #define MTK_WED_EXT_INT_STATUS_TX_DMA_W_RESP_ERR      BIT(23)
- #define MTK_WED_EXT_INT_STATUS_RX_DRV_DMA_RECYCLE     BIT(24)
-+#define MTK_WED_EXT_INT_STATUS_RX_DRV_GET_BM_DMAD_SKIP        BIT(25)
-+#define MTK_WED_EXT_INT_STATUS_WPDMA_RX_D_DRV_ERR     BIT(26)
-+#define MTK_WED_EXT_INT_STATUS_WPDMA_MID_RDY          BIT(27)
- #define MTK_WED_EXT_INT_STATUS_ERROR_MASK             (MTK_WED_EXT_INT_STATUS_TF_LEN_ERR | \
-                                                        MTK_WED_EXT_INT_STATUS_TKID_WO_PYLD | \
-                                                        MTK_WED_EXT_INT_STATUS_TKID_TITO_INVALID | \
-@@ -71,6 +81,8 @@ struct mtk_wdma_desc {
-                                                        MTK_WED_EXT_INT_STATUS_TX_DMA_R_RESP_ERR)
- #define MTK_WED_EXT_INT_MASK                          0x028
-+#define MTK_WED_EXT_INT_MASK1                         0x02c
-+#define MTK_WED_EXT_INT_MASK2                         0x030
- #define MTK_WED_STATUS                                        0x060
- #define MTK_WED_STATUS_TX                             GENMASK(15, 8)
-@@ -151,6 +163,7 @@ struct mtk_wdma_desc {
- #define MTK_WED_RING_TX(_n)                           (0x300 + (_n) * 0x10)
- #define MTK_WED_RING_RX(_n)                           (0x400 + (_n) * 0x10)
-+#define MTK_WED_RING_RX_DATA(_n)                      (0x420 + (_n) * 0x10)
- #define MTK_WED_SCR0                                  0x3c0
- #define MTK_WED_WPDMA_INT_TRIGGER                     0x504
-@@ -213,6 +226,12 @@ struct mtk_wdma_desc {
- #define MTK_WED_WPDMA_INT_CTRL_TX1_DONE_TRIG          GENMASK(14, 10)
- #define MTK_WED_WPDMA_INT_CTRL_RX                     0x534
-+#define MTK_WED_WPDMA_INT_CTRL_RX0_EN                 BIT(0)
-+#define MTK_WED_WPDMA_INT_CTRL_RX0_CLR                        BIT(1)
-+#define MTK_WED_WPDMA_INT_CTRL_RX0_DONE_TRIG          GENMASK(6, 2)
-+#define MTK_WED_WPDMA_INT_CTRL_RX1_EN                 BIT(8)
-+#define MTK_WED_WPDMA_INT_CTRL_RX1_CLR                        BIT(9)
-+#define MTK_WED_WPDMA_INT_CTRL_RX1_DONE_TRIG          GENMASK(14, 10)
- #define MTK_WED_WPDMA_INT_CTRL_TX_FREE                        0x538
- #define MTK_WED_WPDMA_INT_CTRL_TX_FREE_DONE_EN                BIT(0)
-@@ -242,11 +261,34 @@ struct mtk_wdma_desc {
- #define MTK_WED_WPDMA_RING_TX(_n)                     (0x600 + (_n) * 0x10)
- #define MTK_WED_WPDMA_RING_RX(_n)                     (0x700 + (_n) * 0x10)
-+#define MTK_WED_WPDMA_RING_RX_DATA(_n)                        (0x730 + (_n) * 0x10)
-+
-+#define MTK_WED_WPDMA_RX_D_GLO_CFG                    0x75c
-+#define MTK_WED_WPDMA_RX_D_RX_DRV_EN                  BIT(0)
-+#define MTK_WED_WPDMA_RX_D_INIT_PHASE_RXEN_SEL                GENMASK(11, 7)
-+#define MTK_WED_WPDMA_RX_D_RXD_READ_LEN                       GENMASK(31, 24)
-+
-+#define MTK_WED_WPDMA_RX_D_RST_IDX                    0x760
-+#define MTK_WED_WPDMA_RX_D_RST_CRX_IDX                        GENMASK(17, 16)
-+#define MTK_WED_WPDMA_RX_D_RST_DRV_IDX                        GENMASK(25, 24)
-+
-+#define MTK_WED_WPDMA_RX_GLO_CFG                      0x76c
-+#define MTK_WED_WPDMA_RX_RING                         0x770
-+
-+#define MTK_WED_WPDMA_RX_D_MIB(_n)                    (0x774 + (_n) * 4)
-+#define MTK_WED_WPDMA_RX_D_PROCESSED_MIB(_n)          (0x784 + (_n) * 4)
-+#define MTK_WED_WPDMA_RX_D_COHERENT_MIB                       0x78c
-+
-+#define MTK_WED_WDMA_RING_TX                          0x800
-+
-+#define MTK_WED_WDMA_TX_MIB                           0x810
-+
- #define MTK_WED_WDMA_RING_RX(_n)                      (0x900 + (_n) * 0x10)
- #define MTK_WED_WDMA_RX_THRES(_n)                     (0x940 + (_n) * 0x4)
- #define MTK_WED_WDMA_GLO_CFG                          0xa04
- #define MTK_WED_WDMA_GLO_CFG_TX_DRV_EN                        BIT(0)
-+#define MTK_WED_WDMA_GLO_CFG_TX_DDONE_CHK             BIT(1)
- #define MTK_WED_WDMA_GLO_CFG_RX_DRV_EN                        BIT(2)
- #define MTK_WED_WDMA_GLO_CFG_RX_DRV_BUSY              BIT(3)
- #define MTK_WED_WDMA_GLO_CFG_BT_SIZE                  GENMASK(5, 4)
-@@ -291,6 +333,20 @@ struct mtk_wdma_desc {
- #define MTK_WED_WDMA_RX_RECYCLE_MIB(_n)                       (0xae8 + (_n) * 4)
- #define MTK_WED_WDMA_RX_PROCESSED_MIB(_n)             (0xaf0 + (_n) * 4)
-+#define MTK_WED_RX_BM_RX_DMAD                         0xd80
-+#define MTK_WED_RX_BM_RX_DMAD_SDL0                    GENMASK(13, 0)
-+
-+#define MTK_WED_RX_BM_BASE                            0xd84
-+#define MTK_WED_RX_BM_INIT_PTR                                0xd88
-+#define MTK_WED_RX_BM_SW_TAIL                         GENMASK(15, 0)
-+#define MTK_WED_RX_BM_INIT_SW_TAIL                    BIT(16)
-+
-+#define MTK_WED_RX_PTR                                        0xd8c
-+
-+#define MTK_WED_RX_BM_DYN_ALLOC_TH                    0xdb4
-+#define MTK_WED_RX_BM_DYN_ALLOC_TH_H                  GENMASK(31, 16)
-+#define MTK_WED_RX_BM_DYN_ALLOC_TH_L                  GENMASK(15, 0)
-+
- #define MTK_WED_RING_OFS_BASE                         0x00
- #define MTK_WED_RING_OFS_COUNT                                0x04
- #define MTK_WED_RING_OFS_CPU_IDX                      0x08
-@@ -301,7 +357,9 @@ struct mtk_wdma_desc {
- #define MTK_WDMA_GLO_CFG                              0x204
- #define MTK_WDMA_GLO_CFG_TX_DMA_EN                    BIT(0)
-+#define MTK_WDMA_GLO_CFG_TX_DMA_BUSY                  BIT(1)
- #define MTK_WDMA_GLO_CFG_RX_DMA_EN                    BIT(2)
-+#define MTK_WDMA_GLO_CFG_RX_DMA_BUSY                  BIT(3)
- #define MTK_WDMA_GLO_CFG_RX_INFO3_PRERES              BIT(26)
- #define MTK_WDMA_GLO_CFG_RX_INFO2_PRERES              BIT(27)
- #define MTK_WDMA_GLO_CFG_RX_INFO1_PRERES              BIT(28)
-@@ -330,4 +388,70 @@ struct mtk_wdma_desc {
- /* DMA channel mapping */
- #define HIFSYS_DMA_AG_MAP                             0x008
-+#define MTK_WED_RTQM_GLO_CFG                          0xb00
-+#define MTK_WED_RTQM_BUSY                             BIT(1)
-+#define MTK_WED_RTQM_Q_RST                            BIT(2)
-+#define MTK_WED_RTQM_Q_DBG_BYPASS                     BIT(5)
-+#define MTK_WED_RTQM_TXDMAD_FPORT                     GENMASK(23, 20)
-+
-+#define MTK_WED_RTQM_R2H_MIB(_n)                      (0xb70 + (_n) * 0x4)
-+#define MTK_WED_RTQM_R2Q_MIB(_n)                      (0xb78 + (_n) * 0x4)
-+#define MTK_WED_RTQM_Q2N_MIB                          0xb80
-+#define MTK_WED_RTQM_Q2H_MIB(_n)                      (0xb84 + (_n) * 0x4)
-+
-+#define MTK_WED_RTQM_Q2B_MIB                          0xb8c
-+#define MTK_WED_RTQM_PFDBK_MIB                                0xb90
-+
-+#define MTK_WED_RROQM_GLO_CFG                         0xc04
-+#define MTK_WED_RROQM_RST_IDX                         0xc08
-+#define MTK_WED_RROQM_RST_IDX_MIOD                    BIT(0)
-+#define MTK_WED_RROQM_RST_IDX_FDBK                    BIT(4)
-+
-+#define MTK_WED_RROQM_MIOD_CTRL0                      0xc40
-+#define MTK_WED_RROQM_MIOD_CTRL1                      0xc44
-+#define MTK_WED_RROQM_MIOD_CNT                                GENMASK(11, 0)
-+
-+#define MTK_WED_RROQM_MIOD_CTRL2                      0xc48
-+#define MTK_WED_RROQM_MIOD_CTRL3                      0xc4c
-+
-+#define MTK_WED_RROQM_FDBK_CTRL0                      0xc50
-+#define MTK_WED_RROQM_FDBK_CTRL1                      0xc54
-+#define MTK_WED_RROQM_FDBK_CNT                                GENMASK(11, 0)
-+
-+#define MTK_WED_RROQM_FDBK_CTRL2                      0xc58
-+
-+#define MTK_WED_RROQ_BASE_L                           0xc80
-+#define MTK_WED_RROQ_BASE_H                           0xc84
-+
-+#define MTK_WED_RROQM_MIOD_CFG                                0xc8c
-+#define MTK_WED_RROQM_MIOD_MID_DW                     GENMASK(5, 0)
-+#define MTK_WED_RROQM_MIOD_MOD_DW                     GENMASK(13, 8)
-+#define MTK_WED_RROQM_MIOD_ENTRY_DW                   GENMASK(22, 16)
-+
-+#define MTK_WED_RROQM_MID_MIB                         0xcc0
-+#define MTK_WED_RROQM_MOD_MIB                         0xcc4
-+#define MTK_WED_RROQM_MOD_COHERENT_MIB                        0xcc8
-+#define MTK_WED_RROQM_FDBK_MIB                                0xcd0
-+#define MTK_WED_RROQM_FDBK_COHERENT_MIB                       0xcd4
-+#define MTK_WED_RROQM_FDBK_IND_MIB                    0xce0
-+#define MTK_WED_RROQM_FDBK_ENQ_MIB                    0xce4
-+#define MTK_WED_RROQM_FDBK_ANC_MIB                    0xce8
-+#define MTK_WED_RROQM_FDBK_ANC2H_MIB                  0xcec
-+
-+#define MTK_WED_RX_BM_RX_DMAD                         0xd80
-+#define MTK_WED_RX_BM_BASE                            0xd84
-+#define MTK_WED_RX_BM_INIT_PTR                                0xd88
-+#define MTK_WED_RX_BM_PTR                             0xd8c
-+#define MTK_WED_RX_BM_PTR_HEAD                                GENMASK(32, 16)
-+#define MTK_WED_RX_BM_PTR_TAIL                                GENMASK(15, 0)
-+
-+#define MTK_WED_RX_BM_BLEN                            0xd90
-+#define MTK_WED_RX_BM_STS                             0xd94
-+#define MTK_WED_RX_BM_INTF2                           0xd98
-+#define MTK_WED_RX_BM_INTF                            0xd9c
-+#define MTK_WED_RX_BM_ERR_STS                         0xda8
-+
-+#define MTK_WED_WOCPU_VIEW_MIOD_BASE                  0x8000
-+#define MTK_WED_PCIE_INT_MASK                         0x0
-+
- #endif
---- a/drivers/net/ethernet/mediatek/mtk_wed_wo.h
-+++ b/drivers/net/ethernet/mediatek/mtk_wed_wo.h
-@@ -49,6 +49,10 @@ enum {
-       MTK_WED_WARP_CMD_FLAG_FROM_TO_WO        = BIT(2),
- };
-+#define MTK_WED_WO_CPU_MCUSYS_RESET_ADDR      0x15194050
-+#define MTK_WED_WO_CPU_WO0_MCUSYS_RESET_MASK  0x20
-+#define MTK_WED_WO_CPU_WO1_MCUSYS_RESET_MASK  0x1
-+
- enum {
-       MTK_WED_WO_REGION_EMI,
-       MTK_WED_WO_REGION_ILM,
-@@ -57,6 +61,28 @@ enum {
-       __MTK_WED_WO_REGION_MAX,
- };
-+enum mtk_wed_wo_state {
-+      MTK_WED_WO_STATE_UNDEFINED,
-+      MTK_WED_WO_STATE_INIT,
-+      MTK_WED_WO_STATE_ENABLE,
-+      MTK_WED_WO_STATE_DISABLE,
-+      MTK_WED_WO_STATE_HALT,
-+      MTK_WED_WO_STATE_GATING,
-+      MTK_WED_WO_STATE_SER_RESET,
-+      MTK_WED_WO_STATE_WF_RESET,
-+};
-+
-+enum mtk_wed_wo_done_state {
-+      MTK_WED_WOIF_UNDEFINED,
-+      MTK_WED_WOIF_DISABLE_DONE,
-+      MTK_WED_WOIF_TRIGGER_ENABLE,
-+      MTK_WED_WOIF_ENABLE_DONE,
-+      MTK_WED_WOIF_TRIGGER_GATING,
-+      MTK_WED_WOIF_GATING_DONE,
-+      MTK_WED_WOIF_TRIGGER_HALT,
-+      MTK_WED_WOIF_HALT_DONE,
-+};
-+
- enum mtk_wed_dummy_cr_idx {
-       MTK_WED_DUMMY_CR_FWDL,
-       MTK_WED_DUMMY_CR_WO_STATUS,
-@@ -245,6 +271,8 @@ void mtk_wed_mcu_rx_unsolicited_event(st
-                                     struct sk_buff *skb);
- int mtk_wed_mcu_send_msg(struct mtk_wed_wo *wo, int id, int cmd,
-                        const void *data, int len, bool wait_resp);
-+int mtk_wed_mcu_msg_update(struct mtk_wed_device *dev, int id, void *data,
-+                         int len);
- int mtk_wed_mcu_init(struct mtk_wed_wo *wo);
- int mtk_wed_wo_init(struct mtk_wed_hw *hw);
- void mtk_wed_wo_deinit(struct mtk_wed_hw *hw);
---- a/include/linux/soc/mediatek/mtk_wed.h
-+++ b/include/linux/soc/mediatek/mtk_wed.h
-@@ -5,10 +5,13 @@
- #include <linux/rcupdate.h>
- #include <linux/regmap.h>
- #include <linux/pci.h>
-+#include <linux/skbuff.h>
- #define MTK_WED_TX_QUEUES             2
- #define MTK_WED_RX_QUEUES             2
-+#define WED_WO_STA_REC                        0x6
-+
- struct mtk_wed_hw;
- struct mtk_wdma_desc;
-@@ -41,21 +44,37 @@ enum mtk_wed_wo_cmd {
-       MTK_WED_WO_CMD_WED_END
- };
-+struct mtk_rxbm_desc {
-+      __le32 buf0;
-+      __le32 token;
-+} __packed __aligned(4);
-+
- enum mtk_wed_bus_tye {
-       MTK_WED_BUS_PCIE,
-       MTK_WED_BUS_AXI,
- };
-+#define MTK_WED_RING_CONFIGURED               BIT(0)
- struct mtk_wed_ring {
-       struct mtk_wdma_desc *desc;
-       dma_addr_t desc_phys;
-       u32 desc_size;
-       int size;
-+      u32 flags;
-       u32 reg_base;
-       void __iomem *wpdma;
- };
-+struct mtk_wed_wo_rx_stats {
-+      __le16 wlan_idx;
-+      __le16 tid;
-+      __le32 rx_pkt_cnt;
-+      __le32 rx_byte_cnt;
-+      __le32 rx_err_cnt;
-+      __le32 rx_drop_cnt;
-+};
-+
- struct mtk_wed_device {
- #ifdef CONFIG_NET_MEDIATEK_SOC_WED
-       const struct mtk_wed_ops *ops;
-@@ -64,9 +83,12 @@ struct mtk_wed_device {
-       bool init_done, running;
-       int wdma_idx;
-       int irq;
-+      u8 version;
-       struct mtk_wed_ring tx_ring[MTK_WED_TX_QUEUES];
-+      struct mtk_wed_ring rx_ring[MTK_WED_RX_QUEUES];
-       struct mtk_wed_ring txfree_ring;
-+      struct mtk_wed_ring tx_wdma[MTK_WED_TX_QUEUES];
-       struct mtk_wed_ring rx_wdma[MTK_WED_RX_QUEUES];
-       struct {
-@@ -74,7 +96,20 @@ struct mtk_wed_device {
-               void **pages;
-               struct mtk_wdma_desc *desc;
-               dma_addr_t desc_phys;
--      } buf_ring;
-+      } tx_buf_ring;
-+
-+      struct {
-+              int size;
-+              struct page_frag_cache rx_page;
-+              struct mtk_rxbm_desc *desc;
-+              dma_addr_t desc_phys;
-+      } rx_buf_ring;
-+
-+      struct {
-+              struct mtk_wed_ring ring;
-+              dma_addr_t miod_phys;
-+              dma_addr_t fdbk_phys;
-+      } rro;
-       /* filled by driver: */
-       struct {
-@@ -83,22 +118,36 @@ struct mtk_wed_device {
-                       struct pci_dev *pci_dev;
-               };
-               enum mtk_wed_bus_tye bus_type;
-+              void __iomem *base;
-+              u32 phy_base;
-               u32 wpdma_phys;
-               u32 wpdma_int;
-               u32 wpdma_mask;
-               u32 wpdma_tx;
-               u32 wpdma_txfree;
-+              u32 wpdma_rx_glo;
-+              u32 wpdma_rx;
-+
-+              bool wcid_512;
-               u16 token_start;
-               unsigned int nbuf;
-+              unsigned int rx_nbuf;
-+              unsigned int rx_npkt;
-+              unsigned int rx_size;
-               u8 tx_tbit[MTK_WED_TX_QUEUES];
-+              u8 rx_tbit[MTK_WED_RX_QUEUES];
-               u8 txfree_tbit;
-               u32 (*init_buf)(void *ptr, dma_addr_t phys, int token_id);
-               int (*offload_enable)(struct mtk_wed_device *wed);
-               void (*offload_disable)(struct mtk_wed_device *wed);
-+              u32 (*init_rx_buf)(struct mtk_wed_device *wed, int size);
-+              void (*release_rx_buf)(struct mtk_wed_device *wed);
-+              void (*update_wo_rx_stats)(struct mtk_wed_device *wed,
-+                                         struct mtk_wed_wo_rx_stats *stats);
-       } wlan;
- #endif
- };
-@@ -107,9 +156,15 @@ struct mtk_wed_ops {
-       int (*attach)(struct mtk_wed_device *dev);
-       int (*tx_ring_setup)(struct mtk_wed_device *dev, int ring,
-                            void __iomem *regs);
-+      int (*rx_ring_setup)(struct mtk_wed_device *dev, int ring,
-+                           void __iomem *regs);
-       int (*txfree_ring_setup)(struct mtk_wed_device *dev,
-                                void __iomem *regs);
-+      int (*msg_update)(struct mtk_wed_device *dev, int cmd_id,
-+                        void *data, int len);
-       void (*detach)(struct mtk_wed_device *dev);
-+      void (*ppe_check)(struct mtk_wed_device *dev, struct sk_buff *skb,
-+                        u32 reason, u32 hash);
-       void (*stop)(struct mtk_wed_device *dev);
-       void (*start)(struct mtk_wed_device *dev, u32 irq_mask);
-@@ -144,6 +199,16 @@ mtk_wed_device_attach(struct mtk_wed_dev
-       return ret;
- }
-+static inline bool
-+mtk_wed_get_rx_capa(struct mtk_wed_device *dev)
-+{
-+#ifdef CONFIG_NET_MEDIATEK_SOC_WED
-+      return dev->version != 1;
-+#else
-+      return false;
-+#endif
-+}
-+
- #ifdef CONFIG_NET_MEDIATEK_SOC_WED
- #define mtk_wed_device_active(_dev) !!(_dev)->ops
- #define mtk_wed_device_detach(_dev) (_dev)->ops->detach(_dev)
-@@ -160,6 +225,12 @@ mtk_wed_device_attach(struct mtk_wed_dev
-       (_dev)->ops->irq_get(_dev, _mask)
- #define mtk_wed_device_irq_set_mask(_dev, _mask) \
-       (_dev)->ops->irq_set_mask(_dev, _mask)
-+#define mtk_wed_device_rx_ring_setup(_dev, _ring, _regs) \
-+      (_dev)->ops->rx_ring_setup(_dev, _ring, _regs)
-+#define mtk_wed_device_ppe_check(_dev, _skb, _reason, _hash) \
-+      (_dev)->ops->ppe_check(_dev, _skb, _reason, _hash)
-+#define mtk_wed_device_update_msg(_dev, _id, _msg, _len) \
-+      (_dev)->ops->msg_update(_dev, _id, _msg, _len)
- #else
- static inline bool mtk_wed_device_active(struct mtk_wed_device *dev)
- {
-@@ -173,6 +244,9 @@ static inline bool mtk_wed_device_active
- #define mtk_wed_device_reg_write(_dev, _reg, _val) do {} while (0)
- #define mtk_wed_device_irq_get(_dev, _mask) 0
- #define mtk_wed_device_irq_set_mask(_dev, _mask) do {} while (0)
-+#define mtk_wed_device_rx_ring_setup(_dev, _ring, _regs) -ENODEV
-+#define mtk_wed_device_ppe_check(_dev, _skb, _reason, _hash)  do {} while (0)
-+#define mtk_wed_device_update_msg(_dev, _id, _msg, _len) -ENODEV
- #endif
- #endif
diff --git a/target/linux/generic/backport-5.15/729-05-v6.1-net-ethernet-mtk_wed-add-rx-mib-counters.patch b/target/linux/generic/backport-5.15/729-05-v6.1-net-ethernet-mtk_wed-add-rx-mib-counters.patch
deleted file mode 100644 (file)
index bb1066d..0000000
+++ /dev/null
@@ -1,149 +0,0 @@
-From: Lorenzo Bianconi <[email protected]>
-Date: Sat, 5 Nov 2022 23:36:22 +0100
-Subject: [PATCH] net: ethernet: mtk_wed: add rx mib counters
-
-Introduce WED RX MIB counters support available on MT7986a SoC.
-
-Tested-by: Daniel Golle <[email protected]>
-Co-developed-by: Sujuan Chen <[email protected]>
-Signed-off-by: Sujuan Chen <[email protected]>
-Signed-off-by: Lorenzo Bianconi <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
-
---- a/drivers/net/ethernet/mediatek/mtk_wed_debugfs.c
-+++ b/drivers/net/ethernet/mediatek/mtk_wed_debugfs.c
-@@ -2,6 +2,7 @@
- /* Copyright (C) 2021 Felix Fietkau <[email protected]> */
- #include <linux/seq_file.h>
-+#include <linux/soc/mediatek/mtk_wed.h>
- #include "mtk_wed.h"
- #include "mtk_wed_regs.h"
-@@ -18,6 +19,8 @@ enum {
-       DUMP_TYPE_WDMA,
-       DUMP_TYPE_WPDMA_TX,
-       DUMP_TYPE_WPDMA_TXFREE,
-+      DUMP_TYPE_WPDMA_RX,
-+      DUMP_TYPE_WED_RRO,
- };
- #define DUMP_STR(_str) { _str, 0, DUMP_TYPE_STRING }
-@@ -36,6 +39,9 @@ enum {
- #define DUMP_WPDMA_TX_RING(_n) DUMP_RING("WPDMA_TX" #_n, 0, DUMP_TYPE_WPDMA_TX, _n)
- #define DUMP_WPDMA_TXFREE_RING DUMP_RING("WPDMA_RX1", 0, DUMP_TYPE_WPDMA_TXFREE)
-+#define DUMP_WPDMA_RX_RING(_n)        DUMP_RING("WPDMA_RX" #_n, 0, DUMP_TYPE_WPDMA_RX, _n)
-+#define DUMP_WED_RRO_RING(_base)DUMP_RING("WED_RRO_MIOD", MTK_##_base, DUMP_TYPE_WED_RRO)
-+#define DUMP_WED_RRO_FDBK(_base)DUMP_RING("WED_RRO_FDBK", MTK_##_base, DUMP_TYPE_WED_RRO)
- static void
- print_reg_val(struct seq_file *s, const char *name, u32 val)
-@@ -57,6 +63,7 @@ dump_wed_regs(struct seq_file *s, struct
-                                  cur > regs ? "\n" : "",
-                                  cur->name);
-                       continue;
-+              case DUMP_TYPE_WED_RRO:
-               case DUMP_TYPE_WED:
-                       val = wed_r32(dev, cur->offset);
-                       break;
-@@ -69,6 +76,9 @@ dump_wed_regs(struct seq_file *s, struct
-               case DUMP_TYPE_WPDMA_TXFREE:
-                       val = wpdma_txfree_r32(dev, cur->offset);
-                       break;
-+              case DUMP_TYPE_WPDMA_RX:
-+                      val = wpdma_rx_r32(dev, cur->base, cur->offset);
-+                      break;
-               }
-               print_reg_val(s, cur->name, val);
-       }
-@@ -132,6 +142,80 @@ wed_txinfo_show(struct seq_file *s, void
- }
- DEFINE_SHOW_ATTRIBUTE(wed_txinfo);
-+static int
-+wed_rxinfo_show(struct seq_file *s, void *data)
-+{
-+      static const struct reg_dump regs[] = {
-+              DUMP_STR("WPDMA RX"),
-+              DUMP_WPDMA_RX_RING(0),
-+              DUMP_WPDMA_RX_RING(1),
-+
-+              DUMP_STR("WPDMA RX"),
-+              DUMP_WED(WED_WPDMA_RX_D_MIB(0)),
-+              DUMP_WED_RING(WED_WPDMA_RING_RX_DATA(0)),
-+              DUMP_WED(WED_WPDMA_RX_D_PROCESSED_MIB(0)),
-+              DUMP_WED(WED_WPDMA_RX_D_MIB(1)),
-+              DUMP_WED_RING(WED_WPDMA_RING_RX_DATA(1)),
-+              DUMP_WED(WED_WPDMA_RX_D_PROCESSED_MIB(1)),
-+              DUMP_WED(WED_WPDMA_RX_D_COHERENT_MIB),
-+
-+              DUMP_STR("WED RX"),
-+              DUMP_WED_RING(WED_RING_RX_DATA(0)),
-+              DUMP_WED_RING(WED_RING_RX_DATA(1)),
-+
-+              DUMP_STR("WED RRO"),
-+              DUMP_WED_RRO_RING(WED_RROQM_MIOD_CTRL0),
-+              DUMP_WED(WED_RROQM_MID_MIB),
-+              DUMP_WED(WED_RROQM_MOD_MIB),
-+              DUMP_WED(WED_RROQM_MOD_COHERENT_MIB),
-+              DUMP_WED_RRO_FDBK(WED_RROQM_FDBK_CTRL0),
-+              DUMP_WED(WED_RROQM_FDBK_IND_MIB),
-+              DUMP_WED(WED_RROQM_FDBK_ENQ_MIB),
-+              DUMP_WED(WED_RROQM_FDBK_ANC_MIB),
-+              DUMP_WED(WED_RROQM_FDBK_ANC2H_MIB),
-+
-+              DUMP_STR("WED Route QM"),
-+              DUMP_WED(WED_RTQM_R2H_MIB(0)),
-+              DUMP_WED(WED_RTQM_R2Q_MIB(0)),
-+              DUMP_WED(WED_RTQM_Q2H_MIB(0)),
-+              DUMP_WED(WED_RTQM_R2H_MIB(1)),
-+              DUMP_WED(WED_RTQM_R2Q_MIB(1)),
-+              DUMP_WED(WED_RTQM_Q2H_MIB(1)),
-+              DUMP_WED(WED_RTQM_Q2N_MIB),
-+              DUMP_WED(WED_RTQM_Q2B_MIB),
-+              DUMP_WED(WED_RTQM_PFDBK_MIB),
-+
-+              DUMP_STR("WED WDMA TX"),
-+              DUMP_WED(WED_WDMA_TX_MIB),
-+              DUMP_WED_RING(WED_WDMA_RING_TX),
-+
-+              DUMP_STR("WDMA TX"),
-+              DUMP_WDMA(WDMA_GLO_CFG),
-+              DUMP_WDMA_RING(WDMA_RING_TX(0)),
-+              DUMP_WDMA_RING(WDMA_RING_TX(1)),
-+
-+              DUMP_STR("WED RX BM"),
-+              DUMP_WED(WED_RX_BM_BASE),
-+              DUMP_WED(WED_RX_BM_RX_DMAD),
-+              DUMP_WED(WED_RX_BM_PTR),
-+              DUMP_WED(WED_RX_BM_TKID_MIB),
-+              DUMP_WED(WED_RX_BM_BLEN),
-+              DUMP_WED(WED_RX_BM_STS),
-+              DUMP_WED(WED_RX_BM_INTF2),
-+              DUMP_WED(WED_RX_BM_INTF),
-+              DUMP_WED(WED_RX_BM_ERR_STS),
-+      };
-+      struct mtk_wed_hw *hw = s->private;
-+      struct mtk_wed_device *dev = hw->wed_dev;
-+
-+      if (!dev)
-+              return 0;
-+
-+      dump_wed_regs(s, dev, regs, ARRAY_SIZE(regs));
-+
-+      return 0;
-+}
-+DEFINE_SHOW_ATTRIBUTE(wed_rxinfo);
- static int
- mtk_wed_reg_set(void *data, u64 val)
-@@ -175,4 +259,7 @@ void mtk_wed_hw_add_debugfs(struct mtk_w
-       debugfs_create_u32("regidx", 0600, dir, &hw->debugfs_reg);
-       debugfs_create_file_unsafe("regval", 0600, dir, hw, &fops_regval);
-       debugfs_create_file_unsafe("txinfo", 0400, dir, hw, &wed_txinfo_fops);
-+      if (hw->version != 1)
-+              debugfs_create_file_unsafe("rxinfo", 0400, dir, hw,
-+                                         &wed_rxinfo_fops);
- }
diff --git a/target/linux/generic/backport-5.15/729-06-v6.1-net-ethernet-mtk_eth_soc-do-not-overwrite-mtu-config.patch b/target/linux/generic/backport-5.15/729-06-v6.1-net-ethernet-mtk_eth_soc-do-not-overwrite-mtu-config.patch
deleted file mode 100644 (file)
index 7f76e9b..0000000
+++ /dev/null
@@ -1,98 +0,0 @@
-From: Lorenzo Bianconi <[email protected]>
-Date: Thu, 17 Nov 2022 00:35:04 +0100
-Subject: [PATCH] net: ethernet: mtk_eth_soc: do not overwrite mtu
- configuration running reset routine
-
-Restore user configured MTU running mtk_hw_init() during tx timeout routine
-since it will be overwritten after a hw reset.
-
-Reported-by: Felix Fietkau <[email protected]>
-Fixes: 9ea4d311509f ("net: ethernet: mediatek: add the whole ethernet reset into the reset process")
-Signed-off-by: Lorenzo Bianconi <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-@@ -3178,6 +3178,30 @@ static void mtk_dim_tx(struct work_struc
-       dim->state = DIM_START_MEASURE;
- }
-+static void mtk_set_mcr_max_rx(struct mtk_mac *mac, u32 val)
-+{
-+      struct mtk_eth *eth = mac->hw;
-+      u32 mcr_cur, mcr_new;
-+
-+      if (MTK_HAS_CAPS(eth->soc->caps, MTK_SOC_MT7628))
-+              return;
-+
-+      mcr_cur = mtk_r32(mac->hw, MTK_MAC_MCR(mac->id));
-+      mcr_new = mcr_cur & ~MAC_MCR_MAX_RX_MASK;
-+
-+      if (val <= 1518)
-+              mcr_new |= MAC_MCR_MAX_RX(MAC_MCR_MAX_RX_1518);
-+      else if (val <= 1536)
-+              mcr_new |= MAC_MCR_MAX_RX(MAC_MCR_MAX_RX_1536);
-+      else if (val <= 1552)
-+              mcr_new |= MAC_MCR_MAX_RX(MAC_MCR_MAX_RX_1552);
-+      else
-+              mcr_new |= MAC_MCR_MAX_RX(MAC_MCR_MAX_RX_2048);
-+
-+      if (mcr_new != mcr_cur)
-+              mtk_w32(mac->hw, mcr_new, MTK_MAC_MCR(mac->id));
-+}
-+
- static int mtk_hw_init(struct mtk_eth *eth)
- {
-       u32 dma_mask = ETHSYS_DMA_AG_MAP_PDMA | ETHSYS_DMA_AG_MAP_QDMA |
-@@ -3252,8 +3276,16 @@ static int mtk_hw_init(struct mtk_eth *e
-        * up with the more appropriate value when mtk_mac_config call is being
-        * invoked.
-        */
--      for (i = 0; i < MTK_MAC_COUNT; i++)
-+      for (i = 0; i < MTK_MAC_COUNT; i++) {
-+              struct net_device *dev = eth->netdev[i];
-+
-               mtk_w32(eth, MAC_MCR_FORCE_LINK_DOWN, MTK_MAC_MCR(i));
-+              if (dev) {
-+                      struct mtk_mac *mac = netdev_priv(dev);
-+
-+                      mtk_set_mcr_max_rx(mac, dev->mtu + MTK_RX_ETH_HLEN);
-+              }
-+      }
-       /* Indicates CDM to parse the MTK special tag from CPU
-        * which also is working out for untag packets.
-@@ -3352,7 +3384,6 @@ static int mtk_change_mtu(struct net_dev
-       int length = new_mtu + MTK_RX_ETH_HLEN;
-       struct mtk_mac *mac = netdev_priv(dev);
-       struct mtk_eth *eth = mac->hw;
--      u32 mcr_cur, mcr_new;
-       if (rcu_access_pointer(eth->prog) &&
-           length > MTK_PP_MAX_BUF_SIZE) {
-@@ -3360,23 +3391,7 @@ static int mtk_change_mtu(struct net_dev
-               return -EINVAL;
-       }
--      if (!MTK_HAS_CAPS(eth->soc->caps, MTK_SOC_MT7628)) {
--              mcr_cur = mtk_r32(mac->hw, MTK_MAC_MCR(mac->id));
--              mcr_new = mcr_cur & ~MAC_MCR_MAX_RX_MASK;
--
--              if (length <= 1518)
--                      mcr_new |= MAC_MCR_MAX_RX(MAC_MCR_MAX_RX_1518);
--              else if (length <= 1536)
--                      mcr_new |= MAC_MCR_MAX_RX(MAC_MCR_MAX_RX_1536);
--              else if (length <= 1552)
--                      mcr_new |= MAC_MCR_MAX_RX(MAC_MCR_MAX_RX_1552);
--              else
--                      mcr_new |= MAC_MCR_MAX_RX(MAC_MCR_MAX_RX_2048);
--
--              if (mcr_new != mcr_cur)
--                      mtk_w32(mac->hw, mcr_new, MTK_MAC_MCR(mac->id));
--      }
--
-+      mtk_set_mcr_max_rx(mac, length);
-       dev->mtu = new_mtu;
-       return 0;
diff --git a/target/linux/generic/backport-5.15/729-07-v6.1-net-ethernet-mtk_eth_soc-remove-cpu_relax-in-mtk_pen.patch b/target/linux/generic/backport-5.15/729-07-v6.1-net-ethernet-mtk_eth_soc-remove-cpu_relax-in-mtk_pen.patch
deleted file mode 100644 (file)
index 65d9621..0000000
+++ /dev/null
@@ -1,36 +0,0 @@
-From: Lorenzo Bianconi <[email protected]>
-Date: Thu, 17 Nov 2022 00:58:46 +0100
-Subject: [PATCH] net: ethernet: mtk_eth_soc: remove cpu_relax in
- mtk_pending_work
-
-Get rid of cpu_relax in mtk_pending_work routine since MTK_RESETTING is
-set only in mtk_pending_work() and it runs holding rtnl lock
-
-Signed-off-by: Lorenzo Bianconi <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-@@ -3422,11 +3422,8 @@ static void mtk_pending_work(struct work
-       rtnl_lock();
-       dev_dbg(eth->dev, "[%s][%d] reset\n", __func__, __LINE__);
-+      set_bit(MTK_RESETTING, &eth->state);
--      while (test_and_set_bit_lock(MTK_RESETTING, &eth->state))
--              cpu_relax();
--
--      dev_dbg(eth->dev, "[%s][%d] mtk_stop starts\n", __func__, __LINE__);
-       /* stop all devices to make sure that dma is properly shut down */
-       for (i = 0; i < MTK_MAC_COUNT; i++) {
-               if (!eth->netdev[i])
-@@ -3460,7 +3457,7 @@ static void mtk_pending_work(struct work
-       dev_dbg(eth->dev, "[%s][%d] reset done\n", __func__, __LINE__);
--      clear_bit_unlock(MTK_RESETTING, &eth->state);
-+      clear_bit(MTK_RESETTING, &eth->state);
-       rtnl_unlock();
- }
diff --git a/target/linux/generic/backport-5.15/729-08-v6.2-net-ethernet-mtk_eth_soc-fix-RSTCTRL_PPE-0-1-definit.patch b/target/linux/generic/backport-5.15/729-08-v6.2-net-ethernet-mtk_eth_soc-fix-RSTCTRL_PPE-0-1-definit.patch
deleted file mode 100644 (file)
index 4eca30d..0000000
+++ /dev/null
@@ -1,63 +0,0 @@
-From: Lorenzo Bianconi <[email protected]>
-Date: Thu, 17 Nov 2022 15:29:53 +0100
-Subject: [PATCH] net: ethernet: mtk_eth_soc: fix RSTCTRL_PPE{0,1} definitions
-
-Fix RSTCTRL_PPE0 and RSTCTRL_PPE1 register mask definitions for
-MTK_NETSYS_V2.
-Remove duplicated definitions.
-
-Fixes: 160d3a9b1929 ("net: ethernet: mtk_eth_soc: introduce MTK_NETSYS_V2 support")
-Signed-off-by: Lorenzo Bianconi <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-@@ -3241,16 +3241,17 @@ static int mtk_hw_init(struct mtk_eth *e
-               return 0;
-       }
--      val = RSTCTRL_FE | RSTCTRL_PPE;
-       if (MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2)) {
-               regmap_write(eth->ethsys, ETHSYS_FE_RST_CHK_IDLE_EN, 0);
--
--              val |= RSTCTRL_ETH;
--              if (MTK_HAS_CAPS(eth->soc->caps, MTK_RSTCTRL_PPE1))
--                      val |= RSTCTRL_PPE1;
-+              val = RSTCTRL_PPE0_V2;
-+      } else {
-+              val = RSTCTRL_PPE0;
-       }
--      ethsys_reset(eth, val);
-+      if (MTK_HAS_CAPS(eth->soc->caps, MTK_RSTCTRL_PPE1))
-+              val |= RSTCTRL_PPE1;
-+
-+      ethsys_reset(eth, RSTCTRL_ETH | RSTCTRL_FE | val);
-       if (MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2)) {
-               regmap_write(eth->ethsys, ETHSYS_FE_RST_CHK_IDLE_EN,
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-@@ -445,18 +445,14 @@
- /* ethernet reset control register */
- #define ETHSYS_RSTCTRL                        0x34
- #define RSTCTRL_FE                    BIT(6)
--#define RSTCTRL_PPE                   BIT(31)
--#define RSTCTRL_PPE1                  BIT(30)
-+#define RSTCTRL_PPE0                  BIT(31)
-+#define RSTCTRL_PPE0_V2                       BIT(30)
-+#define RSTCTRL_PPE1                  BIT(31)
- #define RSTCTRL_ETH                   BIT(23)
- /* ethernet reset check idle register */
- #define ETHSYS_FE_RST_CHK_IDLE_EN     0x28
--/* ethernet reset control register */
--#define ETHSYS_RSTCTRL                0x34
--#define RSTCTRL_FE            BIT(6)
--#define RSTCTRL_PPE           BIT(31)
--
- /* ethernet dma channel agent map */
- #define ETHSYS_DMA_AG_MAP     0x408
- #define ETHSYS_DMA_AG_MAP_PDMA        BIT(0)
diff --git a/target/linux/generic/backport-5.15/729-09-v6.2-net-ethernet-mtk_wed-add-wcid-overwritten-support-fo.patch b/target/linux/generic/backport-5.15/729-09-v6.2-net-ethernet-mtk_wed-add-wcid-overwritten-support-fo.patch
deleted file mode 100644 (file)
index 117ccc0..0000000
+++ /dev/null
@@ -1,80 +0,0 @@
-From: Sujuan Chen <[email protected]>
-Date: Thu, 24 Nov 2022 11:18:14 +0800
-Subject: [PATCH] net: ethernet: mtk_wed: add wcid overwritten support for wed
- v1
-
-All wed versions should enable the wcid overwritten feature,
-since the wcid size is controlled by the wlan driver.
-
-Tested-by: Sujuan Chen <[email protected]>
-Co-developed-by: Bo Jiao <[email protected]>
-Signed-off-by: Bo Jiao <[email protected]>
-Signed-off-by: Sujuan Chen <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
-
---- a/drivers/net/ethernet/mediatek/mtk_wed.c
-+++ b/drivers/net/ethernet/mediatek/mtk_wed.c
-@@ -526,9 +526,9 @@ mtk_wed_dma_disable(struct mtk_wed_devic
-                       MTK_WED_WPDMA_RX_D_RX_DRV_EN);
-               wed_clr(dev, MTK_WED_WDMA_GLO_CFG,
-                       MTK_WED_WDMA_GLO_CFG_TX_DDONE_CHK);
--
--              mtk_wed_set_512_support(dev, false);
-       }
-+
-+      mtk_wed_set_512_support(dev, false);
- }
- static void
-@@ -1290,9 +1290,10 @@ mtk_wed_start(struct mtk_wed_device *dev
-               if (mtk_wed_rro_cfg(dev))
-                       return;
--              mtk_wed_set_512_support(dev, dev->wlan.wcid_512);
-       }
-+      mtk_wed_set_512_support(dev, dev->wlan.wcid_512);
-+
-       mtk_wed_dma_enable(dev);
-       dev->running = true;
- }
-@@ -1358,11 +1359,13 @@ mtk_wed_attach(struct mtk_wed_device *de
-       }
-       mtk_wed_hw_init_early(dev);
--      if (hw->version == 1)
-+      if (hw->version == 1) {
-               regmap_update_bits(hw->hifsys, HIFSYS_DMA_AG_MAP,
-                                  BIT(hw->index), 0);
--      else
-+      } else {
-+              dev->rev_id = wed_r32(dev, MTK_WED_REV_ID);
-               ret = mtk_wed_wo_init(hw);
-+      }
- out:
-       if (ret)
-               mtk_wed_detach(dev);
---- a/drivers/net/ethernet/mediatek/mtk_wed_regs.h
-+++ b/drivers/net/ethernet/mediatek/mtk_wed_regs.h
-@@ -20,6 +20,8 @@ struct mtk_wdma_desc {
-       __le32 info;
- } __packed __aligned(4);
-+#define MTK_WED_REV_ID                                        0x004
-+
- #define MTK_WED_RESET                                 0x008
- #define MTK_WED_RESET_TX_BM                           BIT(0)
- #define MTK_WED_RESET_TX_FREE_AGENT                   BIT(4)
---- a/include/linux/soc/mediatek/mtk_wed.h
-+++ b/include/linux/soc/mediatek/mtk_wed.h
-@@ -85,6 +85,9 @@ struct mtk_wed_device {
-       int irq;
-       u8 version;
-+      /* used by wlan driver */
-+      u32 rev_id;
-+
-       struct mtk_wed_ring tx_ring[MTK_WED_TX_QUEUES];
-       struct mtk_wed_ring rx_ring[MTK_WED_RX_QUEUES];
-       struct mtk_wed_ring txfree_ring;
diff --git a/target/linux/generic/backport-5.15/729-10-v6.2-net-ethernet-mtk_wed-return-status-value-in-mtk_wdma.patch b/target/linux/generic/backport-5.15/729-10-v6.2-net-ethernet-mtk_wed-return-status-value-in-mtk_wdma.patch
deleted file mode 100644 (file)
index ec58c3f..0000000
+++ /dev/null
@@ -1,85 +0,0 @@
-From: Lorenzo Bianconi <[email protected]>
-Date: Thu, 24 Nov 2022 16:22:51 +0100
-Subject: [PATCH] net: ethernet: mtk_wed: return status value in
- mtk_wdma_rx_reset
-
-Move MTK_WDMA_RESET_IDX configuration in mtk_wdma_rx_reset routine.
-Increase poll timeout to 10ms in order to be aligned with vendor sdk.
-This is a preliminary patch to add Wireless Ethernet Dispatcher reset
-support.
-
-Co-developed-by: Sujuan Chen <[email protected]>
-Signed-off-by: Sujuan Chen <[email protected]>
-Signed-off-by: Lorenzo Bianconi <[email protected]>
-Signed-off-by: Paolo Abeni <[email protected]>
----
-
---- a/drivers/net/ethernet/mediatek/mtk_wed.c
-+++ b/drivers/net/ethernet/mediatek/mtk_wed.c
-@@ -101,17 +101,21 @@ mtk_wdma_read_reset(struct mtk_wed_devic
-       return wdma_r32(dev, MTK_WDMA_GLO_CFG);
- }
--static void
-+static int
- mtk_wdma_rx_reset(struct mtk_wed_device *dev)
- {
-       u32 status, mask = MTK_WDMA_GLO_CFG_RX_DMA_BUSY;
--      int i;
-+      int i, ret;
-       wdma_clr(dev, MTK_WDMA_GLO_CFG, MTK_WDMA_GLO_CFG_RX_DMA_EN);
--      if (readx_poll_timeout(mtk_wdma_read_reset, dev, status,
--                             !(status & mask), 0, 1000))
-+      ret = readx_poll_timeout(mtk_wdma_read_reset, dev, status,
-+                               !(status & mask), 0, 10000);
-+      if (ret)
-               dev_err(dev->hw->dev, "rx reset failed\n");
-+      wdma_w32(dev, MTK_WDMA_RESET_IDX, MTK_WDMA_RESET_IDX_RX);
-+      wdma_w32(dev, MTK_WDMA_RESET_IDX, 0);
-+
-       for (i = 0; i < ARRAY_SIZE(dev->rx_wdma); i++) {
-               if (dev->rx_wdma[i].desc)
-                       continue;
-@@ -119,6 +123,8 @@ mtk_wdma_rx_reset(struct mtk_wed_device
-               wdma_w32(dev,
-                        MTK_WDMA_RING_RX(i) + MTK_WED_RING_OFS_CPU_IDX, 0);
-       }
-+
-+      return ret;
- }
- static void
-@@ -565,9 +571,7 @@ mtk_wed_detach(struct mtk_wed_device *de
-       mtk_wed_stop(dev);
--      wdma_w32(dev, MTK_WDMA_RESET_IDX, MTK_WDMA_RESET_IDX_RX);
--      wdma_w32(dev, MTK_WDMA_RESET_IDX, 0);
--
-+      mtk_wdma_rx_reset(dev);
-       mtk_wed_reset(dev, MTK_WED_RESET_WED);
-       if (mtk_wed_get_rx_capa(dev)) {
-               wdma_clr(dev, MTK_WDMA_GLO_CFG, MTK_WDMA_GLO_CFG_TX_DMA_EN);
-@@ -582,7 +586,6 @@ mtk_wed_detach(struct mtk_wed_device *de
-               mtk_wed_wo_reset(dev);
-               mtk_wed_free_rx_rings(dev);
-               mtk_wed_wo_deinit(hw);
--              mtk_wdma_rx_reset(dev);
-       }
-       if (dev->wlan.bus_type == MTK_WED_BUS_PCIE) {
-@@ -999,11 +1002,7 @@ mtk_wed_reset_dma(struct mtk_wed_device
-               wed_w32(dev, MTK_WED_RESET_IDX, 0);
-       }
--      wdma_w32(dev, MTK_WDMA_RESET_IDX, MTK_WDMA_RESET_IDX_RX);
--      wdma_w32(dev, MTK_WDMA_RESET_IDX, 0);
--
--      if (mtk_wed_get_rx_capa(dev))
--              mtk_wdma_rx_reset(dev);
-+      mtk_wdma_rx_reset(dev);
-       if (busy) {
-               mtk_wed_reset(dev, MTK_WED_RESET_WDMA_INT_AGENT);
diff --git a/target/linux/generic/backport-5.15/729-11-v6.2-net-ethernet-mtk_wed-move-MTK_WDMA_RESET_IDX_TX-conf.patch b/target/linux/generic/backport-5.15/729-11-v6.2-net-ethernet-mtk_wed-move-MTK_WDMA_RESET_IDX_TX-conf.patch
deleted file mode 100644 (file)
index 10c1732..0000000
+++ /dev/null
@@ -1,52 +0,0 @@
-From: Lorenzo Bianconi <[email protected]>
-Date: Thu, 24 Nov 2022 16:22:52 +0100
-Subject: [PATCH] net: ethernet: mtk_wed: move MTK_WDMA_RESET_IDX_TX
- configuration in mtk_wdma_tx_reset
-
-Remove duplicated code. Increase poll timeout to 10ms in order to be
-aligned with vendor sdk.
-This is a preliminary patch to add Wireless Ethernet Dispatcher reset
-support.
-
-Co-developed-by: Sujuan Chen <[email protected]>
-Signed-off-by: Sujuan Chen <[email protected]>
-Signed-off-by: Lorenzo Bianconi <[email protected]>
-Signed-off-by: Paolo Abeni <[email protected]>
----
-
---- a/drivers/net/ethernet/mediatek/mtk_wed.c
-+++ b/drivers/net/ethernet/mediatek/mtk_wed.c
-@@ -135,16 +135,15 @@ mtk_wdma_tx_reset(struct mtk_wed_device
-       wdma_clr(dev, MTK_WDMA_GLO_CFG, MTK_WDMA_GLO_CFG_TX_DMA_EN);
-       if (readx_poll_timeout(mtk_wdma_read_reset, dev, status,
--                             !(status & mask), 0, 1000))
-+                             !(status & mask), 0, 10000))
-               dev_err(dev->hw->dev, "tx reset failed\n");
--      for (i = 0; i < ARRAY_SIZE(dev->tx_wdma); i++) {
--              if (dev->tx_wdma[i].desc)
--                      continue;
-+      wdma_w32(dev, MTK_WDMA_RESET_IDX, MTK_WDMA_RESET_IDX_TX);
-+      wdma_w32(dev, MTK_WDMA_RESET_IDX, 0);
-+      for (i = 0; i < ARRAY_SIZE(dev->tx_wdma); i++)
-               wdma_w32(dev,
-                        MTK_WDMA_RING_TX(i) + MTK_WED_RING_OFS_CPU_IDX, 0);
--      }
- }
- static void
-@@ -573,12 +572,6 @@ mtk_wed_detach(struct mtk_wed_device *de
-       mtk_wdma_rx_reset(dev);
-       mtk_wed_reset(dev, MTK_WED_RESET_WED);
--      if (mtk_wed_get_rx_capa(dev)) {
--              wdma_clr(dev, MTK_WDMA_GLO_CFG, MTK_WDMA_GLO_CFG_TX_DMA_EN);
--              wdma_w32(dev, MTK_WDMA_RESET_IDX, MTK_WDMA_RESET_IDX_TX);
--              wdma_w32(dev, MTK_WDMA_RESET_IDX, 0);
--      }
--
-       mtk_wed_free_tx_buffer(dev);
-       mtk_wed_free_tx_rings(dev);
diff --git a/target/linux/generic/backport-5.15/729-12-v6.2-net-ethernet-mtk_wed-update-mtk_wed_stop.patch b/target/linux/generic/backport-5.15/729-12-v6.2-net-ethernet-mtk_wed-update-mtk_wed_stop.patch
deleted file mode 100644 (file)
index f4e842d..0000000
+++ /dev/null
@@ -1,98 +0,0 @@
-From: Lorenzo Bianconi <[email protected]>
-Date: Thu, 24 Nov 2022 16:22:53 +0100
-Subject: [PATCH] net: ethernet: mtk_wed: update mtk_wed_stop
-
-Update mtk_wed_stop routine and rename old mtk_wed_stop() to
-mtk_wed_deinit(). This is a preliminary patch to add Wireless Ethernet
-Dispatcher reset support.
-
-Co-developed-by: Sujuan Chen <[email protected]>
-Signed-off-by: Sujuan Chen <[email protected]>
-Signed-off-by: Lorenzo Bianconi <[email protected]>
-Signed-off-by: Paolo Abeni <[email protected]>
----
-
---- a/drivers/net/ethernet/mediatek/mtk_wed.c
-+++ b/drivers/net/ethernet/mediatek/mtk_wed.c
-@@ -539,14 +539,8 @@ mtk_wed_dma_disable(struct mtk_wed_devic
- static void
- mtk_wed_stop(struct mtk_wed_device *dev)
- {
--      mtk_wed_dma_disable(dev);
-       mtk_wed_set_ext_int(dev, false);
--      wed_clr(dev, MTK_WED_CTRL,
--              MTK_WED_CTRL_WDMA_INT_AGENT_EN |
--              MTK_WED_CTRL_WPDMA_INT_AGENT_EN |
--              MTK_WED_CTRL_WED_TX_BM_EN |
--              MTK_WED_CTRL_WED_TX_FREE_AGENT_EN);
-       wed_w32(dev, MTK_WED_WPDMA_INT_TRIGGER, 0);
-       wed_w32(dev, MTK_WED_WDMA_INT_TRIGGER, 0);
-       wdma_w32(dev, MTK_WDMA_INT_MASK, 0);
-@@ -558,7 +552,27 @@ mtk_wed_stop(struct mtk_wed_device *dev)
-       wed_w32(dev, MTK_WED_EXT_INT_MASK1, 0);
-       wed_w32(dev, MTK_WED_EXT_INT_MASK2, 0);
--      wed_clr(dev, MTK_WED_CTRL, MTK_WED_CTRL_WED_RX_BM_EN);
-+}
-+
-+static void
-+mtk_wed_deinit(struct mtk_wed_device *dev)
-+{
-+      mtk_wed_stop(dev);
-+      mtk_wed_dma_disable(dev);
-+
-+      wed_clr(dev, MTK_WED_CTRL,
-+              MTK_WED_CTRL_WDMA_INT_AGENT_EN |
-+              MTK_WED_CTRL_WPDMA_INT_AGENT_EN |
-+              MTK_WED_CTRL_WED_TX_BM_EN |
-+              MTK_WED_CTRL_WED_TX_FREE_AGENT_EN);
-+
-+      if (dev->hw->version == 1)
-+              return;
-+
-+      wed_clr(dev, MTK_WED_CTRL,
-+              MTK_WED_CTRL_RX_ROUTE_QM_EN |
-+              MTK_WED_CTRL_WED_RX_BM_EN |
-+              MTK_WED_CTRL_RX_RRO_QM_EN);
- }
- static void
-@@ -568,7 +582,7 @@ mtk_wed_detach(struct mtk_wed_device *de
-       mutex_lock(&hw_lock);
--      mtk_wed_stop(dev);
-+      mtk_wed_deinit(dev);
-       mtk_wdma_rx_reset(dev);
-       mtk_wed_reset(dev, MTK_WED_RESET_WED);
-@@ -670,7 +684,7 @@ mtk_wed_hw_init_early(struct mtk_wed_dev
- {
-       u32 mask, set;
--      mtk_wed_stop(dev);
-+      mtk_wed_deinit(dev);
-       mtk_wed_reset(dev, MTK_WED_RESET_WED);
-       mtk_wed_set_wpdma(dev);
---- a/include/linux/soc/mediatek/mtk_wed.h
-+++ b/include/linux/soc/mediatek/mtk_wed.h
-@@ -234,6 +234,8 @@ mtk_wed_get_rx_capa(struct mtk_wed_devic
-       (_dev)->ops->ppe_check(_dev, _skb, _reason, _hash)
- #define mtk_wed_device_update_msg(_dev, _id, _msg, _len) \
-       (_dev)->ops->msg_update(_dev, _id, _msg, _len)
-+#define mtk_wed_device_stop(_dev) (_dev)->ops->stop(_dev)
-+#define mtk_wed_device_dma_reset(_dev) (_dev)->ops->reset_dma(_dev)
- #else
- static inline bool mtk_wed_device_active(struct mtk_wed_device *dev)
- {
-@@ -250,6 +252,8 @@ static inline bool mtk_wed_device_active
- #define mtk_wed_device_rx_ring_setup(_dev, _ring, _regs) -ENODEV
- #define mtk_wed_device_ppe_check(_dev, _skb, _reason, _hash)  do {} while (0)
- #define mtk_wed_device_update_msg(_dev, _id, _msg, _len) -ENODEV
-+#define mtk_wed_device_stop(_dev) do {} while (0)
-+#define mtk_wed_device_dma_reset(_dev) do {} while (0)
- #endif
- #endif
diff --git a/target/linux/generic/backport-5.15/729-13-v6.2-net-ethernet-mtk_wed-add-mtk_wed_rx_reset-routine.patch b/target/linux/generic/backport-5.15/729-13-v6.2-net-ethernet-mtk_wed-add-mtk_wed_rx_reset-routine.patch
deleted file mode 100644 (file)
index a0fc9da..0000000
+++ /dev/null
@@ -1,309 +0,0 @@
-From: Lorenzo Bianconi <[email protected]>
-Date: Thu, 24 Nov 2022 16:22:54 +0100
-Subject: [PATCH] net: ethernet: mtk_wed: add mtk_wed_rx_reset routine
-
-Introduce mtk_wed_rx_reset routine in order to reset rx DMA for Wireless
-Ethernet Dispatcher available on MT7986 SoC.
-
-Co-developed-by: Sujuan Chen <[email protected]>
-Signed-off-by: Sujuan Chen <[email protected]>
-Signed-off-by: Lorenzo Bianconi <[email protected]>
-Signed-off-by: Paolo Abeni <[email protected]>
----
-
---- a/drivers/net/ethernet/mediatek/mtk_wed.c
-+++ b/drivers/net/ethernet/mediatek/mtk_wed.c
-@@ -944,42 +944,130 @@ mtk_wed_ring_reset(struct mtk_wed_ring *
- }
- static u32
--mtk_wed_check_busy(struct mtk_wed_device *dev)
-+mtk_wed_check_busy(struct mtk_wed_device *dev, u32 reg, u32 mask)
- {
--      if (wed_r32(dev, MTK_WED_GLO_CFG) & MTK_WED_GLO_CFG_TX_DMA_BUSY)
--              return true;
--
--      if (wed_r32(dev, MTK_WED_WPDMA_GLO_CFG) &
--          MTK_WED_WPDMA_GLO_CFG_TX_DRV_BUSY)
--              return true;
--
--      if (wed_r32(dev, MTK_WED_CTRL) & MTK_WED_CTRL_WDMA_INT_AGENT_BUSY)
--              return true;
--
--      if (wed_r32(dev, MTK_WED_WDMA_GLO_CFG) &
--          MTK_WED_WDMA_GLO_CFG_RX_DRV_BUSY)
--              return true;
--
--      if (wdma_r32(dev, MTK_WDMA_GLO_CFG) &
--          MTK_WED_WDMA_GLO_CFG_RX_DRV_BUSY)
--              return true;
--
--      if (wed_r32(dev, MTK_WED_CTRL) &
--          (MTK_WED_CTRL_WED_TX_BM_BUSY | MTK_WED_CTRL_WED_TX_FREE_AGENT_BUSY))
--              return true;
--
--      return false;
-+      return !!(wed_r32(dev, reg) & mask);
- }
- static int
--mtk_wed_poll_busy(struct mtk_wed_device *dev)
-+mtk_wed_poll_busy(struct mtk_wed_device *dev, u32 reg, u32 mask)
- {
-       int sleep = 15000;
-       int timeout = 100 * sleep;
-       u32 val;
-       return read_poll_timeout(mtk_wed_check_busy, val, !val, sleep,
--                               timeout, false, dev);
-+                               timeout, false, dev, reg, mask);
-+}
-+
-+static int
-+mtk_wed_rx_reset(struct mtk_wed_device *dev)
-+{
-+      struct mtk_wed_wo *wo = dev->hw->wed_wo;
-+      u8 val = MTK_WED_WO_STATE_SER_RESET;
-+      int i, ret;
-+
-+      ret = mtk_wed_mcu_send_msg(wo, MTK_WED_MODULE_ID_WO,
-+                                 MTK_WED_WO_CMD_CHANGE_STATE, &val,
-+                                 sizeof(val), true);
-+      if (ret)
-+              return ret;
-+
-+      wed_clr(dev, MTK_WED_WPDMA_RX_D_GLO_CFG, MTK_WED_WPDMA_RX_D_RX_DRV_EN);
-+      ret = mtk_wed_poll_busy(dev, MTK_WED_WPDMA_RX_D_GLO_CFG,
-+                              MTK_WED_WPDMA_RX_D_RX_DRV_BUSY);
-+      if (ret) {
-+              mtk_wed_reset(dev, MTK_WED_RESET_WPDMA_INT_AGENT);
-+              mtk_wed_reset(dev, MTK_WED_RESET_WPDMA_RX_D_DRV);
-+      } else {
-+              wed_w32(dev, MTK_WED_WPDMA_RX_D_RST_IDX,
-+                      MTK_WED_WPDMA_RX_D_RST_CRX_IDX |
-+                      MTK_WED_WPDMA_RX_D_RST_DRV_IDX);
-+
-+              wed_set(dev, MTK_WED_WPDMA_RX_D_GLO_CFG,
-+                      MTK_WED_WPDMA_RX_D_RST_INIT_COMPLETE |
-+                      MTK_WED_WPDMA_RX_D_FSM_RETURN_IDLE);
-+              wed_clr(dev, MTK_WED_WPDMA_RX_D_GLO_CFG,
-+                      MTK_WED_WPDMA_RX_D_RST_INIT_COMPLETE |
-+                      MTK_WED_WPDMA_RX_D_FSM_RETURN_IDLE);
-+
-+              wed_w32(dev, MTK_WED_WPDMA_RX_D_RST_IDX, 0);
-+      }
-+
-+      /* reset rro qm */
-+      wed_clr(dev, MTK_WED_CTRL, MTK_WED_CTRL_RX_RRO_QM_EN);
-+      ret = mtk_wed_poll_busy(dev, MTK_WED_CTRL,
-+                              MTK_WED_CTRL_RX_RRO_QM_BUSY);
-+      if (ret) {
-+              mtk_wed_reset(dev, MTK_WED_RESET_RX_RRO_QM);
-+      } else {
-+              wed_set(dev, MTK_WED_RROQM_RST_IDX,
-+                      MTK_WED_RROQM_RST_IDX_MIOD |
-+                      MTK_WED_RROQM_RST_IDX_FDBK);
-+              wed_w32(dev, MTK_WED_RROQM_RST_IDX, 0);
-+      }
-+
-+      /* reset route qm */
-+      wed_clr(dev, MTK_WED_CTRL, MTK_WED_CTRL_RX_ROUTE_QM_EN);
-+      ret = mtk_wed_poll_busy(dev, MTK_WED_CTRL,
-+                              MTK_WED_CTRL_RX_ROUTE_QM_BUSY);
-+      if (ret)
-+              mtk_wed_reset(dev, MTK_WED_RESET_RX_ROUTE_QM);
-+      else
-+              wed_set(dev, MTK_WED_RTQM_GLO_CFG,
-+                      MTK_WED_RTQM_Q_RST);
-+
-+      /* reset tx wdma */
-+      mtk_wdma_tx_reset(dev);
-+
-+      /* reset tx wdma drv */
-+      wed_clr(dev, MTK_WED_WDMA_GLO_CFG, MTK_WED_WDMA_GLO_CFG_TX_DRV_EN);
-+      mtk_wed_poll_busy(dev, MTK_WED_CTRL,
-+                        MTK_WED_CTRL_WDMA_INT_AGENT_BUSY);
-+      mtk_wed_reset(dev, MTK_WED_RESET_WDMA_TX_DRV);
-+
-+      /* reset wed rx dma */
-+      ret = mtk_wed_poll_busy(dev, MTK_WED_GLO_CFG,
-+                              MTK_WED_GLO_CFG_RX_DMA_BUSY);
-+      wed_clr(dev, MTK_WED_GLO_CFG, MTK_WED_GLO_CFG_RX_DMA_EN);
-+      if (ret) {
-+              mtk_wed_reset(dev, MTK_WED_RESET_WED_RX_DMA);
-+      } else {
-+              struct mtk_eth *eth = dev->hw->eth;
-+
-+              if (MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2))
-+                      wed_set(dev, MTK_WED_RESET_IDX,
-+                              MTK_WED_RESET_IDX_RX_V2);
-+              else
-+                      wed_set(dev, MTK_WED_RESET_IDX, MTK_WED_RESET_IDX_RX);
-+              wed_w32(dev, MTK_WED_RESET_IDX, 0);
-+      }
-+
-+      /* reset rx bm */
-+      wed_clr(dev, MTK_WED_CTRL, MTK_WED_CTRL_WED_RX_BM_EN);
-+      mtk_wed_poll_busy(dev, MTK_WED_CTRL,
-+                        MTK_WED_CTRL_WED_RX_BM_BUSY);
-+      mtk_wed_reset(dev, MTK_WED_RESET_RX_BM);
-+
-+      /* wo change to enable state */
-+      val = MTK_WED_WO_STATE_ENABLE;
-+      ret = mtk_wed_mcu_send_msg(wo, MTK_WED_MODULE_ID_WO,
-+                                 MTK_WED_WO_CMD_CHANGE_STATE, &val,
-+                                 sizeof(val), true);
-+      if (ret)
-+              return ret;
-+
-+      /* wed_rx_ring_reset */
-+      for (i = 0; i < ARRAY_SIZE(dev->rx_ring); i++) {
-+              if (!dev->rx_ring[i].desc)
-+                      continue;
-+
-+              mtk_wed_ring_reset(&dev->rx_ring[i], MTK_WED_RX_RING_SIZE,
-+                                 false);
-+      }
-+      mtk_wed_free_rx_buffer(dev);
-+
-+      return 0;
- }
- static void
-@@ -997,19 +1085,23 @@ mtk_wed_reset_dma(struct mtk_wed_device
-                                  true);
-       }
--      if (mtk_wed_poll_busy(dev))
--              busy = mtk_wed_check_busy(dev);
--
-+      /* 1. reset WED tx DMA */
-+      wed_clr(dev, MTK_WED_GLO_CFG, MTK_WED_GLO_CFG_TX_DMA_EN);
-+      busy = mtk_wed_poll_busy(dev, MTK_WED_GLO_CFG,
-+                               MTK_WED_GLO_CFG_TX_DMA_BUSY);
-       if (busy) {
-               mtk_wed_reset(dev, MTK_WED_RESET_WED_TX_DMA);
-       } else {
--              wed_w32(dev, MTK_WED_RESET_IDX,
--                      MTK_WED_RESET_IDX_TX |
--                      MTK_WED_RESET_IDX_RX);
-+              wed_w32(dev, MTK_WED_RESET_IDX, MTK_WED_RESET_IDX_TX);
-               wed_w32(dev, MTK_WED_RESET_IDX, 0);
-       }
--      mtk_wdma_rx_reset(dev);
-+      /* 2. reset WDMA rx DMA */
-+      busy = !!mtk_wdma_rx_reset(dev);
-+      wed_clr(dev, MTK_WED_WDMA_GLO_CFG, MTK_WED_WDMA_GLO_CFG_RX_DRV_EN);
-+      if (!busy)
-+              busy = mtk_wed_poll_busy(dev, MTK_WED_WDMA_GLO_CFG,
-+                                       MTK_WED_WDMA_GLO_CFG_RX_DRV_BUSY);
-       if (busy) {
-               mtk_wed_reset(dev, MTK_WED_RESET_WDMA_INT_AGENT);
-@@ -1026,6 +1118,9 @@ mtk_wed_reset_dma(struct mtk_wed_device
-                       MTK_WED_WDMA_GLO_CFG_RST_INIT_COMPLETE);
-       }
-+      /* 3. reset WED WPDMA tx */
-+      wed_clr(dev, MTK_WED_CTRL, MTK_WED_CTRL_WED_TX_FREE_AGENT_EN);
-+
-       for (i = 0; i < 100; i++) {
-               val = wed_r32(dev, MTK_WED_TX_BM_INTF);
-               if (FIELD_GET(MTK_WED_TX_BM_INTF_TKFIFO_FDEP, val) == 0x40)
-@@ -1033,8 +1128,19 @@ mtk_wed_reset_dma(struct mtk_wed_device
-       }
-       mtk_wed_reset(dev, MTK_WED_RESET_TX_FREE_AGENT);
-+      wed_clr(dev, MTK_WED_CTRL, MTK_WED_CTRL_WED_TX_BM_EN);
-       mtk_wed_reset(dev, MTK_WED_RESET_TX_BM);
-+      /* 4. reset WED WPDMA tx */
-+      busy = mtk_wed_poll_busy(dev, MTK_WED_WPDMA_GLO_CFG,
-+                               MTK_WED_WPDMA_GLO_CFG_TX_DRV_BUSY);
-+      wed_clr(dev, MTK_WED_WPDMA_GLO_CFG,
-+              MTK_WED_WPDMA_GLO_CFG_TX_DRV_EN |
-+              MTK_WED_WPDMA_GLO_CFG_RX_DRV_EN);
-+      if (!busy)
-+              busy = mtk_wed_poll_busy(dev, MTK_WED_WPDMA_GLO_CFG,
-+                                       MTK_WED_WPDMA_GLO_CFG_RX_DRV_BUSY);
-+
-       if (busy) {
-               mtk_wed_reset(dev, MTK_WED_RESET_WPDMA_INT_AGENT);
-               mtk_wed_reset(dev, MTK_WED_RESET_WPDMA_TX_DRV);
-@@ -1045,6 +1151,17 @@ mtk_wed_reset_dma(struct mtk_wed_device
-                       MTK_WED_WPDMA_RESET_IDX_RX);
-               wed_w32(dev, MTK_WED_WPDMA_RESET_IDX, 0);
-       }
-+
-+      dev->init_done = false;
-+      if (dev->hw->version == 1)
-+              return;
-+
-+      if (!busy) {
-+              wed_w32(dev, MTK_WED_RESET_IDX, MTK_WED_RESET_WPDMA_IDX_RX);
-+              wed_w32(dev, MTK_WED_RESET_IDX, 0);
-+      }
-+
-+      mtk_wed_rx_reset(dev);
- }
- static int
-@@ -1267,6 +1384,9 @@ mtk_wed_start(struct mtk_wed_device *dev
- {
-       int i;
-+      if (mtk_wed_get_rx_capa(dev) && mtk_wed_rx_buffer_alloc(dev))
-+              return;
-+
-       for (i = 0; i < ARRAY_SIZE(dev->rx_wdma); i++)
-               if (!dev->rx_wdma[i].desc)
-                       mtk_wed_wdma_rx_ring_setup(dev, i, 16);
-@@ -1355,10 +1475,6 @@ mtk_wed_attach(struct mtk_wed_device *de
-               goto out;
-       if (mtk_wed_get_rx_capa(dev)) {
--              ret = mtk_wed_rx_buffer_alloc(dev);
--              if (ret)
--                      goto out;
--
-               ret = mtk_wed_rro_alloc(dev);
-               if (ret)
-                       goto out;
---- a/drivers/net/ethernet/mediatek/mtk_wed_regs.h
-+++ b/drivers/net/ethernet/mediatek/mtk_wed_regs.h
-@@ -24,11 +24,15 @@ struct mtk_wdma_desc {
- #define MTK_WED_RESET                                 0x008
- #define MTK_WED_RESET_TX_BM                           BIT(0)
-+#define MTK_WED_RESET_RX_BM                           BIT(1)
- #define MTK_WED_RESET_TX_FREE_AGENT                   BIT(4)
- #define MTK_WED_RESET_WPDMA_TX_DRV                    BIT(8)
- #define MTK_WED_RESET_WPDMA_RX_DRV                    BIT(9)
-+#define MTK_WED_RESET_WPDMA_RX_D_DRV                  BIT(10)
- #define MTK_WED_RESET_WPDMA_INT_AGENT                 BIT(11)
- #define MTK_WED_RESET_WED_TX_DMA                      BIT(12)
-+#define MTK_WED_RESET_WED_RX_DMA                      BIT(13)
-+#define MTK_WED_RESET_WDMA_TX_DRV                     BIT(16)
- #define MTK_WED_RESET_WDMA_RX_DRV                     BIT(17)
- #define MTK_WED_RESET_WDMA_INT_AGENT                  BIT(19)
- #define MTK_WED_RESET_RX_RRO_QM                               BIT(20)
-@@ -158,6 +162,8 @@ struct mtk_wdma_desc {
- #define MTK_WED_RESET_IDX                             0x20c
- #define MTK_WED_RESET_IDX_TX                          GENMASK(3, 0)
- #define MTK_WED_RESET_IDX_RX                          GENMASK(17, 16)
-+#define MTK_WED_RESET_IDX_RX_V2                               GENMASK(7, 6)
-+#define MTK_WED_RESET_WPDMA_IDX_RX                    GENMASK(31, 30)
- #define MTK_WED_TX_MIB(_n)                            (0x2a0 + (_n) * 4)
- #define MTK_WED_RX_MIB(_n)                            (0x2e0 + (_n) * 4)
-@@ -267,6 +273,9 @@ struct mtk_wdma_desc {
- #define MTK_WED_WPDMA_RX_D_GLO_CFG                    0x75c
- #define MTK_WED_WPDMA_RX_D_RX_DRV_EN                  BIT(0)
-+#define MTK_WED_WPDMA_RX_D_RX_DRV_BUSY                        BIT(1)
-+#define MTK_WED_WPDMA_RX_D_FSM_RETURN_IDLE            BIT(3)
-+#define MTK_WED_WPDMA_RX_D_RST_INIT_COMPLETE          BIT(4)
- #define MTK_WED_WPDMA_RX_D_INIT_PHASE_RXEN_SEL                GENMASK(11, 7)
- #define MTK_WED_WPDMA_RX_D_RXD_READ_LEN                       GENMASK(31, 24)
diff --git a/target/linux/generic/backport-5.15/729-14-v6.2-net-ethernet-mtk_wed-add-reset-to-tx_ring_setup-call.patch b/target/linux/generic/backport-5.15/729-14-v6.2-net-ethernet-mtk_wed-add-reset-to-tx_ring_setup-call.patch
deleted file mode 100644 (file)
index 4404971..0000000
+++ /dev/null
@@ -1,103 +0,0 @@
-From: Lorenzo Bianconi <[email protected]>
-Date: Thu, 24 Nov 2022 16:22:55 +0100
-Subject: [PATCH] net: ethernet: mtk_wed: add reset to tx_ring_setup callback
-
-Introduce reset parameter to mtk_wed_tx_ring_setup signature.
-This is a preliminary patch to add Wireless Ethernet Dispatcher reset
-support.
-
-Co-developed-by: Sujuan Chen <[email protected]>
-Signed-off-by: Sujuan Chen <[email protected]>
-Signed-off-by: Lorenzo Bianconi <[email protected]>
-Signed-off-by: Paolo Abeni <[email protected]>
----
-
---- a/drivers/net/ethernet/mediatek/mtk_wed.c
-+++ b/drivers/net/ethernet/mediatek/mtk_wed.c
-@@ -1181,7 +1181,8 @@ mtk_wed_ring_alloc(struct mtk_wed_device
- }
- static int
--mtk_wed_wdma_rx_ring_setup(struct mtk_wed_device *dev, int idx, int size)
-+mtk_wed_wdma_rx_ring_setup(struct mtk_wed_device *dev, int idx, int size,
-+                         bool reset)
- {
-       u32 desc_size = sizeof(struct mtk_wdma_desc) * dev->hw->version;
-       struct mtk_wed_ring *wdma;
-@@ -1190,8 +1191,8 @@ mtk_wed_wdma_rx_ring_setup(struct mtk_we
-               return -EINVAL;
-       wdma = &dev->rx_wdma[idx];
--      if (mtk_wed_ring_alloc(dev, wdma, MTK_WED_WDMA_RING_SIZE, desc_size,
--                             true))
-+      if (!reset && mtk_wed_ring_alloc(dev, wdma, MTK_WED_WDMA_RING_SIZE,
-+                                       desc_size, true))
-               return -ENOMEM;
-       wdma_w32(dev, MTK_WDMA_RING_RX(idx) + MTK_WED_RING_OFS_BASE,
-@@ -1389,7 +1390,7 @@ mtk_wed_start(struct mtk_wed_device *dev
-       for (i = 0; i < ARRAY_SIZE(dev->rx_wdma); i++)
-               if (!dev->rx_wdma[i].desc)
--                      mtk_wed_wdma_rx_ring_setup(dev, i, 16);
-+                      mtk_wed_wdma_rx_ring_setup(dev, i, 16, false);
-       mtk_wed_hw_init(dev);
-       mtk_wed_configure_irq(dev, irq_mask);
-@@ -1498,7 +1499,8 @@ unlock:
- }
- static int
--mtk_wed_tx_ring_setup(struct mtk_wed_device *dev, int idx, void __iomem *regs)
-+mtk_wed_tx_ring_setup(struct mtk_wed_device *dev, int idx, void __iomem *regs,
-+                    bool reset)
- {
-       struct mtk_wed_ring *ring = &dev->tx_ring[idx];
-@@ -1517,11 +1519,12 @@ mtk_wed_tx_ring_setup(struct mtk_wed_dev
-       if (WARN_ON(idx >= ARRAY_SIZE(dev->tx_ring)))
-               return -EINVAL;
--      if (mtk_wed_ring_alloc(dev, ring, MTK_WED_TX_RING_SIZE,
--                             sizeof(*ring->desc), true))
-+      if (!reset && mtk_wed_ring_alloc(dev, ring, MTK_WED_TX_RING_SIZE,
-+                                       sizeof(*ring->desc), true))
-               return -ENOMEM;
--      if (mtk_wed_wdma_rx_ring_setup(dev, idx, MTK_WED_WDMA_RING_SIZE))
-+      if (mtk_wed_wdma_rx_ring_setup(dev, idx, MTK_WED_WDMA_RING_SIZE,
-+                                     reset))
-               return -ENOMEM;
-       ring->reg_base = MTK_WED_RING_TX(idx);
---- a/include/linux/soc/mediatek/mtk_wed.h
-+++ b/include/linux/soc/mediatek/mtk_wed.h
-@@ -158,7 +158,7 @@ struct mtk_wed_device {
- struct mtk_wed_ops {
-       int (*attach)(struct mtk_wed_device *dev);
-       int (*tx_ring_setup)(struct mtk_wed_device *dev, int ring,
--                           void __iomem *regs);
-+                           void __iomem *regs, bool reset);
-       int (*rx_ring_setup)(struct mtk_wed_device *dev, int ring,
-                            void __iomem *regs);
-       int (*txfree_ring_setup)(struct mtk_wed_device *dev,
-@@ -216,8 +216,8 @@ mtk_wed_get_rx_capa(struct mtk_wed_devic
- #define mtk_wed_device_active(_dev) !!(_dev)->ops
- #define mtk_wed_device_detach(_dev) (_dev)->ops->detach(_dev)
- #define mtk_wed_device_start(_dev, _mask) (_dev)->ops->start(_dev, _mask)
--#define mtk_wed_device_tx_ring_setup(_dev, _ring, _regs) \
--      (_dev)->ops->tx_ring_setup(_dev, _ring, _regs)
-+#define mtk_wed_device_tx_ring_setup(_dev, _ring, _regs, _reset) \
-+      (_dev)->ops->tx_ring_setup(_dev, _ring, _regs, _reset)
- #define mtk_wed_device_txfree_ring_setup(_dev, _regs) \
-       (_dev)->ops->txfree_ring_setup(_dev, _regs)
- #define mtk_wed_device_reg_read(_dev, _reg) \
-@@ -243,7 +243,7 @@ static inline bool mtk_wed_device_active
- }
- #define mtk_wed_device_detach(_dev) do {} while (0)
- #define mtk_wed_device_start(_dev, _mask) do {} while (0)
--#define mtk_wed_device_tx_ring_setup(_dev, _ring, _regs) -ENODEV
-+#define mtk_wed_device_tx_ring_setup(_dev, _ring, _regs, _reset) -ENODEV
- #define mtk_wed_device_txfree_ring_setup(_dev, _ring, _regs) -ENODEV
- #define mtk_wed_device_reg_read(_dev, _reg) 0
- #define mtk_wed_device_reg_write(_dev, _reg, _val) do {} while (0)
diff --git a/target/linux/generic/backport-5.15/729-15-v6.2-net-ethernet-mtk_wed-fix-sleep-while-atomic-in-mtk_w.patch b/target/linux/generic/backport-5.15/729-15-v6.2-net-ethernet-mtk_wed-fix-sleep-while-atomic-in-mtk_w.patch
deleted file mode 100644 (file)
index f9b1132..0000000
+++ /dev/null
@@ -1,103 +0,0 @@
-From: Lorenzo Bianconi <[email protected]>
-Date: Thu, 1 Dec 2022 16:26:53 +0100
-Subject: [PATCH] net: ethernet: mtk_wed: fix sleep while atomic in
- mtk_wed_wo_queue_refill
-
-In order to fix the following sleep while atomic bug always alloc pages
-with GFP_ATOMIC in mtk_wed_wo_queue_refill since page_frag_alloc runs in
-spin_lock critical section.
-
-[    9.049719] Hardware name: MediaTek MT7986a RFB (DT)
-[    9.054665] Call trace:
-[    9.057096]  dump_backtrace+0x0/0x154
-[    9.060751]  show_stack+0x14/0x1c
-[    9.064052]  dump_stack_lvl+0x64/0x7c
-[    9.067702]  dump_stack+0x14/0x2c
-[    9.071001]  ___might_sleep+0xec/0x120
-[    9.074736]  __might_sleep+0x4c/0x9c
-[    9.078296]  __alloc_pages+0x184/0x2e4
-[    9.082030]  page_frag_alloc_align+0x98/0x1ac
-[    9.086369]  mtk_wed_wo_queue_refill+0x134/0x234
-[    9.090974]  mtk_wed_wo_init+0x174/0x2c0
-[    9.094881]  mtk_wed_attach+0x7c8/0x7e0
-[    9.098701]  mt7915_mmio_wed_init+0x1f0/0x3a0 [mt7915e]
-[    9.103940]  mt7915_pci_probe+0xec/0x3bc [mt7915e]
-[    9.108727]  pci_device_probe+0xac/0x13c
-[    9.112638]  really_probe.part.0+0x98/0x2f4
-[    9.116807]  __driver_probe_device+0x94/0x13c
-[    9.121147]  driver_probe_device+0x40/0x114
-[    9.125314]  __driver_attach+0x7c/0x180
-[    9.129133]  bus_for_each_dev+0x5c/0x90
-[    9.132953]  driver_attach+0x20/0x2c
-[    9.136513]  bus_add_driver+0x104/0x1fc
-[    9.140333]  driver_register+0x74/0x120
-[    9.144153]  __pci_register_driver+0x40/0x50
-[    9.148407]  mt7915_init+0x5c/0x1000 [mt7915e]
-[    9.152848]  do_one_initcall+0x40/0x25c
-[    9.156669]  do_init_module+0x44/0x230
-[    9.160403]  load_module+0x1f30/0x2750
-[    9.164135]  __do_sys_init_module+0x150/0x200
-[    9.168475]  __arm64_sys_init_module+0x18/0x20
-[    9.172901]  invoke_syscall.constprop.0+0x4c/0xe0
-[    9.177589]  do_el0_svc+0x48/0xe0
-[    9.180889]  el0_svc+0x14/0x50
-[    9.183929]  el0t_64_sync_handler+0x9c/0x120
-[    9.188183]  el0t_64_sync+0x158/0x15c
-
-Fixes: 799684448e3e ("net: ethernet: mtk_wed: introduce wed wo support")
-Signed-off-by: Lorenzo Bianconi <[email protected]>
-Reviewed-by: Pavan Chebbi <[email protected]>
-Link: https://lore.kernel.org/r/67ca94bdd3d9eaeb86e52b3050fbca0bcf7bb02f.1669908312.git.lorenzo@kernel.org
-Signed-off-by: Jakub Kicinski <[email protected]>
----
-
---- a/drivers/net/ethernet/mediatek/mtk_wed_wo.c
-+++ b/drivers/net/ethernet/mediatek/mtk_wed_wo.c
-@@ -133,17 +133,18 @@ mtk_wed_wo_dequeue(struct mtk_wed_wo *wo
- static int
- mtk_wed_wo_queue_refill(struct mtk_wed_wo *wo, struct mtk_wed_wo_queue *q,
--                      gfp_t gfp, bool rx)
-+                      bool rx)
- {
-       enum dma_data_direction dir = rx ? DMA_FROM_DEVICE : DMA_TO_DEVICE;
-       int n_buf = 0;
-       spin_lock_bh(&q->lock);
-       while (q->queued < q->n_desc) {
--              void *buf = page_frag_alloc(&q->cache, q->buf_size, gfp);
-               struct mtk_wed_wo_queue_entry *entry;
-               dma_addr_t addr;
-+              void *buf;
-+              buf = page_frag_alloc(&q->cache, q->buf_size, GFP_ATOMIC);
-               if (!buf)
-                       break;
-@@ -215,7 +216,7 @@ mtk_wed_wo_rx_run_queue(struct mtk_wed_w
-                       mtk_wed_mcu_rx_unsolicited_event(wo, skb);
-       }
--      if (mtk_wed_wo_queue_refill(wo, q, GFP_ATOMIC, true)) {
-+      if (mtk_wed_wo_queue_refill(wo, q, true)) {
-               u32 index = (q->head - 1) % q->n_desc;
-               mtk_wed_wo_queue_kick(wo, q, index);
-@@ -432,7 +433,7 @@ mtk_wed_wo_hardware_init(struct mtk_wed_
-       if (ret)
-               goto error;
--      mtk_wed_wo_queue_refill(wo, &wo->q_tx, GFP_KERNEL, false);
-+      mtk_wed_wo_queue_refill(wo, &wo->q_tx, false);
-       mtk_wed_wo_queue_reset(wo, &wo->q_tx);
-       regs.desc_base = MTK_WED_WO_CCIF_DUMMY5;
-@@ -446,7 +447,7 @@ mtk_wed_wo_hardware_init(struct mtk_wed_
-       if (ret)
-               goto error;
--      mtk_wed_wo_queue_refill(wo, &wo->q_rx, GFP_KERNEL, true);
-+      mtk_wed_wo_queue_refill(wo, &wo->q_rx, true);
-       mtk_wed_wo_queue_reset(wo, &wo->q_rx);
-       /* rx queue irqmask */
diff --git a/target/linux/generic/backport-5.15/729-16-v6.3-net-ethernet-mtk_wed-get-rid-of-queue-lock-for-rx-qu.patch b/target/linux/generic/backport-5.15/729-16-v6.3-net-ethernet-mtk_wed-get-rid-of-queue-lock-for-rx-qu.patch
deleted file mode 100644 (file)
index fa6f56d..0000000
+++ /dev/null
@@ -1,52 +0,0 @@
-From: Lorenzo Bianconi <[email protected]>
-Date: Tue, 10 Jan 2023 10:31:26 +0100
-Subject: [PATCH] net: ethernet: mtk_wed: get rid of queue lock for rx queue
-
-Queue spinlock is currently held in mtk_wed_wo_queue_rx_clean and
-mtk_wed_wo_queue_refill routines for MTK Wireless Ethernet Dispatcher
-MCU rx queue. mtk_wed_wo_queue_refill() is running during initialization
-and in rx tasklet while mtk_wed_wo_queue_rx_clean() is running in
-mtk_wed_wo_hw_deinit() during hw de-init phase after rx tasklet has been
-disabled. Since mtk_wed_wo_queue_rx_clean and mtk_wed_wo_queue_refill
-routines can't run concurrently get rid of spinlock for mcu rx queue.
-
-Reviewed-by: Alexander Duyck <[email protected]>
-Signed-off-by: Lorenzo Bianconi <[email protected]>
-Link: https://lore.kernel.org/r/36ec3b729542ea60898471d890796f745479ba32.1673342990.git.lorenzo@kernel.org
-Signed-off-by: Jakub Kicinski <[email protected]>
----
-
---- a/drivers/net/ethernet/mediatek/mtk_wed_wo.c
-+++ b/drivers/net/ethernet/mediatek/mtk_wed_wo.c
-@@ -138,7 +138,6 @@ mtk_wed_wo_queue_refill(struct mtk_wed_w
-       enum dma_data_direction dir = rx ? DMA_FROM_DEVICE : DMA_TO_DEVICE;
-       int n_buf = 0;
--      spin_lock_bh(&q->lock);
-       while (q->queued < q->n_desc) {
-               struct mtk_wed_wo_queue_entry *entry;
-               dma_addr_t addr;
-@@ -172,7 +171,6 @@ mtk_wed_wo_queue_refill(struct mtk_wed_w
-               q->queued++;
-               n_buf++;
-       }
--      spin_unlock_bh(&q->lock);
-       return n_buf;
- }
-@@ -316,7 +314,6 @@ mtk_wed_wo_queue_rx_clean(struct mtk_wed
- {
-       struct page *page;
--      spin_lock_bh(&q->lock);
-       for (;;) {
-               void *buf = mtk_wed_wo_dequeue(wo, q, NULL, true);
-@@ -325,7 +322,6 @@ mtk_wed_wo_queue_rx_clean(struct mtk_wed
-               skb_free_frag(buf);
-       }
--      spin_unlock_bh(&q->lock);
-       if (!q->cache.va)
-               return;
diff --git a/target/linux/generic/backport-5.15/729-17-v6.3-net-ethernet-mtk_wed-get-rid-of-queue-lock-for-tx-qu.patch b/target/linux/generic/backport-5.15/729-17-v6.3-net-ethernet-mtk_wed-get-rid-of-queue-lock-for-tx-qu.patch
deleted file mode 100644 (file)
index 9b1e4c3..0000000
+++ /dev/null
@@ -1,75 +0,0 @@
-From: Lorenzo Bianconi <[email protected]>
-Date: Thu, 12 Jan 2023 10:21:29 +0100
-Subject: [PATCH] net: ethernet: mtk_wed: get rid of queue lock for tx queue
-
-Similar to MTK Wireless Ethernet Dispatcher (WED) MCU rx queue,
-we do not need to protect WED MCU tx queue with a spin lock since
-the tx queue is accessed in the two following routines:
-- mtk_wed_wo_queue_tx_skb():
-  it is run at initialization and during mt7915 normal operation.
-  Moreover MCU messages are serialized through MCU mutex.
-- mtk_wed_wo_queue_tx_clean():
-  it runs just at mt7915 driver module unload when no more messages
-  are sent to the MCU.
-
-Remove tx queue spinlock.
-
-Signed-off-by: Lorenzo Bianconi <[email protected]>
-Link: https://lore.kernel.org/r/7bd0337b2a13ab1a63673b7c03fd35206b3b284e.1673515140.git.lorenzo@kernel.org
-Signed-off-by: Jakub Kicinski <[email protected]>
----
-
---- a/drivers/net/ethernet/mediatek/mtk_wed_wo.c
-+++ b/drivers/net/ethernet/mediatek/mtk_wed_wo.c
-@@ -258,7 +258,6 @@ mtk_wed_wo_queue_alloc(struct mtk_wed_wo
-                      int n_desc, int buf_size, int index,
-                      struct mtk_wed_wo_queue_regs *regs)
- {
--      spin_lock_init(&q->lock);
-       q->regs = *regs;
-       q->n_desc = n_desc;
-       q->buf_size = buf_size;
-@@ -290,7 +289,6 @@ mtk_wed_wo_queue_tx_clean(struct mtk_wed
-       struct page *page;
-       int i;
--      spin_lock_bh(&q->lock);
-       for (i = 0; i < q->n_desc; i++) {
-               struct mtk_wed_wo_queue_entry *entry = &q->entry[i];
-@@ -299,7 +297,6 @@ mtk_wed_wo_queue_tx_clean(struct mtk_wed
-               skb_free_frag(entry->buf);
-               entry->buf = NULL;
-       }
--      spin_unlock_bh(&q->lock);
-       if (!q->cache.va)
-               return;
-@@ -347,8 +344,6 @@ int mtk_wed_wo_queue_tx_skb(struct mtk_w
-       int ret = 0, index;
-       u32 ctrl;
--      spin_lock_bh(&q->lock);
--
-       q->tail = mtk_wed_mmio_r32(wo, q->regs.dma_idx);
-       index = (q->head + 1) % q->n_desc;
-       if (q->tail == index) {
-@@ -379,8 +374,6 @@ int mtk_wed_wo_queue_tx_skb(struct mtk_w
-       mtk_wed_wo_queue_kick(wo, q, q->head);
-       mtk_wed_wo_kickout(wo);
- out:
--      spin_unlock_bh(&q->lock);
--
-       dev_kfree_skb(skb);
-       return ret;
---- a/drivers/net/ethernet/mediatek/mtk_wed_wo.h
-+++ b/drivers/net/ethernet/mediatek/mtk_wed_wo.h
-@@ -211,7 +211,6 @@ struct mtk_wed_wo_queue {
-       struct mtk_wed_wo_queue_regs regs;
-       struct page_frag_cache cache;
--      spinlock_t lock;
-       struct mtk_wed_wo_queue_desc *desc;
-       dma_addr_t desc_dma;
diff --git a/target/linux/generic/backport-5.15/729-18-v6.3-net-ethernet-mtk_eth_soc-introduce-mtk_hw_reset-util.patch b/target/linux/generic/backport-5.15/729-18-v6.3-net-ethernet-mtk_eth_soc-introduce-mtk_hw_reset-util.patch
deleted file mode 100644 (file)
index 33f2b5b..0000000
+++ /dev/null
@@ -1,70 +0,0 @@
-From: Lorenzo Bianconi <[email protected]>
-Date: Sat, 14 Jan 2023 18:01:28 +0100
-Subject: [PATCH] net: ethernet: mtk_eth_soc: introduce mtk_hw_reset utility
- routine
-
-This is a preliminary patch to add Wireless Ethernet Dispatcher reset
-support.
-
-Reviewed-by: Leon Romanovsky <[email protected]>
-Tested-by: Daniel Golle <[email protected]>
-Co-developed-by: Sujuan Chen <[email protected]>
-Signed-off-by: Sujuan Chen <[email protected]>
-Signed-off-by: Lorenzo Bianconi <[email protected]>
-Signed-off-by: Paolo Abeni <[email protected]>
----
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-@@ -3202,6 +3202,27 @@ static void mtk_set_mcr_max_rx(struct mt
-               mtk_w32(mac->hw, mcr_new, MTK_MAC_MCR(mac->id));
- }
-+static void mtk_hw_reset(struct mtk_eth *eth)
-+{
-+      u32 val;
-+
-+      if (MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2)) {
-+              regmap_write(eth->ethsys, ETHSYS_FE_RST_CHK_IDLE_EN, 0);
-+              val = RSTCTRL_PPE0_V2;
-+      } else {
-+              val = RSTCTRL_PPE0;
-+      }
-+
-+      if (MTK_HAS_CAPS(eth->soc->caps, MTK_RSTCTRL_PPE1))
-+              val |= RSTCTRL_PPE1;
-+
-+      ethsys_reset(eth, RSTCTRL_ETH | RSTCTRL_FE | val);
-+
-+      if (MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2))
-+              regmap_write(eth->ethsys, ETHSYS_FE_RST_CHK_IDLE_EN,
-+                           0x3ffffff);
-+}
-+
- static int mtk_hw_init(struct mtk_eth *eth)
- {
-       u32 dma_mask = ETHSYS_DMA_AG_MAP_PDMA | ETHSYS_DMA_AG_MAP_QDMA |
-@@ -3241,22 +3262,9 @@ static int mtk_hw_init(struct mtk_eth *e
-               return 0;
-       }
--      if (MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2)) {
--              regmap_write(eth->ethsys, ETHSYS_FE_RST_CHK_IDLE_EN, 0);
--              val = RSTCTRL_PPE0_V2;
--      } else {
--              val = RSTCTRL_PPE0;
--      }
--
--      if (MTK_HAS_CAPS(eth->soc->caps, MTK_RSTCTRL_PPE1))
--              val |= RSTCTRL_PPE1;
--
--      ethsys_reset(eth, RSTCTRL_ETH | RSTCTRL_FE | val);
-+      mtk_hw_reset(eth);
-       if (MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2)) {
--              regmap_write(eth->ethsys, ETHSYS_FE_RST_CHK_IDLE_EN,
--                           0x3ffffff);
--
-               /* Set FE to PDMAv2 if necessary */
-               val = mtk_r32(eth, MTK_FE_GLO_MISC);
-               mtk_w32(eth,  val | BIT(4), MTK_FE_GLO_MISC);
diff --git a/target/linux/generic/backport-5.15/729-19-v6.3-net-ethernet-mtk_eth_soc-introduce-mtk_hw_warm_reset.patch b/target/linux/generic/backport-5.15/729-19-v6.3-net-ethernet-mtk_eth_soc-introduce-mtk_hw_warm_reset.patch
deleted file mode 100644 (file)
index 84209fc..0000000
+++ /dev/null
@@ -1,107 +0,0 @@
-From: Lorenzo Bianconi <[email protected]>
-Date: Sat, 14 Jan 2023 18:01:29 +0100
-Subject: [PATCH] net: ethernet: mtk_eth_soc: introduce mtk_hw_warm_reset
- support
-
-Introduce mtk_hw_warm_reset utility routine. This is a preliminary patch
-to align reset procedure to vendor sdk and avoid to power down the chip
-during hw reset.
-
-Reviewed-by: Leon Romanovsky <[email protected]>
-Tested-by: Daniel Golle <[email protected]>
-Co-developed-by: Sujuan Chen <[email protected]>
-Signed-off-by: Sujuan Chen <[email protected]>
-Signed-off-by: Lorenzo Bianconi <[email protected]>
-Signed-off-by: Paolo Abeni <[email protected]>
----
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-@@ -3223,7 +3223,54 @@ static void mtk_hw_reset(struct mtk_eth
-                            0x3ffffff);
- }
--static int mtk_hw_init(struct mtk_eth *eth)
-+static u32 mtk_hw_reset_read(struct mtk_eth *eth)
-+{
-+      u32 val;
-+
-+      regmap_read(eth->ethsys, ETHSYS_RSTCTRL, &val);
-+      return val;
-+}
-+
-+static void mtk_hw_warm_reset(struct mtk_eth *eth)
-+{
-+      u32 rst_mask, val;
-+
-+      regmap_update_bits(eth->ethsys, ETHSYS_RSTCTRL, RSTCTRL_FE,
-+                         RSTCTRL_FE);
-+      if (readx_poll_timeout_atomic(mtk_hw_reset_read, eth, val,
-+                                    val & RSTCTRL_FE, 1, 1000)) {
-+              dev_err(eth->dev, "warm reset failed\n");
-+              mtk_hw_reset(eth);
-+              return;
-+      }
-+
-+      if (MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2))
-+              rst_mask = RSTCTRL_ETH | RSTCTRL_PPE0_V2;
-+      else
-+              rst_mask = RSTCTRL_ETH | RSTCTRL_PPE0;
-+
-+      if (MTK_HAS_CAPS(eth->soc->caps, MTK_RSTCTRL_PPE1))
-+              rst_mask |= RSTCTRL_PPE1;
-+
-+      regmap_update_bits(eth->ethsys, ETHSYS_RSTCTRL, rst_mask, rst_mask);
-+
-+      udelay(1);
-+      val = mtk_hw_reset_read(eth);
-+      if (!(val & rst_mask))
-+              dev_err(eth->dev, "warm reset stage0 failed %08x (%08x)\n",
-+                      val, rst_mask);
-+
-+      rst_mask |= RSTCTRL_FE;
-+      regmap_update_bits(eth->ethsys, ETHSYS_RSTCTRL, rst_mask, ~rst_mask);
-+
-+      udelay(1);
-+      val = mtk_hw_reset_read(eth);
-+      if (val & rst_mask)
-+              dev_err(eth->dev, "warm reset stage1 failed %08x (%08x)\n",
-+                      val, rst_mask);
-+}
-+
-+static int mtk_hw_init(struct mtk_eth *eth, bool reset)
- {
-       u32 dma_mask = ETHSYS_DMA_AG_MAP_PDMA | ETHSYS_DMA_AG_MAP_QDMA |
-                      ETHSYS_DMA_AG_MAP_PPE;
-@@ -3262,7 +3309,12 @@ static int mtk_hw_init(struct mtk_eth *e
-               return 0;
-       }
--      mtk_hw_reset(eth);
-+      msleep(100);
-+
-+      if (reset)
-+              mtk_hw_warm_reset(eth);
-+      else
-+              mtk_hw_reset(eth);
-       if (MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2)) {
-               /* Set FE to PDMAv2 if necessary */
-@@ -3450,7 +3502,7 @@ static void mtk_pending_work(struct work
-       if (eth->dev->pins)
-               pinctrl_select_state(eth->dev->pins->p,
-                                    eth->dev->pins->default_state);
--      mtk_hw_init(eth);
-+      mtk_hw_init(eth, true);
-       /* restart DMA and enable IRQs */
-       for (i = 0; i < MTK_MAC_COUNT; i++) {
-@@ -4052,7 +4104,7 @@ static int mtk_probe(struct platform_dev
-       eth->msg_enable = netif_msg_init(mtk_msg_level, MTK_DEFAULT_MSG_ENABLE);
-       INIT_WORK(&eth->pending_work, mtk_pending_work);
--      err = mtk_hw_init(eth);
-+      err = mtk_hw_init(eth, false);
-       if (err)
-               goto err_wed_exit;
diff --git a/target/linux/generic/backport-5.15/729-20-v6.3-net-ethernet-mtk_eth_soc-align-reset-procedure-to-ve.patch b/target/linux/generic/backport-5.15/729-20-v6.3-net-ethernet-mtk_eth_soc-align-reset-procedure-to-ve.patch
deleted file mode 100644 (file)
index e75a4cc..0000000
+++ /dev/null
@@ -1,262 +0,0 @@
-From: Lorenzo Bianconi <[email protected]>
-Date: Sat, 14 Jan 2023 18:01:30 +0100
-Subject: [PATCH] net: ethernet: mtk_eth_soc: align reset procedure to vendor
- sdk
-
-Avoid to power-down the ethernet chip during hw reset and align reset
-procedure to vendor sdk.
-
-Reviewed-by: Leon Romanovsky <[email protected]>
-Tested-by: Daniel Golle <[email protected]>
-Co-developed-by: Sujuan Chen <[email protected]>
-Signed-off-by: Sujuan Chen <[email protected]>
-Signed-off-by: Lorenzo Bianconi <[email protected]>
-Signed-off-by: Paolo Abeni <[email protected]>
----
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-@@ -2788,14 +2788,29 @@ static void mtk_dma_free(struct mtk_eth
-       kfree(eth->scratch_head);
- }
-+static bool mtk_hw_reset_check(struct mtk_eth *eth)
-+{
-+      u32 val = mtk_r32(eth, MTK_INT_STATUS2);
-+
-+      return (val & MTK_FE_INT_FQ_EMPTY) || (val & MTK_FE_INT_RFIFO_UF) ||
-+             (val & MTK_FE_INT_RFIFO_OV) || (val & MTK_FE_INT_TSO_FAIL) ||
-+             (val & MTK_FE_INT_TSO_ALIGN) || (val & MTK_FE_INT_TSO_ILLEGAL);
-+}
-+
- static void mtk_tx_timeout(struct net_device *dev, unsigned int txqueue)
- {
-       struct mtk_mac *mac = netdev_priv(dev);
-       struct mtk_eth *eth = mac->hw;
-+      if (test_bit(MTK_RESETTING, &eth->state))
-+              return;
-+
-+      if (!mtk_hw_reset_check(eth))
-+              return;
-+
-       eth->netdev[mac->id]->stats.tx_errors++;
--      netif_err(eth, tx_err, dev,
--                "transmit timed out\n");
-+      netif_err(eth, tx_err, dev, "transmit timed out\n");
-+
-       schedule_work(&eth->pending_work);
- }
-@@ -3277,15 +3292,17 @@ static int mtk_hw_init(struct mtk_eth *e
-       const struct mtk_reg_map *reg_map = eth->soc->reg_map;
-       int i, val, ret;
--      if (test_and_set_bit(MTK_HW_INIT, &eth->state))
-+      if (!reset && test_and_set_bit(MTK_HW_INIT, &eth->state))
-               return 0;
--      pm_runtime_enable(eth->dev);
--      pm_runtime_get_sync(eth->dev);
-+      if (!reset) {
-+              pm_runtime_enable(eth->dev);
-+              pm_runtime_get_sync(eth->dev);
--      ret = mtk_clk_enable(eth);
--      if (ret)
--              goto err_disable_pm;
-+              ret = mtk_clk_enable(eth);
-+              if (ret)
-+                      goto err_disable_pm;
-+      }
-       if (eth->ethsys)
-               regmap_update_bits(eth->ethsys, ETHSYS_DMA_AG_MAP, dma_mask,
-@@ -3411,8 +3428,10 @@ static int mtk_hw_init(struct mtk_eth *e
-       return 0;
- err_disable_pm:
--      pm_runtime_put_sync(eth->dev);
--      pm_runtime_disable(eth->dev);
-+      if (!reset) {
-+              pm_runtime_put_sync(eth->dev);
-+              pm_runtime_disable(eth->dev);
-+      }
-       return ret;
- }
-@@ -3474,30 +3493,53 @@ static int mtk_do_ioctl(struct net_devic
-       return -EOPNOTSUPP;
- }
-+static void mtk_prepare_for_reset(struct mtk_eth *eth)
-+{
-+      u32 val;
-+      int i;
-+
-+      /* disabe FE P3 and P4 */
-+      val = mtk_r32(eth, MTK_FE_GLO_CFG) | MTK_FE_LINK_DOWN_P3;
-+      if (MTK_HAS_CAPS(eth->soc->caps, MTK_RSTCTRL_PPE1))
-+              val |= MTK_FE_LINK_DOWN_P4;
-+      mtk_w32(eth, val, MTK_FE_GLO_CFG);
-+
-+      /* adjust PPE configurations to prepare for reset */
-+      for (i = 0; i < ARRAY_SIZE(eth->ppe); i++)
-+              mtk_ppe_prepare_reset(eth->ppe[i]);
-+
-+      /* disable NETSYS interrupts */
-+      mtk_w32(eth, 0, MTK_FE_INT_ENABLE);
-+
-+      /* force link down GMAC */
-+      for (i = 0; i < 2; i++) {
-+              val = mtk_r32(eth, MTK_MAC_MCR(i)) & ~MAC_MCR_FORCE_LINK;
-+              mtk_w32(eth, val, MTK_MAC_MCR(i));
-+      }
-+}
-+
- static void mtk_pending_work(struct work_struct *work)
- {
-       struct mtk_eth *eth = container_of(work, struct mtk_eth, pending_work);
--      int err, i;
-       unsigned long restart = 0;
-+      u32 val;
-+      int i;
-       rtnl_lock();
--
--      dev_dbg(eth->dev, "[%s][%d] reset\n", __func__, __LINE__);
-       set_bit(MTK_RESETTING, &eth->state);
-+      mtk_prepare_for_reset(eth);
-+
-       /* stop all devices to make sure that dma is properly shut down */
-       for (i = 0; i < MTK_MAC_COUNT; i++) {
--              if (!eth->netdev[i])
-+              if (!eth->netdev[i] || !netif_running(eth->netdev[i]))
-                       continue;
-+
-               mtk_stop(eth->netdev[i]);
-               __set_bit(i, &restart);
-       }
--      dev_dbg(eth->dev, "[%s][%d] mtk_stop ends\n", __func__, __LINE__);
--      /* restart underlying hardware such as power, clock, pin mux
--       * and the connected phy
--       */
--      mtk_hw_deinit(eth);
-+      usleep_range(15000, 16000);
-       if (eth->dev->pins)
-               pinctrl_select_state(eth->dev->pins->p,
-@@ -3508,15 +3550,19 @@ static void mtk_pending_work(struct work
-       for (i = 0; i < MTK_MAC_COUNT; i++) {
-               if (!test_bit(i, &restart))
-                       continue;
--              err = mtk_open(eth->netdev[i]);
--              if (err) {
-+
-+              if (mtk_open(eth->netdev[i])) {
-                       netif_alert(eth, ifup, eth->netdev[i],
--                            "Driver up/down cycle failed, closing device.\n");
-+                                  "Driver up/down cycle failed\n");
-                       dev_close(eth->netdev[i]);
-               }
-       }
--      dev_dbg(eth->dev, "[%s][%d] reset done\n", __func__, __LINE__);
-+      /* enabe FE P3 and P4 */
-+      val = mtk_r32(eth, MTK_FE_GLO_CFG) & ~MTK_FE_LINK_DOWN_P3;
-+      if (MTK_HAS_CAPS(eth->soc->caps, MTK_RSTCTRL_PPE1))
-+              val &= ~MTK_FE_LINK_DOWN_P4;
-+      mtk_w32(eth, val, MTK_FE_GLO_CFG);
-       clear_bit(MTK_RESETTING, &eth->state);
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-@@ -72,12 +72,24 @@
- #define       MTK_HW_LRO_REPLACE_DELTA        1000
- #define       MTK_HW_LRO_SDL_REMAIN_ROOM      1522
-+/* Frame Engine Global Configuration */
-+#define MTK_FE_GLO_CFG                0x00
-+#define MTK_FE_LINK_DOWN_P3   BIT(11)
-+#define MTK_FE_LINK_DOWN_P4   BIT(12)
-+
- /* Frame Engine Global Reset Register */
- #define MTK_RST_GL            0x04
- #define RST_GL_PSE            BIT(0)
- /* Frame Engine Interrupt Status Register */
- #define MTK_INT_STATUS2               0x08
-+#define MTK_FE_INT_ENABLE     0x0c
-+#define MTK_FE_INT_FQ_EMPTY   BIT(8)
-+#define MTK_FE_INT_TSO_FAIL   BIT(12)
-+#define MTK_FE_INT_TSO_ILLEGAL        BIT(13)
-+#define MTK_FE_INT_TSO_ALIGN  BIT(14)
-+#define MTK_FE_INT_RFIFO_OV   BIT(18)
-+#define MTK_FE_INT_RFIFO_UF   BIT(19)
- #define MTK_GDM1_AF           BIT(28)
- #define MTK_GDM2_AF           BIT(29)
---- a/drivers/net/ethernet/mediatek/mtk_ppe.c
-+++ b/drivers/net/ethernet/mediatek/mtk_ppe.c
-@@ -716,6 +716,33 @@ int mtk_foe_entry_idle_time(struct mtk_p
-       return __mtk_foe_entry_idle_time(ppe, entry->data.ib1);
- }
-+int mtk_ppe_prepare_reset(struct mtk_ppe *ppe)
-+{
-+      if (!ppe)
-+              return -EINVAL;
-+
-+      /* disable KA */
-+      ppe_clear(ppe, MTK_PPE_TB_CFG, MTK_PPE_TB_CFG_KEEPALIVE);
-+      ppe_clear(ppe, MTK_PPE_BIND_LMT1, MTK_PPE_NTU_KEEPALIVE);
-+      ppe_w32(ppe, MTK_PPE_KEEPALIVE, 0);
-+      usleep_range(10000, 11000);
-+
-+      /* set KA timer to maximum */
-+      ppe_set(ppe, MTK_PPE_BIND_LMT1, MTK_PPE_NTU_KEEPALIVE);
-+      ppe_w32(ppe, MTK_PPE_KEEPALIVE, 0xffffffff);
-+
-+      /* set KA tick select */
-+      ppe_set(ppe, MTK_PPE_TB_CFG, MTK_PPE_TB_TICK_SEL);
-+      ppe_set(ppe, MTK_PPE_TB_CFG, MTK_PPE_TB_CFG_KEEPALIVE);
-+      usleep_range(10000, 11000);
-+
-+      /* disable scan mode */
-+      ppe_clear(ppe, MTK_PPE_TB_CFG, MTK_PPE_TB_CFG_SCAN_MODE);
-+      usleep_range(10000, 11000);
-+
-+      return mtk_ppe_wait_busy(ppe);
-+}
-+
- struct mtk_ppe *mtk_ppe_init(struct mtk_eth *eth, void __iomem *base,
-                            int version, int index)
- {
---- a/drivers/net/ethernet/mediatek/mtk_ppe.h
-+++ b/drivers/net/ethernet/mediatek/mtk_ppe.h
-@@ -307,6 +307,7 @@ struct mtk_ppe *mtk_ppe_init(struct mtk_
- void mtk_ppe_deinit(struct mtk_eth *eth);
- void mtk_ppe_start(struct mtk_ppe *ppe);
- int mtk_ppe_stop(struct mtk_ppe *ppe);
-+int mtk_ppe_prepare_reset(struct mtk_ppe *ppe);
- void __mtk_ppe_check_skb(struct mtk_ppe *ppe, struct sk_buff *skb, u16 hash);
---- a/drivers/net/ethernet/mediatek/mtk_ppe_regs.h
-+++ b/drivers/net/ethernet/mediatek/mtk_ppe_regs.h
-@@ -58,6 +58,12 @@
- #define MTK_PPE_TB_CFG_SCAN_MODE              GENMASK(17, 16)
- #define MTK_PPE_TB_CFG_HASH_DEBUG             GENMASK(19, 18)
- #define MTK_PPE_TB_CFG_INFO_SEL                       BIT(20)
-+#define MTK_PPE_TB_TICK_SEL                   BIT(24)
-+
-+#define MTK_PPE_BIND_LMT1                     0x230
-+#define MTK_PPE_NTU_KEEPALIVE                 GENMASK(23, 16)
-+
-+#define MTK_PPE_KEEPALIVE                     0x234
- enum {
-       MTK_PPE_SCAN_MODE_DISABLED,
diff --git a/target/linux/generic/backport-5.15/729-21-v6.3-net-ethernet-mtk_eth_soc-add-dma-checks-to-mtk_hw_re.patch b/target/linux/generic/backport-5.15/729-21-v6.3-net-ethernet-mtk_eth_soc-add-dma-checks-to-mtk_hw_re.patch
deleted file mode 100644 (file)
index 898785e..0000000
+++ /dev/null
@@ -1,249 +0,0 @@
-From: Lorenzo Bianconi <[email protected]>
-Date: Sat, 14 Jan 2023 18:01:31 +0100
-Subject: [PATCH] net: ethernet: mtk_eth_soc: add dma checks to
- mtk_hw_reset_check
-
-Introduce mtk_hw_check_dma_hang routine to monitor possible dma hangs.
-
-Reviewed-by: Leon Romanovsky <[email protected]>
-Tested-by: Daniel Golle <[email protected]>
-Co-developed-by: Sujuan Chen <[email protected]>
-Signed-off-by: Sujuan Chen <[email protected]>
-Signed-off-by: Lorenzo Bianconi <[email protected]>
-Signed-off-by: Paolo Abeni <[email protected]>
----
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-@@ -50,6 +50,7 @@ static const struct mtk_reg_map mtk_reg_
-               .delay_irq      = 0x0a0c,
-               .irq_status     = 0x0a20,
-               .irq_mask       = 0x0a28,
-+              .adma_rx_dbg0   = 0x0a38,
-               .int_grp        = 0x0a50,
-       },
-       .qdma = {
-@@ -79,6 +80,8 @@ static const struct mtk_reg_map mtk_reg_
-               [0]             = 0x2800,
-               [1]             = 0x2c00,
-       },
-+      .pse_iq_sta             = 0x0110,
-+      .pse_oq_sta             = 0x0118,
- };
- static const struct mtk_reg_map mt7628_reg_map = {
-@@ -109,6 +112,7 @@ static const struct mtk_reg_map mt7986_r
-               .delay_irq      = 0x620c,
-               .irq_status     = 0x6220,
-               .irq_mask       = 0x6228,
-+              .adma_rx_dbg0   = 0x6238,
-               .int_grp        = 0x6250,
-       },
-       .qdma = {
-@@ -138,6 +142,8 @@ static const struct mtk_reg_map mt7986_r
-               [0]             = 0x4800,
-               [1]             = 0x4c00,
-       },
-+      .pse_iq_sta             = 0x0180,
-+      .pse_oq_sta             = 0x01a0,
- };
- /* strings used by ethtool */
-@@ -3285,6 +3291,102 @@ static void mtk_hw_warm_reset(struct mtk
-                       val, rst_mask);
- }
-+static bool mtk_hw_check_dma_hang(struct mtk_eth *eth)
-+{
-+      const struct mtk_reg_map *reg_map = eth->soc->reg_map;
-+      bool gmac1_tx, gmac2_tx, gdm1_tx, gdm2_tx;
-+      bool oq_hang, cdm1_busy, adma_busy;
-+      bool wtx_busy, cdm_full, oq_free;
-+      u32 wdidx, val, gdm1_fc, gdm2_fc;
-+      bool qfsm_hang, qfwd_hang;
-+      bool ret = false;
-+
-+      if (MTK_HAS_CAPS(eth->soc->caps, MTK_SOC_MT7628))
-+              return false;
-+
-+      /* WDMA sanity checks */
-+      wdidx = mtk_r32(eth, reg_map->wdma_base[0] + 0xc);
-+
-+      val = mtk_r32(eth, reg_map->wdma_base[0] + 0x204);
-+      wtx_busy = FIELD_GET(MTK_TX_DMA_BUSY, val);
-+
-+      val = mtk_r32(eth, reg_map->wdma_base[0] + 0x230);
-+      cdm_full = !FIELD_GET(MTK_CDM_TXFIFO_RDY, val);
-+
-+      oq_free  = (!(mtk_r32(eth, reg_map->pse_oq_sta) & GENMASK(24, 16)) &&
-+                  !(mtk_r32(eth, reg_map->pse_oq_sta + 0x4) & GENMASK(8, 0)) &&
-+                  !(mtk_r32(eth, reg_map->pse_oq_sta + 0x10) & GENMASK(24, 16)));
-+
-+      if (wdidx == eth->reset.wdidx && wtx_busy && cdm_full && oq_free) {
-+              if (++eth->reset.wdma_hang_count > 2) {
-+                      eth->reset.wdma_hang_count = 0;
-+                      ret = true;
-+              }
-+              goto out;
-+      }
-+
-+      /* QDMA sanity checks */
-+      qfsm_hang = !!mtk_r32(eth, reg_map->qdma.qtx_cfg + 0x234);
-+      qfwd_hang = !mtk_r32(eth, reg_map->qdma.qtx_cfg + 0x308);
-+
-+      gdm1_tx = FIELD_GET(GENMASK(31, 16), mtk_r32(eth, MTK_FE_GDM1_FSM)) > 0;
-+      gdm2_tx = FIELD_GET(GENMASK(31, 16), mtk_r32(eth, MTK_FE_GDM2_FSM)) > 0;
-+      gmac1_tx = FIELD_GET(GENMASK(31, 24), mtk_r32(eth, MTK_MAC_FSM(0))) != 1;
-+      gmac2_tx = FIELD_GET(GENMASK(31, 24), mtk_r32(eth, MTK_MAC_FSM(1))) != 1;
-+      gdm1_fc = mtk_r32(eth, reg_map->gdm1_cnt + 0x24);
-+      gdm2_fc = mtk_r32(eth, reg_map->gdm1_cnt + 0x64);
-+
-+      if (qfsm_hang && qfwd_hang &&
-+          ((gdm1_tx && gmac1_tx && gdm1_fc < 1) ||
-+           (gdm2_tx && gmac2_tx && gdm2_fc < 1))) {
-+              if (++eth->reset.qdma_hang_count > 2) {
-+                      eth->reset.qdma_hang_count = 0;
-+                      ret = true;
-+              }
-+              goto out;
-+      }
-+
-+      /* ADMA sanity checks */
-+      oq_hang = !!(mtk_r32(eth, reg_map->pse_oq_sta) & GENMASK(8, 0));
-+      cdm1_busy = !!(mtk_r32(eth, MTK_FE_CDM1_FSM) & GENMASK(31, 16));
-+      adma_busy = !(mtk_r32(eth, reg_map->pdma.adma_rx_dbg0) & GENMASK(4, 0)) &&
-+                  !(mtk_r32(eth, reg_map->pdma.adma_rx_dbg0) & BIT(6));
-+
-+      if (oq_hang && cdm1_busy && adma_busy) {
-+              if (++eth->reset.adma_hang_count > 2) {
-+                      eth->reset.adma_hang_count = 0;
-+                      ret = true;
-+              }
-+              goto out;
-+      }
-+
-+      eth->reset.wdma_hang_count = 0;
-+      eth->reset.qdma_hang_count = 0;
-+      eth->reset.adma_hang_count = 0;
-+out:
-+      eth->reset.wdidx = wdidx;
-+
-+      return ret;
-+}
-+
-+static void mtk_hw_reset_monitor_work(struct work_struct *work)
-+{
-+      struct delayed_work *del_work = to_delayed_work(work);
-+      struct mtk_eth *eth = container_of(del_work, struct mtk_eth,
-+                                         reset.monitor_work);
-+
-+      if (test_bit(MTK_RESETTING, &eth->state))
-+              goto out;
-+
-+      /* DMA stuck checks */
-+      if (mtk_hw_check_dma_hang(eth))
-+              schedule_work(&eth->pending_work);
-+
-+out:
-+      schedule_delayed_work(&eth->reset.monitor_work,
-+                            MTK_DMA_MONITOR_TIMEOUT);
-+}
-+
- static int mtk_hw_init(struct mtk_eth *eth, bool reset)
- {
-       u32 dma_mask = ETHSYS_DMA_AG_MAP_PDMA | ETHSYS_DMA_AG_MAP_QDMA |
-@@ -3600,6 +3702,7 @@ static int mtk_cleanup(struct mtk_eth *e
-       mtk_unreg_dev(eth);
-       mtk_free_dev(eth);
-       cancel_work_sync(&eth->pending_work);
-+      cancel_delayed_work_sync(&eth->reset.monitor_work);
-       return 0;
- }
-@@ -4037,6 +4140,7 @@ static int mtk_probe(struct platform_dev
-       eth->rx_dim.mode = DIM_CQ_PERIOD_MODE_START_FROM_EQE;
-       INIT_WORK(&eth->rx_dim.work, mtk_dim_rx);
-+      INIT_DELAYED_WORK(&eth->reset.monitor_work, mtk_hw_reset_monitor_work);
-       eth->tx_dim.mode = DIM_CQ_PERIOD_MODE_START_FROM_EQE;
-       INIT_WORK(&eth->tx_dim.work, mtk_dim_tx);
-@@ -4241,6 +4345,8 @@ static int mtk_probe(struct platform_dev
-                      NAPI_POLL_WEIGHT);
-       platform_set_drvdata(pdev, eth);
-+      schedule_delayed_work(&eth->reset.monitor_work,
-+                            MTK_DMA_MONITOR_TIMEOUT);
-       return 0;
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-@@ -256,6 +256,8 @@
- #define MTK_RX_DONE_INT_V2    BIT(14)
-+#define MTK_CDM_TXFIFO_RDY    BIT(7)
-+
- /* QDMA Interrupt grouping registers */
- #define MTK_RLS_DONE_INT      BIT(0)
-@@ -538,6 +540,17 @@
- #define MT7628_SDM_RBCNT      (MT7628_SDM_OFFSET + 0x10c)
- #define MT7628_SDM_CS_ERR     (MT7628_SDM_OFFSET + 0x110)
-+#define MTK_FE_CDM1_FSM               0x220
-+#define MTK_FE_CDM2_FSM               0x224
-+#define MTK_FE_CDM3_FSM               0x238
-+#define MTK_FE_CDM4_FSM               0x298
-+#define MTK_FE_CDM5_FSM               0x318
-+#define MTK_FE_CDM6_FSM               0x328
-+#define MTK_FE_GDM1_FSM               0x228
-+#define MTK_FE_GDM2_FSM               0x22C
-+
-+#define MTK_MAC_FSM(x)                (0x1010C + ((x) * 0x100))
-+
- struct mtk_rx_dma {
-       unsigned int rxd1;
-       unsigned int rxd2;
-@@ -934,6 +947,7 @@ struct mtk_reg_map {
-               u32     delay_irq;      /* delay interrupt */
-               u32     irq_status;     /* interrupt status */
-               u32     irq_mask;       /* interrupt mask */
-+              u32     adma_rx_dbg0;
-               u32     int_grp;
-       } pdma;
-       struct {
-@@ -960,6 +974,8 @@ struct mtk_reg_map {
-       u32     gdma_to_ppe0;
-       u32     ppe_base;
-       u32     wdma_base[2];
-+      u32     pse_iq_sta;
-+      u32     pse_oq_sta;
- };
- /* struct mtk_eth_data -      This is the structure holding all differences
-@@ -1002,6 +1018,8 @@ struct mtk_soc_data {
-       } txrx;
- };
-+#define MTK_DMA_MONITOR_TIMEOUT               msecs_to_jiffies(1000)
-+
- /* currently no SoC has more than 2 macs */
- #define MTK_MAX_DEVS                  2
-@@ -1124,6 +1142,14 @@ struct mtk_eth {
-       struct rhashtable               flow_table;
-       struct bpf_prog                 __rcu *prog;
-+
-+      struct {
-+              struct delayed_work monitor_work;
-+              u32 wdidx;
-+              u8 wdma_hang_count;
-+              u8 qdma_hang_count;
-+              u8 adma_hang_count;
-+      } reset;
- };
- /* struct mtk_mac -   the structure that holds the info about the MACs of the
diff --git a/target/linux/generic/backport-5.15/729-22-v6.3-net-ethernet-mtk_wed-add-reset-reset_complete-callba.patch b/target/linux/generic/backport-5.15/729-22-v6.3-net-ethernet-mtk_wed-add-reset-reset_complete-callba.patch
deleted file mode 100644 (file)
index cc9aaaf..0000000
+++ /dev/null
@@ -1,124 +0,0 @@
-From: Lorenzo Bianconi <[email protected]>
-Date: Sat, 14 Jan 2023 18:01:32 +0100
-Subject: [PATCH] net: ethernet: mtk_wed: add reset/reset_complete callbacks
-
-Introduce reset and reset_complete wlan callback to schedule WLAN driver
-reset when ethernet/wed driver is resetting.
-
-Tested-by: Daniel Golle <[email protected]>
-Co-developed-by: Sujuan Chen <[email protected]>
-Signed-off-by: Sujuan Chen <[email protected]>
-Signed-off-by: Lorenzo Bianconi <[email protected]>
-Signed-off-by: Paolo Abeni <[email protected]>
----
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-@@ -3631,6 +3631,11 @@ static void mtk_pending_work(struct work
-       set_bit(MTK_RESETTING, &eth->state);
-       mtk_prepare_for_reset(eth);
-+      mtk_wed_fe_reset();
-+      /* Run again reset preliminary configuration in order to avoid any
-+       * possible race during FE reset since it can run releasing RTNL lock.
-+       */
-+      mtk_prepare_for_reset(eth);
-       /* stop all devices to make sure that dma is properly shut down */
-       for (i = 0; i < MTK_MAC_COUNT; i++) {
-@@ -3668,6 +3673,8 @@ static void mtk_pending_work(struct work
-       clear_bit(MTK_RESETTING, &eth->state);
-+      mtk_wed_fe_reset_complete();
-+
-       rtnl_unlock();
- }
---- a/drivers/net/ethernet/mediatek/mtk_wed.c
-+++ b/drivers/net/ethernet/mediatek/mtk_wed.c
-@@ -205,6 +205,48 @@ mtk_wed_wo_reset(struct mtk_wed_device *
-       iounmap(reg);
- }
-+void mtk_wed_fe_reset(void)
-+{
-+      int i;
-+
-+      mutex_lock(&hw_lock);
-+
-+      for (i = 0; i < ARRAY_SIZE(hw_list); i++) {
-+              struct mtk_wed_hw *hw = hw_list[i];
-+              struct mtk_wed_device *dev = hw->wed_dev;
-+              int err;
-+
-+              if (!dev || !dev->wlan.reset)
-+                      continue;
-+
-+              /* reset callback blocks until WLAN reset is completed */
-+              err = dev->wlan.reset(dev);
-+              if (err)
-+                      dev_err(dev->dev, "wlan reset failed: %d\n", err);
-+      }
-+
-+      mutex_unlock(&hw_lock);
-+}
-+
-+void mtk_wed_fe_reset_complete(void)
-+{
-+      int i;
-+
-+      mutex_lock(&hw_lock);
-+
-+      for (i = 0; i < ARRAY_SIZE(hw_list); i++) {
-+              struct mtk_wed_hw *hw = hw_list[i];
-+              struct mtk_wed_device *dev = hw->wed_dev;
-+
-+              if (!dev || !dev->wlan.reset_complete)
-+                      continue;
-+
-+              dev->wlan.reset_complete(dev);
-+      }
-+
-+      mutex_unlock(&hw_lock);
-+}
-+
- static struct mtk_wed_hw *
- mtk_wed_assign(struct mtk_wed_device *dev)
- {
---- a/drivers/net/ethernet/mediatek/mtk_wed.h
-+++ b/drivers/net/ethernet/mediatek/mtk_wed.h
-@@ -128,6 +128,8 @@ void mtk_wed_add_hw(struct device_node *
- void mtk_wed_exit(void);
- int mtk_wed_flow_add(int index);
- void mtk_wed_flow_remove(int index);
-+void mtk_wed_fe_reset(void);
-+void mtk_wed_fe_reset_complete(void);
- #else
- static inline void
- mtk_wed_add_hw(struct device_node *np, struct mtk_eth *eth,
-@@ -147,6 +149,13 @@ static inline void mtk_wed_flow_remove(i
- {
- }
-+static inline void mtk_wed_fe_reset(void)
-+{
-+}
-+
-+static inline void mtk_wed_fe_reset_complete(void)
-+{
-+}
- #endif
- #ifdef CONFIG_DEBUG_FS
---- a/include/linux/soc/mediatek/mtk_wed.h
-+++ b/include/linux/soc/mediatek/mtk_wed.h
-@@ -151,6 +151,8 @@ struct mtk_wed_device {
-               void (*release_rx_buf)(struct mtk_wed_device *wed);
-               void (*update_wo_rx_stats)(struct mtk_wed_device *wed,
-                                          struct mtk_wed_wo_rx_stats *stats);
-+              int (*reset)(struct mtk_wed_device *wed);
-+              void (*reset_complete)(struct mtk_wed_device *wed);
-       } wlan;
- #endif
- };
diff --git a/target/linux/generic/backport-5.15/729-23-v6.3-net-ethernet-mtk_wed-add-reset-to-rx_ring_setup-call.patch b/target/linux/generic/backport-5.15/729-23-v6.3-net-ethernet-mtk_wed-add-reset-to-rx_ring_setup-call.patch
deleted file mode 100644 (file)
index c63628d..0000000
+++ /dev/null
@@ -1,106 +0,0 @@
-From: Lorenzo Bianconi <[email protected]>
-Date: Mon, 5 Dec 2022 12:34:42 +0100
-Subject: [PATCH] net: ethernet: mtk_wed: add reset to rx_ring_setup callback
-
-This patch adds reset parameter to mtk_wed_rx_ring_setup signature
-in order to align rx_ring_setup callback to tx_ring_setup one introduced
-in 'commit 23dca7a90017 ("net: ethernet: mtk_wed: add reset to
-tx_ring_setup callback")'
-
-Co-developed-by: Sujuan Chen <[email protected]>
-Signed-off-by: Sujuan Chen <[email protected]>
-Signed-off-by: Lorenzo Bianconi <[email protected]>
-Reviewed-by: Leon Romanovsky <[email protected]>
-Link: https://lore.kernel.org/r/29c6e7a5469e784406cf3e2920351d1207713d05.1670239984.git.lorenzo@kernel.org
-Signed-off-by: Jakub Kicinski <[email protected]>
----
-
---- a/drivers/net/ethernet/mediatek/mtk_wed.c
-+++ b/drivers/net/ethernet/mediatek/mtk_wed.c
-@@ -1252,7 +1252,8 @@ mtk_wed_wdma_rx_ring_setup(struct mtk_we
- }
- static int
--mtk_wed_wdma_tx_ring_setup(struct mtk_wed_device *dev, int idx, int size)
-+mtk_wed_wdma_tx_ring_setup(struct mtk_wed_device *dev, int idx, int size,
-+                         bool reset)
- {
-       u32 desc_size = sizeof(struct mtk_wdma_desc) * dev->hw->version;
-       struct mtk_wed_ring *wdma;
-@@ -1261,8 +1262,8 @@ mtk_wed_wdma_tx_ring_setup(struct mtk_we
-               return -EINVAL;
-       wdma = &dev->tx_wdma[idx];
--      if (mtk_wed_ring_alloc(dev, wdma, MTK_WED_WDMA_RING_SIZE, desc_size,
--                             true))
-+      if (!reset && mtk_wed_ring_alloc(dev, wdma, MTK_WED_WDMA_RING_SIZE,
-+                                       desc_size, true))
-               return -ENOMEM;
-       wdma_w32(dev, MTK_WDMA_RING_TX(idx) + MTK_WED_RING_OFS_BASE,
-@@ -1272,6 +1273,9 @@ mtk_wed_wdma_tx_ring_setup(struct mtk_we
-       wdma_w32(dev, MTK_WDMA_RING_TX(idx) + MTK_WED_RING_OFS_CPU_IDX, 0);
-       wdma_w32(dev, MTK_WDMA_RING_TX(idx) + MTK_WED_RING_OFS_DMA_IDX, 0);
-+      if (reset)
-+              mtk_wed_ring_reset(wdma, MTK_WED_WDMA_RING_SIZE, true);
-+
-       if (!idx)  {
-               wed_w32(dev, MTK_WED_WDMA_RING_TX + MTK_WED_RING_OFS_BASE,
-                       wdma->desc_phys);
-@@ -1611,18 +1615,20 @@ mtk_wed_txfree_ring_setup(struct mtk_wed
- }
- static int
--mtk_wed_rx_ring_setup(struct mtk_wed_device *dev, int idx, void __iomem *regs)
-+mtk_wed_rx_ring_setup(struct mtk_wed_device *dev, int idx, void __iomem *regs,
-+                    bool reset)
- {
-       struct mtk_wed_ring *ring = &dev->rx_ring[idx];
-       if (WARN_ON(idx >= ARRAY_SIZE(dev->rx_ring)))
-               return -EINVAL;
--      if (mtk_wed_ring_alloc(dev, ring, MTK_WED_RX_RING_SIZE,
--                             sizeof(*ring->desc), false))
-+      if (!reset && mtk_wed_ring_alloc(dev, ring, MTK_WED_RX_RING_SIZE,
-+                                       sizeof(*ring->desc), false))
-               return -ENOMEM;
--      if (mtk_wed_wdma_tx_ring_setup(dev, idx, MTK_WED_WDMA_RING_SIZE))
-+      if (mtk_wed_wdma_tx_ring_setup(dev, idx, MTK_WED_WDMA_RING_SIZE,
-+                                     reset))
-               return -ENOMEM;
-       ring->reg_base = MTK_WED_RING_RX_DATA(idx);
---- a/include/linux/soc/mediatek/mtk_wed.h
-+++ b/include/linux/soc/mediatek/mtk_wed.h
-@@ -162,7 +162,7 @@ struct mtk_wed_ops {
-       int (*tx_ring_setup)(struct mtk_wed_device *dev, int ring,
-                            void __iomem *regs, bool reset);
-       int (*rx_ring_setup)(struct mtk_wed_device *dev, int ring,
--                           void __iomem *regs);
-+                           void __iomem *regs, bool reset);
-       int (*txfree_ring_setup)(struct mtk_wed_device *dev,
-                                void __iomem *regs);
-       int (*msg_update)(struct mtk_wed_device *dev, int cmd_id,
-@@ -230,8 +230,8 @@ mtk_wed_get_rx_capa(struct mtk_wed_devic
-       (_dev)->ops->irq_get(_dev, _mask)
- #define mtk_wed_device_irq_set_mask(_dev, _mask) \
-       (_dev)->ops->irq_set_mask(_dev, _mask)
--#define mtk_wed_device_rx_ring_setup(_dev, _ring, _regs) \
--      (_dev)->ops->rx_ring_setup(_dev, _ring, _regs)
-+#define mtk_wed_device_rx_ring_setup(_dev, _ring, _regs, _reset) \
-+      (_dev)->ops->rx_ring_setup(_dev, _ring, _regs, _reset)
- #define mtk_wed_device_ppe_check(_dev, _skb, _reason, _hash) \
-       (_dev)->ops->ppe_check(_dev, _skb, _reason, _hash)
- #define mtk_wed_device_update_msg(_dev, _id, _msg, _len) \
-@@ -251,7 +251,7 @@ static inline bool mtk_wed_device_active
- #define mtk_wed_device_reg_write(_dev, _reg, _val) do {} while (0)
- #define mtk_wed_device_irq_get(_dev, _mask) 0
- #define mtk_wed_device_irq_set_mask(_dev, _mask) do {} while (0)
--#define mtk_wed_device_rx_ring_setup(_dev, _ring, _regs) -ENODEV
-+#define mtk_wed_device_rx_ring_setup(_dev, _ring, _regs, _reset) -ENODEV
- #define mtk_wed_device_ppe_check(_dev, _skb, _reason, _hash)  do {} while (0)
- #define mtk_wed_device_update_msg(_dev, _id, _msg, _len) -ENODEV
- #define mtk_wed_device_stop(_dev) do {} while (0)
diff --git a/target/linux/generic/backport-5.15/730-01-v6.3-net-ethernet-mtk_eth_soc-account-for-vlan-in-rx-head.patch b/target/linux/generic/backport-5.15/730-01-v6.3-net-ethernet-mtk_eth_soc-account-for-vlan-in-rx-head.patch
deleted file mode 100644 (file)
index 45af898..0000000
+++ /dev/null
@@ -1,22 +0,0 @@
-From: Felix Fietkau <[email protected]>
-Date: Thu, 27 Oct 2022 19:50:31 +0200
-Subject: [PATCH] net: ethernet: mtk_eth_soc: account for vlan in rx
- header length
-
-The network stack assumes that devices can handle an extra VLAN tag without
-increasing the MTU
-
-Signed-off-by: Felix Fietkau <[email protected]>
----
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-@@ -29,7 +29,7 @@
- #define MTK_TX_DMA_BUF_LEN_V2 0xffff
- #define MTK_DMA_SIZE          512
- #define MTK_MAC_COUNT         2
--#define MTK_RX_ETH_HLEN               (ETH_HLEN + ETH_FCS_LEN)
-+#define MTK_RX_ETH_HLEN               (VLAN_ETH_HLEN + ETH_FCS_LEN)
- #define MTK_RX_HLEN           (NET_SKB_PAD + MTK_RX_ETH_HLEN + NET_IP_ALIGN)
- #define MTK_DMA_DUMMY_DESC    0xffffffff
- #define MTK_DEFAULT_MSG_ENABLE        (NETIF_MSG_DRV | \
diff --git a/target/linux/generic/backport-5.15/730-02-v6.3-net-ethernet-mtk_eth_soc-increase-tx-ring-side-for-Q.patch b/target/linux/generic/backport-5.15/730-02-v6.3-net-ethernet-mtk_eth_soc-increase-tx-ring-side-for-Q.patch
deleted file mode 100644 (file)
index 908b2d8..0000000
+++ /dev/null
@@ -1,143 +0,0 @@
-From: Felix Fietkau <[email protected]>
-Date: Thu, 27 Oct 2022 19:53:57 +0200
-Subject: [PATCH] net: ethernet: mtk_eth_soc: increase tx ring side for
- QDMA devices
-
-In order to use the hardware traffic shaper feature, a larger tx ring is
-needed, especially for the scratch ring, which the hardware shaper uses to
-reorder packets.
-
-Signed-off-by: Felix Fietkau <[email protected]>
----
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-@@ -900,7 +900,7 @@ static int mtk_init_fq_dma(struct mtk_et
- {
-       const struct mtk_soc_data *soc = eth->soc;
-       dma_addr_t phy_ring_tail;
--      int cnt = MTK_DMA_SIZE;
-+      int cnt = MTK_QDMA_RING_SIZE;
-       dma_addr_t dma_addr;
-       int i;
-@@ -2154,19 +2154,25 @@ static int mtk_tx_alloc(struct mtk_eth *
-       struct mtk_tx_ring *ring = &eth->tx_ring;
-       int i, sz = soc->txrx.txd_size;
-       struct mtk_tx_dma_v2 *txd;
-+      int ring_size;
--      ring->buf = kcalloc(MTK_DMA_SIZE, sizeof(*ring->buf),
-+      if (MTK_HAS_CAPS(soc->caps, MTK_QDMA))
-+              ring_size = MTK_QDMA_RING_SIZE;
-+      else
-+              ring_size = MTK_DMA_SIZE;
-+
-+      ring->buf = kcalloc(ring_size, sizeof(*ring->buf),
-                              GFP_KERNEL);
-       if (!ring->buf)
-               goto no_tx_mem;
--      ring->dma = dma_alloc_coherent(eth->dma_dev, MTK_DMA_SIZE * sz,
-+      ring->dma = dma_alloc_coherent(eth->dma_dev, ring_size * sz,
-                                      &ring->phys, GFP_KERNEL);
-       if (!ring->dma)
-               goto no_tx_mem;
--      for (i = 0; i < MTK_DMA_SIZE; i++) {
--              int next = (i + 1) % MTK_DMA_SIZE;
-+      for (i = 0; i < ring_size; i++) {
-+              int next = (i + 1) % ring_size;
-               u32 next_ptr = ring->phys + next * sz;
-               txd = ring->dma + i * sz;
-@@ -2186,22 +2192,22 @@ static int mtk_tx_alloc(struct mtk_eth *
-        * descriptors in ring->dma_pdma.
-        */
-       if (!MTK_HAS_CAPS(soc->caps, MTK_QDMA)) {
--              ring->dma_pdma = dma_alloc_coherent(eth->dma_dev, MTK_DMA_SIZE * sz,
-+              ring->dma_pdma = dma_alloc_coherent(eth->dma_dev, ring_size * sz,
-                                                   &ring->phys_pdma, GFP_KERNEL);
-               if (!ring->dma_pdma)
-                       goto no_tx_mem;
--              for (i = 0; i < MTK_DMA_SIZE; i++) {
-+              for (i = 0; i < ring_size; i++) {
-                       ring->dma_pdma[i].txd2 = TX_DMA_DESP2_DEF;
-                       ring->dma_pdma[i].txd4 = 0;
-               }
-       }
--      ring->dma_size = MTK_DMA_SIZE;
--      atomic_set(&ring->free_count, MTK_DMA_SIZE - 2);
-+      ring->dma_size = ring_size;
-+      atomic_set(&ring->free_count, ring_size - 2);
-       ring->next_free = ring->dma;
-       ring->last_free = (void *)txd;
--      ring->last_free_ptr = (u32)(ring->phys + ((MTK_DMA_SIZE - 1) * sz));
-+      ring->last_free_ptr = (u32)(ring->phys + ((ring_size - 1) * sz));
-       ring->thresh = MAX_SKB_FRAGS;
-       /* make sure that all changes to the dma ring are flushed before we
-@@ -2213,14 +2219,14 @@ static int mtk_tx_alloc(struct mtk_eth *
-               mtk_w32(eth, ring->phys, soc->reg_map->qdma.ctx_ptr);
-               mtk_w32(eth, ring->phys, soc->reg_map->qdma.dtx_ptr);
-               mtk_w32(eth,
--                      ring->phys + ((MTK_DMA_SIZE - 1) * sz),
-+                      ring->phys + ((ring_size - 1) * sz),
-                       soc->reg_map->qdma.crx_ptr);
-               mtk_w32(eth, ring->last_free_ptr, soc->reg_map->qdma.drx_ptr);
-               mtk_w32(eth, (QDMA_RES_THRES << 8) | QDMA_RES_THRES,
-                       soc->reg_map->qdma.qtx_cfg);
-       } else {
-               mtk_w32(eth, ring->phys_pdma, MT7628_TX_BASE_PTR0);
--              mtk_w32(eth, MTK_DMA_SIZE, MT7628_TX_MAX_CNT0);
-+              mtk_w32(eth, ring_size, MT7628_TX_MAX_CNT0);
-               mtk_w32(eth, 0, MT7628_TX_CTX_IDX0);
-               mtk_w32(eth, MT7628_PST_DTX_IDX0, soc->reg_map->pdma.rst_idx);
-       }
-@@ -2238,7 +2244,7 @@ static void mtk_tx_clean(struct mtk_eth
-       int i;
-       if (ring->buf) {
--              for (i = 0; i < MTK_DMA_SIZE; i++)
-+              for (i = 0; i < ring->dma_size; i++)
-                       mtk_tx_unmap(eth, &ring->buf[i], false);
-               kfree(ring->buf);
-               ring->buf = NULL;
-@@ -2246,14 +2252,14 @@ static void mtk_tx_clean(struct mtk_eth
-       if (ring->dma) {
-               dma_free_coherent(eth->dma_dev,
--                                MTK_DMA_SIZE * soc->txrx.txd_size,
-+                                ring->dma_size * soc->txrx.txd_size,
-                                 ring->dma, ring->phys);
-               ring->dma = NULL;
-       }
-       if (ring->dma_pdma) {
-               dma_free_coherent(eth->dma_dev,
--                                MTK_DMA_SIZE * soc->txrx.txd_size,
-+                                ring->dma_size * soc->txrx.txd_size,
-                                 ring->dma_pdma, ring->phys_pdma);
-               ring->dma_pdma = NULL;
-       }
-@@ -2776,7 +2782,7 @@ static void mtk_dma_free(struct mtk_eth
-                       netdev_reset_queue(eth->netdev[i]);
-       if (eth->scratch_ring) {
-               dma_free_coherent(eth->dma_dev,
--                                MTK_DMA_SIZE * soc->txrx.txd_size,
-+                                MTK_QDMA_RING_SIZE * soc->txrx.txd_size,
-                                 eth->scratch_ring, eth->phy_scratch_ring);
-               eth->scratch_ring = NULL;
-               eth->phy_scratch_ring = 0;
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-@@ -27,6 +27,7 @@
- #define MTK_MAX_RX_LENGTH_2K  2048
- #define MTK_TX_DMA_BUF_LEN    0x3fff
- #define MTK_TX_DMA_BUF_LEN_V2 0xffff
-+#define MTK_QDMA_RING_SIZE    2048
- #define MTK_DMA_SIZE          512
- #define MTK_MAC_COUNT         2
- #define MTK_RX_ETH_HLEN               (VLAN_ETH_HLEN + ETH_FCS_LEN)
diff --git a/target/linux/generic/backport-5.15/730-03-v6.3-net-ethernet-mtk_eth_soc-avoid-port_mg-assignment-on.patch b/target/linux/generic/backport-5.15/730-03-v6.3-net-ethernet-mtk_eth_soc-avoid-port_mg-assignment-on.patch
deleted file mode 100644 (file)
index 34aa7b1..0000000
+++ /dev/null
@@ -1,52 +0,0 @@
-From: Felix Fietkau <[email protected]>
-Date: Fri, 4 Nov 2022 19:49:08 +0100
-Subject: [PATCH] net: ethernet: mtk_eth_soc: avoid port_mg assignment on
- MT7622 and newer
-
-On newer chips, this field is unused and contains some bits related to queue
-assignment. Initialize it to 0 in those cases.
-Fix offload_version on MT7621 and MT7623, which still need the previous value.
-
-Signed-off-by: Felix Fietkau <[email protected]>
----
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-@@ -4424,7 +4424,7 @@ static const struct mtk_soc_data mt7621_
-       .hw_features = MTK_HW_FEATURES,
-       .required_clks = MT7621_CLKS_BITMAP,
-       .required_pctl = false,
--      .offload_version = 2,
-+      .offload_version = 1,
-       .hash_offset = 2,
-       .foe_entry_size = sizeof(struct mtk_foe_entry) - 16,
-       .txrx = {
-@@ -4463,7 +4463,7 @@ static const struct mtk_soc_data mt7623_
-       .hw_features = MTK_HW_FEATURES,
-       .required_clks = MT7623_CLKS_BITMAP,
-       .required_pctl = true,
--      .offload_version = 2,
-+      .offload_version = 1,
-       .hash_offset = 2,
-       .foe_entry_size = sizeof(struct mtk_foe_entry) - 16,
-       .txrx = {
---- a/drivers/net/ethernet/mediatek/mtk_ppe.c
-+++ b/drivers/net/ethernet/mediatek/mtk_ppe.c
-@@ -175,6 +175,8 @@ int mtk_foe_entry_prepare(struct mtk_eth
-               val = FIELD_PREP(MTK_FOE_IB2_DEST_PORT_V2, pse_port) |
-                     FIELD_PREP(MTK_FOE_IB2_PORT_AG_V2, 0xf);
-       } else {
-+              int port_mg = eth->soc->offload_version > 1 ? 0 : 0x3f;
-+
-               val = FIELD_PREP(MTK_FOE_IB1_STATE, MTK_FOE_STATE_BIND) |
-                     FIELD_PREP(MTK_FOE_IB1_PACKET_TYPE, type) |
-                     FIELD_PREP(MTK_FOE_IB1_UDP, l4proto == IPPROTO_UDP) |
-@@ -182,7 +184,7 @@ int mtk_foe_entry_prepare(struct mtk_eth
-               entry->ib1 = val;
-               val = FIELD_PREP(MTK_FOE_IB2_DEST_PORT, pse_port) |
--                    FIELD_PREP(MTK_FOE_IB2_PORT_MG, 0x3f) |
-+                    FIELD_PREP(MTK_FOE_IB2_PORT_MG, port_mg) |
-                     FIELD_PREP(MTK_FOE_IB2_PORT_AG, 0x1f);
-       }
diff --git a/target/linux/generic/backport-5.15/730-04-v6.3-net-ethernet-mtk_eth_soc-implement-multi-queue-suppo.patch b/target/linux/generic/backport-5.15/730-04-v6.3-net-ethernet-mtk_eth_soc-implement-multi-queue-suppo.patch
deleted file mode 100644 (file)
index 7656666..0000000
+++ /dev/null
@@ -1,654 +0,0 @@
-From: Felix Fietkau <[email protected]>
-Date: Thu, 27 Oct 2022 20:17:27 +0200
-Subject: [PATCH] net: ethernet: mtk_eth_soc: implement multi-queue
- support for per-port queues
-
-When sending traffic to multiple ports with different link speeds, queued
-packets to one port can drown out tx to other ports.
-In order to better handle transmission to multiple ports, use the hardware
-shaper feature to implement weighted fair queueing between ports.
-Weight and maximum rate are automatically adjusted based on the link speed
-of the port.
-The first 3 queues are unrestricted and reserved for non-DSA direct tx on
-GMAC ports. The following queues are automatically assigned by the MTK DSA
-tag driver based on the target port number.
-The PPE offload code configures the queues for offloaded traffic in the same
-way.
-This feature is only supported on devices supporting QDMA. All queues still
-share the same DMA ring and descriptor pool.
-
-Signed-off-by: Felix Fietkau <[email protected]>
----
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-@@ -55,6 +55,7 @@ static const struct mtk_reg_map mtk_reg_
-       },
-       .qdma = {
-               .qtx_cfg        = 0x1800,
-+              .qtx_sch        = 0x1804,
-               .rx_ptr         = 0x1900,
-               .rx_cnt_cfg     = 0x1904,
-               .qcrx_ptr       = 0x1908,
-@@ -62,6 +63,7 @@ static const struct mtk_reg_map mtk_reg_
-               .rst_idx        = 0x1a08,
-               .delay_irq      = 0x1a0c,
-               .fc_th          = 0x1a10,
-+              .tx_sch_rate    = 0x1a14,
-               .int_grp        = 0x1a20,
-               .hred           = 0x1a44,
-               .ctx_ptr        = 0x1b00,
-@@ -117,6 +119,7 @@ static const struct mtk_reg_map mt7986_r
-       },
-       .qdma = {
-               .qtx_cfg        = 0x4400,
-+              .qtx_sch        = 0x4404,
-               .rx_ptr         = 0x4500,
-               .rx_cnt_cfg     = 0x4504,
-               .qcrx_ptr       = 0x4508,
-@@ -134,6 +137,7 @@ static const struct mtk_reg_map mt7986_r
-               .fq_tail        = 0x4724,
-               .fq_count       = 0x4728,
-               .fq_blen        = 0x472c,
-+              .tx_sch_rate    = 0x4798,
-       },
-       .gdm1_cnt               = 0x1c00,
-       .gdma_to_ppe0           = 0x3333,
-@@ -576,6 +580,75 @@ static void mtk_mac_link_down(struct phy
-       mtk_w32(mac->hw, mcr, MTK_MAC_MCR(mac->id));
- }
-+static void mtk_set_queue_speed(struct mtk_eth *eth, unsigned int idx,
-+                              int speed)
-+{
-+      const struct mtk_soc_data *soc = eth->soc;
-+      u32 ofs, val;
-+
-+      if (!MTK_HAS_CAPS(soc->caps, MTK_QDMA))
-+              return;
-+
-+      val = MTK_QTX_SCH_MIN_RATE_EN |
-+            /* minimum: 10 Mbps */
-+            FIELD_PREP(MTK_QTX_SCH_MIN_RATE_MAN, 1) |
-+            FIELD_PREP(MTK_QTX_SCH_MIN_RATE_EXP, 4) |
-+            MTK_QTX_SCH_LEAKY_BUCKET_SIZE;
-+      if (!MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2))
-+              val |= MTK_QTX_SCH_LEAKY_BUCKET_EN;
-+
-+      if (IS_ENABLED(CONFIG_SOC_MT7621)) {
-+              switch (speed) {
-+              case SPEED_10:
-+                      val |= MTK_QTX_SCH_MAX_RATE_EN |
-+                             FIELD_PREP(MTK_QTX_SCH_MAX_RATE_MAN, 103) |
-+                             FIELD_PREP(MTK_QTX_SCH_MAX_RATE_EXP, 2) |
-+                             FIELD_PREP(MTK_QTX_SCH_MAX_RATE_WEIGHT, 1);
-+                      break;
-+              case SPEED_100:
-+                      val |= MTK_QTX_SCH_MAX_RATE_EN |
-+                             FIELD_PREP(MTK_QTX_SCH_MAX_RATE_MAN, 103) |
-+                             FIELD_PREP(MTK_QTX_SCH_MAX_RATE_EXP, 3);
-+                             FIELD_PREP(MTK_QTX_SCH_MAX_RATE_WEIGHT, 1);
-+                      break;
-+              case SPEED_1000:
-+                      val |= MTK_QTX_SCH_MAX_RATE_EN |
-+                             FIELD_PREP(MTK_QTX_SCH_MAX_RATE_MAN, 105) |
-+                             FIELD_PREP(MTK_QTX_SCH_MAX_RATE_EXP, 4) |
-+                             FIELD_PREP(MTK_QTX_SCH_MAX_RATE_WEIGHT, 10);
-+                      break;
-+              default:
-+                      break;
-+              }
-+      } else {
-+              switch (speed) {
-+              case SPEED_10:
-+                      val |= MTK_QTX_SCH_MAX_RATE_EN |
-+                             FIELD_PREP(MTK_QTX_SCH_MAX_RATE_MAN, 1) |
-+                             FIELD_PREP(MTK_QTX_SCH_MAX_RATE_EXP, 4) |
-+                             FIELD_PREP(MTK_QTX_SCH_MAX_RATE_WEIGHT, 1);
-+                      break;
-+              case SPEED_100:
-+                      val |= MTK_QTX_SCH_MAX_RATE_EN |
-+                             FIELD_PREP(MTK_QTX_SCH_MAX_RATE_MAN, 1) |
-+                             FIELD_PREP(MTK_QTX_SCH_MAX_RATE_EXP, 5);
-+                             FIELD_PREP(MTK_QTX_SCH_MAX_RATE_WEIGHT, 1);
-+                      break;
-+              case SPEED_1000:
-+                      val |= MTK_QTX_SCH_MAX_RATE_EN |
-+                             FIELD_PREP(MTK_QTX_SCH_MAX_RATE_MAN, 10) |
-+                             FIELD_PREP(MTK_QTX_SCH_MAX_RATE_EXP, 5) |
-+                             FIELD_PREP(MTK_QTX_SCH_MAX_RATE_WEIGHT, 10);
-+                      break;
-+              default:
-+                      break;
-+              }
-+      }
-+
-+      ofs = MTK_QTX_OFFSET * idx;
-+      mtk_w32(eth, val, soc->reg_map->qdma.qtx_sch + ofs);
-+}
-+
- static void mtk_mac_link_up(struct phylink_config *config,
-                           struct phy_device *phy,
-                           unsigned int mode, phy_interface_t interface,
-@@ -601,6 +674,8 @@ static void mtk_mac_link_up(struct phyli
-               break;
-       }
-+      mtk_set_queue_speed(mac->hw, mac->id, speed);
-+
-       /* Configure duplex */
-       if (duplex == DUPLEX_FULL)
-               mcr |= MAC_MCR_FORCE_DPX;
-@@ -1059,7 +1134,8 @@ static void mtk_tx_set_dma_desc_v1(struc
-       WRITE_ONCE(desc->txd1, info->addr);
--      data = TX_DMA_SWC | TX_DMA_PLEN0(info->size);
-+      data = TX_DMA_SWC | TX_DMA_PLEN0(info->size) |
-+             FIELD_PREP(TX_DMA_PQID, info->qid);
-       if (info->last)
-               data |= TX_DMA_LS0;
-       WRITE_ONCE(desc->txd3, data);
-@@ -1093,9 +1169,6 @@ static void mtk_tx_set_dma_desc_v2(struc
-               data |= TX_DMA_LS0;
-       WRITE_ONCE(desc->txd3, data);
--      if (!info->qid && mac->id)
--              info->qid = MTK_QDMA_GMAC2_QID;
--
-       data = (mac->id + 1) << TX_DMA_FPORT_SHIFT_V2; /* forward port */
-       data |= TX_DMA_SWC_V2 | QID_BITS_V2(info->qid);
-       WRITE_ONCE(desc->txd4, data);
-@@ -1139,11 +1212,12 @@ static int mtk_tx_map(struct sk_buff *sk
-               .gso = gso,
-               .csum = skb->ip_summed == CHECKSUM_PARTIAL,
-               .vlan = skb_vlan_tag_present(skb),
--              .qid = skb->mark & MTK_QDMA_TX_MASK,
-+              .qid = skb_get_queue_mapping(skb),
-               .vlan_tci = skb_vlan_tag_get(skb),
-               .first = true,
-               .last = !skb_is_nonlinear(skb),
-       };
-+      struct netdev_queue *txq;
-       struct mtk_mac *mac = netdev_priv(dev);
-       struct mtk_eth *eth = mac->hw;
-       const struct mtk_soc_data *soc = eth->soc;
-@@ -1151,8 +1225,10 @@ static int mtk_tx_map(struct sk_buff *sk
-       struct mtk_tx_dma *itxd_pdma, *txd_pdma;
-       struct mtk_tx_buf *itx_buf, *tx_buf;
-       int i, n_desc = 1;
-+      int queue = skb_get_queue_mapping(skb);
-       int k = 0;
-+      txq = netdev_get_tx_queue(dev, queue);
-       itxd = ring->next_free;
-       itxd_pdma = qdma_to_pdma(ring, itxd);
-       if (itxd == ring->last_free)
-@@ -1201,7 +1277,7 @@ static int mtk_tx_map(struct sk_buff *sk
-                       memset(&txd_info, 0, sizeof(struct mtk_tx_dma_desc_info));
-                       txd_info.size = min_t(unsigned int, frag_size,
-                                             soc->txrx.dma_max_len);
--                      txd_info.qid = skb->mark & MTK_QDMA_TX_MASK;
-+                      txd_info.qid = queue;
-                       txd_info.last = i == skb_shinfo(skb)->nr_frags - 1 &&
-                                       !(frag_size - txd_info.size);
-                       txd_info.addr = skb_frag_dma_map(eth->dma_dev, frag,
-@@ -1240,7 +1316,7 @@ static int mtk_tx_map(struct sk_buff *sk
-                       txd_pdma->txd2 |= TX_DMA_LS1;
-       }
--      netdev_sent_queue(dev, skb->len);
-+      netdev_tx_sent_queue(txq, skb->len);
-       skb_tx_timestamp(skb);
-       ring->next_free = mtk_qdma_phys_to_virt(ring, txd->txd2);
-@@ -1252,8 +1328,7 @@ static int mtk_tx_map(struct sk_buff *sk
-       wmb();
-       if (MTK_HAS_CAPS(soc->caps, MTK_QDMA)) {
--              if (netif_xmit_stopped(netdev_get_tx_queue(dev, 0)) ||
--                  !netdev_xmit_more())
-+              if (netif_xmit_stopped(txq) || !netdev_xmit_more())
-                       mtk_w32(eth, txd->txd2, soc->reg_map->qdma.ctx_ptr);
-       } else {
-               int next_idx;
-@@ -1322,7 +1397,7 @@ static void mtk_wake_queue(struct mtk_et
-       for (i = 0; i < MTK_MAC_COUNT; i++) {
-               if (!eth->netdev[i])
-                       continue;
--              netif_wake_queue(eth->netdev[i]);
-+              netif_tx_wake_all_queues(eth->netdev[i]);
-       }
- }
-@@ -1346,7 +1421,7 @@ static netdev_tx_t mtk_start_xmit(struct
-       tx_num = mtk_cal_txd_req(eth, skb);
-       if (unlikely(atomic_read(&ring->free_count) <= tx_num)) {
--              netif_stop_queue(dev);
-+              netif_tx_stop_all_queues(dev);
-               netif_err(eth, tx_queued, dev,
-                         "Tx Ring full when queue awake!\n");
-               spin_unlock(&eth->page_lock);
-@@ -1372,7 +1447,7 @@ static netdev_tx_t mtk_start_xmit(struct
-               goto drop;
-       if (unlikely(atomic_read(&ring->free_count) <= ring->thresh))
--              netif_stop_queue(dev);
-+              netif_tx_stop_all_queues(dev);
-       spin_unlock(&eth->page_lock);
-@@ -1539,10 +1614,12 @@ static int mtk_xdp_submit_frame(struct m
-       struct skb_shared_info *sinfo = xdp_get_shared_info_from_frame(xdpf);
-       const struct mtk_soc_data *soc = eth->soc;
-       struct mtk_tx_ring *ring = &eth->tx_ring;
-+      struct mtk_mac *mac = netdev_priv(dev);
-       struct mtk_tx_dma_desc_info txd_info = {
-               .size   = xdpf->len,
-               .first  = true,
-               .last   = !xdp_frame_has_frags(xdpf),
-+              .qid    = mac->id,
-       };
-       int err, index = 0, n_desc = 1, nr_frags;
-       struct mtk_tx_dma *htxd, *txd, *txd_pdma;
-@@ -1593,6 +1670,7 @@ static int mtk_xdp_submit_frame(struct m
-               memset(&txd_info, 0, sizeof(struct mtk_tx_dma_desc_info));
-               txd_info.size = skb_frag_size(&sinfo->frags[index]);
-               txd_info.last = index + 1 == nr_frags;
-+              txd_info.qid = mac->id;
-               data = skb_frag_address(&sinfo->frags[index]);
-               index++;
-@@ -1944,8 +2022,46 @@ rx_done:
-       return done;
- }
-+struct mtk_poll_state {
-+    struct netdev_queue *txq;
-+    unsigned int total;
-+    unsigned int done;
-+    unsigned int bytes;
-+};
-+
-+static void
-+mtk_poll_tx_done(struct mtk_eth *eth, struct mtk_poll_state *state, u8 mac,
-+               struct sk_buff *skb)
-+{
-+      struct netdev_queue *txq;
-+      struct net_device *dev;
-+      unsigned int bytes = skb->len;
-+
-+      state->total++;
-+      eth->tx_packets++;
-+      eth->tx_bytes += bytes;
-+
-+      dev = eth->netdev[mac];
-+      if (!dev)
-+              return;
-+
-+      txq = netdev_get_tx_queue(dev, skb_get_queue_mapping(skb));
-+      if (state->txq == txq) {
-+              state->done++;
-+              state->bytes += bytes;
-+              return;
-+      }
-+
-+      if (state->txq)
-+              netdev_tx_completed_queue(state->txq, state->done, state->bytes);
-+
-+      state->txq = txq;
-+      state->done = 1;
-+      state->bytes = bytes;
-+}
-+
- static int mtk_poll_tx_qdma(struct mtk_eth *eth, int budget,
--                          unsigned int *done, unsigned int *bytes)
-+                          struct mtk_poll_state *state)
- {
-       const struct mtk_reg_map *reg_map = eth->soc->reg_map;
-       struct mtk_tx_ring *ring = &eth->tx_ring;
-@@ -1975,12 +2091,9 @@ static int mtk_poll_tx_qdma(struct mtk_e
-                       break;
-               if (tx_buf->data != (void *)MTK_DMA_DUMMY_DESC) {
--                      if (tx_buf->type == MTK_TYPE_SKB) {
--                              struct sk_buff *skb = tx_buf->data;
-+                      if (tx_buf->type == MTK_TYPE_SKB)
-+                              mtk_poll_tx_done(eth, state, mac, tx_buf->data);
--                              bytes[mac] += skb->len;
--                              done[mac]++;
--                      }
-                       budget--;
-               }
-               mtk_tx_unmap(eth, tx_buf, true);
-@@ -1998,7 +2111,7 @@ static int mtk_poll_tx_qdma(struct mtk_e
- }
- static int mtk_poll_tx_pdma(struct mtk_eth *eth, int budget,
--                          unsigned int *done, unsigned int *bytes)
-+                          struct mtk_poll_state *state)
- {
-       struct mtk_tx_ring *ring = &eth->tx_ring;
-       struct mtk_tx_buf *tx_buf;
-@@ -2014,12 +2127,8 @@ static int mtk_poll_tx_pdma(struct mtk_e
-                       break;
-               if (tx_buf->data != (void *)MTK_DMA_DUMMY_DESC) {
--                      if (tx_buf->type == MTK_TYPE_SKB) {
--                              struct sk_buff *skb = tx_buf->data;
--
--                              bytes[0] += skb->len;
--                              done[0]++;
--                      }
-+                      if (tx_buf->type == MTK_TYPE_SKB)
-+                              mtk_poll_tx_done(eth, state, 0, tx_buf->data);
-                       budget--;
-               }
-               mtk_tx_unmap(eth, tx_buf, true);
-@@ -2040,26 +2149,15 @@ static int mtk_poll_tx(struct mtk_eth *e
- {
-       struct mtk_tx_ring *ring = &eth->tx_ring;
-       struct dim_sample dim_sample = {};
--      unsigned int done[MTK_MAX_DEVS];
--      unsigned int bytes[MTK_MAX_DEVS];
--      int total = 0, i;
--
--      memset(done, 0, sizeof(done));
--      memset(bytes, 0, sizeof(bytes));
-+      struct mtk_poll_state state = {};
-       if (MTK_HAS_CAPS(eth->soc->caps, MTK_QDMA))
--              budget = mtk_poll_tx_qdma(eth, budget, done, bytes);
-+              budget = mtk_poll_tx_qdma(eth, budget, &state);
-       else
--              budget = mtk_poll_tx_pdma(eth, budget, done, bytes);
-+              budget = mtk_poll_tx_pdma(eth, budget, &state);
--      for (i = 0; i < MTK_MAC_COUNT; i++) {
--              if (!eth->netdev[i] || !done[i])
--                      continue;
--              netdev_completed_queue(eth->netdev[i], done[i], bytes[i]);
--              total += done[i];
--              eth->tx_packets += done[i];
--              eth->tx_bytes += bytes[i];
--      }
-+      if (state.txq)
-+              netdev_tx_completed_queue(state.txq, state.done, state.bytes);
-       dim_update_sample(eth->tx_events, eth->tx_packets, eth->tx_bytes,
-                         &dim_sample);
-@@ -2069,7 +2167,7 @@ static int mtk_poll_tx(struct mtk_eth *e
-           (atomic_read(&ring->free_count) > ring->thresh))
-               mtk_wake_queue(eth);
--      return total;
-+      return state.total;
- }
- static void mtk_handle_status_irq(struct mtk_eth *eth)
-@@ -2155,6 +2253,7 @@ static int mtk_tx_alloc(struct mtk_eth *
-       int i, sz = soc->txrx.txd_size;
-       struct mtk_tx_dma_v2 *txd;
-       int ring_size;
-+      u32 ofs, val;
-       if (MTK_HAS_CAPS(soc->caps, MTK_QDMA))
-               ring_size = MTK_QDMA_RING_SIZE;
-@@ -2222,8 +2321,25 @@ static int mtk_tx_alloc(struct mtk_eth *
-                       ring->phys + ((ring_size - 1) * sz),
-                       soc->reg_map->qdma.crx_ptr);
-               mtk_w32(eth, ring->last_free_ptr, soc->reg_map->qdma.drx_ptr);
--              mtk_w32(eth, (QDMA_RES_THRES << 8) | QDMA_RES_THRES,
--                      soc->reg_map->qdma.qtx_cfg);
-+
-+              for (i = 0, ofs = 0; i < MTK_QDMA_NUM_QUEUES; i++) {
-+                      val = (QDMA_RES_THRES << 8) | QDMA_RES_THRES;
-+                      mtk_w32(eth, val, soc->reg_map->qdma.qtx_cfg + ofs);
-+
-+                      val = MTK_QTX_SCH_MIN_RATE_EN |
-+                            /* minimum: 10 Mbps */
-+                            FIELD_PREP(MTK_QTX_SCH_MIN_RATE_MAN, 1) |
-+                            FIELD_PREP(MTK_QTX_SCH_MIN_RATE_EXP, 4) |
-+                            MTK_QTX_SCH_LEAKY_BUCKET_SIZE;
-+                      if (!MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2))
-+                              val |= MTK_QTX_SCH_LEAKY_BUCKET_EN;
-+                      mtk_w32(eth, val, soc->reg_map->qdma.qtx_sch + ofs);
-+                      ofs += MTK_QTX_OFFSET;
-+              }
-+              val = MTK_QDMA_TX_SCH_MAX_WFQ | (MTK_QDMA_TX_SCH_MAX_WFQ << 16);
-+              mtk_w32(eth, val, soc->reg_map->qdma.tx_sch_rate);
-+              if (MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2))
-+                      mtk_w32(eth, val, soc->reg_map->qdma.tx_sch_rate + 4);
-       } else {
-               mtk_w32(eth, ring->phys_pdma, MT7628_TX_BASE_PTR0);
-               mtk_w32(eth, ring_size, MT7628_TX_MAX_CNT0);
-@@ -2906,7 +3022,7 @@ static int mtk_start_dma(struct mtk_eth
-               if (MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2))
-                       val |= MTK_MUTLI_CNT | MTK_RESV_BUF |
-                              MTK_WCOMP_EN | MTK_DMAD_WR_WDONE |
--                             MTK_CHK_DDONE_EN;
-+                             MTK_CHK_DDONE_EN | MTK_LEAKY_BUCKET_EN;
-               else
-                       val |= MTK_RX_BT_32DWORDS;
-               mtk_w32(eth, val, reg_map->qdma.glo_cfg);
-@@ -2952,6 +3068,45 @@ static void mtk_gdm_config(struct mtk_et
-       mtk_w32(eth, 0, MTK_RST_GL);
- }
-+static int mtk_device_event(struct notifier_block *n, unsigned long event, void *ptr)
-+{
-+      struct mtk_mac *mac = container_of(n, struct mtk_mac, device_notifier);
-+      struct mtk_eth *eth = mac->hw;
-+      struct net_device *dev = netdev_notifier_info_to_dev(ptr);
-+      struct ethtool_link_ksettings s;
-+      struct net_device *ldev;
-+      struct list_head *iter;
-+      struct dsa_port *dp;
-+
-+      if (event != NETDEV_CHANGE)
-+              return NOTIFY_DONE;
-+
-+      netdev_for_each_lower_dev(dev, ldev, iter) {
-+              if (netdev_priv(ldev) == mac)
-+                      goto found;
-+      }
-+
-+      return NOTIFY_DONE;
-+
-+found:
-+      if (!dsa_slave_dev_check(dev))
-+              return NOTIFY_DONE;
-+
-+      if (__ethtool_get_link_ksettings(dev, &s))
-+              return NOTIFY_DONE;
-+
-+      if (s.base.speed == 0 || s.base.speed == ((__u32)-1))
-+              return NOTIFY_DONE;
-+
-+      dp = dsa_port_from_netdev(dev);
-+      if (dp->index >= MTK_QDMA_NUM_QUEUES)
-+              return NOTIFY_DONE;
-+
-+      mtk_set_queue_speed(eth, dp->index + 3, s.base.speed);
-+
-+      return NOTIFY_DONE;
-+}
-+
- static int mtk_open(struct net_device *dev)
- {
-       struct mtk_mac *mac = netdev_priv(dev);
-@@ -2996,7 +3151,8 @@ static int mtk_open(struct net_device *d
-               refcount_inc(&eth->dma_refcnt);
-       phylink_start(mac->phylink);
--      netif_start_queue(dev);
-+      netif_tx_start_all_queues(dev);
-+
-       return 0;
- }
-@@ -3702,8 +3858,12 @@ static int mtk_unreg_dev(struct mtk_eth
-       int i;
-       for (i = 0; i < MTK_MAC_COUNT; i++) {
-+              struct mtk_mac *mac;
-               if (!eth->netdev[i])
-                       continue;
-+              mac = netdev_priv(eth->netdev[i]);
-+              if (MTK_HAS_CAPS(eth->soc->caps, MTK_QDMA))
-+                      unregister_netdevice_notifier(&mac->device_notifier);
-               unregister_netdev(eth->netdev[i]);
-       }
-@@ -3920,6 +4080,23 @@ static int mtk_set_rxnfc(struct net_devi
-       return ret;
- }
-+static u16 mtk_select_queue(struct net_device *dev, struct sk_buff *skb,
-+                          struct net_device *sb_dev)
-+{
-+      struct mtk_mac *mac = netdev_priv(dev);
-+      unsigned int queue = 0;
-+
-+      if (netdev_uses_dsa(dev))
-+              queue = skb_get_queue_mapping(skb) + 3;
-+      else
-+              queue = mac->id;
-+
-+      if (queue >= dev->num_tx_queues)
-+              queue = 0;
-+
-+      return queue;
-+}
-+
- static const struct ethtool_ops mtk_ethtool_ops = {
-       .get_link_ksettings     = mtk_get_link_ksettings,
-       .set_link_ksettings     = mtk_set_link_ksettings,
-@@ -3954,6 +4131,7 @@ static const struct net_device_ops mtk_n
-       .ndo_setup_tc           = mtk_eth_setup_tc,
-       .ndo_bpf                = mtk_xdp,
-       .ndo_xdp_xmit           = mtk_xdp_xmit,
-+      .ndo_select_queue       = mtk_select_queue,
- };
- static int mtk_add_mac(struct mtk_eth *eth, struct device_node *np)
-@@ -3963,6 +4141,7 @@ static int mtk_add_mac(struct mtk_eth *e
-       struct phylink *phylink;
-       struct mtk_mac *mac;
-       int id, err;
-+      int txqs = 1;
-       if (!_id) {
-               dev_err(eth->dev, "missing mac id\n");
-@@ -3980,7 +4159,10 @@ static int mtk_add_mac(struct mtk_eth *e
-               return -EINVAL;
-       }
--      eth->netdev[id] = alloc_etherdev(sizeof(*mac));
-+      if (MTK_HAS_CAPS(eth->soc->caps, MTK_QDMA))
-+              txqs = MTK_QDMA_NUM_QUEUES;
-+
-+      eth->netdev[id] = alloc_etherdev_mqs(sizeof(*mac), txqs, 1);
-       if (!eth->netdev[id]) {
-               dev_err(eth->dev, "alloc_etherdev failed\n");
-               return -ENOMEM;
-@@ -4088,6 +4270,11 @@ static int mtk_add_mac(struct mtk_eth *e
-       else
-               eth->netdev[id]->max_mtu = MTK_MAX_RX_LENGTH_2K - MTK_RX_ETH_HLEN;
-+      if (MTK_HAS_CAPS(eth->soc->caps, MTK_QDMA)) {
-+              mac->device_notifier.notifier_call = mtk_device_event;
-+              register_netdevice_notifier(&mac->device_notifier);
-+      }
-+
-       return 0;
- free_netdev:
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-@@ -22,6 +22,7 @@
- #include <linux/bpf_trace.h>
- #include "mtk_ppe.h"
-+#define MTK_QDMA_NUM_QUEUES   16
- #define MTK_QDMA_PAGE_SIZE    2048
- #define MTK_MAX_RX_LENGTH     1536
- #define MTK_MAX_RX_LENGTH_2K  2048
-@@ -215,8 +216,26 @@
- #define MTK_RING_MAX_AGG_CNT_H                ((MTK_HW_LRO_MAX_AGG_CNT >> 6) & 0x3)
- /* QDMA TX Queue Configuration Registers */
-+#define MTK_QTX_OFFSET                0x10
- #define QDMA_RES_THRES                4
-+/* QDMA Tx Queue Scheduler Configuration Registers */
-+#define MTK_QTX_SCH_TX_SEL            BIT(31)
-+#define MTK_QTX_SCH_TX_SEL_V2         GENMASK(31, 30)
-+
-+#define MTK_QTX_SCH_LEAKY_BUCKET_EN   BIT(30)
-+#define MTK_QTX_SCH_LEAKY_BUCKET_SIZE GENMASK(29, 28)
-+#define MTK_QTX_SCH_MIN_RATE_EN               BIT(27)
-+#define MTK_QTX_SCH_MIN_RATE_MAN      GENMASK(26, 20)
-+#define MTK_QTX_SCH_MIN_RATE_EXP      GENMASK(19, 16)
-+#define MTK_QTX_SCH_MAX_RATE_WEIGHT   GENMASK(15, 12)
-+#define MTK_QTX_SCH_MAX_RATE_EN               BIT(11)
-+#define MTK_QTX_SCH_MAX_RATE_MAN      GENMASK(10, 4)
-+#define MTK_QTX_SCH_MAX_RATE_EXP      GENMASK(3, 0)
-+
-+/* QDMA TX Scheduler Rate Control Register */
-+#define MTK_QDMA_TX_SCH_MAX_WFQ               BIT(15)
-+
- /* QDMA Global Configuration Register */
- #define MTK_RX_2B_OFFSET      BIT(31)
- #define MTK_RX_BT_32DWORDS    (3 << 11)
-@@ -235,6 +254,7 @@
- #define MTK_WCOMP_EN          BIT(24)
- #define MTK_RESV_BUF          (0x40 << 16)
- #define MTK_MUTLI_CNT         (0x4 << 12)
-+#define MTK_LEAKY_BUCKET_EN   BIT(11)
- /* QDMA Flow Control Register */
- #define FC_THRES_DROP_MODE    BIT(20)
-@@ -265,8 +285,6 @@
- #define MTK_STAT_OFFSET               0x40
- /* QDMA TX NUM */
--#define MTK_QDMA_TX_NUM               16
--#define MTK_QDMA_TX_MASK      (MTK_QDMA_TX_NUM - 1)
- #define QID_BITS_V2(x)                (((x) & 0x3f) << 16)
- #define MTK_QDMA_GMAC2_QID    8
-@@ -296,6 +314,7 @@
- #define TX_DMA_PLEN0(x)               (((x) & eth->soc->txrx.dma_max_len) << eth->soc->txrx.dma_len_offset)
- #define TX_DMA_PLEN1(x)               ((x) & eth->soc->txrx.dma_max_len)
- #define TX_DMA_SWC            BIT(14)
-+#define TX_DMA_PQID           GENMASK(3, 0)
- /* PDMA on MT7628 */
- #define TX_DMA_DONE           BIT(31)
-@@ -953,6 +972,7 @@ struct mtk_reg_map {
-       } pdma;
-       struct {
-               u32     qtx_cfg;        /* tx queue configuration */
-+              u32     qtx_sch;        /* tx queue scheduler configuration */
-               u32     rx_ptr;         /* rx base pointer */
-               u32     rx_cnt_cfg;     /* rx max count configuration */
-               u32     qcrx_ptr;       /* rx cpu pointer */
-@@ -970,6 +990,7 @@ struct mtk_reg_map {
-               u32     fq_tail;        /* fq tail pointer */
-               u32     fq_count;       /* fq free page count */
-               u32     fq_blen;        /* fq free page buffer length */
-+              u32     tx_sch_rate;    /* tx scheduler rate control registers */
-       } qdma;
-       u32     gdm1_cnt;
-       u32     gdma_to_ppe0;
-@@ -1173,6 +1194,7 @@ struct mtk_mac {
-       __be32                          hwlro_ip[MTK_MAX_LRO_IP_CNT];
-       int                             hwlro_ip_cnt;
-       unsigned int                    syscfg0;
-+      struct notifier_block           device_notifier;
- };
- /* the struct describing the SoC. these are declared in the soc_xyz.c files */
diff --git a/target/linux/generic/backport-5.15/730-05-v6.3-net-dsa-tag_mtk-assign-per-port-queues.patch b/target/linux/generic/backport-5.15/730-05-v6.3-net-dsa-tag_mtk-assign-per-port-queues.patch
deleted file mode 100644 (file)
index 186df4b..0000000
+++ /dev/null
@@ -1,20 +0,0 @@
-From: Felix Fietkau <[email protected]>
-Date: Fri, 28 Oct 2022 18:16:03 +0200
-Subject: [PATCH] net: dsa: tag_mtk: assign per-port queues
-
-Keeps traffic sent to the switch within link speed limits
-
-Signed-off-by: Felix Fietkau <[email protected]>
----
-
---- a/net/dsa/tag_mtk.c
-+++ b/net/dsa/tag_mtk.c
-@@ -25,6 +25,8 @@ static struct sk_buff *mtk_tag_xmit(stru
-       u8 xmit_tpid;
-       u8 *mtk_tag;
-+      skb_set_queue_mapping(skb, dp->index);
-+
-       /* Build the special tag after the MAC Source Address. If VLAN header
-        * is present, it's required that VLAN header and special tag is
-        * being combined. Only in this way we can allow the switch can parse
diff --git a/target/linux/generic/backport-5.15/730-06-v6.3-net-ethernet-mediatek-ppe-assign-per-port-queues-for.patch b/target/linux/generic/backport-5.15/730-06-v6.3-net-ethernet-mediatek-ppe-assign-per-port-queues-for.patch
deleted file mode 100644 (file)
index e05042c..0000000
+++ /dev/null
@@ -1,93 +0,0 @@
-From: Felix Fietkau <[email protected]>
-Date: Thu, 3 Nov 2022 17:49:44 +0100
-Subject: [PATCH] net: ethernet: mediatek: ppe: assign per-port queues
- for offloaded traffic
-
-Keeps traffic sent to the switch within link speed limits
-
-Signed-off-by: Felix Fietkau <[email protected]>
----
-
---- a/drivers/net/ethernet/mediatek/mtk_ppe.c
-+++ b/drivers/net/ethernet/mediatek/mtk_ppe.c
-@@ -405,6 +405,24 @@ static inline bool mtk_foe_entry_usable(
-              FIELD_GET(MTK_FOE_IB1_STATE, entry->ib1) != MTK_FOE_STATE_BIND;
- }
-+int mtk_foe_entry_set_queue(struct mtk_eth *eth, struct mtk_foe_entry *entry,
-+                          unsigned int queue)
-+{
-+      u32 *ib2 = mtk_foe_entry_ib2(eth, entry);
-+
-+      if (MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2)) {
-+              *ib2 &= ~MTK_FOE_IB2_QID_V2;
-+              *ib2 |= FIELD_PREP(MTK_FOE_IB2_QID_V2, queue);
-+              *ib2 |= MTK_FOE_IB2_PSE_QOS_V2;
-+      } else {
-+              *ib2 &= ~MTK_FOE_IB2_QID;
-+              *ib2 |= FIELD_PREP(MTK_FOE_IB2_QID, queue);
-+              *ib2 |= MTK_FOE_IB2_PSE_QOS;
-+      }
-+
-+      return 0;
-+}
-+
- static bool
- mtk_flow_entry_match(struct mtk_eth *eth, struct mtk_flow_entry *entry,
-                    struct mtk_foe_entry *data)
---- a/drivers/net/ethernet/mediatek/mtk_ppe.h
-+++ b/drivers/net/ethernet/mediatek/mtk_ppe.h
-@@ -68,7 +68,9 @@ enum {
- #define MTK_FOE_IB2_DSCP              GENMASK(31, 24)
- /* CONFIG_MEDIATEK_NETSYS_V2 */
-+#define MTK_FOE_IB2_QID_V2                    GENMASK(6, 0)
- #define MTK_FOE_IB2_PORT_MG_V2                BIT(7)
-+#define MTK_FOE_IB2_PSE_QOS_V2                BIT(8)
- #define MTK_FOE_IB2_DEST_PORT_V2      GENMASK(12, 9)
- #define MTK_FOE_IB2_MULTICAST_V2      BIT(13)
- #define MTK_FOE_IB2_WDMA_WINFO_V2     BIT(19)
-@@ -352,6 +354,8 @@ int mtk_foe_entry_set_pppoe(struct mtk_e
-                           int sid);
- int mtk_foe_entry_set_wdma(struct mtk_eth *eth, struct mtk_foe_entry *entry,
-                          int wdma_idx, int txq, int bss, int wcid);
-+int mtk_foe_entry_set_queue(struct mtk_eth *eth, struct mtk_foe_entry *entry,
-+                          unsigned int queue);
- int mtk_foe_entry_commit(struct mtk_ppe *ppe, struct mtk_flow_entry *entry);
- void mtk_foe_entry_clear(struct mtk_ppe *ppe, struct mtk_flow_entry *entry);
- int mtk_foe_entry_idle_time(struct mtk_ppe *ppe, struct mtk_flow_entry *entry);
---- a/drivers/net/ethernet/mediatek/mtk_ppe_offload.c
-+++ b/drivers/net/ethernet/mediatek/mtk_ppe_offload.c
-@@ -188,7 +188,7 @@ mtk_flow_set_output_device(struct mtk_et
-                          int *wed_index)
- {
-       struct mtk_wdma_info info = {};
--      int pse_port, dsa_port;
-+      int pse_port, dsa_port, queue;
-       if (mtk_flow_get_wdma_info(dev, dest_mac, &info) == 0) {
-               mtk_foe_entry_set_wdma(eth, foe, info.wdma_idx, info.queue,
-@@ -212,8 +212,6 @@ mtk_flow_set_output_device(struct mtk_et
-       }
-       dsa_port = mtk_flow_get_dsa_port(&dev);
--      if (dsa_port >= 0)
--              mtk_foe_entry_set_dsa(eth, foe, dsa_port);
-       if (dev == eth->netdev[0])
-               pse_port = 1;
-@@ -222,6 +220,14 @@ mtk_flow_set_output_device(struct mtk_et
-       else
-               return -EOPNOTSUPP;
-+      if (dsa_port >= 0) {
-+              mtk_foe_entry_set_dsa(eth, foe, dsa_port);
-+              queue = 3 + dsa_port;
-+      } else {
-+              queue = pse_port - 1;
-+      }
-+      mtk_foe_entry_set_queue(eth, foe, queue);
-+
- out:
-       mtk_foe_entry_set_pse_port(eth, foe, pse_port);
diff --git a/target/linux/generic/backport-5.15/730-08-v6.3-net-dsa-add-support-for-DSA-rx-offloading-via-metada.patch b/target/linux/generic/backport-5.15/730-08-v6.3-net-dsa-add-support-for-DSA-rx-offloading-via-metada.patch
deleted file mode 100644 (file)
index 0478cb5..0000000
+++ /dev/null
@@ -1,72 +0,0 @@
-From: Felix Fietkau <[email protected]>
-Date: Tue, 8 Nov 2022 15:03:15 +0100
-Subject: [PATCH] net: dsa: add support for DSA rx offloading via
- metadata dst
-
-If a metadata dst is present with the type METADATA_HW_PORT_MUX on a dsa cpu
-port netdev, assume that it carries the port number and that there is no DSA
-tag present in the skb data.
-
-Signed-off-by: Felix Fietkau <[email protected]>
----
-
---- a/net/core/flow_dissector.c
-+++ b/net/core/flow_dissector.c
-@@ -940,12 +940,14 @@ bool __skb_flow_dissect(const struct net
- #if IS_ENABLED(CONFIG_NET_DSA)
-               if (unlikely(skb->dev && netdev_uses_dsa(skb->dev) &&
-                            proto == htons(ETH_P_XDSA))) {
-+                      struct metadata_dst *md_dst = skb_metadata_dst(skb);
-                       const struct dsa_device_ops *ops;
-                       int offset = 0;
-                       ops = skb->dev->dsa_ptr->tag_ops;
-                       /* Only DSA header taggers break flow dissection */
--                      if (ops->needed_headroom) {
-+                      if (ops->needed_headroom &&
-+                          (!md_dst || md_dst->type != METADATA_HW_PORT_MUX)) {
-                               if (ops->flow_dissect)
-                                       ops->flow_dissect(skb, &proto, &offset);
-                               else
---- a/net/dsa/dsa.c
-+++ b/net/dsa/dsa.c
-@@ -20,6 +20,7 @@
- #include <linux/phy_fixed.h>
- #include <linux/ptp_classify.h>
- #include <linux/etherdevice.h>
-+#include <net/dst_metadata.h>
- #include "dsa_priv.h"
-@@ -225,6 +226,7 @@ static bool dsa_skb_defer_rx_timestamp(s
- static int dsa_switch_rcv(struct sk_buff *skb, struct net_device *dev,
-                         struct packet_type *pt, struct net_device *unused)
- {
-+      struct metadata_dst *md_dst = skb_metadata_dst(skb);
-       struct dsa_port *cpu_dp = dev->dsa_ptr;
-       struct sk_buff *nskb = NULL;
-       struct dsa_slave_priv *p;
-@@ -238,7 +240,22 @@ static int dsa_switch_rcv(struct sk_buff
-       if (!skb)
-               return 0;
--      nskb = cpu_dp->rcv(skb, dev);
-+      if (md_dst && md_dst->type == METADATA_HW_PORT_MUX) {
-+              unsigned int port = md_dst->u.port_info.port_id;
-+
-+              skb_dst_drop(skb);
-+              if (!skb_has_extensions(skb))
-+                      skb->slow_gro = 0;
-+
-+              skb->dev = dsa_master_find_slave(dev, 0, port);
-+              if (likely(skb->dev)) {
-+                      dsa_default_offload_fwd_mark(skb);
-+                      nskb = skb;
-+              }
-+      } else {
-+              nskb = cpu_dp->rcv(skb, dev);
-+      }
-+
-       if (!nskb) {
-               kfree_skb(skb);
-               return 0;
diff --git a/target/linux/generic/backport-5.15/730-09-v6.3-net-ethernet-mtk_eth_soc-fix-VLAN-rx-hardware-accele.patch b/target/linux/generic/backport-5.15/730-09-v6.3-net-ethernet-mtk_eth_soc-fix-VLAN-rx-hardware-accele.patch
deleted file mode 100644 (file)
index b64f434..0000000
+++ /dev/null
@@ -1,192 +0,0 @@
-From: Felix Fietkau <[email protected]>
-Date: Fri, 28 Oct 2022 11:01:12 +0200
-Subject: [PATCH] net: ethernet: mtk_eth_soc: fix VLAN rx hardware
- acceleration
-
-- enable VLAN untagging for PDMA rx
-- make it possible to disable the feature via ethtool
-- pass VLAN tag to the DSA driver
-- untag special tag on PDMA only if no non-DSA devices are in use
-- disable special tag untagging on 7986 for now, since it's not working yet
-
-Signed-off-by: Felix Fietkau <[email protected]>
----
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-@@ -23,6 +23,7 @@
- #include <linux/jhash.h>
- #include <linux/bitfield.h>
- #include <net/dsa.h>
-+#include <net/dst_metadata.h>
- #include "mtk_eth_soc.h"
- #include "mtk_wed.h"
-@@ -1973,16 +1974,22 @@ static int mtk_poll_rx(struct napi_struc
-                                               htons(RX_DMA_VPID(trxd.rxd4)),
-                                               RX_DMA_VID(trxd.rxd4));
-                       } else if (trxd.rxd2 & RX_DMA_VTAG) {
--                              __vlan_hwaccel_put_tag(skb, htons(ETH_P_8021Q),
-+                              __vlan_hwaccel_put_tag(skb, htons(RX_DMA_VPID(trxd.rxd3)),
-                                                      RX_DMA_VID(trxd.rxd3));
-                       }
-+              }
-+
-+              /* When using VLAN untagging in combination with DSA, the
-+               * hardware treats the MTK special tag as a VLAN and untags it.
-+               */
-+              if (skb_vlan_tag_present(skb) && netdev_uses_dsa(netdev)) {
-+                      unsigned int port = ntohs(skb->vlan_proto) & GENMASK(2, 0);
--                      /* If the device is attached to a dsa switch, the special
--                       * tag inserted in VLAN field by hw switch can * be offloaded
--                       * by RX HW VLAN offload. Clear vlan info.
--                       */
--                      if (netdev_uses_dsa(netdev))
--                              __vlan_hwaccel_clear_tag(skb);
-+                      if (port < ARRAY_SIZE(eth->dsa_meta) &&
-+                          eth->dsa_meta[port])
-+                              skb_dst_set_noref(skb, &eth->dsa_meta[port]->dst);
-+
-+                      __vlan_hwaccel_clear_tag(skb);
-               }
-               skb_record_rx_queue(skb, 0);
-@@ -2802,15 +2809,30 @@ static netdev_features_t mtk_fix_feature
- static int mtk_set_features(struct net_device *dev, netdev_features_t features)
- {
--      int err = 0;
-+      struct mtk_mac *mac = netdev_priv(dev);
-+      struct mtk_eth *eth = mac->hw;
-+      netdev_features_t diff = dev->features ^ features;
-+      int i;
-+
-+      if ((diff & NETIF_F_LRO) && !(features & NETIF_F_LRO))
-+              mtk_hwlro_netdev_disable(dev);
--      if (!((dev->features ^ features) & NETIF_F_LRO))
-+      /* Set RX VLAN offloading */
-+      if (!(diff & NETIF_F_HW_VLAN_CTAG_RX))
-               return 0;
--      if (!(features & NETIF_F_LRO))
--              mtk_hwlro_netdev_disable(dev);
-+      mtk_w32(eth, !!(features & NETIF_F_HW_VLAN_CTAG_RX),
-+              MTK_CDMP_EG_CTRL);
--      return err;
-+      /* sync features with other MAC */
-+      for (i = 0; i < MTK_MAC_COUNT; i++) {
-+              if (!eth->netdev[i] || eth->netdev[i] == dev)
-+                      continue;
-+              eth->netdev[i]->features &= ~NETIF_F_HW_VLAN_CTAG_RX;
-+              eth->netdev[i]->features |= features & NETIF_F_HW_VLAN_CTAG_RX;
-+      }
-+
-+      return 0;
- }
- /* wait for DMA to finish whatever it is doing before we start using it again */
-@@ -3107,11 +3129,45 @@ found:
-       return NOTIFY_DONE;
- }
-+static bool mtk_uses_dsa(struct net_device *dev)
-+{
-+#if IS_ENABLED(CONFIG_NET_DSA)
-+      return netdev_uses_dsa(dev) &&
-+             dev->dsa_ptr->tag_ops->proto == DSA_TAG_PROTO_MTK;
-+#else
-+      return false;
-+#endif
-+}
-+
- static int mtk_open(struct net_device *dev)
- {
-       struct mtk_mac *mac = netdev_priv(dev);
-       struct mtk_eth *eth = mac->hw;
--      int err;
-+      int i, err;
-+
-+      if (mtk_uses_dsa(dev) && !eth->prog) {
-+              for (i = 0; i < ARRAY_SIZE(eth->dsa_meta); i++) {
-+                      struct metadata_dst *md_dst = eth->dsa_meta[i];
-+
-+                      if (md_dst)
-+                              continue;
-+
-+                      md_dst = metadata_dst_alloc(0, METADATA_HW_PORT_MUX,
-+                                                  GFP_KERNEL);
-+                      if (!md_dst)
-+                              return -ENOMEM;
-+
-+                      md_dst->u.port_info.port_id = i;
-+                      eth->dsa_meta[i] = md_dst;
-+              }
-+      } else {
-+              /* Hardware special tag parsing needs to be disabled if at least
-+               * one MAC does not use DSA.
-+               */
-+              u32 val = mtk_r32(eth, MTK_CDMP_IG_CTRL);
-+              val &= ~MTK_CDMP_STAG_EN;
-+              mtk_w32(eth, val, MTK_CDMP_IG_CTRL);
-+      }
-       err = phylink_of_phy_connect(mac->phylink, mac->of_node, 0);
-       if (err) {
-@@ -3634,6 +3690,10 @@ static int mtk_hw_init(struct mtk_eth *e
-        */
-       val = mtk_r32(eth, MTK_CDMQ_IG_CTRL);
-       mtk_w32(eth, val | MTK_CDMQ_STAG_EN, MTK_CDMQ_IG_CTRL);
-+      if (!MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2)) {
-+              val = mtk_r32(eth, MTK_CDMP_IG_CTRL);
-+              mtk_w32(eth, val | MTK_CDMP_STAG_EN, MTK_CDMP_IG_CTRL);
-+      }
-       /* Enable RX VLan Offloading */
-       mtk_w32(eth, 1, MTK_CDMP_EG_CTRL);
-@@ -3850,6 +3910,12 @@ static int mtk_free_dev(struct mtk_eth *
-               free_netdev(eth->netdev[i]);
-       }
-+      for (i = 0; i < ARRAY_SIZE(eth->dsa_meta); i++) {
-+              if (!eth->dsa_meta[i])
-+                      break;
-+              metadata_dst_free(eth->dsa_meta[i]);
-+      }
-+
-       return 0;
- }
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-@@ -22,6 +22,9 @@
- #include <linux/bpf_trace.h>
- #include "mtk_ppe.h"
-+#define MTK_MAX_DSA_PORTS     7
-+#define MTK_DSA_PORT_MASK     GENMASK(2, 0)
-+
- #define MTK_QDMA_NUM_QUEUES   16
- #define MTK_QDMA_PAGE_SIZE    2048
- #define MTK_MAX_RX_LENGTH     1536
-@@ -105,6 +108,9 @@
- #define MTK_CDMQ_IG_CTRL      0x1400
- #define MTK_CDMQ_STAG_EN      BIT(0)
-+/* CDMQ Exgress Control Register */
-+#define MTK_CDMQ_EG_CTRL      0x1404
-+
- /* CDMP Ingress Control Register */
- #define MTK_CDMP_IG_CTRL      0x400
- #define MTK_CDMP_STAG_EN      BIT(0)
-@@ -1160,6 +1166,8 @@ struct mtk_eth {
-       int                             ip_align;
-+      struct metadata_dst             *dsa_meta[MTK_MAX_DSA_PORTS];
-+
-       struct mtk_ppe                  *ppe[2];
-       struct rhashtable               flow_table;
diff --git a/target/linux/generic/backport-5.15/730-10-v6.3-net-ethernet-mtk_eth_soc-drop-packets-to-WDMA-if-the.patch b/target/linux/generic/backport-5.15/730-10-v6.3-net-ethernet-mtk_eth_soc-drop-packets-to-WDMA-if-the.patch
deleted file mode 100644 (file)
index b8c7865..0000000
+++ /dev/null
@@ -1,37 +0,0 @@
-From: Felix Fietkau <[email protected]>
-Date: Thu, 3 Nov 2022 17:46:25 +0100
-Subject: [PATCH] net: ethernet: mtk_eth_soc: drop packets to WDMA if the
- ring is full
-
-Improves handling of DMA ring overflow.
-Clarify other WDMA drop related comment.
-
-Signed-off-by: Felix Fietkau <[email protected]>
----
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-@@ -3714,9 +3714,12 @@ static int mtk_hw_init(struct mtk_eth *e
-       mtk_w32(eth, 0x21021000, MTK_FE_INT_GRP);
-       if (MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2)) {
--              /* PSE should not drop port8 and port9 packets */
-+              /* PSE should not drop port8 and port9 packets from WDMA Tx */
-               mtk_w32(eth, 0x00000300, PSE_DROP_CFG);
-+              /* PSE should drop packets to port 8/9 on WDMA Rx ring full */
-+              mtk_w32(eth, 0x00000300, PSE_PPE0_DROP);
-+
-               /* PSE Free Queue Flow Control  */
-               mtk_w32(eth, 0x01fa01f4, PSE_FQFC_CFG2);
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-@@ -140,6 +140,7 @@
- #define PSE_FQFC_CFG1         0x100
- #define PSE_FQFC_CFG2         0x104
- #define PSE_DROP_CFG          0x108
-+#define PSE_PPE0_DROP         0x110
- /* PSE Input Queue Reservation Register*/
- #define PSE_IQ_REV(x)         (0x140 + (((x) - 1) << 2))
diff --git a/target/linux/generic/backport-5.15/730-12-v6.3-net-ethernet-mtk_eth_soc-disable-hardware-DSA-untagg.patch b/target/linux/generic/backport-5.15/730-12-v6.3-net-ethernet-mtk_eth_soc-disable-hardware-DSA-untagg.patch
deleted file mode 100644 (file)
index 346db89..0000000
+++ /dev/null
@@ -1,42 +0,0 @@
-From: =?UTF-8?q?Ar=C4=B1n=C3=A7=20=C3=9CNAL?= <[email protected]>
-Date: Sat, 28 Jan 2023 12:42:32 +0300
-Subject: [PATCH] net: ethernet: mtk_eth_soc: disable hardware DSA untagging
- for second MAC
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-According to my tests on MT7621AT and MT7623NI SoCs, hardware DSA untagging
-won't work on the second MAC. Therefore, disable this feature when the
-second MAC of the MT7621 and MT7623 SoCs is being used.
-
-Fixes: 2d7605a72906 ("net: ethernet: mtk_eth_soc: enable hardware DSA untagging")
-Link: https://lore.kernel.org/netdev/[email protected]/
-Tested-by: Arınç ÜNAL <[email protected]>
-Signed-off-by: Arınç ÜNAL <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Jakub Kicinski <[email protected]>
----
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-@@ -3145,7 +3145,8 @@ static int mtk_open(struct net_device *d
-       struct mtk_eth *eth = mac->hw;
-       int i, err;
--      if (mtk_uses_dsa(dev) && !eth->prog) {
-+      if ((mtk_uses_dsa(dev) && !eth->prog) &&
-+          !(mac->id == 1 && MTK_HAS_CAPS(eth->soc->caps, MTK_GMAC1_TRGMII))) {
-               for (i = 0; i < ARRAY_SIZE(eth->dsa_meta); i++) {
-                       struct metadata_dst *md_dst = eth->dsa_meta[i];
-@@ -3162,7 +3163,8 @@ static int mtk_open(struct net_device *d
-               }
-       } else {
-               /* Hardware special tag parsing needs to be disabled if at least
--               * one MAC does not use DSA.
-+               * one MAC does not use DSA, or the second MAC of the MT7621 and
-+               * MT7623 SoCs is being used.
-                */
-               u32 val = mtk_r32(eth, MTK_CDMP_IG_CTRL);
-               val &= ~MTK_CDMP_STAG_EN;
diff --git a/target/linux/generic/backport-5.15/730-13-v6.3-net-ethernet-mtk_eth_soc-enable-special-tag-when-any.patch b/target/linux/generic/backport-5.15/730-13-v6.3-net-ethernet-mtk_eth_soc-enable-special-tag-when-any.patch
deleted file mode 100644 (file)
index ec5dc49..0000000
+++ /dev/null
@@ -1,54 +0,0 @@
-From: =?UTF-8?q?Ar=C4=B1n=C3=A7=20=C3=9CNAL?= <[email protected]>
-Date: Sun, 5 Feb 2023 20:53:31 +0300
-Subject: [PATCH] net: ethernet: mtk_eth_soc: enable special tag when any MAC
- uses DSA
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-The special tag is only enabled when the first MAC uses DSA. However, it
-must be enabled when any MAC uses DSA. Change the check accordingly.
-
-This fixes hardware DSA untagging not working on the second MAC of the
-MT7621 and MT7623 SoCs, and likely other SoCs too. Therefore, remove the
-check that disables hardware DSA untagging for the second MAC of the MT7621
-and MT7623 SoCs.
-
-Fixes: a1f47752fd62 ("net: ethernet: mtk_eth_soc: disable hardware DSA untagging for second MAC")
-Co-developed-by: Richard van Schagen <[email protected]>
-Signed-off-by: Richard van Schagen <[email protected]>
-Signed-off-by: Arınç ÜNAL <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-@@ -3080,7 +3080,7 @@ static void mtk_gdm_config(struct mtk_et
-               val |= config;
--              if (!i && eth->netdev[0] && netdev_uses_dsa(eth->netdev[0]))
-+              if (eth->netdev[i] && netdev_uses_dsa(eth->netdev[i]))
-                       val |= MTK_GDMA_SPECIAL_TAG;
-               mtk_w32(eth, val, MTK_GDMA_FWD_CFG(i));
-@@ -3145,8 +3145,7 @@ static int mtk_open(struct net_device *d
-       struct mtk_eth *eth = mac->hw;
-       int i, err;
--      if ((mtk_uses_dsa(dev) && !eth->prog) &&
--          !(mac->id == 1 && MTK_HAS_CAPS(eth->soc->caps, MTK_GMAC1_TRGMII))) {
-+      if (mtk_uses_dsa(dev) && !eth->prog) {
-               for (i = 0; i < ARRAY_SIZE(eth->dsa_meta); i++) {
-                       struct metadata_dst *md_dst = eth->dsa_meta[i];
-@@ -3163,8 +3162,7 @@ static int mtk_open(struct net_device *d
-               }
-       } else {
-               /* Hardware special tag parsing needs to be disabled if at least
--               * one MAC does not use DSA, or the second MAC of the MT7621 and
--               * MT7623 SoCs is being used.
-+               * one MAC does not use DSA.
-                */
-               u32 val = mtk_r32(eth, MTK_CDMP_IG_CTRL);
-               val &= ~MTK_CDMP_STAG_EN;
diff --git a/target/linux/generic/backport-5.15/730-14-v6.3-net-ethernet-mtk_eth_soc-fix-DSA-TX-tag-hwaccel-for-.patch b/target/linux/generic/backport-5.15/730-14-v6.3-net-ethernet-mtk_eth_soc-fix-DSA-TX-tag-hwaccel-for-.patch
deleted file mode 100644 (file)
index e754596..0000000
+++ /dev/null
@@ -1,129 +0,0 @@
-From: Vladimir Oltean <[email protected]>
-Date: Tue, 7 Feb 2023 12:30:27 +0200
-Subject: [PATCH] net: ethernet: mtk_eth_soc: fix DSA TX tag hwaccel for switch
- port 0
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-Arınç reports that on his MT7621AT Unielec U7621-06 board and MT7623NI
-Bananapi BPI-R2, packets received by the CPU over mt7530 switch port 0
-(of which this driver acts as the DSA master) are not processed
-correctly by software. More precisely, they arrive without a DSA tag
-(in packet or in the hwaccel area - skb_metadata_dst()), so DSA cannot
-demux them towards the switch's interface for port 0. Traffic from other
-ports receives a skb_metadata_dst() with the correct port and is demuxed
-properly.
-
-Looking at mtk_poll_rx(), it becomes apparent that this driver uses the
-skb vlan hwaccel area:
-
-       union {
-               u32             vlan_all;
-               struct {
-                       __be16  vlan_proto;
-                       __u16   vlan_tci;
-               };
-       };
-
-as a temporary storage for the VLAN hwaccel tag, or the DSA hwaccel tag.
-If this is a DSA master it's a DSA hwaccel tag, and finally clears up
-the skb VLAN hwaccel header.
-
-I'm guessing that the problem is the (mis)use of API.
-skb_vlan_tag_present() looks like this:
-
- #define skb_vlan_tag_present(__skb)   (!!(__skb)->vlan_all)
-
-So if both vlan_proto and vlan_tci are zeroes, skb_vlan_tag_present()
-returns precisely false. I don't know for sure what is the format of the
-DSA hwaccel tag, but I surely know that lowermost 3 bits of vlan_proto
-are 0 when receiving from port 0:
-
-       unsigned int port = vlan_proto & GENMASK(2, 0);
-
-If the RX descriptor has no other bits set to non-zero values in
-RX_DMA_VTAG, then the call to __vlan_hwaccel_put_tag() will not, in
-fact, make the subsequent skb_vlan_tag_present() return true, because
-it's implemented like this:
-
-static inline void __vlan_hwaccel_put_tag(struct sk_buff *skb,
-                                         __be16 vlan_proto, u16 vlan_tci)
-{
-       skb->vlan_proto = vlan_proto;
-       skb->vlan_tci = vlan_tci;
-}
-
-What we need to do to fix this problem (assuming this is the problem) is
-to stop using skb->vlan_all as temporary storage for driver affairs, and
-just create some local variables that serve the same purpose, but
-hopefully better. Instead of calling skb_vlan_tag_present(), let's look
-at a boolean has_hwaccel_tag which we set to true when the RX DMA
-descriptors have something. Disambiguate based on netdev_uses_dsa()
-whether this is a VLAN or DSA hwaccel tag, and only call
-__vlan_hwaccel_put_tag() if we're certain it's a VLAN tag.
-
-Arınç confirms that the treatment works, so this validates the
-assumption.
-
-Link: https://lore.kernel.org/netdev/[email protected]/
-Fixes: 2d7605a72906 ("net: ethernet: mtk_eth_soc: enable hardware DSA untagging")
-Reported-by: Arınç ÜNAL <[email protected]>
-Tested-by: Arınç ÜNAL <[email protected]>
-Signed-off-by: Vladimir Oltean <[email protected]>
-Reviewed-by: Felix Fietkau <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-@@ -1829,7 +1829,9 @@ static int mtk_poll_rx(struct napi_struc
-       while (done < budget) {
-               unsigned int pktlen, *rxdcsum;
-+              bool has_hwaccel_tag = false;
-               struct net_device *netdev;
-+              u16 vlan_proto, vlan_tci;
-               dma_addr_t dma_addr;
-               u32 hash, reason;
-               int mac = 0;
-@@ -1969,27 +1971,29 @@ static int mtk_poll_rx(struct napi_struc
-               if (netdev->features & NETIF_F_HW_VLAN_CTAG_RX) {
-                       if (MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2)) {
--                              if (trxd.rxd3 & RX_DMA_VTAG_V2)
--                                      __vlan_hwaccel_put_tag(skb,
--                                              htons(RX_DMA_VPID(trxd.rxd4)),
--                                              RX_DMA_VID(trxd.rxd4));
-+                              if (trxd.rxd3 & RX_DMA_VTAG_V2) {
-+                                      vlan_proto = RX_DMA_VPID(trxd.rxd4);
-+                                      vlan_tci = RX_DMA_VID(trxd.rxd4);
-+                                      has_hwaccel_tag = true;
-+                              }
-                       } else if (trxd.rxd2 & RX_DMA_VTAG) {
--                              __vlan_hwaccel_put_tag(skb, htons(RX_DMA_VPID(trxd.rxd3)),
--                                                     RX_DMA_VID(trxd.rxd3));
-+                              vlan_proto = RX_DMA_VPID(trxd.rxd3);
-+                              vlan_tci = RX_DMA_VID(trxd.rxd3);
-+                              has_hwaccel_tag = true;
-                       }
-               }
-               /* When using VLAN untagging in combination with DSA, the
-                * hardware treats the MTK special tag as a VLAN and untags it.
-                */
--              if (skb_vlan_tag_present(skb) && netdev_uses_dsa(netdev)) {
--                      unsigned int port = ntohs(skb->vlan_proto) & GENMASK(2, 0);
-+              if (has_hwaccel_tag && netdev_uses_dsa(netdev)) {
-+                      unsigned int port = vlan_proto & GENMASK(2, 0);
-                       if (port < ARRAY_SIZE(eth->dsa_meta) &&
-                           eth->dsa_meta[port])
-                               skb_dst_set_noref(skb, &eth->dsa_meta[port]->dst);
--
--                      __vlan_hwaccel_clear_tag(skb);
-+              } else if (has_hwaccel_tag) {
-+                      __vlan_hwaccel_put_tag(skb, htons(vlan_proto), vlan_tci);
-               }
-               skb_record_rx_queue(skb, 0);
diff --git a/target/linux/generic/backport-5.15/730-15-v6.3-net-ethernet-mtk_wed-No-need-to-clear-memory-after-a.patch b/target/linux/generic/backport-5.15/730-15-v6.3-net-ethernet-mtk_wed-No-need-to-clear-memory-after-a.patch
deleted file mode 100644 (file)
index a3bb1c5..0000000
+++ /dev/null
@@ -1,26 +0,0 @@
-From: Christophe JAILLET <[email protected]>
-Date: Sun, 12 Feb 2023 07:51:51 +0100
-Subject: [PATCH] net: ethernet: mtk_wed: No need to clear memory after a
- dma_alloc_coherent() call
-
-dma_alloc_coherent() already clears the allocated memory, there is no need
-to explicitly call memset().
-
-Moreover, it is likely that the size in the memset() is incorrect and
-should be "size * sizeof(*ring->desc)".
-
-Signed-off-by: Christophe JAILLET <[email protected]>
-Link: https://lore.kernel.org/r/d5acce7dd108887832c9719f62c7201b4c83b3fb.1676184599.git.christophe.jaillet@wanadoo.fr
-Signed-off-by: Jakub Kicinski <[email protected]>
----
-
---- a/drivers/net/ethernet/mediatek/mtk_wed.c
-+++ b/drivers/net/ethernet/mediatek/mtk_wed.c
-@@ -779,7 +779,6 @@ mtk_wed_rro_ring_alloc(struct mtk_wed_de
-       ring->desc_size = sizeof(*ring->desc);
-       ring->size = size;
--      memset(ring->desc, 0, size);
-       return 0;
- }
diff --git a/target/linux/generic/backport-5.15/730-16-v6.3-net-ethernet-mtk_wed-fix-some-possible-NULL-pointer-.patch b/target/linux/generic/backport-5.15/730-16-v6.3-net-ethernet-mtk_wed-fix-some-possible-NULL-pointer-.patch
deleted file mode 100644 (file)
index e043a68..0000000
+++ /dev/null
@@ -1,61 +0,0 @@
-From: Lorenzo Bianconi <[email protected]>
-Date: Wed, 7 Dec 2022 15:04:54 +0100
-Subject: [PATCH] net: ethernet: mtk_wed: fix some possible NULL pointer
- dereferences
-
-Fix possible NULL pointer dereference in mtk_wed_detach routine checking
-wo pointer is properly allocated before running mtk_wed_wo_reset() and
-mtk_wed_wo_deinit().
-Even if it is just a theoretical issue at the moment check wo pointer is
-not NULL in mtk_wed_mcu_msg_update.
-Moreover, honor mtk_wed_mcu_send_msg return value in mtk_wed_wo_reset()
-
-Fixes: 799684448e3e ("net: ethernet: mtk_wed: introduce wed wo support")
-Fixes: 4c5de09eb0d0 ("net: ethernet: mtk_wed: add configure wed wo support")
-Signed-off-by: Lorenzo Bianconi <[email protected]>
-Reviewed-by: Leon Romanovsky <[email protected]>
-Signed-off-by: Jakub Kicinski <[email protected]>
----
-
---- a/drivers/net/ethernet/mediatek/mtk_wed.c
-+++ b/drivers/net/ethernet/mediatek/mtk_wed.c
-@@ -174,9 +174,10 @@ mtk_wed_wo_reset(struct mtk_wed_device *
-       mtk_wdma_tx_reset(dev);
-       mtk_wed_reset(dev, MTK_WED_RESET_WED);
--      mtk_wed_mcu_send_msg(wo, MTK_WED_MODULE_ID_WO,
--                           MTK_WED_WO_CMD_CHANGE_STATE, &state,
--                           sizeof(state), false);
-+      if (mtk_wed_mcu_send_msg(wo, MTK_WED_MODULE_ID_WO,
-+                               MTK_WED_WO_CMD_CHANGE_STATE, &state,
-+                               sizeof(state), false))
-+              return;
-       if (readx_poll_timeout(mtk_wed_wo_read_status, dev, val,
-                              val == MTK_WED_WOIF_DISABLE_DONE,
-@@ -632,9 +633,11 @@ mtk_wed_detach(struct mtk_wed_device *de
-       mtk_wed_free_tx_rings(dev);
-       if (mtk_wed_get_rx_capa(dev)) {
--              mtk_wed_wo_reset(dev);
-+              if (hw->wed_wo)
-+                      mtk_wed_wo_reset(dev);
-               mtk_wed_free_rx_rings(dev);
--              mtk_wed_wo_deinit(hw);
-+              if (hw->wed_wo)
-+                      mtk_wed_wo_deinit(hw);
-       }
-       if (dev->wlan.bus_type == MTK_WED_BUS_PCIE) {
---- a/drivers/net/ethernet/mediatek/mtk_wed_mcu.c
-+++ b/drivers/net/ethernet/mediatek/mtk_wed_mcu.c
-@@ -207,6 +207,9 @@ int mtk_wed_mcu_msg_update(struct mtk_we
-       if (dev->hw->version == 1)
-               return 0;
-+      if (WARN_ON(!wo))
-+              return -ENODEV;
-+
-       return mtk_wed_mcu_send_msg(wo, MTK_WED_MODULE_ID_WO, id, data, len,
-                                   true);
- }
diff --git a/target/linux/generic/backport-5.15/730-17-v6.3-net-ethernet-mtk_wed-fix-possible-deadlock-if-mtk_we.patch b/target/linux/generic/backport-5.15/730-17-v6.3-net-ethernet-mtk_wed-fix-possible-deadlock-if-mtk_we.patch
deleted file mode 100644 (file)
index 0afe710..0000000
+++ /dev/null
@@ -1,58 +0,0 @@
-From: Lorenzo Bianconi <[email protected]>
-Date: Wed, 7 Dec 2022 15:04:55 +0100
-Subject: [PATCH] net: ethernet: mtk_wed: fix possible deadlock if
- mtk_wed_wo_init fails
-
-Introduce __mtk_wed_detach() in order to avoid a deadlock in
-mtk_wed_attach routine if mtk_wed_wo_init fails since both
-mtk_wed_attach and mtk_wed_detach run holding hw_lock mutex.
-
-Fixes: 4c5de09eb0d0 ("net: ethernet: mtk_wed: add configure wed wo support")
-Signed-off-by: Lorenzo Bianconi <[email protected]>
-Reviewed-by: Leon Romanovsky <[email protected]>
-Signed-off-by: Jakub Kicinski <[email protected]>
----
-
---- a/drivers/net/ethernet/mediatek/mtk_wed.c
-+++ b/drivers/net/ethernet/mediatek/mtk_wed.c
-@@ -619,12 +619,10 @@ mtk_wed_deinit(struct mtk_wed_device *de
- }
- static void
--mtk_wed_detach(struct mtk_wed_device *dev)
-+__mtk_wed_detach(struct mtk_wed_device *dev)
- {
-       struct mtk_wed_hw *hw = dev->hw;
--      mutex_lock(&hw_lock);
--
-       mtk_wed_deinit(dev);
-       mtk_wdma_rx_reset(dev);
-@@ -657,6 +655,13 @@ mtk_wed_detach(struct mtk_wed_device *de
-       module_put(THIS_MODULE);
-       hw->wed_dev = NULL;
-+}
-+
-+static void
-+mtk_wed_detach(struct mtk_wed_device *dev)
-+{
-+      mutex_lock(&hw_lock);
-+      __mtk_wed_detach(dev);
-       mutex_unlock(&hw_lock);
- }
-@@ -1538,8 +1543,10 @@ mtk_wed_attach(struct mtk_wed_device *de
-               ret = mtk_wed_wo_init(hw);
-       }
- out:
--      if (ret)
--              mtk_wed_detach(dev);
-+      if (ret) {
-+              dev_err(dev->hw->dev, "failed to attach wed device\n");
-+              __mtk_wed_detach(dev);
-+      }
- unlock:
-       mutex_unlock(&hw_lock);
diff --git a/target/linux/generic/backport-5.15/730-18-v6.3-net-ethernet-mtk_eth_soc-fix-tx-throughput-regressio.patch b/target/linux/generic/backport-5.15/730-18-v6.3-net-ethernet-mtk_eth_soc-fix-tx-throughput-regressio.patch
deleted file mode 100644 (file)
index 4ba4920..0000000
+++ /dev/null
@@ -1,31 +0,0 @@
-From: Felix Fietkau <[email protected]>
-Date: Fri, 24 Mar 2023 14:56:58 +0100
-Subject: [PATCH] net: ethernet: mtk_eth_soc: fix tx throughput regression with
- direct 1G links
-
-Using the QDMA tx scheduler to throttle tx to line speed works fine for
-switch ports, but apparently caused a regression on non-switch ports.
-
-Based on a number of tests, it seems that this throttling can be safely
-dropped without re-introducing the issues on switch ports that the
-tx scheduling changes resolved.
-
-Link: https://lore.kernel.org/netdev/trinity-92c3826f-c2c8-40af-8339-bc6d0d3ffea4-1678213958520@3c-app-gmx-bs16/
-Fixes: f63959c7eec3 ("net: ethernet: mtk_eth_soc: implement multi-queue support for per-port queues")
-Reported-by: Frank Wunderlich <[email protected]>
-Reported-by: Daniel Golle <[email protected]>
-Tested-by: Daniel Golle <[email protected]>
-Signed-off-by: Felix Fietkau <[email protected]>
----
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-@@ -675,8 +675,6 @@ static void mtk_mac_link_up(struct phyli
-               break;
-       }
--      mtk_set_queue_speed(mac->hw, mac->id, speed);
--
-       /* Configure duplex */
-       if (duplex == DUPLEX_FULL)
-               mcr |= MAC_MCR_FORCE_DPX;
diff --git a/target/linux/generic/backport-5.15/731-v6.1-0001-net-phy-Introduce-QUSGMII-PHY-mode.patch b/target/linux/generic/backport-5.15/731-v6.1-0001-net-phy-Introduce-QUSGMII-PHY-mode.patch
deleted file mode 100644 (file)
index 40b14fc..0000000
+++ /dev/null
@@ -1,99 +0,0 @@
-From 5e61fe157a27afc7c0d4f7bcbceefdca536c015f Mon Sep 17 00:00:00 2001
-From: Maxime Chevallier <[email protected]>
-Date: Wed, 17 Aug 2022 14:32:52 +0200
-Subject: [PATCH] net: phy: Introduce QUSGMII PHY mode
-
-The QUSGMII mode is a derivative of Cisco's USXGMII standard. This
-standard is pretty similar to SGMII, but allows for faster speeds, and
-has the build-in bits for Quad and Octa variants (like QSGMII).
-
-The main difference with SGMII/QSGMII is that USXGMII/QUSGMII re-uses
-the preamble to carry various information, named 'Extensions'.
-
-As of today, the USXGMII standard only mentions the "PCH" extension,
-which is used to convey timestamps, allowing in-band signaling of PTP
-timestamps without having to modify the frame itself.
-
-This commit adds support for that mode. When no extension is in use, it
-behaves exactly like QSGMII, although it's not compatible with QSGMII.
-
-Signed-off-by: Maxime Chevallier <[email protected]>
-Reviewed-by: Andrew Lunn <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- Documentation/networking/phy.rst | 9 +++++++++
- drivers/net/phy/phylink.c        | 3 +++
- include/linux/phy.h              | 4 ++++
- 3 files changed, 16 insertions(+)
-
---- a/Documentation/networking/phy.rst
-+++ b/Documentation/networking/phy.rst
-@@ -303,6 +303,15 @@ Some of the interface modes are describe
-     rate of 125Mpbs using a 4B/5B encoding scheme, resulting in an underlying
-     data rate of 100Mpbs.
-+``PHY_INTERFACE_MODE_QUSGMII``
-+    This defines the Cisco the Quad USGMII mode, which is the Quad variant of
-+    the USGMII (Universal SGMII) link. It's very similar to QSGMII, but uses
-+    a Packet Control Header (PCH) instead of the 7 bytes preamble to carry not
-+    only the port id, but also so-called "extensions". The only documented
-+    extension so-far in the specification is the inclusion of timestamps, for
-+    PTP-enabled PHYs. This mode isn't compatible with QSGMII, but offers the
-+    same capabilities in terms of link speed and negociation.
-+
- Pause frames / flow control
- ===========================
---- a/drivers/net/phy/phylink.c
-+++ b/drivers/net/phy/phylink.c
-@@ -367,6 +367,7 @@ void phylink_get_linkmodes(unsigned long
-       case PHY_INTERFACE_MODE_RGMII_ID:
-       case PHY_INTERFACE_MODE_RGMII:
-       case PHY_INTERFACE_MODE_QSGMII:
-+      case PHY_INTERFACE_MODE_QUSGMII:
-       case PHY_INTERFACE_MODE_SGMII:
-       case PHY_INTERFACE_MODE_GMII:
-               caps |= MAC_1000HD | MAC_1000FD;
-@@ -630,6 +631,7 @@ static int phylink_parse_mode(struct phy
-               switch (pl->link_config.interface) {
-               case PHY_INTERFACE_MODE_SGMII:
-               case PHY_INTERFACE_MODE_QSGMII:
-+              case PHY_INTERFACE_MODE_QUSGMII:
-                       phylink_set(pl->supported, 10baseT_Half);
-                       phylink_set(pl->supported, 10baseT_Full);
-                       phylink_set(pl->supported, 100baseT_Half);
-@@ -2956,6 +2958,7 @@ void phylink_mii_c22_pcs_get_state(struc
-       case PHY_INTERFACE_MODE_SGMII:
-       case PHY_INTERFACE_MODE_QSGMII:
-+      case PHY_INTERFACE_MODE_QUSGMII:
-               phylink_decode_sgmii_word(state, lpa);
-               break;
---- a/include/linux/phy.h
-+++ b/include/linux/phy.h
-@@ -115,6 +115,7 @@ extern const int phy_10gbit_features_arr
-  * @PHY_INTERFACE_MODE_25GBASER: 25G BaseR
-  * @PHY_INTERFACE_MODE_USXGMII:  Universal Serial 10GE MII
-  * @PHY_INTERFACE_MODE_10GKR: 10GBASE-KR - with Clause 73 AN
-+ * @PHY_INTERFACE_MODE_QUSGMII: Quad Universal SGMII
-  * @PHY_INTERFACE_MODE_MAX: Book keeping
-  *
-  * Describes the interface between the MAC and PHY.
-@@ -152,6 +153,7 @@ typedef enum {
-       PHY_INTERFACE_MODE_USXGMII,
-       /* 10GBASE-KR - with Clause 73 AN */
-       PHY_INTERFACE_MODE_10GKR,
-+      PHY_INTERFACE_MODE_QUSGMII,
-       PHY_INTERFACE_MODE_MAX,
- } phy_interface_t;
-@@ -267,6 +269,8 @@ static inline const char *phy_modes(phy_
-               return "10gbase-kr";
-       case PHY_INTERFACE_MODE_100BASEX:
-               return "100base-x";
-+      case PHY_INTERFACE_MODE_QUSGMII:
-+              return "qusgmii";
-       default:
-               return "unknown";
-       }
diff --git a/target/linux/generic/backport-5.15/731-v6.1-0002-net-phy-Add-helper-to-derive-the-number-of-ports-fro.patch b/target/linux/generic/backport-5.15/731-v6.1-0002-net-phy-Add-helper-to-derive-the-number-of-ports-fro.patch
deleted file mode 100644 (file)
index a9706af..0000000
+++ /dev/null
@@ -1,93 +0,0 @@
-From c04ade27cb7b952b6b9b9a0efa0a6129cc63f2ae Mon Sep 17 00:00:00 2001
-From: Maxime Chevallier <[email protected]>
-Date: Wed, 17 Aug 2022 14:32:54 +0200
-Subject: [PATCH] net: phy: Add helper to derive the number of ports from a phy
- mode
-
-Some phy modes such as QSGMII multiplex several MAC<->PHY links on one
-single physical interface. QSGMII used to be the only one supported, but
-other modes such as QUSGMII also carry multiple links.
-
-This helper allows getting the number of links that are multiplexed
-on a given interface.
-
-Signed-off-by: Maxime Chevallier <[email protected]>
-Reviewed-by: Andrew Lunn <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/phy/phy-core.c | 52 ++++++++++++++++++++++++++++++++++++++
- include/linux/phy.h        |  2 ++
- 2 files changed, 54 insertions(+)
-
---- a/drivers/net/phy/phy-core.c
-+++ b/drivers/net/phy/phy-core.c
-@@ -74,6 +74,58 @@ const char *phy_duplex_to_str(unsigned i
- }
- EXPORT_SYMBOL_GPL(phy_duplex_to_str);
-+/**
-+ * phy_interface_num_ports - Return the number of links that can be carried by
-+ *                         a given MAC-PHY physical link. Returns 0 if this is
-+ *                         unknown, the number of links else.
-+ *
-+ * @interface: The interface mode we want to get the number of ports
-+ */
-+int phy_interface_num_ports(phy_interface_t interface)
-+{
-+      switch (interface) {
-+      case PHY_INTERFACE_MODE_NA:
-+              return 0;
-+      case PHY_INTERFACE_MODE_INTERNAL:
-+      case PHY_INTERFACE_MODE_MII:
-+      case PHY_INTERFACE_MODE_GMII:
-+      case PHY_INTERFACE_MODE_TBI:
-+      case PHY_INTERFACE_MODE_REVMII:
-+      case PHY_INTERFACE_MODE_RMII:
-+      case PHY_INTERFACE_MODE_REVRMII:
-+      case PHY_INTERFACE_MODE_RGMII:
-+      case PHY_INTERFACE_MODE_RGMII_ID:
-+      case PHY_INTERFACE_MODE_RGMII_RXID:
-+      case PHY_INTERFACE_MODE_RGMII_TXID:
-+      case PHY_INTERFACE_MODE_RTBI:
-+      case PHY_INTERFACE_MODE_XGMII:
-+      case PHY_INTERFACE_MODE_XLGMII:
-+      case PHY_INTERFACE_MODE_MOCA:
-+      case PHY_INTERFACE_MODE_TRGMII:
-+      case PHY_INTERFACE_MODE_USXGMII:
-+      case PHY_INTERFACE_MODE_SGMII:
-+      case PHY_INTERFACE_MODE_SMII:
-+      case PHY_INTERFACE_MODE_1000BASEX:
-+      case PHY_INTERFACE_MODE_2500BASEX:
-+      case PHY_INTERFACE_MODE_5GBASER:
-+      case PHY_INTERFACE_MODE_10GBASER:
-+      case PHY_INTERFACE_MODE_25GBASER:
-+      case PHY_INTERFACE_MODE_10GKR:
-+      case PHY_INTERFACE_MODE_100BASEX:
-+      case PHY_INTERFACE_MODE_RXAUI:
-+      case PHY_INTERFACE_MODE_XAUI:
-+              return 1;
-+      case PHY_INTERFACE_MODE_QSGMII:
-+      case PHY_INTERFACE_MODE_QUSGMII:
-+              return 4;
-+      case PHY_INTERFACE_MODE_MAX:
-+              WARN_ONCE(1, "PHY_INTERFACE_MODE_MAX isn't a valid interface mode");
-+              return 0;
-+      }
-+      return 0;
-+}
-+EXPORT_SYMBOL_GPL(phy_interface_num_ports);
-+
- /* A mapping of all SUPPORTED settings to speed/duplex.  This table
-  * must be grouped by speed and sorted in descending match priority
-  * - iow, descending speed.
---- a/include/linux/phy.h
-+++ b/include/linux/phy.h
-@@ -964,6 +964,8 @@ struct phy_fixup {
- const char *phy_speed_to_str(int speed);
- const char *phy_duplex_to_str(unsigned int duplex);
-+int phy_interface_num_ports(phy_interface_t interface);
-+
- /* A structure for mapping a particular speed and duplex
-  * combination to a particular SUPPORTED and ADVERTISED value
-  */
diff --git a/target/linux/generic/backport-5.15/731-v6.1-0003-net-phy-Add-1000BASE-KX-interface-mode.patch b/target/linux/generic/backport-5.15/731-v6.1-0003-net-phy-Add-1000BASE-KX-interface-mode.patch
deleted file mode 100644 (file)
index 70669dd..0000000
+++ /dev/null
@@ -1,96 +0,0 @@
-From 05ad5d4581c3c1cc724fe50d4652833fb9f3037b Mon Sep 17 00:00:00 2001
-From: Sean Anderson <[email protected]>
-Date: Fri, 2 Sep 2022 18:02:39 -0400
-Subject: [PATCH] net: phy: Add 1000BASE-KX interface mode
-
-Add 1000BASE-KX interface mode. This 1G backplane ethernet as described in
-clause 70. Clause 73 autonegotiation is mandatory, and only full duplex
-operation is supported.
-
-Although at the PMA level this interface mode is identical to
-1000BASE-X, it uses a different form of in-band autonegation. This
-justifies a separate interface mode, since the interface mode (along
-with the MLO_AN_* autonegotiation mode) sets the type of autonegotiation
-which will be used on a link. This results in more than just electrical
-differences between the link modes.
-
-With regard to 1000BASE-X, 1000BASE-KX holds a similar position to
-SGMII: same signaling, but different autonegotiation. PCS drivers
-(which typically handle in-band autonegotiation) may only support
-1000BASE-X, and not 1000BASE-KX. Similarly, the phy mode is used to
-configure serdes phys with phy_set_mode_ext. Due to the different
-electrical standards (SFI or XFI vs Clause 70), they will likely want to
-use different configuration. Adding a phy interface mode for
-1000BASE-KX helps simplify configuration in these areas.
-
-Signed-off-by: Sean Anderson <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- Documentation/networking/phy.rst | 6 ++++++
- drivers/net/phy/phy-core.c       | 1 +
- drivers/net/phy/phylink.c        | 1 +
- include/linux/phy.h              | 4 ++++
- 4 files changed, 12 insertions(+)
-
---- a/Documentation/networking/phy.rst
-+++ b/Documentation/networking/phy.rst
-@@ -312,6 +312,12 @@ Some of the interface modes are describe
-     PTP-enabled PHYs. This mode isn't compatible with QSGMII, but offers the
-     same capabilities in terms of link speed and negociation.
-+``PHY_INTERFACE_MODE_1000BASEKX``
-+    This is 1000BASE-X as defined by IEEE 802.3 Clause 36 with Clause 73
-+    autonegotiation. Generally, it will be used with a Clause 70 PMD. To
-+    contrast with the 1000BASE-X phy mode used for Clause 38 and 39 PMDs, this
-+    interface mode has different autonegotiation and only supports full duplex.
-+
- Pause frames / flow control
- ===========================
---- a/drivers/net/phy/phy-core.c
-+++ b/drivers/net/phy/phy-core.c
-@@ -114,6 +114,7 @@ int phy_interface_num_ports(phy_interfac
-       case PHY_INTERFACE_MODE_100BASEX:
-       case PHY_INTERFACE_MODE_RXAUI:
-       case PHY_INTERFACE_MODE_XAUI:
-+      case PHY_INTERFACE_MODE_1000BASEKX:
-               return 1;
-       case PHY_INTERFACE_MODE_QSGMII:
-       case PHY_INTERFACE_MODE_QUSGMII:
---- a/drivers/net/phy/phylink.c
-+++ b/drivers/net/phy/phylink.c
-@@ -390,6 +390,7 @@ void phylink_get_linkmodes(unsigned long
-       case PHY_INTERFACE_MODE_1000BASEX:
-               caps |= MAC_1000HD;
-               fallthrough;
-+      case PHY_INTERFACE_MODE_1000BASEKX:
-       case PHY_INTERFACE_MODE_TRGMII:
-               caps |= MAC_1000FD;
-               break;
---- a/include/linux/phy.h
-+++ b/include/linux/phy.h
-@@ -116,6 +116,7 @@ extern const int phy_10gbit_features_arr
-  * @PHY_INTERFACE_MODE_USXGMII:  Universal Serial 10GE MII
-  * @PHY_INTERFACE_MODE_10GKR: 10GBASE-KR - with Clause 73 AN
-  * @PHY_INTERFACE_MODE_QUSGMII: Quad Universal SGMII
-+ * @PHY_INTERFACE_MODE_1000BASEKX: 1000Base-KX - with Clause 73 AN
-  * @PHY_INTERFACE_MODE_MAX: Book keeping
-  *
-  * Describes the interface between the MAC and PHY.
-@@ -154,6 +155,7 @@ typedef enum {
-       /* 10GBASE-KR - with Clause 73 AN */
-       PHY_INTERFACE_MODE_10GKR,
-       PHY_INTERFACE_MODE_QUSGMII,
-+      PHY_INTERFACE_MODE_1000BASEKX,
-       PHY_INTERFACE_MODE_MAX,
- } phy_interface_t;
-@@ -251,6 +253,8 @@ static inline const char *phy_modes(phy_
-               return "trgmii";
-       case PHY_INTERFACE_MODE_1000BASEX:
-               return "1000base-x";
-+      case PHY_INTERFACE_MODE_1000BASEKX:
-+              return "1000base-kx";
-       case PHY_INTERFACE_MODE_2500BASEX:
-               return "2500base-x";
-       case PHY_INTERFACE_MODE_5GBASER:
diff --git a/target/linux/generic/backport-5.15/731-v6.1-0004-net-phy-Add-support-for-rate-matching.patch b/target/linux/generic/backport-5.15/731-v6.1-0004-net-phy-Add-support-for-rate-matching.patch
deleted file mode 100644 (file)
index fc02d7a..0000000
+++ /dev/null
@@ -1,294 +0,0 @@
-From 0c3e10cb44232833a50cb8e3e784c432906a60c1 Mon Sep 17 00:00:00 2001
-From: Sean Anderson <[email protected]>
-Date: Tue, 20 Sep 2022 18:12:31 -0400
-Subject: [PATCH] net: phy: Add support for rate matching
-
-This adds support for rate matching (also known as rate adaptation) to
-the phy subsystem. The general idea is that the phy interface runs at
-one speed, and the MAC throttles the rate at which it sends packets to
-the link speed. There's a good overview of several techniques for
-achieving this at [1]. This patch adds support for three: pause-frame
-based (such as in Aquantia phys), CRS-based (such as in 10PASS-TS and
-2BASE-TL), and open-loop-based (such as in 10GBASE-W).
-
-This patch makes a few assumptions and a few non assumptions about the
-types of rate matching available. First, it assumes that different phys
-may use different forms of rate matching. Second, it assumes that phys
-can use rate matching for any of their supported link speeds (e.g. if a
-phy supports 10BASE-T and XGMII, then it can adapt XGMII to 10BASE-T).
-Third, it does not assume that all interface modes will use the same
-form of rate matching. Fourth, it does not assume that all phy devices
-will support rate matching (even if some do). Relaxing or strengthening
-these (non-)assumptions could result in a different API. For example, if
-all interface modes were assumed to use the same form of rate matching,
-then a bitmask of interface modes supportting rate matching would
-suffice.
-
-For some better visibility into the process, the current rate matching
-mode is exposed as part of the ethtool ksettings. For the moment, only
-read access is supported. I'm not sure what userspace might want to
-configure yet (disable it altogether, disable just one mode, specify the
-mode to use, etc.). For the moment, since only pause-based rate
-adaptation support is added in the next few commits, rate matching can
-be disabled altogether by adjusting the advertisement.
-
-802.3 calls this feature "rate adaptation" in clause 49 (10GBASE-R) and
-"rate matching" in clause 61 (10PASS-TL and 2BASE-TS). Aquantia also calls
-this feature "rate adaptation". I chose "rate matching" because it is
-shorter, and because Russell doesn't think "adaptation" is correct in this
-context.
-
-Signed-off-by: Sean Anderson <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- Documentation/networking/ethtool-netlink.rst |  2 ++
- drivers/net/phy/phy-core.c                   | 21 +++++++++++++++
- drivers/net/phy/phy.c                        | 28 ++++++++++++++++++++
- include/linux/phy.h                          | 22 ++++++++++++++-
- include/uapi/linux/ethtool.h                 | 18 +++++++++++--
- include/uapi/linux/ethtool_netlink.h         |  1 +
- net/ethtool/ioctl.c                          |  1 +
- net/ethtool/linkmodes.c                      |  5 ++++
- 8 files changed, 95 insertions(+), 3 deletions(-)
-
---- a/Documentation/networking/ethtool-netlink.rst
-+++ b/Documentation/networking/ethtool-netlink.rst
-@@ -418,6 +418,7 @@ Kernel response contents:
-   ``ETHTOOL_A_LINKMODES_DUPLEX``              u8      duplex mode
-   ``ETHTOOL_A_LINKMODES_MASTER_SLAVE_CFG``    u8      Master/slave port mode
-   ``ETHTOOL_A_LINKMODES_MASTER_SLAVE_STATE``  u8      Master/slave port state
-+  ``ETHTOOL_A_LINKMODES_RATE_MATCHING``       u8      PHY rate matching
-   ==========================================  ======  ==========================
- For ``ETHTOOL_A_LINKMODES_OURS``, value represents advertised modes and mask
-@@ -441,6 +442,7 @@ Request contents:
-   ``ETHTOOL_A_LINKMODES_SPEED``               u32     link speed (Mb/s)
-   ``ETHTOOL_A_LINKMODES_DUPLEX``              u8      duplex mode
-   ``ETHTOOL_A_LINKMODES_MASTER_SLAVE_CFG``    u8      Master/slave port mode
-+  ``ETHTOOL_A_LINKMODES_RATE_MATCHING``       u8      PHY rate matching
-   ``ETHTOOL_A_LINKMODES_LANES``               u32     lanes
-   ==========================================  ======  ==========================
---- a/drivers/net/phy/phy-core.c
-+++ b/drivers/net/phy/phy-core.c
-@@ -75,6 +75,27 @@ const char *phy_duplex_to_str(unsigned i
- EXPORT_SYMBOL_GPL(phy_duplex_to_str);
- /**
-+ * phy_rate_matching_to_str - Return a string describing the rate matching
-+ *
-+ * @rate_matching: Type of rate matching to describe
-+ */
-+const char *phy_rate_matching_to_str(int rate_matching)
-+{
-+      switch (rate_matching) {
-+      case RATE_MATCH_NONE:
-+              return "none";
-+      case RATE_MATCH_PAUSE:
-+              return "pause";
-+      case RATE_MATCH_CRS:
-+              return "crs";
-+      case RATE_MATCH_OPEN_LOOP:
-+              return "open-loop";
-+      }
-+      return "Unsupported (update phy-core.c)";
-+}
-+EXPORT_SYMBOL_GPL(phy_rate_matching_to_str);
-+
-+/**
-  * phy_interface_num_ports - Return the number of links that can be carried by
-  *                         a given MAC-PHY physical link. Returns 0 if this is
-  *                         unknown, the number of links else.
---- a/drivers/net/phy/phy.c
-+++ b/drivers/net/phy/phy.c
-@@ -127,6 +127,33 @@ void phy_print_status(struct phy_device
- EXPORT_SYMBOL(phy_print_status);
- /**
-+ * phy_get_rate_matching - determine if rate matching is supported
-+ * @phydev: The phy device to return rate matching for
-+ * @iface: The interface mode to use
-+ *
-+ * This determines the type of rate matching (if any) that @phy supports
-+ * using @iface. @iface may be %PHY_INTERFACE_MODE_NA to determine if any
-+ * interface supports rate matching.
-+ *
-+ * Return: The type of rate matching @phy supports for @iface, or
-+ *         %RATE_MATCH_NONE.
-+ */
-+int phy_get_rate_matching(struct phy_device *phydev,
-+                        phy_interface_t iface)
-+{
-+      int ret = RATE_MATCH_NONE;
-+
-+      if (phydev->drv->get_rate_matching) {
-+              mutex_lock(&phydev->lock);
-+              ret = phydev->drv->get_rate_matching(phydev, iface);
-+              mutex_unlock(&phydev->lock);
-+      }
-+
-+      return ret;
-+}
-+EXPORT_SYMBOL_GPL(phy_get_rate_matching);
-+
-+/**
-  * phy_config_interrupt - configure the PHY device for the requested interrupts
-  * @phydev: the phy_device struct
-  * @interrupts: interrupt flags to configure for this @phydev
-@@ -268,6 +295,7 @@ void phy_ethtool_ksettings_get(struct ph
-       cmd->base.duplex = phydev->duplex;
-       cmd->base.master_slave_cfg = phydev->master_slave_get;
-       cmd->base.master_slave_state = phydev->master_slave_state;
-+      cmd->base.rate_matching = phydev->rate_matching;
-       if (phydev->interface == PHY_INTERFACE_MODE_MOCA)
-               cmd->base.port = PORT_BNC;
-       else
---- a/include/linux/phy.h
-+++ b/include/linux/phy.h
-@@ -280,7 +280,6 @@ static inline const char *phy_modes(phy_
-       }
- }
--
- #define PHY_INIT_TIMEOUT      100000
- #define PHY_FORCE_TIMEOUT     10
-@@ -573,6 +572,7 @@ struct macsec_ops;
-  * @lp_advertising: Current link partner advertised linkmodes
-  * @eee_broken_modes: Energy efficient ethernet modes which should be prohibited
-  * @autoneg: Flag autoneg being used
-+ * @rate_matching: Current rate matching mode
-  * @link: Current link state
-  * @autoneg_complete: Flag auto negotiation of the link has completed
-  * @mdix: Current crossover
-@@ -639,6 +639,8 @@ struct phy_device {
-       unsigned irq_suspended:1;
-       unsigned irq_rerun:1;
-+      int rate_matching;
-+
-       enum phy_state state;
-       u32 dev_flags;
-@@ -801,6 +803,21 @@ struct phy_driver {
-        */
-       int (*get_features)(struct phy_device *phydev);
-+      /**
-+       * @get_rate_matching: Get the supported type of rate matching for a
-+       * particular phy interface. This is used by phy consumers to determine
-+       * whether to advertise lower-speed modes for that interface. It is
-+       * assumed that if a rate matching mode is supported on an interface,
-+       * then that interface's rate can be adapted to all slower link speeds
-+       * supported by the phy. If iface is %PHY_INTERFACE_MODE_NA, and the phy
-+       * supports any kind of rate matching for any interface, then it must
-+       * return that rate matching mode (preferring %RATE_MATCH_PAUSE to
-+       * %RATE_MATCH_CRS). If the interface is not supported, this should
-+       * return %RATE_MATCH_NONE.
-+       */
-+      int (*get_rate_matching)(struct phy_device *phydev,
-+                                 phy_interface_t iface);
-+
-       /* PHY Power Management */
-       /** @suspend: Suspend the hardware, saving state if needed */
-       int (*suspend)(struct phy_device *phydev);
-@@ -967,6 +984,7 @@ struct phy_fixup {
- const char *phy_speed_to_str(int speed);
- const char *phy_duplex_to_str(unsigned int duplex);
-+const char *phy_rate_matching_to_str(int rate_matching);
- int phy_interface_num_ports(phy_interface_t interface);
-@@ -1675,6 +1693,8 @@ int phy_disable_interrupts(struct phy_de
- void phy_request_interrupt(struct phy_device *phydev);
- void phy_free_interrupt(struct phy_device *phydev);
- void phy_print_status(struct phy_device *phydev);
-+int phy_get_rate_matching(struct phy_device *phydev,
-+                          phy_interface_t iface);
- int phy_set_max_speed(struct phy_device *phydev, u32 max_speed);
- void phy_remove_link_mode(struct phy_device *phydev, u32 link_mode);
- void phy_advertise_supported(struct phy_device *phydev);
---- a/include/uapi/linux/ethtool.h
-+++ b/include/uapi/linux/ethtool.h
-@@ -1809,6 +1809,20 @@ static inline int ethtool_validate_duple
- #define MASTER_SLAVE_STATE_SLAVE              3
- #define MASTER_SLAVE_STATE_ERR                        4
-+/* These are used to throttle the rate of data on the phy interface when the
-+ * native speed of the interface is higher than the link speed. These should
-+ * not be used for phy interfaces which natively support multiple speeds (e.g.
-+ * MII or SGMII).
-+ */
-+/* No rate matching performed. */
-+#define RATE_MATCH_NONE               0
-+/* The phy sends pause frames to throttle the MAC. */
-+#define RATE_MATCH_PAUSE      1
-+/* The phy asserts CRS to prevent the MAC from transmitting. */
-+#define RATE_MATCH_CRS                2
-+/* The MAC is programmed with a sufficiently-large IPG. */
-+#define RATE_MATCH_OPEN_LOOP  3
-+
- /* Which connector port. */
- #define PORT_TP                       0x00
- #define PORT_AUI              0x01
-@@ -2002,8 +2016,8 @@ enum ethtool_reset_flags {
-  *    reported consistently by PHYLIB.  Read-only.
-  * @master_slave_cfg: Master/slave port mode.
-  * @master_slave_state: Master/slave port state.
-+ * @rate_matching: Rate adaptation performed by the PHY
-  * @reserved: Reserved for future use; see the note on reserved space.
-- * @reserved1: Reserved for future use; see the note on reserved space.
-  * @link_mode_masks: Variable length bitmaps.
-  *
-  * If autonegotiation is disabled, the speed and @duplex represent the
-@@ -2054,7 +2068,7 @@ struct ethtool_link_settings {
-       __u8    transceiver;
-       __u8    master_slave_cfg;
-       __u8    master_slave_state;
--      __u8    reserved1[1];
-+      __u8    rate_matching;
-       __u32   reserved[7];
-       __u32   link_mode_masks[0];
-       /* layout of link_mode_masks fields:
---- a/include/uapi/linux/ethtool_netlink.h
-+++ b/include/uapi/linux/ethtool_netlink.h
-@@ -238,6 +238,7 @@ enum {
-       ETHTOOL_A_LINKMODES_MASTER_SLAVE_CFG,   /* u8 */
-       ETHTOOL_A_LINKMODES_MASTER_SLAVE_STATE, /* u8 */
-       ETHTOOL_A_LINKMODES_LANES,              /* u32 */
-+      ETHTOOL_A_LINKMODES_RATE_MATCHING,      /* u8 */
-       /* add new constants above here */
-       __ETHTOOL_A_LINKMODES_CNT,
---- a/net/ethtool/ioctl.c
-+++ b/net/ethtool/ioctl.c
-@@ -559,6 +559,7 @@ static int ethtool_get_link_ksettings(st
-               = __ETHTOOL_LINK_MODE_MASK_NU32;
-       link_ksettings.base.master_slave_cfg = MASTER_SLAVE_CFG_UNSUPPORTED;
-       link_ksettings.base.master_slave_state = MASTER_SLAVE_STATE_UNSUPPORTED;
-+      link_ksettings.base.rate_matching = RATE_MATCH_NONE;
-       return store_link_ksettings_for_user(useraddr, &link_ksettings);
- }
---- a/net/ethtool/linkmodes.c
-+++ b/net/ethtool/linkmodes.c
-@@ -70,6 +70,7 @@ static int linkmodes_reply_size(const st
-               + nla_total_size(sizeof(u32)) /* LINKMODES_SPEED */
-               + nla_total_size(sizeof(u32)) /* LINKMODES_LANES */
-               + nla_total_size(sizeof(u8)) /* LINKMODES_DUPLEX */
-+              + nla_total_size(sizeof(u8)) /* LINKMODES_RATE_MATCHING */
-               + 0;
-       ret = ethnl_bitset_size(ksettings->link_modes.advertising,
-                               ksettings->link_modes.supported,
-@@ -143,6 +144,10 @@ static int linkmodes_fill_reply(struct s
-                      lsettings->master_slave_state))
-               return -EMSGSIZE;
-+      if (nla_put_u8(skb, ETHTOOL_A_LINKMODES_RATE_MATCHING,
-+                     lsettings->rate_matching))
-+              return -EMSGSIZE;
-+
-       return 0;
- }
diff --git a/target/linux/generic/backport-5.15/733-v6.2-01-net-ethernet-mtk_eth_soc-Avoid-truncating-allocation.patch b/target/linux/generic/backport-5.15/733-v6.2-01-net-ethernet-mtk_eth_soc-Avoid-truncating-allocation.patch
deleted file mode 100644 (file)
index 460c5c2..0000000
+++ /dev/null
@@ -1,60 +0,0 @@
-From f3eceaed9edd7c0e0d9fb057613131f92973626f Mon Sep 17 00:00:00 2001
-From: Kees Cook <[email protected]>
-Date: Fri, 27 Jan 2023 14:38:54 -0800
-Subject: [PATCH] net: ethernet: mtk_eth_soc: Avoid truncating allocation
-
-There doesn't appear to be a reason to truncate the allocation used for
-flow_info, so do a full allocation and remove the unused empty struct.
-GCC does not like having a reference to an object that has been
-partially allocated, as bounds checking may become impossible when
-such an object is passed to other code. Seen with GCC 13:
-
-../drivers/net/ethernet/mediatek/mtk_ppe.c: In function 'mtk_foe_entry_commit_subflow':
-../drivers/net/ethernet/mediatek/mtk_ppe.c:623:18: warning: array subscript 'struct mtk_flow_entry[0]' is partly outside array bounds of 'unsigned char[48]' [-Warray-bounds=]
-  623 |         flow_info->l2_data.base_flow = entry;
-      |                  ^~
-
-Cc: Felix Fietkau <[email protected]>
-Cc: John Crispin <[email protected]>
-Cc: Sean Wang <[email protected]>
-Cc: Mark Lee <[email protected]>
-Cc: Lorenzo Bianconi <[email protected]>
-Cc: "David S. Miller" <[email protected]>
-Cc: Eric Dumazet <[email protected]>
-Cc: Jakub Kicinski <[email protected]>
-Cc: Paolo Abeni <[email protected]>
-Cc: Matthias Brugger <[email protected]>
-Signed-off-by: Kees Cook <[email protected]>
-Reviewed-by: Simon Horman <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Paolo Abeni <[email protected]>
----
- drivers/net/ethernet/mediatek/mtk_ppe.c | 3 +--
- drivers/net/ethernet/mediatek/mtk_ppe.h | 1 -
- 2 files changed, 1 insertion(+), 3 deletions(-)
-
---- a/drivers/net/ethernet/mediatek/mtk_ppe.c
-+++ b/drivers/net/ethernet/mediatek/mtk_ppe.c
-@@ -621,8 +621,7 @@ mtk_foe_entry_commit_subflow(struct mtk_
-       u32 ib1_mask = mtk_get_ib1_pkt_type_mask(ppe->eth) | MTK_FOE_IB1_UDP;
-       int type;
--      flow_info = kzalloc(offsetof(struct mtk_flow_entry, l2_data.end),
--                          GFP_ATOMIC);
-+      flow_info = kzalloc(sizeof(*flow_info), GFP_ATOMIC);
-       if (!flow_info)
-               return;
---- a/drivers/net/ethernet/mediatek/mtk_ppe.h
-+++ b/drivers/net/ethernet/mediatek/mtk_ppe.h
-@@ -279,7 +279,6 @@ struct mtk_flow_entry {
-               struct {
-                       struct mtk_flow_entry *base_flow;
-                       struct hlist_node list;
--                      struct {} end;
-               } l2_data;
-       };
-       struct rhash_head node;
diff --git a/target/linux/generic/backport-5.15/733-v6.2-02-net-mtk_eth_soc-add-definitions-for-PCS.patch b/target/linux/generic/backport-5.15/733-v6.2-02-net-mtk_eth_soc-add-definitions-for-PCS.patch
deleted file mode 100644 (file)
index 68f3659..0000000
+++ /dev/null
@@ -1,55 +0,0 @@
-From b6a709cb51f7bdc55c01cec886098a9753ce8c28 Mon Sep 17 00:00:00 2001
-From: "Russell King (Oracle)" <[email protected]>
-Date: Thu, 27 Oct 2022 14:10:42 +0100
-Subject: [PATCH 01/10] net: mtk_eth_soc: add definitions for PCS
-
-As a result of help from Frank Wunderlich to investigate and test, we
-know a bit more about the PCS on the Mediatek platforms. Update the
-definitions from this investigation.
-
-This PCS appears similar, but not identical to the Lynx PCS.
-
-Although not included in this patch, but for future reference, the PHY
-ID registers at offset 4 read as 0x4d544950 'MTIP'.
-
-Signed-off-by: Russell King (Oracle) <[email protected]>
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- drivers/net/ethernet/mediatek/mtk_eth_soc.h | 13 ++++++++++---
- 1 file changed, 10 insertions(+), 3 deletions(-)
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-@@ -501,8 +501,10 @@
- #define ETHSYS_DMA_AG_MAP_PPE BIT(2)
- /* SGMII subsystem config registers */
--/* Register to auto-negotiation restart */
-+/* BMCR (low 16) BMSR (high 16) */
- #define SGMSYS_PCS_CONTROL_1  0x0
-+#define SGMII_BMCR            GENMASK(15, 0)
-+#define SGMII_BMSR            GENMASK(31, 16)
- #define SGMII_AN_RESTART      BIT(9)
- #define SGMII_ISOLATE         BIT(10)
- #define SGMII_AN_ENABLE               BIT(12)
-@@ -512,13 +514,18 @@
- #define SGMII_PCS_FAULT               BIT(23)
- #define SGMII_AN_EXPANSION_CLR        BIT(30)
-+#define SGMSYS_PCS_ADVERTISE  0x8
-+#define SGMII_ADVERTISE               GENMASK(15, 0)
-+#define SGMII_LPA             GENMASK(31, 16)
-+
- /* Register to programmable link timer, the unit in 2 * 8ns */
- #define SGMSYS_PCS_LINK_TIMER 0x18
--#define SGMII_LINK_TIMER_DEFAULT      (0x186a0 & GENMASK(19, 0))
-+#define SGMII_LINK_TIMER_MASK GENMASK(19, 0)
-+#define SGMII_LINK_TIMER_DEFAULT      (0x186a0 & SGMII_LINK_TIMER_MASK)
- /* Register to control remote fault */
- #define SGMSYS_SGMII_MODE             0x20
--#define SGMII_IF_MODE_BIT0            BIT(0)
-+#define SGMII_IF_MODE_SGMII           BIT(0)
- #define SGMII_SPEED_DUPLEX_AN         BIT(1)
- #define SGMII_SPEED_MASK              GENMASK(3, 2)
- #define SGMII_SPEED_10                        FIELD_PREP(SGMII_SPEED_MASK, 0)
diff --git a/target/linux/generic/backport-5.15/733-v6.2-03-net-mtk_eth_soc-eliminate-unnecessary-error-handling.patch b/target/linux/generic/backport-5.15/733-v6.2-03-net-mtk_eth_soc-eliminate-unnecessary-error-handling.patch
deleted file mode 100644 (file)
index 4ea428c..0000000
+++ /dev/null
@@ -1,74 +0,0 @@
-From 5cf7797526ee81bea0f627bccaa3d887f48f53e0 Mon Sep 17 00:00:00 2001
-From: "Russell King (Oracle)" <[email protected]>
-Date: Thu, 27 Oct 2022 14:10:47 +0100
-Subject: [PATCH 02/10] net: mtk_eth_soc: eliminate unnecessary error handling
-
-The functions called by the pcs_config() method always return zero, so
-there is no point trying to handle an error from these functions. Make
-these functions void, eliminate the "err" variable and simply return
-zero from the pcs_config() function itself.
-
-Signed-off-by: Russell King (Oracle) <[email protected]>
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- drivers/net/ethernet/mediatek/mtk_sgmii.c | 18 ++++++------------
- 1 file changed, 6 insertions(+), 12 deletions(-)
-
---- a/drivers/net/ethernet/mediatek/mtk_sgmii.c
-+++ b/drivers/net/ethernet/mediatek/mtk_sgmii.c
-@@ -20,7 +20,7 @@ static struct mtk_pcs *pcs_to_mtk_pcs(st
- }
- /* For SGMII interface mode */
--static int mtk_pcs_setup_mode_an(struct mtk_pcs *mpcs)
-+static void mtk_pcs_setup_mode_an(struct mtk_pcs *mpcs)
- {
-       unsigned int val;
-@@ -39,16 +39,13 @@ static int mtk_pcs_setup_mode_an(struct
-       regmap_read(mpcs->regmap, SGMSYS_QPHY_PWR_STATE_CTRL, &val);
-       val &= ~SGMII_PHYA_PWD;
-       regmap_write(mpcs->regmap, SGMSYS_QPHY_PWR_STATE_CTRL, val);
--
--      return 0;
--
- }
- /* For 1000BASE-X and 2500BASE-X interface modes, which operate at a
-  * fixed speed.
-  */
--static int mtk_pcs_setup_mode_force(struct mtk_pcs *mpcs,
--                                  phy_interface_t interface)
-+static void mtk_pcs_setup_mode_force(struct mtk_pcs *mpcs,
-+                                   phy_interface_t interface)
- {
-       unsigned int val;
-@@ -73,8 +70,6 @@ static int mtk_pcs_setup_mode_force(stru
-       regmap_read(mpcs->regmap, SGMSYS_QPHY_PWR_STATE_CTRL, &val);
-       val &= ~SGMII_PHYA_PWD;
-       regmap_write(mpcs->regmap, SGMSYS_QPHY_PWR_STATE_CTRL, val);
--
--      return 0;
- }
- static int mtk_pcs_config(struct phylink_pcs *pcs, unsigned int mode,
-@@ -83,15 +78,14 @@ static int mtk_pcs_config(struct phylink
-                         bool permit_pause_to_mac)
- {
-       struct mtk_pcs *mpcs = pcs_to_mtk_pcs(pcs);
--      int err = 0;
-       /* Setup SGMIISYS with the determined property */
-       if (interface != PHY_INTERFACE_MODE_SGMII)
--              err = mtk_pcs_setup_mode_force(mpcs, interface);
-+              mtk_pcs_setup_mode_force(mpcs, interface);
-       else if (phylink_autoneg_inband(mode))
--              err = mtk_pcs_setup_mode_an(mpcs);
-+              mtk_pcs_setup_mode_an(mpcs);
--      return err;
-+      return 0;
- }
- static void mtk_pcs_restart_an(struct phylink_pcs *pcs)
diff --git a/target/linux/generic/backport-5.15/733-v6.2-04-net-mtk_eth_soc-add-pcs_get_state-implementation.patch b/target/linux/generic/backport-5.15/733-v6.2-04-net-mtk_eth_soc-add-pcs_get_state-implementation.patch
deleted file mode 100644 (file)
index 64a4a72..0000000
+++ /dev/null
@@ -1,46 +0,0 @@
-From c000dca098002da193b98099df051c9ead0cacb4 Mon Sep 17 00:00:00 2001
-From: "Russell King (Oracle)" <[email protected]>
-Date: Thu, 27 Oct 2022 14:10:52 +0100
-Subject: [PATCH 03/10] net: mtk_eth_soc: add pcs_get_state() implementation
-
-Add a pcs_get_state() implementation which uses the advertisements
-to compute the resulting link modes, and BMSR contents to determine
-negotiation and link status.
-
-Signed-off-by: Russell King (Oracle) <[email protected]>
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- drivers/net/ethernet/mediatek/mtk_sgmii.c | 15 +++++++++++++++
- 1 file changed, 15 insertions(+)
-
---- a/drivers/net/ethernet/mediatek/mtk_sgmii.c
-+++ b/drivers/net/ethernet/mediatek/mtk_sgmii.c
-@@ -19,6 +19,20 @@ static struct mtk_pcs *pcs_to_mtk_pcs(st
-       return container_of(pcs, struct mtk_pcs, pcs);
- }
-+static void mtk_pcs_get_state(struct phylink_pcs *pcs,
-+                            struct phylink_link_state *state)
-+{
-+      struct mtk_pcs *mpcs = pcs_to_mtk_pcs(pcs);
-+      unsigned int bm, adv;
-+
-+      /* Read the BMSR and LPA */
-+      regmap_read(mpcs->regmap, SGMSYS_PCS_CONTROL_1, &bm);
-+      regmap_read(mpcs->regmap, SGMSYS_PCS_ADVERTISE, &adv);
-+
-+      phylink_mii_c22_pcs_decode_state(state, FIELD_GET(SGMII_BMSR, bm),
-+                                       FIELD_GET(SGMII_LPA, adv));
-+}
-+
- /* For SGMII interface mode */
- static void mtk_pcs_setup_mode_an(struct mtk_pcs *mpcs)
- {
-@@ -117,6 +131,7 @@ static void mtk_pcs_link_up(struct phyli
- }
- static const struct phylink_pcs_ops mtk_pcs_ops = {
-+      .pcs_get_state = mtk_pcs_get_state,
-       .pcs_config = mtk_pcs_config,
-       .pcs_an_restart = mtk_pcs_restart_an,
-       .pcs_link_up = mtk_pcs_link_up,
diff --git a/target/linux/generic/backport-5.15/733-v6.2-05-net-mtk_eth_soc-convert-mtk_sgmii-to-use-regmap_upda.patch b/target/linux/generic/backport-5.15/733-v6.2-05-net-mtk_eth_soc-convert-mtk_sgmii-to-use-regmap_upda.patch
deleted file mode 100644 (file)
index 24610fe..0000000
+++ /dev/null
@@ -1,130 +0,0 @@
-From 0d2351dc2768061689abd4de1529fa206bbd574e Mon Sep 17 00:00:00 2001
-From: "Russell King (Oracle)" <[email protected]>
-Date: Thu, 27 Oct 2022 14:10:58 +0100
-Subject: [PATCH 04/10] net: mtk_eth_soc: convert mtk_sgmii to use
- regmap_update_bits()
-
-mtk_sgmii does a lot of read-modify-write operations, for which there
-is a specific regmap function. Use this function instead of open-coding
-the operations.
-
-Signed-off-by: Russell King (Oracle) <[email protected]>
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- drivers/net/ethernet/mediatek/mtk_sgmii.c | 61 ++++++++++-------------
- 1 file changed, 26 insertions(+), 35 deletions(-)
-
---- a/drivers/net/ethernet/mediatek/mtk_sgmii.c
-+++ b/drivers/net/ethernet/mediatek/mtk_sgmii.c
-@@ -36,23 +36,18 @@ static void mtk_pcs_get_state(struct phy
- /* For SGMII interface mode */
- static void mtk_pcs_setup_mode_an(struct mtk_pcs *mpcs)
- {
--      unsigned int val;
--
-       /* Setup the link timer and QPHY power up inside SGMIISYS */
-       regmap_write(mpcs->regmap, SGMSYS_PCS_LINK_TIMER,
-                    SGMII_LINK_TIMER_DEFAULT);
--      regmap_read(mpcs->regmap, SGMSYS_SGMII_MODE, &val);
--      val |= SGMII_REMOTE_FAULT_DIS;
--      regmap_write(mpcs->regmap, SGMSYS_SGMII_MODE, val);
--
--      regmap_read(mpcs->regmap, SGMSYS_PCS_CONTROL_1, &val);
--      val |= SGMII_AN_RESTART;
--      regmap_write(mpcs->regmap, SGMSYS_PCS_CONTROL_1, val);
--
--      regmap_read(mpcs->regmap, SGMSYS_QPHY_PWR_STATE_CTRL, &val);
--      val &= ~SGMII_PHYA_PWD;
--      regmap_write(mpcs->regmap, SGMSYS_QPHY_PWR_STATE_CTRL, val);
-+      regmap_update_bits(mpcs->regmap, SGMSYS_SGMII_MODE,
-+                         SGMII_REMOTE_FAULT_DIS, SGMII_REMOTE_FAULT_DIS);
-+
-+      regmap_update_bits(mpcs->regmap, SGMSYS_PCS_CONTROL_1,
-+                         SGMII_AN_RESTART, SGMII_AN_RESTART);
-+
-+      regmap_update_bits(mpcs->regmap, SGMSYS_QPHY_PWR_STATE_CTRL,
-+                         SGMII_PHYA_PWD, 0);
- }
- /* For 1000BASE-X and 2500BASE-X interface modes, which operate at a
-@@ -61,29 +56,26 @@ static void mtk_pcs_setup_mode_an(struct
- static void mtk_pcs_setup_mode_force(struct mtk_pcs *mpcs,
-                                    phy_interface_t interface)
- {
--      unsigned int val;
-+      unsigned int rgc3;
--      regmap_read(mpcs->regmap, mpcs->ana_rgc3, &val);
--      val &= ~RG_PHY_SPEED_MASK;
-       if (interface == PHY_INTERFACE_MODE_2500BASEX)
--              val |= RG_PHY_SPEED_3_125G;
--      regmap_write(mpcs->regmap, mpcs->ana_rgc3, val);
-+              rgc3 = RG_PHY_SPEED_3_125G;
-+
-+      regmap_update_bits(mpcs->regmap, mpcs->ana_rgc3,
-+                         RG_PHY_SPEED_3_125G, rgc3);
-       /* Disable SGMII AN */
--      regmap_read(mpcs->regmap, SGMSYS_PCS_CONTROL_1, &val);
--      val &= ~SGMII_AN_ENABLE;
--      regmap_write(mpcs->regmap, SGMSYS_PCS_CONTROL_1, val);
-+      regmap_update_bits(mpcs->regmap, SGMSYS_PCS_CONTROL_1,
-+                         SGMII_AN_ENABLE, 0);
-       /* Set the speed etc but leave the duplex unchanged */
--      regmap_read(mpcs->regmap, SGMSYS_SGMII_MODE, &val);
--      val &= SGMII_DUPLEX_FULL | ~SGMII_IF_MODE_MASK;
--      val |= SGMII_SPEED_1000;
--      regmap_write(mpcs->regmap, SGMSYS_SGMII_MODE, val);
-+      regmap_update_bits(mpcs->regmap, SGMSYS_SGMII_MODE,
-+                         SGMII_IF_MODE_MASK & ~SGMII_DUPLEX_FULL,
-+                         SGMII_SPEED_1000);
-       /* Release PHYA power down state */
--      regmap_read(mpcs->regmap, SGMSYS_QPHY_PWR_STATE_CTRL, &val);
--      val &= ~SGMII_PHYA_PWD;
--      regmap_write(mpcs->regmap, SGMSYS_QPHY_PWR_STATE_CTRL, val);
-+      regmap_update_bits(mpcs->regmap, SGMSYS_QPHY_PWR_STATE_CTRL,
-+                         SGMII_PHYA_PWD, 0);
- }
- static int mtk_pcs_config(struct phylink_pcs *pcs, unsigned int mode,
-@@ -105,29 +97,28 @@ static int mtk_pcs_config(struct phylink
- static void mtk_pcs_restart_an(struct phylink_pcs *pcs)
- {
-       struct mtk_pcs *mpcs = pcs_to_mtk_pcs(pcs);
--      unsigned int val;
--      regmap_read(mpcs->regmap, SGMSYS_PCS_CONTROL_1, &val);
--      val |= SGMII_AN_RESTART;
--      regmap_write(mpcs->regmap, SGMSYS_PCS_CONTROL_1, val);
-+      regmap_update_bits(mpcs->regmap, SGMSYS_PCS_CONTROL_1,
-+                         SGMII_AN_RESTART, SGMII_AN_RESTART);
- }
- static void mtk_pcs_link_up(struct phylink_pcs *pcs, unsigned int mode,
-                           phy_interface_t interface, int speed, int duplex)
- {
-       struct mtk_pcs *mpcs = pcs_to_mtk_pcs(pcs);
--      unsigned int val;
-+      unsigned int sgm_mode;
-       if (!phy_interface_mode_is_8023z(interface))
-               return;
-       /* SGMII force duplex setting */
--      regmap_read(mpcs->regmap, SGMSYS_SGMII_MODE, &val);
--      val &= ~SGMII_DUPLEX_FULL;
-       if (duplex == DUPLEX_FULL)
--              val |= SGMII_DUPLEX_FULL;
-+              sgm_mode = SGMII_DUPLEX_FULL;
-+      else
-+              sgm_mode = 0;
--      regmap_write(mpcs->regmap, SGMSYS_SGMII_MODE, val);
-+      regmap_update_bits(mpcs->regmap, SGMSYS_SGMII_MODE,
-+                         SGMII_DUPLEX_FULL, sgm_mode);
- }
- static const struct phylink_pcs_ops mtk_pcs_ops = {
diff --git a/target/linux/generic/backport-5.15/733-v6.2-06-net-mtk_eth_soc-add-out-of-band-forcing-of-speed-and.patch b/target/linux/generic/backport-5.15/733-v6.2-06-net-mtk_eth_soc-add-out-of-band-forcing-of-speed-and.patch
deleted file mode 100644 (file)
index ba76ca4..0000000
+++ /dev/null
@@ -1,52 +0,0 @@
-From 12198c3a410fe69843e335c1bbf6d4c2a4d48e4e Mon Sep 17 00:00:00 2001
-From: "Russell King (Oracle)" <[email protected]>
-Date: Thu, 27 Oct 2022 14:11:03 +0100
-Subject: [PATCH 05/10] net: mtk_eth_soc: add out of band forcing of speed and
- duplex in pcs_link_up
-
-Add support for forcing the link speed and duplex setting in the
-pcs_link_up() method for out of band modes, which will be useful when
-we finish converting the pcs_config() method. Until then, we still have
-to force duplex for 802.3z modes to work correctly.
-
-Signed-off-by: Russell King (Oracle) <[email protected]>
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- drivers/net/ethernet/mediatek/mtk_sgmii.c | 28 ++++++++++++++---------
- 1 file changed, 17 insertions(+), 11 deletions(-)
-
---- a/drivers/net/ethernet/mediatek/mtk_sgmii.c
-+++ b/drivers/net/ethernet/mediatek/mtk_sgmii.c
-@@ -108,17 +108,23 @@ static void mtk_pcs_link_up(struct phyli
-       struct mtk_pcs *mpcs = pcs_to_mtk_pcs(pcs);
-       unsigned int sgm_mode;
--      if (!phy_interface_mode_is_8023z(interface))
--              return;
-+      if (!phylink_autoneg_inband(mode) ||
-+          phy_interface_mode_is_8023z(interface)) {
-+              /* Force the speed and duplex setting */
-+              if (speed == SPEED_10)
-+                      sgm_mode = SGMII_SPEED_10;
-+              else if (speed == SPEED_100)
-+                      sgm_mode = SGMII_SPEED_100;
-+              else
-+                      sgm_mode = SGMII_SPEED_1000;
--      /* SGMII force duplex setting */
--      if (duplex == DUPLEX_FULL)
--              sgm_mode = SGMII_DUPLEX_FULL;
--      else
--              sgm_mode = 0;
-+              if (duplex == DUPLEX_FULL)
-+                      sgm_mode |= SGMII_DUPLEX_FULL;
--      regmap_update_bits(mpcs->regmap, SGMSYS_SGMII_MODE,
--                         SGMII_DUPLEX_FULL, sgm_mode);
-+              regmap_update_bits(mpcs->regmap, SGMSYS_SGMII_MODE,
-+                                 SGMII_DUPLEX_FULL | SGMII_SPEED_MASK,
-+                                 sgm_mode);
-+      }
- }
- static const struct phylink_pcs_ops mtk_pcs_ops = {
diff --git a/target/linux/generic/backport-5.15/733-v6.2-07-net-mtk_eth_soc-move-PHY-power-up.patch b/target/linux/generic/backport-5.15/733-v6.2-07-net-mtk_eth_soc-move-PHY-power-up.patch
deleted file mode 100644 (file)
index b76e159..0000000
+++ /dev/null
@@ -1,48 +0,0 @@
-From 6f38fffe2179dd29612aea2c67c46ed6682b4e46 Mon Sep 17 00:00:00 2001
-From: "Russell King (Oracle)" <[email protected]>
-Date: Thu, 27 Oct 2022 14:11:08 +0100
-Subject: [PATCH 06/10] net: mtk_eth_soc: move PHY power up
-
-The PHY power up is common to both configuration paths, so move it into
-the parent function. We need to do this for all serdes modes.
-
-Signed-off-by: Russell King (Oracle) <[email protected]>
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- drivers/net/ethernet/mediatek/mtk_sgmii.c | 11 ++++-------
- 1 file changed, 4 insertions(+), 7 deletions(-)
-
---- a/drivers/net/ethernet/mediatek/mtk_sgmii.c
-+++ b/drivers/net/ethernet/mediatek/mtk_sgmii.c
-@@ -45,9 +45,6 @@ static void mtk_pcs_setup_mode_an(struct
-       regmap_update_bits(mpcs->regmap, SGMSYS_PCS_CONTROL_1,
-                          SGMII_AN_RESTART, SGMII_AN_RESTART);
--
--      regmap_update_bits(mpcs->regmap, SGMSYS_QPHY_PWR_STATE_CTRL,
--                         SGMII_PHYA_PWD, 0);
- }
- /* For 1000BASE-X and 2500BASE-X interface modes, which operate at a
-@@ -72,10 +69,6 @@ static void mtk_pcs_setup_mode_force(str
-       regmap_update_bits(mpcs->regmap, SGMSYS_SGMII_MODE,
-                          SGMII_IF_MODE_MASK & ~SGMII_DUPLEX_FULL,
-                          SGMII_SPEED_1000);
--
--      /* Release PHYA power down state */
--      regmap_update_bits(mpcs->regmap, SGMSYS_QPHY_PWR_STATE_CTRL,
--                         SGMII_PHYA_PWD, 0);
- }
- static int mtk_pcs_config(struct phylink_pcs *pcs, unsigned int mode,
-@@ -91,6 +84,10 @@ static int mtk_pcs_config(struct phylink
-       else if (phylink_autoneg_inband(mode))
-               mtk_pcs_setup_mode_an(mpcs);
-+      /* Release PHYA power down state */
-+      regmap_update_bits(mpcs->regmap, SGMSYS_QPHY_PWR_STATE_CTRL,
-+                         SGMII_PHYA_PWD, 0);
-+
-       return 0;
- }
diff --git a/target/linux/generic/backport-5.15/733-v6.2-08-net-mtk_eth_soc-move-interface-speed-selection.patch b/target/linux/generic/backport-5.15/733-v6.2-08-net-mtk_eth_soc-move-interface-speed-selection.patch
deleted file mode 100644 (file)
index cd9f069..0000000
+++ /dev/null
@@ -1,48 +0,0 @@
-From f752c0df13dfeb721c11d3debb79f08cf437344f Mon Sep 17 00:00:00 2001
-From: "Russell King (Oracle)" <[email protected]>
-Date: Thu, 27 Oct 2022 14:11:13 +0100
-Subject: [PATCH 07/10] net: mtk_eth_soc: move interface speed selection
-
-Move the selection of the underlying interface speed to the pcs_config
-function, so we always program the interface speed.
-
-Signed-off-by: Russell King (Oracle) <[email protected]>
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- drivers/net/ethernet/mediatek/mtk_sgmii.c | 18 ++++++++++--------
- 1 file changed, 10 insertions(+), 8 deletions(-)
-
---- a/drivers/net/ethernet/mediatek/mtk_sgmii.c
-+++ b/drivers/net/ethernet/mediatek/mtk_sgmii.c
-@@ -53,14 +53,6 @@ static void mtk_pcs_setup_mode_an(struct
- static void mtk_pcs_setup_mode_force(struct mtk_pcs *mpcs,
-                                    phy_interface_t interface)
- {
--      unsigned int rgc3;
--
--      if (interface == PHY_INTERFACE_MODE_2500BASEX)
--              rgc3 = RG_PHY_SPEED_3_125G;
--
--      regmap_update_bits(mpcs->regmap, mpcs->ana_rgc3,
--                         RG_PHY_SPEED_3_125G, rgc3);
--
-       /* Disable SGMII AN */
-       regmap_update_bits(mpcs->regmap, SGMSYS_PCS_CONTROL_1,
-                          SGMII_AN_ENABLE, 0);
-@@ -77,6 +69,16 @@ static int mtk_pcs_config(struct phylink
-                         bool permit_pause_to_mac)
- {
-       struct mtk_pcs *mpcs = pcs_to_mtk_pcs(pcs);
-+      unsigned int rgc3;
-+
-+      if (interface == PHY_INTERFACE_MODE_2500BASEX)
-+              rgc3 = RG_PHY_SPEED_3_125G;
-+      else
-+              rgc3 = 0;
-+
-+      /* Configure the underlying interface speed */
-+      regmap_update_bits(mpcs->regmap, mpcs->ana_rgc3,
-+                         RG_PHY_SPEED_3_125G, rgc3);
-       /* Setup SGMIISYS with the determined property */
-       if (interface != PHY_INTERFACE_MODE_SGMII)
diff --git a/target/linux/generic/backport-5.15/733-v6.2-09-net-mtk_eth_soc-add-advertisement-programming.patch b/target/linux/generic/backport-5.15/733-v6.2-09-net-mtk_eth_soc-add-advertisement-programming.patch
deleted file mode 100644 (file)
index f08358e..0000000
+++ /dev/null
@@ -1,52 +0,0 @@
-From c125c66ea71b9377ae2478c4f1b87b180cc5c6ef Mon Sep 17 00:00:00 2001
-From: "Russell King (Oracle)" <[email protected]>
-Date: Thu, 27 Oct 2022 14:11:18 +0100
-Subject: [PATCH 08/10] net: mtk_eth_soc: add advertisement programming
-
-Program the advertisement into the mtk PCS block.
-
-Signed-off-by: Russell King (Oracle) <[email protected]>
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- drivers/net/ethernet/mediatek/mtk_sgmii.c | 13 ++++++++++++-
- 1 file changed, 12 insertions(+), 1 deletion(-)
-
---- a/drivers/net/ethernet/mediatek/mtk_sgmii.c
-+++ b/drivers/net/ethernet/mediatek/mtk_sgmii.c
-@@ -70,16 +70,27 @@ static int mtk_pcs_config(struct phylink
- {
-       struct mtk_pcs *mpcs = pcs_to_mtk_pcs(pcs);
-       unsigned int rgc3;
-+      int advertise;
-+      bool changed;
-       if (interface == PHY_INTERFACE_MODE_2500BASEX)
-               rgc3 = RG_PHY_SPEED_3_125G;
-       else
-               rgc3 = 0;
-+      advertise = phylink_mii_c22_pcs_encode_advertisement(interface,
-+                                                           advertising);
-+      if (advertise < 0)
-+              return advertise;
-+
-       /* Configure the underlying interface speed */
-       regmap_update_bits(mpcs->regmap, mpcs->ana_rgc3,
-                          RG_PHY_SPEED_3_125G, rgc3);
-+      /* Update the advertisement, noting whether it has changed */
-+      regmap_update_bits_check(mpcs->regmap, SGMSYS_PCS_ADVERTISE,
-+                               SGMII_ADVERTISE, advertise, &changed);
-+
-       /* Setup SGMIISYS with the determined property */
-       if (interface != PHY_INTERFACE_MODE_SGMII)
-               mtk_pcs_setup_mode_force(mpcs, interface);
-@@ -90,7 +101,7 @@ static int mtk_pcs_config(struct phylink
-       regmap_update_bits(mpcs->regmap, SGMSYS_QPHY_PWR_STATE_CTRL,
-                          SGMII_PHYA_PWD, 0);
--      return 0;
-+      return changed;
- }
- static void mtk_pcs_restart_an(struct phylink_pcs *pcs)
diff --git a/target/linux/generic/backport-5.15/733-v6.2-10-net-mtk_eth_soc-move-and-correct-link-timer-programm.patch b/target/linux/generic/backport-5.15/733-v6.2-10-net-mtk_eth_soc-move-and-correct-link-timer-programm.patch
deleted file mode 100644 (file)
index 602d52c..0000000
+++ /dev/null
@@ -1,63 +0,0 @@
-From 3027d89f87707e7f3e5b683e0d37a32afb5bde96 Mon Sep 17 00:00:00 2001
-From: "Russell King (Oracle)" <[email protected]>
-Date: Thu, 27 Oct 2022 14:11:23 +0100
-Subject: [PATCH 09/10] net: mtk_eth_soc: move and correct link timer
- programming
-
-Program the link timer appropriately for the interface mode being
-used, using the newly introduced phylink helper that provides the
-nanosecond link timer interval.
-
-The intervals are 1.6ms for SGMII based protocols and 10ms for
-802.3z based protocols.
-
-Signed-off-by: Russell King (Oracle) <[email protected]>
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- drivers/net/ethernet/mediatek/mtk_sgmii.c | 13 ++++++++-----
- 1 file changed, 8 insertions(+), 5 deletions(-)
-
---- a/drivers/net/ethernet/mediatek/mtk_sgmii.c
-+++ b/drivers/net/ethernet/mediatek/mtk_sgmii.c
-@@ -36,10 +36,6 @@ static void mtk_pcs_get_state(struct phy
- /* For SGMII interface mode */
- static void mtk_pcs_setup_mode_an(struct mtk_pcs *mpcs)
- {
--      /* Setup the link timer and QPHY power up inside SGMIISYS */
--      regmap_write(mpcs->regmap, SGMSYS_PCS_LINK_TIMER,
--                   SGMII_LINK_TIMER_DEFAULT);
--
-       regmap_update_bits(mpcs->regmap, SGMSYS_SGMII_MODE,
-                          SGMII_REMOTE_FAULT_DIS, SGMII_REMOTE_FAULT_DIS);
-@@ -69,8 +65,8 @@ static int mtk_pcs_config(struct phylink
-                         bool permit_pause_to_mac)
- {
-       struct mtk_pcs *mpcs = pcs_to_mtk_pcs(pcs);
-+      int advertise, link_timer;
-       unsigned int rgc3;
--      int advertise;
-       bool changed;
-       if (interface == PHY_INTERFACE_MODE_2500BASEX)
-@@ -83,6 +79,10 @@ static int mtk_pcs_config(struct phylink
-       if (advertise < 0)
-               return advertise;
-+      link_timer = phylink_get_link_timer_ns(interface);
-+      if (link_timer < 0)
-+              return link_timer;
-+
-       /* Configure the underlying interface speed */
-       regmap_update_bits(mpcs->regmap, mpcs->ana_rgc3,
-                          RG_PHY_SPEED_3_125G, rgc3);
-@@ -91,6 +91,9 @@ static int mtk_pcs_config(struct phylink
-       regmap_update_bits_check(mpcs->regmap, SGMSYS_PCS_ADVERTISE,
-                                SGMII_ADVERTISE, advertise, &changed);
-+      /* Setup the link timer and QPHY power up inside SGMIISYS */
-+      regmap_write(mpcs->regmap, SGMSYS_PCS_LINK_TIMER, link_timer / 2 / 8);
-+
-       /* Setup SGMIISYS with the determined property */
-       if (interface != PHY_INTERFACE_MODE_SGMII)
-               mtk_pcs_setup_mode_force(mpcs, interface);
diff --git a/target/linux/generic/backport-5.15/733-v6.2-11-net-mtk_eth_soc-add-support-for-in-band-802.3z-negot.patch b/target/linux/generic/backport-5.15/733-v6.2-11-net-mtk_eth_soc-add-support-for-in-band-802.3z-negot.patch
deleted file mode 100644 (file)
index 0e9a053..0000000
+++ /dev/null
@@ -1,132 +0,0 @@
-From 81b0f12a2a8a1699a7d49c3995e5f71e4ec018e6 Mon Sep 17 00:00:00 2001
-From: "Russell King (Oracle)" <[email protected]>
-Date: Thu, 27 Oct 2022 14:11:28 +0100
-Subject: [PATCH 10/10] net: mtk_eth_soc: add support for in-band 802.3z
- negotiation
-
-As a result of help from Frank Wunderlich to investigate and test, we
-now know how to program this PCS for in-band 802.3z negotiation. Add
-support for this by moving the contents of the two functions into the
-common mtk_pcs_config() function and adding the register settings for
-802.3z negotiation.
-
-Signed-off-by: Russell King (Oracle) <[email protected]>
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- drivers/net/ethernet/mediatek/mtk_sgmii.c | 77 ++++++++++++-----------
- 1 file changed, 42 insertions(+), 35 deletions(-)
-
---- a/drivers/net/ethernet/mediatek/mtk_sgmii.c
-+++ b/drivers/net/ethernet/mediatek/mtk_sgmii.c
-@@ -33,41 +33,15 @@ static void mtk_pcs_get_state(struct phy
-                                        FIELD_GET(SGMII_LPA, adv));
- }
--/* For SGMII interface mode */
--static void mtk_pcs_setup_mode_an(struct mtk_pcs *mpcs)
--{
--      regmap_update_bits(mpcs->regmap, SGMSYS_SGMII_MODE,
--                         SGMII_REMOTE_FAULT_DIS, SGMII_REMOTE_FAULT_DIS);
--
--      regmap_update_bits(mpcs->regmap, SGMSYS_PCS_CONTROL_1,
--                         SGMII_AN_RESTART, SGMII_AN_RESTART);
--}
--
--/* For 1000BASE-X and 2500BASE-X interface modes, which operate at a
-- * fixed speed.
-- */
--static void mtk_pcs_setup_mode_force(struct mtk_pcs *mpcs,
--                                   phy_interface_t interface)
--{
--      /* Disable SGMII AN */
--      regmap_update_bits(mpcs->regmap, SGMSYS_PCS_CONTROL_1,
--                         SGMII_AN_ENABLE, 0);
--
--      /* Set the speed etc but leave the duplex unchanged */
--      regmap_update_bits(mpcs->regmap, SGMSYS_SGMII_MODE,
--                         SGMII_IF_MODE_MASK & ~SGMII_DUPLEX_FULL,
--                         SGMII_SPEED_1000);
--}
--
- static int mtk_pcs_config(struct phylink_pcs *pcs, unsigned int mode,
-                         phy_interface_t interface,
-                         const unsigned long *advertising,
-                         bool permit_pause_to_mac)
- {
-       struct mtk_pcs *mpcs = pcs_to_mtk_pcs(pcs);
-+      unsigned int rgc3, sgm_mode, bmcr;
-       int advertise, link_timer;
--      unsigned int rgc3;
--      bool changed;
-+      bool changed, use_an;
-       if (interface == PHY_INTERFACE_MODE_2500BASEX)
-               rgc3 = RG_PHY_SPEED_3_125G;
-@@ -83,6 +57,37 @@ static int mtk_pcs_config(struct phylink
-       if (link_timer < 0)
-               return link_timer;
-+      /* Clearing IF_MODE_BIT0 switches the PCS to BASE-X mode, and
-+       * we assume that fixes it's speed at bitrate = line rate (in
-+       * other words, 1000Mbps or 2500Mbps).
-+       */
-+      if (interface == PHY_INTERFACE_MODE_SGMII) {
-+              sgm_mode = SGMII_IF_MODE_SGMII;
-+              if (phylink_autoneg_inband(mode)) {
-+                      sgm_mode |= SGMII_REMOTE_FAULT_DIS |
-+                                  SGMII_SPEED_DUPLEX_AN;
-+                      use_an = true;
-+              } else {
-+                      use_an = false;
-+              }
-+      } else if (phylink_autoneg_inband(mode)) {
-+              /* 1000base-X or 2500base-X autoneg */
-+              sgm_mode = SGMII_REMOTE_FAULT_DIS;
-+              use_an = linkmode_test_bit(ETHTOOL_LINK_MODE_Autoneg_BIT,
-+                                         advertising);
-+      } else {
-+              /* 1000base-X or 2500base-X without autoneg */
-+              sgm_mode = 0;
-+              use_an = false;
-+      }
-+
-+      if (use_an) {
-+              /* FIXME: Do we need to set AN_RESTART here? */
-+              bmcr = SGMII_AN_RESTART | SGMII_AN_ENABLE;
-+      } else {
-+              bmcr = 0;
-+      }
-+
-       /* Configure the underlying interface speed */
-       regmap_update_bits(mpcs->regmap, mpcs->ana_rgc3,
-                          RG_PHY_SPEED_3_125G, rgc3);
-@@ -94,11 +99,14 @@ static int mtk_pcs_config(struct phylink
-       /* Setup the link timer and QPHY power up inside SGMIISYS */
-       regmap_write(mpcs->regmap, SGMSYS_PCS_LINK_TIMER, link_timer / 2 / 8);
--      /* Setup SGMIISYS with the determined property */
--      if (interface != PHY_INTERFACE_MODE_SGMII)
--              mtk_pcs_setup_mode_force(mpcs, interface);
--      else if (phylink_autoneg_inband(mode))
--              mtk_pcs_setup_mode_an(mpcs);
-+      /* Update the sgmsys mode register */
-+      regmap_update_bits(mpcs->regmap, SGMSYS_SGMII_MODE,
-+                         SGMII_REMOTE_FAULT_DIS | SGMII_SPEED_DUPLEX_AN |
-+                         SGMII_IF_MODE_SGMII, sgm_mode);
-+
-+      /* Update the BMCR */
-+      regmap_update_bits(mpcs->regmap, SGMSYS_PCS_CONTROL_1,
-+                         SGMII_AN_RESTART | SGMII_AN_ENABLE, bmcr);
-       /* Release PHYA power down state */
-       regmap_update_bits(mpcs->regmap, SGMSYS_QPHY_PWR_STATE_CTRL,
-@@ -121,8 +129,7 @@ static void mtk_pcs_link_up(struct phyli
-       struct mtk_pcs *mpcs = pcs_to_mtk_pcs(pcs);
-       unsigned int sgm_mode;
--      if (!phylink_autoneg_inband(mode) ||
--          phy_interface_mode_is_8023z(interface)) {
-+      if (!phylink_autoneg_inband(mode)) {
-               /* Force the speed and duplex setting */
-               if (speed == SPEED_10)
-                       sgm_mode = SGMII_SPEED_10;
diff --git a/target/linux/generic/backport-5.15/733-v6.2-12-net-mediatek-sgmii-ensure-the-SGMII-PHY-is-powered-d.patch b/target/linux/generic/backport-5.15/733-v6.2-12-net-mediatek-sgmii-ensure-the-SGMII-PHY-is-powered-d.patch
deleted file mode 100644 (file)
index 598788d..0000000
+++ /dev/null
@@ -1,119 +0,0 @@
-From 7ff82416de8295c61423ef6fd75f052d3837d2f7 Mon Sep 17 00:00:00 2001
-From: Alexander Couzens <[email protected]>
-Date: Wed, 1 Feb 2023 19:23:29 +0100
-Subject: [PATCH 11/13] net: mediatek: sgmii: ensure the SGMII PHY is powered
- down on configuration
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-The code expect the PHY to be in power down which is only true after reset.
-Allow changes of the SGMII parameters more than once.
-
-Only power down when reconfiguring to avoid bouncing the link when there's
-no reason to - based on code from Russell King.
-
-There are cases when the SGMII_PHYA_PWD register contains 0x9 which
-prevents SGMII from working. The SGMII still shows link but no traffic
-can flow. Writing 0x0 to the PHYA_PWD register fix the issue. 0x0 was
-taken from a good working state of the SGMII interface.
-
-Fixes: 42c03844e93d ("net-next: mediatek: add support for MediaTek MT7622 SoC")
-Suggested-by: Russell King (Oracle) <[email protected]>
-Signed-off-by: Alexander Couzens <[email protected]>
-[ bmork: rebased and squashed into one patch ]
-Reviewed-by: Russell King (Oracle) <[email protected]>
-Signed-off-by: Bjørn Mork <[email protected]>
-Acked-by: Daniel Golle <[email protected]>
-Tested-by: Daniel Golle <[email protected]>
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- drivers/net/ethernet/mediatek/mtk_eth_soc.h |  2 ++
- drivers/net/ethernet/mediatek/mtk_sgmii.c   | 39 +++++++++++++++------
- 2 files changed, 30 insertions(+), 11 deletions(-)
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-@@ -1064,11 +1064,13 @@ struct mtk_soc_data {
-  * @regmap:            The register map pointing at the range used to setup
-  *                     SGMII modes
-  * @ana_rgc3:          The offset refers to register ANA_RGC3 related to regmap
-+ * @interface:         Currently configured interface mode
-  * @pcs:               Phylink PCS structure
-  */
- struct mtk_pcs {
-       struct regmap   *regmap;
-       u32             ana_rgc3;
-+      phy_interface_t interface;
-       struct phylink_pcs pcs;
- };
---- a/drivers/net/ethernet/mediatek/mtk_sgmii.c
-+++ b/drivers/net/ethernet/mediatek/mtk_sgmii.c
-@@ -43,11 +43,6 @@ static int mtk_pcs_config(struct phylink
-       int advertise, link_timer;
-       bool changed, use_an;
--      if (interface == PHY_INTERFACE_MODE_2500BASEX)
--              rgc3 = RG_PHY_SPEED_3_125G;
--      else
--              rgc3 = 0;
--
-       advertise = phylink_mii_c22_pcs_encode_advertisement(interface,
-                                                            advertising);
-       if (advertise < 0)
-@@ -88,9 +83,22 @@ static int mtk_pcs_config(struct phylink
-               bmcr = 0;
-       }
--      /* Configure the underlying interface speed */
--      regmap_update_bits(mpcs->regmap, mpcs->ana_rgc3,
--                         RG_PHY_SPEED_3_125G, rgc3);
-+      if (mpcs->interface != interface) {
-+              /* PHYA power down */
-+              regmap_update_bits(mpcs->regmap, SGMSYS_QPHY_PWR_STATE_CTRL,
-+                                 SGMII_PHYA_PWD, SGMII_PHYA_PWD);
-+
-+              if (interface == PHY_INTERFACE_MODE_2500BASEX)
-+                      rgc3 = RG_PHY_SPEED_3_125G;
-+              else
-+                      rgc3 = 0;
-+
-+              /* Configure the underlying interface speed */
-+              regmap_update_bits(mpcs->regmap, mpcs->ana_rgc3,
-+                                 RG_PHY_SPEED_3_125G, rgc3);
-+
-+              mpcs->interface = interface;
-+      }
-       /* Update the advertisement, noting whether it has changed */
-       regmap_update_bits_check(mpcs->regmap, SGMSYS_PCS_ADVERTISE,
-@@ -108,9 +116,17 @@ static int mtk_pcs_config(struct phylink
-       regmap_update_bits(mpcs->regmap, SGMSYS_PCS_CONTROL_1,
-                          SGMII_AN_RESTART | SGMII_AN_ENABLE, bmcr);
--      /* Release PHYA power down state */
--      regmap_update_bits(mpcs->regmap, SGMSYS_QPHY_PWR_STATE_CTRL,
--                         SGMII_PHYA_PWD, 0);
-+      /* Release PHYA power down state
-+       * Only removing bit SGMII_PHYA_PWD isn't enough.
-+       * There are cases when the SGMII_PHYA_PWD register contains 0x9 which
-+       * prevents SGMII from working. The SGMII still shows link but no traffic
-+       * can flow. Writing 0x0 to the PHYA_PWD register fix the issue. 0x0 was
-+       * taken from a good working state of the SGMII interface.
-+       * Unknown how much the QPHY needs but it is racy without a sleep.
-+       * Tested on mt7622 & mt7986.
-+       */
-+      usleep_range(50, 100);
-+      regmap_write(mpcs->regmap, SGMSYS_QPHY_PWR_STATE_CTRL, 0);
-       return changed;
- }
-@@ -171,6 +187,7 @@ int mtk_sgmii_init(struct mtk_sgmii *ss,
-                       return PTR_ERR(ss->pcs[i].regmap);
-               ss->pcs[i].pcs.ops = &mtk_pcs_ops;
-+              ss->pcs[i].interface = PHY_INTERFACE_MODE_NA;
-       }
-       return 0;
diff --git a/target/linux/generic/backport-5.15/733-v6.2-13-net-mediatek-sgmii-fix-duplex-configuration.patch b/target/linux/generic/backport-5.15/733-v6.2-13-net-mediatek-sgmii-fix-duplex-configuration.patch
deleted file mode 100644 (file)
index 79e5ad1..0000000
+++ /dev/null
@@ -1,52 +0,0 @@
-From 9d32637122de88f1ef614c29703f0e050cad342e Mon Sep 17 00:00:00 2001
-From: =?UTF-8?q?Bj=C3=B8rn=20Mork?= <[email protected]>
-Date: Wed, 1 Feb 2023 19:23:30 +0100
-Subject: [PATCH 12/13] net: mediatek: sgmii: fix duplex configuration
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-The logic of the duplex bit is inverted.  Setting it means half
-duplex, not full duplex.
-
-Fix and rename macro to avoid confusion.
-
-Fixes: 7e538372694b ("net: ethernet: mediatek: Re-add support SGMII")
-Reviewed-by: Russell King (Oracle) <[email protected]>
-Signed-off-by: Bjørn Mork <[email protected]>
-Acked-by: Daniel Golle <[email protected]>
-Tested-by: Daniel Golle <[email protected]>
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- drivers/net/ethernet/mediatek/mtk_eth_soc.h | 2 +-
- drivers/net/ethernet/mediatek/mtk_sgmii.c   | 6 +++---
- 2 files changed, 4 insertions(+), 4 deletions(-)
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-@@ -531,7 +531,7 @@
- #define SGMII_SPEED_10                        FIELD_PREP(SGMII_SPEED_MASK, 0)
- #define SGMII_SPEED_100                       FIELD_PREP(SGMII_SPEED_MASK, 1)
- #define SGMII_SPEED_1000              FIELD_PREP(SGMII_SPEED_MASK, 2)
--#define SGMII_DUPLEX_FULL             BIT(4)
-+#define SGMII_DUPLEX_HALF             BIT(4)
- #define SGMII_IF_MODE_BIT5            BIT(5)
- #define SGMII_REMOTE_FAULT_DIS                BIT(8)
- #define SGMII_CODE_SYNC_SET_VAL               BIT(9)
---- a/drivers/net/ethernet/mediatek/mtk_sgmii.c
-+++ b/drivers/net/ethernet/mediatek/mtk_sgmii.c
-@@ -154,11 +154,11 @@ static void mtk_pcs_link_up(struct phyli
-               else
-                       sgm_mode = SGMII_SPEED_1000;
--              if (duplex == DUPLEX_FULL)
--                      sgm_mode |= SGMII_DUPLEX_FULL;
-+              if (duplex != DUPLEX_FULL)
-+                      sgm_mode |= SGMII_DUPLEX_HALF;
-               regmap_update_bits(mpcs->regmap, SGMSYS_SGMII_MODE,
--                                 SGMII_DUPLEX_FULL | SGMII_SPEED_MASK,
-+                                 SGMII_DUPLEX_HALF | SGMII_SPEED_MASK,
-                                  sgm_mode);
-       }
- }
diff --git a/target/linux/generic/backport-5.15/733-v6.2-14-mtk_sgmii-enable-PCS-polling-to-allow-SFP-work.patch b/target/linux/generic/backport-5.15/733-v6.2-14-mtk_sgmii-enable-PCS-polling-to-allow-SFP-work.patch
deleted file mode 100644 (file)
index 56d7a13..0000000
+++ /dev/null
@@ -1,33 +0,0 @@
-From 3337a6e04ddf2923a1bdcf3d31b3b52412bf82dd Mon Sep 17 00:00:00 2001
-From: Alexander Couzens <[email protected]>
-Date: Wed, 1 Feb 2023 19:23:31 +0100
-Subject: [PATCH 13/13] mtk_sgmii: enable PCS polling to allow SFP work
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-Currently there is no IRQ handling (even the SGMII supports it).
-Enable polling to support SFP ports.
-
-Fixes: 14a44ab0330d ("net: mtk_eth_soc: partially convert to phylink_pcs")
-Reviewed-by: Russell King (Oracle) <[email protected]>
-Signed-off-by: Alexander Couzens <[email protected]>
-[ bmork: changed "1" => "true" ]
-Signed-off-by: Bjørn Mork <[email protected]>
-Acked-by: Daniel Golle <[email protected]>
-Tested-by: Daniel Golle <[email protected]>
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- drivers/net/ethernet/mediatek/mtk_sgmii.c | 1 +
- 1 file changed, 1 insertion(+)
-
---- a/drivers/net/ethernet/mediatek/mtk_sgmii.c
-+++ b/drivers/net/ethernet/mediatek/mtk_sgmii.c
-@@ -187,6 +187,7 @@ int mtk_sgmii_init(struct mtk_sgmii *ss,
-                       return PTR_ERR(ss->pcs[i].regmap);
-               ss->pcs[i].pcs.ops = &mtk_pcs_ops;
-+              ss->pcs[i].pcs.poll = true;
-               ss->pcs[i].interface = PHY_INTERFACE_MODE_NA;
-       }
diff --git a/target/linux/generic/backport-5.15/733-v6.3-15-net-ethernet-mtk_eth_soc-reset-PCS-state.patch b/target/linux/generic/backport-5.15/733-v6.3-15-net-ethernet-mtk_eth_soc-reset-PCS-state.patch
deleted file mode 100644 (file)
index a63b110..0000000
+++ /dev/null
@@ -1,48 +0,0 @@
-From 611e2dabb4b3243d176739fd6a5a34d007fa3f86 Mon Sep 17 00:00:00 2001
-From: Daniel Golle <[email protected]>
-Date: Tue, 14 Mar 2023 00:34:26 +0000
-Subject: [PATCH 1/2] net: ethernet: mtk_eth_soc: reset PCS state
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-Reset the internal PCS state machine when changing interface mode.
-This prevents confusing the state machine when changing interface
-modes, e.g. from SGMII to 2500Base-X or vice-versa.
-
-Fixes: 7e538372694b ("net: ethernet: mediatek: Re-add support SGMII")
-Reviewed-by: Russell King (Oracle) <[email protected]>
-Tested-by: Bjørn Mork <[email protected]>
-Signed-off-by: Daniel Golle <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/ethernet/mediatek/mtk_eth_soc.h | 4 ++++
- drivers/net/ethernet/mediatek/mtk_sgmii.c   | 4 ++++
- 2 files changed, 8 insertions(+)
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-@@ -539,6 +539,10 @@
- #define SGMII_SEND_AN_ERROR_EN                BIT(11)
- #define SGMII_IF_MODE_MASK            GENMASK(5, 1)
-+/* Register to reset SGMII design */
-+#define SGMII_RESERVED_0      0x34
-+#define SGMII_SW_RESET                BIT(0)
-+
- /* Register to set SGMII speed, ANA RG_ Control Signals III*/
- #define SGMSYS_ANA_RG_CS3     0x2028
- #define RG_PHY_SPEED_MASK     (BIT(2) | BIT(3))
---- a/drivers/net/ethernet/mediatek/mtk_sgmii.c
-+++ b/drivers/net/ethernet/mediatek/mtk_sgmii.c
-@@ -88,6 +88,10 @@ static int mtk_pcs_config(struct phylink
-               regmap_update_bits(mpcs->regmap, SGMSYS_QPHY_PWR_STATE_CTRL,
-                                  SGMII_PHYA_PWD, SGMII_PHYA_PWD);
-+              /* Reset SGMII PCS state */
-+              regmap_update_bits(mpcs->regmap, SGMII_RESERVED_0,
-+                                 SGMII_SW_RESET, SGMII_SW_RESET);
-+
-               if (interface == PHY_INTERFACE_MODE_2500BASEX)
-                       rgc3 = RG_PHY_SPEED_3_125G;
-               else
diff --git a/target/linux/generic/backport-5.15/733-v6.3-16-net-ethernet-mtk_eth_soc-only-write-values-if-needed.patch b/target/linux/generic/backport-5.15/733-v6.3-16-net-ethernet-mtk_eth_soc-only-write-values-if-needed.patch
deleted file mode 100644 (file)
index 0fabeea..0000000
+++ /dev/null
@@ -1,103 +0,0 @@
-From 6e933a804c7db8be64f367f33e63cd7dcc302ebb Mon Sep 17 00:00:00 2001
-From: Daniel Golle <[email protected]>
-Date: Tue, 14 Mar 2023 00:34:45 +0000
-Subject: [PATCH 2/2] net: ethernet: mtk_eth_soc: only write values if needed
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-Only restart auto-negotiation and write link timer if actually
-necessary. This prevents losing the link in case of minor
-changes.
-
-Fixes: 7e538372694b ("net: ethernet: mediatek: Re-add support SGMII")
-Reviewed-by: Russell King (Oracle) <[email protected]>
-Tested-by: Bjørn Mork <[email protected]>
-Signed-off-by: Daniel Golle <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/ethernet/mediatek/mtk_sgmii.c | 24 +++++++++++------------
- 1 file changed, 12 insertions(+), 12 deletions(-)
-
---- a/drivers/net/ethernet/mediatek/mtk_sgmii.c
-+++ b/drivers/net/ethernet/mediatek/mtk_sgmii.c
-@@ -38,20 +38,16 @@ static int mtk_pcs_config(struct phylink
-                         const unsigned long *advertising,
-                         bool permit_pause_to_mac)
- {
-+      bool mode_changed = false, changed, use_an;
-       struct mtk_pcs *mpcs = pcs_to_mtk_pcs(pcs);
-       unsigned int rgc3, sgm_mode, bmcr;
-       int advertise, link_timer;
--      bool changed, use_an;
-       advertise = phylink_mii_c22_pcs_encode_advertisement(interface,
-                                                            advertising);
-       if (advertise < 0)
-               return advertise;
--      link_timer = phylink_get_link_timer_ns(interface);
--      if (link_timer < 0)
--              return link_timer;
--
-       /* Clearing IF_MODE_BIT0 switches the PCS to BASE-X mode, and
-        * we assume that fixes it's speed at bitrate = line rate (in
-        * other words, 1000Mbps or 2500Mbps).
-@@ -77,13 +73,16 @@ static int mtk_pcs_config(struct phylink
-       }
-       if (use_an) {
--              /* FIXME: Do we need to set AN_RESTART here? */
--              bmcr = SGMII_AN_RESTART | SGMII_AN_ENABLE;
-+              bmcr = SGMII_AN_ENABLE;
-       } else {
-               bmcr = 0;
-       }
-       if (mpcs->interface != interface) {
-+              link_timer = phylink_get_link_timer_ns(interface);
-+              if (link_timer < 0)
-+                      return link_timer;
-+
-               /* PHYA power down */
-               regmap_update_bits(mpcs->regmap, SGMSYS_QPHY_PWR_STATE_CTRL,
-                                  SGMII_PHYA_PWD, SGMII_PHYA_PWD);
-@@ -101,16 +100,17 @@ static int mtk_pcs_config(struct phylink
-               regmap_update_bits(mpcs->regmap, mpcs->ana_rgc3,
-                                  RG_PHY_SPEED_3_125G, rgc3);
-+              /* Setup the link timer */
-+              regmap_write(mpcs->regmap, SGMSYS_PCS_LINK_TIMER, link_timer / 2 / 8);
-+
-               mpcs->interface = interface;
-+              mode_changed = true;
-       }
-       /* Update the advertisement, noting whether it has changed */
-       regmap_update_bits_check(mpcs->regmap, SGMSYS_PCS_ADVERTISE,
-                                SGMII_ADVERTISE, advertise, &changed);
--      /* Setup the link timer and QPHY power up inside SGMIISYS */
--      regmap_write(mpcs->regmap, SGMSYS_PCS_LINK_TIMER, link_timer / 2 / 8);
--
-       /* Update the sgmsys mode register */
-       regmap_update_bits(mpcs->regmap, SGMSYS_SGMII_MODE,
-                          SGMII_REMOTE_FAULT_DIS | SGMII_SPEED_DUPLEX_AN |
-@@ -118,7 +118,7 @@ static int mtk_pcs_config(struct phylink
-       /* Update the BMCR */
-       regmap_update_bits(mpcs->regmap, SGMSYS_PCS_CONTROL_1,
--                         SGMII_AN_RESTART | SGMII_AN_ENABLE, bmcr);
-+                         SGMII_AN_ENABLE, bmcr);
-       /* Release PHYA power down state
-        * Only removing bit SGMII_PHYA_PWD isn't enough.
-@@ -132,7 +132,7 @@ static int mtk_pcs_config(struct phylink
-       usleep_range(50, 100);
-       regmap_write(mpcs->regmap, SGMSYS_QPHY_PWR_STATE_CTRL, 0);
--      return changed;
-+      return changed || mode_changed;
- }
- static void mtk_pcs_restart_an(struct phylink_pcs *pcs)
diff --git a/target/linux/generic/backport-5.15/733-v6.3-18-net-ethernet-mtk_eth_soc-add-support-for-MT7981.patch b/target/linux/generic/backport-5.15/733-v6.3-18-net-ethernet-mtk_eth_soc-add-support-for-MT7981.patch
deleted file mode 100644 (file)
index 741831f..0000000
+++ /dev/null
@@ -1,200 +0,0 @@
-From f5d43ddd334b7c32fcaed9ba46afbd85cb467f1f Mon Sep 17 00:00:00 2001
-From: Daniel Golle <[email protected]>
-Date: Sun, 19 Mar 2023 12:56:28 +0000
-Subject: [PATCH] net: ethernet: mtk_eth_soc: add support for MT7981 SoC
-
-The MediaTek MT7981 SoC comes with two 1G/2.5G SGMII ports, just like
-MT7986.
-
-In addition MT7981 is equipped with a built-in 1000Base-T PHY which can
-be used with GMAC1.
-
-As many MT7981 boards make use of inverting SGMII signal polarity, add
-new device-tree attribute 'mediatek,pn_swap' to support them.
-
-Signed-off-by: Daniel Golle <[email protected]>
-Signed-off-by: Jakub Kicinski <[email protected]>
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_path.c
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_path.c
-@@ -96,12 +96,20 @@ static int set_mux_gmac2_gmac0_to_gephy(
- static int set_mux_u3_gmac2_to_qphy(struct mtk_eth *eth, int path)
- {
--      unsigned int val = 0;
-+      unsigned int val = 0, mask = 0, reg = 0;
-       bool updated = true;
-       switch (path) {
-       case MTK_ETH_PATH_GMAC2_SGMII:
--              val = CO_QPHY_SEL;
-+              if (MTK_HAS_CAPS(eth->soc->caps, MTK_U3_COPHY_V2)) {
-+                      reg = USB_PHY_SWITCH_REG;
-+                      val = SGMII_QPHY_SEL;
-+                      mask = QPHY_SEL_MASK;
-+              } else {
-+                      reg = INFRA_MISC2;
-+                      val = CO_QPHY_SEL;
-+                      mask = val;
-+              }
-               break;
-       default:
-               updated = false;
-@@ -109,7 +117,7 @@ static int set_mux_u3_gmac2_to_qphy(stru
-       }
-       if (updated)
--              regmap_update_bits(eth->infra, INFRA_MISC2, CO_QPHY_SEL, val);
-+              regmap_update_bits(eth->infra, reg, mask, val);
-       dev_dbg(eth->dev, "path %s in %s updated = %d\n",
-               mtk_eth_path_name(path), __func__, updated);
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-@@ -4751,6 +4751,26 @@ static const struct mtk_soc_data mt7629_
-       },
- };
-+static const struct mtk_soc_data mt7981_data = {
-+      .reg_map = &mt7986_reg_map,
-+      .ana_rgc3 = 0x128,
-+      .caps = MT7981_CAPS,
-+      .hw_features = MTK_HW_FEATURES,
-+      .required_clks = MT7981_CLKS_BITMAP,
-+      .required_pctl = false,
-+      .offload_version = 2,
-+      .hash_offset = 4,
-+      .foe_entry_size = sizeof(struct mtk_foe_entry),
-+      .txrx = {
-+              .txd_size = sizeof(struct mtk_tx_dma_v2),
-+              .rxd_size = sizeof(struct mtk_rx_dma_v2),
-+              .rx_irq_done_mask = MTK_RX_DONE_INT_V2,
-+              .rx_dma_l4_valid = RX_DMA_L4_VALID_V2,
-+              .dma_max_len = MTK_TX_DMA_BUF_LEN_V2,
-+              .dma_len_offset = 8,
-+      },
-+};
-+
- static const struct mtk_soc_data mt7986_data = {
-       .reg_map = &mt7986_reg_map,
-       .ana_rgc3 = 0x128,
-@@ -4793,6 +4813,7 @@ const struct of_device_id of_mtk_match[]
-       { .compatible = "mediatek,mt7622-eth", .data = &mt7622_data},
-       { .compatible = "mediatek,mt7623-eth", .data = &mt7623_data},
-       { .compatible = "mediatek,mt7629-eth", .data = &mt7629_data},
-+      { .compatible = "mediatek,mt7981-eth", .data = &mt7981_data},
-       { .compatible = "mediatek,mt7986-eth", .data = &mt7986_data},
-       { .compatible = "ralink,rt5350-eth", .data = &rt5350_data},
-       {},
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-@@ -553,11 +553,22 @@
- #define SGMSYS_QPHY_PWR_STATE_CTRL 0xe8
- #define       SGMII_PHYA_PWD          BIT(4)
-+/* Register to QPHY wrapper control */
-+#define SGMSYS_QPHY_WRAP_CTRL 0xec
-+#define SGMII_PN_SWAP_MASK    GENMASK(1, 0)
-+#define SGMII_PN_SWAP_TX_RX   (BIT(0) | BIT(1))
-+#define MTK_SGMII_FLAG_PN_SWAP        BIT(0)
-+
- /* Infrasys subsystem config registers */
- #define INFRA_MISC2            0x70c
- #define CO_QPHY_SEL            BIT(0)
- #define GEPHY_MAC_SEL          BIT(1)
-+/* Top misc registers */
-+#define USB_PHY_SWITCH_REG    0x218
-+#define QPHY_SEL_MASK         GENMASK(1, 0)
-+#define SGMII_QPHY_SEL                0x2
-+
- /* MT7628/88 specific stuff */
- #define MT7628_PDMA_OFFSET    0x0800
- #define MT7628_SDM_OFFSET     0x0c00
-@@ -738,6 +749,17 @@ enum mtk_clks_map {
-                                BIT(MTK_CLK_SGMII2_CDR_FB) | \
-                                BIT(MTK_CLK_SGMII_CK) | \
-                                BIT(MTK_CLK_ETH2PLL) | BIT(MTK_CLK_SGMIITOP))
-+#define MT7981_CLKS_BITMAP    (BIT(MTK_CLK_FE) | BIT(MTK_CLK_GP2) | BIT(MTK_CLK_GP1) | \
-+                               BIT(MTK_CLK_WOCPU0) | \
-+                               BIT(MTK_CLK_SGMII_TX_250M) | \
-+                               BIT(MTK_CLK_SGMII_RX_250M) | \
-+                               BIT(MTK_CLK_SGMII_CDR_REF) | \
-+                               BIT(MTK_CLK_SGMII_CDR_FB) | \
-+                               BIT(MTK_CLK_SGMII2_TX_250M) | \
-+                               BIT(MTK_CLK_SGMII2_RX_250M) | \
-+                               BIT(MTK_CLK_SGMII2_CDR_REF) | \
-+                               BIT(MTK_CLK_SGMII2_CDR_FB) | \
-+                               BIT(MTK_CLK_SGMII_CK))
- #define MT7986_CLKS_BITMAP    (BIT(MTK_CLK_FE) | BIT(MTK_CLK_GP2) | BIT(MTK_CLK_GP1) | \
-                                BIT(MTK_CLK_WOCPU1) | BIT(MTK_CLK_WOCPU0) | \
-                                BIT(MTK_CLK_SGMII_TX_250M) | \
-@@ -851,6 +873,7 @@ enum mkt_eth_capabilities {
-       MTK_NETSYS_V2_BIT,
-       MTK_SOC_MT7628_BIT,
-       MTK_RSTCTRL_PPE1_BIT,
-+      MTK_U3_COPHY_V2_BIT,
-       /* MUX BITS*/
-       MTK_ETH_MUX_GDM1_TO_GMAC1_ESW_BIT,
-@@ -885,6 +908,7 @@ enum mkt_eth_capabilities {
- #define MTK_NETSYS_V2         BIT(MTK_NETSYS_V2_BIT)
- #define MTK_SOC_MT7628                BIT(MTK_SOC_MT7628_BIT)
- #define MTK_RSTCTRL_PPE1      BIT(MTK_RSTCTRL_PPE1_BIT)
-+#define MTK_U3_COPHY_V2               BIT(MTK_U3_COPHY_V2_BIT)
- #define MTK_ETH_MUX_GDM1_TO_GMAC1_ESW         \
-       BIT(MTK_ETH_MUX_GDM1_TO_GMAC1_ESW_BIT)
-@@ -957,6 +981,11 @@ enum mkt_eth_capabilities {
-                     MTK_MUX_U3_GMAC2_TO_QPHY | \
-                     MTK_MUX_GMAC12_TO_GEPHY_SGMII | MTK_QDMA)
-+#define MT7981_CAPS  (MTK_GMAC1_SGMII | MTK_GMAC2_SGMII | MTK_GMAC2_GEPHY | \
-+                    MTK_MUX_GMAC12_TO_GEPHY_SGMII | MTK_QDMA | \
-+                    MTK_MUX_U3_GMAC2_TO_QPHY | MTK_U3_COPHY_V2 | \
-+                    MTK_NETSYS_V2 | MTK_RSTCTRL_PPE1)
-+
- #define MT7986_CAPS  (MTK_GMAC1_SGMII | MTK_GMAC2_SGMII | \
-                     MTK_MUX_GMAC12_TO_GEPHY_SGMII | MTK_QDMA | \
-                     MTK_NETSYS_V2 | MTK_RSTCTRL_PPE1)
-@@ -1070,12 +1099,14 @@ struct mtk_soc_data {
-  * @ana_rgc3:          The offset refers to register ANA_RGC3 related to regmap
-  * @interface:         Currently configured interface mode
-  * @pcs:               Phylink PCS structure
-+ * @flags:             Flags indicating hardware properties
-  */
- struct mtk_pcs {
-       struct regmap   *regmap;
-       u32             ana_rgc3;
-       phy_interface_t interface;
-       struct phylink_pcs pcs;
-+      u32             flags;
- };
- /* struct mtk_sgmii -  This is the structure holding sgmii regmap and its
---- a/drivers/net/ethernet/mediatek/mtk_sgmii.c
-+++ b/drivers/net/ethernet/mediatek/mtk_sgmii.c
-@@ -87,6 +87,11 @@ static int mtk_pcs_config(struct phylink
-               regmap_update_bits(mpcs->regmap, SGMSYS_QPHY_PWR_STATE_CTRL,
-                                  SGMII_PHYA_PWD, SGMII_PHYA_PWD);
-+              if (mpcs->flags & MTK_SGMII_FLAG_PN_SWAP)
-+                      regmap_update_bits(mpcs->regmap, SGMSYS_QPHY_WRAP_CTRL,
-+                                         SGMII_PN_SWAP_MASK,
-+                                         SGMII_PN_SWAP_TX_RX);
-+
-               /* Reset SGMII PCS state */
-               regmap_update_bits(mpcs->regmap, SGMII_RESERVED_0,
-                                  SGMII_SW_RESET, SGMII_SW_RESET);
-@@ -186,6 +191,11 @@ int mtk_sgmii_init(struct mtk_sgmii *ss,
-               ss->pcs[i].ana_rgc3 = ana_rgc3;
-               ss->pcs[i].regmap = syscon_node_to_regmap(np);
-+
-+              ss->pcs[i].flags = 0;
-+              if (of_property_read_bool(np, "mediatek,pnswap"))
-+                      ss->pcs[i].flags |= MTK_SGMII_FLAG_PN_SWAP;
-+
-               of_node_put(np);
-               if (IS_ERR(ss->pcs[i].regmap))
-                       return PTR_ERR(ss->pcs[i].regmap);
diff --git a/target/linux/generic/backport-5.15/733-v6.3-19-net-ethernet-mtk_eth_soc-set-MDIO-bus-clock-frequenc.patch b/target/linux/generic/backport-5.15/733-v6.3-19-net-ethernet-mtk_eth_soc-set-MDIO-bus-clock-frequenc.patch
deleted file mode 100644 (file)
index d4c1ecf..0000000
+++ /dev/null
@@ -1,76 +0,0 @@
-From c0a440031d4314d1023c1b87f43a4233634eebdb Mon Sep 17 00:00:00 2001
-From: Daniel Golle <[email protected]>
-Date: Sun, 19 Mar 2023 12:57:15 +0000
-Subject: [PATCH] net: ethernet: mtk_eth_soc: set MDIO bus clock frequency
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-Set MDIO bus clock frequency and allow setting a custom maximum
-frequency from device tree.
-
-Reviewed-by: Andrew Lunn <[email protected]>
-Reviewed-by: Florian Fainelli <[email protected]>
-Tested-by: Bjørn Mork <[email protected]>
-Signed-off-by: Daniel Golle <[email protected]>
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- drivers/net/ethernet/mediatek/mtk_eth_soc.c | 21 +++++++++++++++++++++
- drivers/net/ethernet/mediatek/mtk_eth_soc.h |  7 +++++++
- 2 files changed, 28 insertions(+)
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-@@ -701,8 +701,10 @@ static const struct phylink_mac_ops mtk_
- static int mtk_mdio_init(struct mtk_eth *eth)
- {
-+      unsigned int max_clk = 2500000, divider;
-       struct device_node *mii_np;
-       int ret;
-+      u32 val;
-       mii_np = of_get_child_by_name(eth->dev->of_node, "mdio-bus");
-       if (!mii_np) {
-@@ -728,6 +730,25 @@ static int mtk_mdio_init(struct mtk_eth
-       eth->mii_bus->parent = eth->dev;
-       snprintf(eth->mii_bus->id, MII_BUS_ID_SIZE, "%pOFn", mii_np);
-+
-+      if (!of_property_read_u32(mii_np, "clock-frequency", &val)) {
-+              if (val > MDC_MAX_FREQ || val < MDC_MAX_FREQ / MDC_MAX_DIVIDER) {
-+                      dev_err(eth->dev, "MDIO clock frequency out of range");
-+                      ret = -EINVAL;
-+                      goto err_put_node;
-+              }
-+              max_clk = val;
-+      }
-+      divider = min_t(unsigned int, DIV_ROUND_UP(MDC_MAX_FREQ, max_clk), 63);
-+
-+      /* Configure MDC Divider */
-+      val = mtk_r32(eth, MTK_PPSC);
-+      val &= ~PPSC_MDC_CFG;
-+      val |= FIELD_PREP(PPSC_MDC_CFG, divider) | PPSC_MDC_TURBO;
-+      mtk_w32(eth, val, MTK_PPSC);
-+
-+      dev_dbg(eth->dev, "MDC is running on %d Hz\n", MDC_MAX_FREQ / divider);
-+
-       ret = of_mdiobus_register(eth->mii_bus, mii_np);
- err_put_node:
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-@@ -363,6 +363,13 @@
- #define RX_DMA_VTAG_V2                BIT(0)
- #define RX_DMA_L4_VALID_V2    BIT(2)
-+/* PHY Polling and SMI Master Control registers */
-+#define MTK_PPSC              0x10000
-+#define PPSC_MDC_CFG          GENMASK(29, 24)
-+#define PPSC_MDC_TURBO                BIT(20)
-+#define MDC_MAX_FREQ          25000000
-+#define MDC_MAX_DIVIDER               63
-+
- /* PHY Indirect Access Control registers */
- #define MTK_PHY_IAC           0x10004
- #define PHY_IAC_ACCESS                BIT(31)
diff --git a/target/linux/generic/backport-5.15/733-v6.3-20-net-ethernet-mtk_eth_soc-switch-to-external-PCS-driv.patch b/target/linux/generic/backport-5.15/733-v6.3-20-net-ethernet-mtk_eth_soc-switch-to-external-PCS-driv.patch
deleted file mode 100644 (file)
index 8f76206..0000000
+++ /dev/null
@@ -1,512 +0,0 @@
-From 2a3ec7ae313310c1092e4256208cc04d1958e469 Mon Sep 17 00:00:00 2001
-From: Daniel Golle <[email protected]>
-Date: Sun, 19 Mar 2023 12:58:02 +0000
-Subject: [PATCH] net: ethernet: mtk_eth_soc: switch to external PCS driver
-
-Now that we got a PCS driver, use it and remove the now redundant
-PCS code and it's header macros from the Ethernet driver.
-
-Signed-off-by: Daniel Golle <[email protected]>
-Tested-by: Frank Wunderlich <[email protected]>
-Reviewed-by: Russell King (Oracle) <[email protected]>
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- drivers/net/ethernet/mediatek/Kconfig       |   2 +
- drivers/net/ethernet/mediatek/Makefile      |   2 +-
- drivers/net/ethernet/mediatek/mtk_eth_soc.c |  61 +++++-
- drivers/net/ethernet/mediatek/mtk_eth_soc.h |  93 +--------
- drivers/net/ethernet/mediatek/mtk_sgmii.c   | 217 --------------------
- 5 files changed, 56 insertions(+), 319 deletions(-)
- delete mode 100644 drivers/net/ethernet/mediatek/mtk_sgmii.c
-
---- a/drivers/net/ethernet/mediatek/Kconfig
-+++ b/drivers/net/ethernet/mediatek/Kconfig
-@@ -18,6 +18,8 @@ config NET_MEDIATEK_SOC
-       select DIMLIB
-       select PAGE_POOL
-       select PAGE_POOL_STATS
-+      select PCS_MTK_LYNXI
-+      select REGMAP_MMIO
-       help
-         This driver supports the gigabit ethernet MACs in the
-         MediaTek SoC family.
---- a/drivers/net/ethernet/mediatek/Makefile
-+++ b/drivers/net/ethernet/mediatek/Makefile
-@@ -4,7 +4,7 @@
- #
- obj-$(CONFIG_NET_MEDIATEK_SOC) += mtk_eth.o
--mtk_eth-y := mtk_eth_soc.o mtk_sgmii.o mtk_eth_path.o mtk_ppe.o mtk_ppe_debugfs.o mtk_ppe_offload.o
-+mtk_eth-y := mtk_eth_soc.o mtk_eth_path.o mtk_ppe.o mtk_ppe_debugfs.o mtk_ppe_offload.o
- mtk_eth-$(CONFIG_NET_MEDIATEK_SOC_WED) += mtk_wed.o mtk_wed_mcu.o mtk_wed_wo.o
- ifdef CONFIG_DEBUG_FS
- mtk_eth-$(CONFIG_NET_MEDIATEK_SOC_WED) += mtk_wed_debugfs.o
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-@@ -20,6 +20,7 @@
- #include <linux/interrupt.h>
- #include <linux/pinctrl/devinfo.h>
- #include <linux/phylink.h>
-+#include <linux/pcs/pcs-mtk-lynxi.h>
- #include <linux/jhash.h>
- #include <linux/bitfield.h>
- #include <net/dsa.h>
-@@ -357,7 +358,7 @@ static struct phylink_pcs *mtk_mac_selec
-               sid = (MTK_HAS_CAPS(eth->soc->caps, MTK_SHARED_SGMII)) ?
-                      0 : mac->id;
--              return mtk_sgmii_select_pcs(eth->sgmii, sid);
-+              return eth->sgmii_pcs[sid];
-       }
-       return NULL;
-@@ -3962,8 +3963,17 @@ static int mtk_unreg_dev(struct mtk_eth
-       return 0;
- }
-+static void mtk_sgmii_destroy(struct mtk_eth *eth)
-+{
-+      int i;
-+
-+      for (i = 0; i < MTK_MAX_DEVS; i++)
-+              mtk_pcs_lynxi_destroy(eth->sgmii_pcs[i]);
-+}
-+
- static int mtk_cleanup(struct mtk_eth *eth)
- {
-+      mtk_sgmii_destroy(eth);
-       mtk_unreg_dev(eth);
-       mtk_free_dev(eth);
-       cancel_work_sync(&eth->pending_work);
-@@ -4403,6 +4413,36 @@ void mtk_eth_set_dma_device(struct mtk_e
-       rtnl_unlock();
- }
-+static int mtk_sgmii_init(struct mtk_eth *eth)
-+{
-+      struct device_node *np;
-+      struct regmap *regmap;
-+      u32 flags;
-+      int i;
-+
-+      for (i = 0; i < MTK_MAX_DEVS; i++) {
-+              np = of_parse_phandle(eth->dev->of_node, "mediatek,sgmiisys", i);
-+              if (!np)
-+                      break;
-+
-+              regmap = syscon_node_to_regmap(np);
-+              flags = 0;
-+              if (of_property_read_bool(np, "mediatek,pnswap"))
-+                      flags |= MTK_SGMII_FLAG_PN_SWAP;
-+
-+              of_node_put(np);
-+
-+              if (IS_ERR(regmap))
-+                      return PTR_ERR(regmap);
-+
-+              eth->sgmii_pcs[i] = mtk_pcs_lynxi_create(eth->dev, regmap,
-+                                                       eth->soc->ana_rgc3,
-+                                                       flags);
-+      }
-+
-+      return 0;
-+}
-+
- static int mtk_probe(struct platform_device *pdev)
- {
-       struct resource *res = NULL;
-@@ -4466,13 +4506,7 @@ static int mtk_probe(struct platform_dev
-       }
-       if (MTK_HAS_CAPS(eth->soc->caps, MTK_SGMII)) {
--              eth->sgmii = devm_kzalloc(eth->dev, sizeof(*eth->sgmii),
--                                        GFP_KERNEL);
--              if (!eth->sgmii)
--                      return -ENOMEM;
--
--              err = mtk_sgmii_init(eth->sgmii, pdev->dev.of_node,
--                                   eth->soc->ana_rgc3);
-+              err = mtk_sgmii_init(eth);
-               if (err)
-                       return err;
-@@ -4483,14 +4517,17 @@ static int mtk_probe(struct platform_dev
-                                                           "mediatek,pctl");
-               if (IS_ERR(eth->pctl)) {
-                       dev_err(&pdev->dev, "no pctl regmap found\n");
--                      return PTR_ERR(eth->pctl);
-+                      err = PTR_ERR(eth->pctl);
-+                      goto err_destroy_sgmii;
-               }
-       }
-       if (MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2)) {
-               res = platform_get_resource(pdev, IORESOURCE_MEM, 0);
--              if (!res)
--                      return -EINVAL;
-+              if (!res) {
-+                      err = -EINVAL;
-+                      goto err_destroy_sgmii;
-+              }
-       }
-       if (eth->soc->offload_version) {
-@@ -4651,6 +4688,8 @@ err_deinit_hw:
-       mtk_hw_deinit(eth);
- err_wed_exit:
-       mtk_wed_exit();
-+err_destroy_sgmii:
-+      mtk_sgmii_destroy(eth);
-       return err;
- }
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-@@ -507,65 +507,6 @@
- #define ETHSYS_DMA_AG_MAP_QDMA        BIT(1)
- #define ETHSYS_DMA_AG_MAP_PPE BIT(2)
--/* SGMII subsystem config registers */
--/* BMCR (low 16) BMSR (high 16) */
--#define SGMSYS_PCS_CONTROL_1  0x0
--#define SGMII_BMCR            GENMASK(15, 0)
--#define SGMII_BMSR            GENMASK(31, 16)
--#define SGMII_AN_RESTART      BIT(9)
--#define SGMII_ISOLATE         BIT(10)
--#define SGMII_AN_ENABLE               BIT(12)
--#define SGMII_LINK_STATYS     BIT(18)
--#define SGMII_AN_ABILITY      BIT(19)
--#define SGMII_AN_COMPLETE     BIT(21)
--#define SGMII_PCS_FAULT               BIT(23)
--#define SGMII_AN_EXPANSION_CLR        BIT(30)
--
--#define SGMSYS_PCS_ADVERTISE  0x8
--#define SGMII_ADVERTISE               GENMASK(15, 0)
--#define SGMII_LPA             GENMASK(31, 16)
--
--/* Register to programmable link timer, the unit in 2 * 8ns */
--#define SGMSYS_PCS_LINK_TIMER 0x18
--#define SGMII_LINK_TIMER_MASK GENMASK(19, 0)
--#define SGMII_LINK_TIMER_DEFAULT      (0x186a0 & SGMII_LINK_TIMER_MASK)
--
--/* Register to control remote fault */
--#define SGMSYS_SGMII_MODE             0x20
--#define SGMII_IF_MODE_SGMII           BIT(0)
--#define SGMII_SPEED_DUPLEX_AN         BIT(1)
--#define SGMII_SPEED_MASK              GENMASK(3, 2)
--#define SGMII_SPEED_10                        FIELD_PREP(SGMII_SPEED_MASK, 0)
--#define SGMII_SPEED_100                       FIELD_PREP(SGMII_SPEED_MASK, 1)
--#define SGMII_SPEED_1000              FIELD_PREP(SGMII_SPEED_MASK, 2)
--#define SGMII_DUPLEX_HALF             BIT(4)
--#define SGMII_IF_MODE_BIT5            BIT(5)
--#define SGMII_REMOTE_FAULT_DIS                BIT(8)
--#define SGMII_CODE_SYNC_SET_VAL               BIT(9)
--#define SGMII_CODE_SYNC_SET_EN                BIT(10)
--#define SGMII_SEND_AN_ERROR_EN                BIT(11)
--#define SGMII_IF_MODE_MASK            GENMASK(5, 1)
--
--/* Register to reset SGMII design */
--#define SGMII_RESERVED_0      0x34
--#define SGMII_SW_RESET                BIT(0)
--
--/* Register to set SGMII speed, ANA RG_ Control Signals III*/
--#define SGMSYS_ANA_RG_CS3     0x2028
--#define RG_PHY_SPEED_MASK     (BIT(2) | BIT(3))
--#define RG_PHY_SPEED_1_25G    0x0
--#define RG_PHY_SPEED_3_125G   BIT(2)
--
--/* Register to power up QPHY */
--#define SGMSYS_QPHY_PWR_STATE_CTRL 0xe8
--#define       SGMII_PHYA_PWD          BIT(4)
--
--/* Register to QPHY wrapper control */
--#define SGMSYS_QPHY_WRAP_CTRL 0xec
--#define SGMII_PN_SWAP_MASK    GENMASK(1, 0)
--#define SGMII_PN_SWAP_TX_RX   (BIT(0) | BIT(1))
--#define MTK_SGMII_FLAG_PN_SWAP        BIT(0)
--
- /* Infrasys subsystem config registers */
- #define INFRA_MISC2            0x70c
- #define CO_QPHY_SEL            BIT(0)
-@@ -1099,31 +1040,6 @@ struct mtk_soc_data {
- /* currently no SoC has more than 2 macs */
- #define MTK_MAX_DEVS                  2
--/* struct mtk_pcs -    This structure holds each sgmii regmap and associated
-- *                     data
-- * @regmap:            The register map pointing at the range used to setup
-- *                     SGMII modes
-- * @ana_rgc3:          The offset refers to register ANA_RGC3 related to regmap
-- * @interface:         Currently configured interface mode
-- * @pcs:               Phylink PCS structure
-- * @flags:             Flags indicating hardware properties
-- */
--struct mtk_pcs {
--      struct regmap   *regmap;
--      u32             ana_rgc3;
--      phy_interface_t interface;
--      struct phylink_pcs pcs;
--      u32             flags;
--};
--
--/* struct mtk_sgmii -  This is the structure holding sgmii regmap and its
-- *                     characteristics
-- * @pcs                Array of individual PCS structures
-- */
--struct mtk_sgmii {
--      struct mtk_pcs  pcs[MTK_MAX_DEVS];
--};
--
- /* struct mtk_eth -   This is the main datasructure for holding the state
-  *                    of the driver
-  * @dev:              The device pointer
-@@ -1143,6 +1059,7 @@ struct mtk_sgmii {
-  *                    MII modes
-  * @infra:              The register map pointing at the range used to setup
-  *                      SGMII and GePHY path
-+ * @sgmii_pcs:                Pointers to mtk-pcs-lynxi phylink_pcs instances
-  * @pctl:             The register map pointing at the range used to setup
-  *                    GMAC port drive/slew values
-  * @dma_refcnt:               track how many netdevs are using the DMA engine
-@@ -1183,8 +1100,8 @@ struct mtk_eth {
-       u32                             msg_enable;
-       unsigned long                   sysclk;
-       struct regmap                   *ethsys;
--      struct regmap                   *infra;
--      struct mtk_sgmii                *sgmii;
-+      struct regmap                   *infra;
-+      struct phylink_pcs              *sgmii_pcs[MTK_MAX_DEVS];
-       struct regmap                   *pctl;
-       bool                            hwlro;
-       refcount_t                      dma_refcnt;
-@@ -1346,10 +1263,6 @@ void mtk_stats_update_mac(struct mtk_mac
- void mtk_w32(struct mtk_eth *eth, u32 val, unsigned reg);
- u32 mtk_r32(struct mtk_eth *eth, unsigned reg);
--struct phylink_pcs *mtk_sgmii_select_pcs(struct mtk_sgmii *ss, int id);
--int mtk_sgmii_init(struct mtk_sgmii *ss, struct device_node *np,
--                 u32 ana_rgc3);
--
- int mtk_gmac_sgmii_path_setup(struct mtk_eth *eth, int mac_id);
- int mtk_gmac_gephy_path_setup(struct mtk_eth *eth, int mac_id);
- int mtk_gmac_rgmii_path_setup(struct mtk_eth *eth, int mac_id);
---- a/drivers/net/ethernet/mediatek/mtk_sgmii.c
-+++ /dev/null
-@@ -1,217 +0,0 @@
--// SPDX-License-Identifier: GPL-2.0
--// Copyright (c) 2018-2019 MediaTek Inc.
--
--/* A library for MediaTek SGMII circuit
-- *
-- * Author: Sean Wang <[email protected]>
-- *
-- */
--
--#include <linux/mfd/syscon.h>
--#include <linux/of.h>
--#include <linux/phylink.h>
--#include <linux/regmap.h>
--
--#include "mtk_eth_soc.h"
--
--static struct mtk_pcs *pcs_to_mtk_pcs(struct phylink_pcs *pcs)
--{
--      return container_of(pcs, struct mtk_pcs, pcs);
--}
--
--static void mtk_pcs_get_state(struct phylink_pcs *pcs,
--                            struct phylink_link_state *state)
--{
--      struct mtk_pcs *mpcs = pcs_to_mtk_pcs(pcs);
--      unsigned int bm, adv;
--
--      /* Read the BMSR and LPA */
--      regmap_read(mpcs->regmap, SGMSYS_PCS_CONTROL_1, &bm);
--      regmap_read(mpcs->regmap, SGMSYS_PCS_ADVERTISE, &adv);
--
--      phylink_mii_c22_pcs_decode_state(state, FIELD_GET(SGMII_BMSR, bm),
--                                       FIELD_GET(SGMII_LPA, adv));
--}
--
--static int mtk_pcs_config(struct phylink_pcs *pcs, unsigned int mode,
--                        phy_interface_t interface,
--                        const unsigned long *advertising,
--                        bool permit_pause_to_mac)
--{
--      bool mode_changed = false, changed, use_an;
--      struct mtk_pcs *mpcs = pcs_to_mtk_pcs(pcs);
--      unsigned int rgc3, sgm_mode, bmcr;
--      int advertise, link_timer;
--
--      advertise = phylink_mii_c22_pcs_encode_advertisement(interface,
--                                                           advertising);
--      if (advertise < 0)
--              return advertise;
--
--      /* Clearing IF_MODE_BIT0 switches the PCS to BASE-X mode, and
--       * we assume that fixes it's speed at bitrate = line rate (in
--       * other words, 1000Mbps or 2500Mbps).
--       */
--      if (interface == PHY_INTERFACE_MODE_SGMII) {
--              sgm_mode = SGMII_IF_MODE_SGMII;
--              if (phylink_autoneg_inband(mode)) {
--                      sgm_mode |= SGMII_REMOTE_FAULT_DIS |
--                                  SGMII_SPEED_DUPLEX_AN;
--                      use_an = true;
--              } else {
--                      use_an = false;
--              }
--      } else if (phylink_autoneg_inband(mode)) {
--              /* 1000base-X or 2500base-X autoneg */
--              sgm_mode = SGMII_REMOTE_FAULT_DIS;
--              use_an = linkmode_test_bit(ETHTOOL_LINK_MODE_Autoneg_BIT,
--                                         advertising);
--      } else {
--              /* 1000base-X or 2500base-X without autoneg */
--              sgm_mode = 0;
--              use_an = false;
--      }
--
--      if (use_an) {
--              bmcr = SGMII_AN_ENABLE;
--      } else {
--              bmcr = 0;
--      }
--
--      if (mpcs->interface != interface) {
--              link_timer = phylink_get_link_timer_ns(interface);
--              if (link_timer < 0)
--                      return link_timer;
--
--              /* PHYA power down */
--              regmap_update_bits(mpcs->regmap, SGMSYS_QPHY_PWR_STATE_CTRL,
--                                 SGMII_PHYA_PWD, SGMII_PHYA_PWD);
--
--              if (mpcs->flags & MTK_SGMII_FLAG_PN_SWAP)
--                      regmap_update_bits(mpcs->regmap, SGMSYS_QPHY_WRAP_CTRL,
--                                         SGMII_PN_SWAP_MASK,
--                                         SGMII_PN_SWAP_TX_RX);
--
--              /* Reset SGMII PCS state */
--              regmap_update_bits(mpcs->regmap, SGMII_RESERVED_0,
--                                 SGMII_SW_RESET, SGMII_SW_RESET);
--
--              if (interface == PHY_INTERFACE_MODE_2500BASEX)
--                      rgc3 = RG_PHY_SPEED_3_125G;
--              else
--                      rgc3 = 0;
--
--              /* Configure the underlying interface speed */
--              regmap_update_bits(mpcs->regmap, mpcs->ana_rgc3,
--                                 RG_PHY_SPEED_3_125G, rgc3);
--
--              /* Setup the link timer */
--              regmap_write(mpcs->regmap, SGMSYS_PCS_LINK_TIMER, link_timer / 2 / 8);
--
--              mpcs->interface = interface;
--              mode_changed = true;
--      }
--
--      /* Update the advertisement, noting whether it has changed */
--      regmap_update_bits_check(mpcs->regmap, SGMSYS_PCS_ADVERTISE,
--                               SGMII_ADVERTISE, advertise, &changed);
--
--      /* Update the sgmsys mode register */
--      regmap_update_bits(mpcs->regmap, SGMSYS_SGMII_MODE,
--                         SGMII_REMOTE_FAULT_DIS | SGMII_SPEED_DUPLEX_AN |
--                         SGMII_IF_MODE_SGMII, sgm_mode);
--
--      /* Update the BMCR */
--      regmap_update_bits(mpcs->regmap, SGMSYS_PCS_CONTROL_1,
--                         SGMII_AN_ENABLE, bmcr);
--
--      /* Release PHYA power down state
--       * Only removing bit SGMII_PHYA_PWD isn't enough.
--       * There are cases when the SGMII_PHYA_PWD register contains 0x9 which
--       * prevents SGMII from working. The SGMII still shows link but no traffic
--       * can flow. Writing 0x0 to the PHYA_PWD register fix the issue. 0x0 was
--       * taken from a good working state of the SGMII interface.
--       * Unknown how much the QPHY needs but it is racy without a sleep.
--       * Tested on mt7622 & mt7986.
--       */
--      usleep_range(50, 100);
--      regmap_write(mpcs->regmap, SGMSYS_QPHY_PWR_STATE_CTRL, 0);
--
--      return changed || mode_changed;
--}
--
--static void mtk_pcs_restart_an(struct phylink_pcs *pcs)
--{
--      struct mtk_pcs *mpcs = pcs_to_mtk_pcs(pcs);
--
--      regmap_update_bits(mpcs->regmap, SGMSYS_PCS_CONTROL_1,
--                         SGMII_AN_RESTART, SGMII_AN_RESTART);
--}
--
--static void mtk_pcs_link_up(struct phylink_pcs *pcs, unsigned int mode,
--                          phy_interface_t interface, int speed, int duplex)
--{
--      struct mtk_pcs *mpcs = pcs_to_mtk_pcs(pcs);
--      unsigned int sgm_mode;
--
--      if (!phylink_autoneg_inband(mode)) {
--              /* Force the speed and duplex setting */
--              if (speed == SPEED_10)
--                      sgm_mode = SGMII_SPEED_10;
--              else if (speed == SPEED_100)
--                      sgm_mode = SGMII_SPEED_100;
--              else
--                      sgm_mode = SGMII_SPEED_1000;
--
--              if (duplex != DUPLEX_FULL)
--                      sgm_mode |= SGMII_DUPLEX_HALF;
--
--              regmap_update_bits(mpcs->regmap, SGMSYS_SGMII_MODE,
--                                 SGMII_DUPLEX_HALF | SGMII_SPEED_MASK,
--                                 sgm_mode);
--      }
--}
--
--static const struct phylink_pcs_ops mtk_pcs_ops = {
--      .pcs_get_state = mtk_pcs_get_state,
--      .pcs_config = mtk_pcs_config,
--      .pcs_an_restart = mtk_pcs_restart_an,
--      .pcs_link_up = mtk_pcs_link_up,
--};
--
--int mtk_sgmii_init(struct mtk_sgmii *ss, struct device_node *r, u32 ana_rgc3)
--{
--      struct device_node *np;
--      int i;
--
--      for (i = 0; i < MTK_MAX_DEVS; i++) {
--              np = of_parse_phandle(r, "mediatek,sgmiisys", i);
--              if (!np)
--                      break;
--
--              ss->pcs[i].ana_rgc3 = ana_rgc3;
--              ss->pcs[i].regmap = syscon_node_to_regmap(np);
--
--              ss->pcs[i].flags = 0;
--              if (of_property_read_bool(np, "mediatek,pnswap"))
--                      ss->pcs[i].flags |= MTK_SGMII_FLAG_PN_SWAP;
--
--              of_node_put(np);
--              if (IS_ERR(ss->pcs[i].regmap))
--                      return PTR_ERR(ss->pcs[i].regmap);
--
--              ss->pcs[i].pcs.ops = &mtk_pcs_ops;
--              ss->pcs[i].pcs.poll = true;
--              ss->pcs[i].interface = PHY_INTERFACE_MODE_NA;
--      }
--
--      return 0;
--}
--
--struct phylink_pcs *mtk_sgmii_select_pcs(struct mtk_sgmii *ss, int id)
--{
--      if (!ss->pcs[id].regmap)
--              return NULL;
--
--      return &ss->pcs[id].pcs;
--}
diff --git a/target/linux/generic/backport-5.15/733-v6.3-21-net-ethernet-mtk_eth_soc-add-missing-ppe-cache-flush.patch b/target/linux/generic/backport-5.15/733-v6.3-21-net-ethernet-mtk_eth_soc-add-missing-ppe-cache-flush.patch
deleted file mode 100644 (file)
index 7742b09..0000000
+++ /dev/null
@@ -1,21 +0,0 @@
-From: Felix Fietkau <[email protected]>
-Date: Thu, 23 Mar 2023 11:19:14 +0100
-Subject: [PATCH] net: ethernet: mtk_eth_soc: add missing ppe cache flush when
- deleting a flow
-
-The cache needs to be flushed to ensure that the hardware stops offloading
-the flow immediately.
-
-Signed-off-by: Felix Fietkau <[email protected]>
----
-
---- a/drivers/net/ethernet/mediatek/mtk_ppe.c
-+++ b/drivers/net/ethernet/mediatek/mtk_ppe.c
-@@ -464,6 +464,7 @@ __mtk_foe_entry_clear(struct mtk_ppe *pp
-               hwe->ib1 &= ~MTK_FOE_IB1_STATE;
-               hwe->ib1 |= FIELD_PREP(MTK_FOE_IB1_STATE, MTK_FOE_STATE_INVALID);
-               dma_wmb();
-+              mtk_ppe_cache_clear(ppe);
-       }
-       entry->hash = 0xffff;
diff --git a/target/linux/generic/backport-5.15/733-v6.4-22-net-mtk_eth_soc-use-WO-firmware-for-MT7981.patch b/target/linux/generic/backport-5.15/733-v6.4-22-net-mtk_eth_soc-use-WO-firmware-for-MT7981.patch
deleted file mode 100644 (file)
index 9ce2735..0000000
+++ /dev/null
@@ -1,46 +0,0 @@
-From f5af7931d2a2cae66d0f9dad4ba517b1b00620b3 Mon Sep 17 00:00:00 2001
-From: Daniel Golle <[email protected]>
-Date: Wed, 19 Apr 2023 19:07:23 +0100
-Subject: [PATCH] net: mtk_eth_soc: use WO firmware for MT7981
-
-In order to support wireless offloading on MT7981 we need to load the
-appropriate firmware. Recognize MT7981 and load mt7981_wo.bin.
-
-Signed-off-by: Daniel Golle <[email protected]>
----
- drivers/net/ethernet/mediatek/mtk_wed_mcu.c | 7 ++++++-
- drivers/net/ethernet/mediatek/mtk_wed_wo.h  | 1 +
- 2 files changed, 7 insertions(+), 1 deletion(-)
-
---- a/drivers/net/ethernet/mediatek/mtk_wed_mcu.c
-+++ b/drivers/net/ethernet/mediatek/mtk_wed_mcu.c
-@@ -326,7 +326,11 @@ mtk_wed_mcu_load_firmware(struct mtk_wed
-               wo->hw->index + 1);
-       /* load firmware */
--      fw_name = wo->hw->index ? MT7986_FIRMWARE_WO1 : MT7986_FIRMWARE_WO0;
-+      if (of_device_is_compatible(wo->hw->node, "mediatek,mt7981-wed"))
-+              fw_name = MT7981_FIRMWARE_WO;
-+      else
-+              fw_name = wo->hw->index ? MT7986_FIRMWARE_WO1 : MT7986_FIRMWARE_WO0;
-+
-       ret = request_firmware(&fw, fw_name, wo->hw->dev);
-       if (ret)
-               return ret;
-@@ -386,5 +390,6 @@ int mtk_wed_mcu_init(struct mtk_wed_wo *
-                                 100, MTK_FW_DL_TIMEOUT);
- }
-+MODULE_FIRMWARE(MT7981_FIRMWARE_WO);
- MODULE_FIRMWARE(MT7986_FIRMWARE_WO0);
- MODULE_FIRMWARE(MT7986_FIRMWARE_WO1);
---- a/drivers/net/ethernet/mediatek/mtk_wed_wo.h
-+++ b/drivers/net/ethernet/mediatek/mtk_wed_wo.h
-@@ -88,6 +88,7 @@ enum mtk_wed_dummy_cr_idx {
-       MTK_WED_DUMMY_CR_WO_STATUS,
- };
-+#define MT7981_FIRMWARE_WO    "mediatek/mt7981_wo.bin"
- #define MT7986_FIRMWARE_WO0   "mediatek/mt7986_wo_0.bin"
- #define MT7986_FIRMWARE_WO1   "mediatek/mt7986_wo_1.bin"
diff --git a/target/linux/generic/backport-5.15/733-v6.4-23-net-ethernet-mtk_eth_soc-fix-NULL-pointer-dereferenc.patch b/target/linux/generic/backport-5.15/733-v6.4-23-net-ethernet-mtk_eth_soc-fix-NULL-pointer-dereferenc.patch
deleted file mode 100644 (file)
index d715c4a..0000000
+++ /dev/null
@@ -1,28 +0,0 @@
-From 7c83e28f10830aa5105c25eaabe890e3adac36aa Mon Sep 17 00:00:00 2001
-From: Daniel Golle <[email protected]>
-Date: Tue, 9 May 2023 03:20:06 +0200
-Subject: [PATCH] net: ethernet: mtk_eth_soc: fix NULL pointer dereference
-
-Check for NULL pointer to avoid kernel crashing in case of missing WO
-firmware in case only a single WEDv2 device has been initialized, e.g. on
-MT7981 which can connect just one wireless frontend.
-
-Fixes: 86ce0d09e424 ("net: ethernet: mtk_eth_soc: use WO firmware for MT7981")
-Signed-off-by: Daniel Golle <[email protected]>
-Reviewed-by: Simon Horman <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/ethernet/mediatek/mtk_wed.c | 2 +-
- 1 file changed, 1 insertion(+), 1 deletion(-)
-
---- a/drivers/net/ethernet/mediatek/mtk_wed.c
-+++ b/drivers/net/ethernet/mediatek/mtk_wed.c
-@@ -647,7 +647,7 @@ __mtk_wed_detach(struct mtk_wed_device *
-                                          BIT(hw->index), BIT(hw->index));
-       }
--      if (!hw_list[!hw->index]->wed_dev &&
-+      if ((!hw_list[!hw->index] || !hw_list[!hw->index]->wed_dev) &&
-           hw->eth->dma_dev != hw->eth->dev)
-               mtk_eth_set_dma_device(hw->eth, hw->eth->dev);
diff --git a/target/linux/generic/backport-5.15/733-v6.4-24-net-ethernet-mtk_eth_soc-ppe-add-support-for-flow-ac.patch b/target/linux/generic/backport-5.15/733-v6.4-24-net-ethernet-mtk_eth_soc-ppe-add-support-for-flow-ac.patch
deleted file mode 100644 (file)
index e4022ff..0000000
+++ /dev/null
@@ -1,428 +0,0 @@
-From patchwork Wed Nov  2 00:58:01 2022
-Content-Type: text/plain; charset="utf-8"
-MIME-Version: 1.0
-Content-Transfer-Encoding: 7bit
-X-Patchwork-Submitter: Daniel Golle <[email protected]>
-X-Patchwork-Id: 13027653
-X-Patchwork-Delegate: [email protected]
-Return-Path: <[email protected]>
-Date: Wed, 2 Nov 2022 00:58:01 +0000
-From: Daniel Golle <[email protected]>
-To: Felix Fietkau <[email protected]>, John Crispin <[email protected]>,
-        Sean Wang <[email protected]>,
-        Mark Lee <[email protected]>,
-        "David S. Miller" <[email protected]>,
-        Eric Dumazet <[email protected]>,
-        Jakub Kicinski <[email protected]>,
-        Paolo Abeni <[email protected]>,
-        Matthias Brugger <[email protected]>,
-Subject: [PATCH v4] net: ethernet: mediatek: ppe: add support for flow
- accounting
-Message-ID: <[email protected]>
-MIME-Version: 1.0
-Content-Disposition: inline
-Precedence: bulk
-List-ID: <netdev.vger.kernel.org>
-X-Mailing-List: [email protected]
-X-Patchwork-Delegate: [email protected]
-
-The PPE units found in MT7622 and newer support packet and byte
-accounting of hw-offloaded flows. Add support for reading those
-counters as found in MediaTek's SDK[1].
-
-[1]: https://git01.mediatek.com/plugins/gitiles/openwrt/feeds/mtk-openwrt-feeds/+/bc6a6a375c800dc2b80e1a325a2c732d1737df92
-Signed-off-by: Daniel Golle <[email protected]>
----
-v4: declare function mtk_mib_entry_read as static
-v3: don't bother to set 'false' values in any zero-initialized struct
-    use mtk_foe_entry_ib2
-    both changes were requested by Felix Fietkau
-
-v2: fix wrong variable name in return value check spotted by Denis Kirjanov
-
- drivers/net/ethernet/mediatek/mtk_eth_soc.c   |   7 +-
- drivers/net/ethernet/mediatek/mtk_eth_soc.h   |   1 +
- drivers/net/ethernet/mediatek/mtk_ppe.c       | 110 +++++++++++++++++-
- drivers/net/ethernet/mediatek/mtk_ppe.h       |  23 +++-
- .../net/ethernet/mediatek/mtk_ppe_debugfs.c   |   9 +-
- .../net/ethernet/mediatek/mtk_ppe_offload.c   |   7 ++
- drivers/net/ethernet/mediatek/mtk_ppe_regs.h  |  14 +++
- 7 files changed, 166 insertions(+), 5 deletions(-)
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-@@ -4637,8 +4637,8 @@ static int mtk_probe(struct platform_dev
-               for (i = 0; i < num_ppe; i++) {
-                       u32 ppe_addr = eth->soc->reg_map->ppe_base + i * 0x400;
--                      eth->ppe[i] = mtk_ppe_init(eth, eth->base + ppe_addr,
--                                                 eth->soc->offload_version, i);
-+                      eth->ppe[i] = mtk_ppe_init(eth, eth->base + ppe_addr, i);
-+
-                       if (!eth->ppe[i]) {
-                               err = -ENOMEM;
-                               goto err_deinit_ppe;
-@@ -4764,6 +4764,7 @@ static const struct mtk_soc_data mt7622_
-       .required_pctl = false,
-       .offload_version = 2,
-       .hash_offset = 2,
-+      .has_accounting = true,
-       .foe_entry_size = sizeof(struct mtk_foe_entry) - 16,
-       .txrx = {
-               .txd_size = sizeof(struct mtk_tx_dma),
-@@ -4801,6 +4802,7 @@ static const struct mtk_soc_data mt7629_
-       .hw_features = MTK_HW_FEATURES,
-       .required_clks = MT7629_CLKS_BITMAP,
-       .required_pctl = false,
-+      .has_accounting = true,
-       .txrx = {
-               .txd_size = sizeof(struct mtk_tx_dma),
-               .rxd_size = sizeof(struct mtk_rx_dma),
-@@ -4821,6 +4823,7 @@ static const struct mtk_soc_data mt7981_
-       .offload_version = 2,
-       .hash_offset = 4,
-       .foe_entry_size = sizeof(struct mtk_foe_entry),
-+      .has_accounting = true,
-       .txrx = {
-               .txd_size = sizeof(struct mtk_tx_dma_v2),
-               .rxd_size = sizeof(struct mtk_rx_dma_v2),
-@@ -4841,6 +4844,7 @@ static const struct mtk_soc_data mt7986_
-       .offload_version = 2,
-       .hash_offset = 4,
-       .foe_entry_size = sizeof(struct mtk_foe_entry),
-+      .has_accounting = true,
-       .txrx = {
-               .txd_size = sizeof(struct mtk_tx_dma_v2),
-               .rxd_size = sizeof(struct mtk_rx_dma_v2),
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-@@ -1008,6 +1008,8 @@ struct mtk_reg_map {
-  *                            the extra setup for those pins used by GMAC.
-  * @hash_offset                       Flow table hash offset.
-  * @foe_entry_size            Foe table entry size.
-+ * @has_accounting            Bool indicating support for accounting of
-+ *                            offloaded flows.
-  * @txd_size                  Tx DMA descriptor size.
-  * @rxd_size                  Rx DMA descriptor size.
-  * @rx_irq_done_mask          Rx irq done register mask.
-@@ -1025,6 +1027,7 @@ struct mtk_soc_data {
-       u8              hash_offset;
-       u16             foe_entry_size;
-       netdev_features_t hw_features;
-+      bool            has_accounting;
-       struct {
-               u32     txd_size;
-               u32     rxd_size;
---- a/drivers/net/ethernet/mediatek/mtk_ppe.c
-+++ b/drivers/net/ethernet/mediatek/mtk_ppe.c
-@@ -74,6 +74,48 @@ static int mtk_ppe_wait_busy(struct mtk_
-       return ret;
- }
-+static int mtk_ppe_mib_wait_busy(struct mtk_ppe *ppe)
-+{
-+      int ret;
-+      u32 val;
-+
-+      ret = readl_poll_timeout(ppe->base + MTK_PPE_MIB_SER_CR, val,
-+                               !(val & MTK_PPE_MIB_SER_CR_ST),
-+                               20, MTK_PPE_WAIT_TIMEOUT_US);
-+
-+      if (ret)
-+              dev_err(ppe->dev, "MIB table busy");
-+
-+      return ret;
-+}
-+
-+static int mtk_mib_entry_read(struct mtk_ppe *ppe, u16 index, u64 *bytes, u64 *packets)
-+{
-+      u32 byte_cnt_low, byte_cnt_high, pkt_cnt_low, pkt_cnt_high;
-+      u32 val, cnt_r0, cnt_r1, cnt_r2;
-+      int ret;
-+
-+      val = FIELD_PREP(MTK_PPE_MIB_SER_CR_ADDR, index) | MTK_PPE_MIB_SER_CR_ST;
-+      ppe_w32(ppe, MTK_PPE_MIB_SER_CR, val);
-+
-+      ret = mtk_ppe_mib_wait_busy(ppe);
-+      if (ret)
-+              return ret;
-+
-+      cnt_r0 = readl(ppe->base + MTK_PPE_MIB_SER_R0);
-+      cnt_r1 = readl(ppe->base + MTK_PPE_MIB_SER_R1);
-+      cnt_r2 = readl(ppe->base + MTK_PPE_MIB_SER_R2);
-+
-+      byte_cnt_low = FIELD_GET(MTK_PPE_MIB_SER_R0_BYTE_CNT_LOW, cnt_r0);
-+      byte_cnt_high = FIELD_GET(MTK_PPE_MIB_SER_R1_BYTE_CNT_HIGH, cnt_r1);
-+      pkt_cnt_low = FIELD_GET(MTK_PPE_MIB_SER_R1_PKT_CNT_LOW, cnt_r1);
-+      pkt_cnt_high = FIELD_GET(MTK_PPE_MIB_SER_R2_PKT_CNT_HIGH, cnt_r2);
-+      *bytes = ((u64)byte_cnt_high << 32) | byte_cnt_low;
-+      *packets = (pkt_cnt_high << 16) | pkt_cnt_low;
-+
-+      return 0;
-+}
-+
- static void mtk_ppe_cache_clear(struct mtk_ppe *ppe)
- {
-       ppe_set(ppe, MTK_PPE_CACHE_CTL, MTK_PPE_CACHE_CTL_CLEAR);
-@@ -465,6 +507,13 @@ __mtk_foe_entry_clear(struct mtk_ppe *pp
-               hwe->ib1 |= FIELD_PREP(MTK_FOE_IB1_STATE, MTK_FOE_STATE_INVALID);
-               dma_wmb();
-               mtk_ppe_cache_clear(ppe);
-+              if (ppe->accounting) {
-+                      struct mtk_foe_accounting *acct;
-+
-+                      acct = ppe->acct_table + entry->hash * sizeof(*acct);
-+                      acct->packets = 0;
-+                      acct->bytes = 0;
-+              }
-       }
-       entry->hash = 0xffff;
-@@ -572,6 +621,9 @@ __mtk_foe_entry_commit(struct mtk_ppe *p
-       wmb();
-       hwe->ib1 = entry->ib1;
-+      if (ppe->accounting)
-+              *mtk_foe_entry_ib2(eth, hwe) |= MTK_FOE_IB2_MIB_CNT;
-+
-       dma_wmb();
-       mtk_ppe_cache_clear(ppe);
-@@ -763,11 +815,39 @@ int mtk_ppe_prepare_reset(struct mtk_ppe
-       return mtk_ppe_wait_busy(ppe);
- }
--struct mtk_ppe *mtk_ppe_init(struct mtk_eth *eth, void __iomem *base,
--                           int version, int index)
-+struct mtk_foe_accounting *mtk_foe_entry_get_mib(struct mtk_ppe *ppe, u32 index,
-+                                               struct mtk_foe_accounting *diff)
-+{
-+      struct mtk_foe_accounting *acct;
-+      int size = sizeof(struct mtk_foe_accounting);
-+      u64 bytes, packets;
-+
-+      if (!ppe->accounting)
-+              return NULL;
-+
-+      if (mtk_mib_entry_read(ppe, index, &bytes, &packets))
-+              return NULL;
-+
-+      acct = ppe->acct_table + index * size;
-+
-+      acct->bytes += bytes;
-+      acct->packets += packets;
-+
-+      if (diff) {
-+              diff->bytes = bytes;
-+              diff->packets = packets;
-+      }
-+
-+      return acct;
-+}
-+
-+struct mtk_ppe *mtk_ppe_init(struct mtk_eth *eth, void __iomem *base, int index)
- {
-+      bool accounting = eth->soc->has_accounting;
-       const struct mtk_soc_data *soc = eth->soc;
-+      struct mtk_foe_accounting *acct;
-       struct device *dev = eth->dev;
-+      struct mtk_mib_entry *mib;
-       struct mtk_ppe *ppe;
-       u32 foe_flow_size;
-       void *foe;
-@@ -784,7 +864,8 @@ struct mtk_ppe *mtk_ppe_init(struct mtk_
-       ppe->base = base;
-       ppe->eth = eth;
-       ppe->dev = dev;
--      ppe->version = version;
-+      ppe->version = eth->soc->offload_version;
-+      ppe->accounting = accounting;
-       foe = dmam_alloc_coherent(ppe->dev,
-                                 MTK_PPE_ENTRIES * soc->foe_entry_size,
-@@ -800,6 +881,23 @@ struct mtk_ppe *mtk_ppe_init(struct mtk_
-       if (!ppe->foe_flow)
-               goto err_free_l2_flows;
-+      if (accounting) {
-+              mib = dmam_alloc_coherent(ppe->dev, MTK_PPE_ENTRIES * sizeof(*mib),
-+                                        &ppe->mib_phys, GFP_KERNEL);
-+              if (!mib)
-+                      return NULL;
-+
-+              ppe->mib_table = mib;
-+
-+              acct = devm_kzalloc(dev, MTK_PPE_ENTRIES * sizeof(*acct),
-+                                  GFP_KERNEL);
-+
-+              if (!acct)
-+                      return NULL;
-+
-+              ppe->acct_table = acct;
-+      }
-+
-       mtk_ppe_debugfs_init(ppe, index);
-       return ppe;
-@@ -929,6 +1027,16 @@ void mtk_ppe_start(struct mtk_ppe *ppe)
-               ppe_w32(ppe, MTK_PPE_DEFAULT_CPU_PORT1, 0xcb777);
-               ppe_w32(ppe, MTK_PPE_SBW_CTRL, 0x7f);
-       }
-+
-+      if (ppe->accounting && ppe->mib_phys) {
-+              ppe_w32(ppe, MTK_PPE_MIB_TB_BASE, ppe->mib_phys);
-+              ppe_m32(ppe, MTK_PPE_MIB_CFG, MTK_PPE_MIB_CFG_EN,
-+                      MTK_PPE_MIB_CFG_EN);
-+              ppe_m32(ppe, MTK_PPE_MIB_CFG, MTK_PPE_MIB_CFG_RD_CLR,
-+                      MTK_PPE_MIB_CFG_RD_CLR);
-+              ppe_m32(ppe, MTK_PPE_MIB_CACHE_CTL, MTK_PPE_MIB_CACHE_CTL_EN,
-+                      MTK_PPE_MIB_CFG_RD_CLR);
-+      }
- }
- int mtk_ppe_stop(struct mtk_ppe *ppe)
---- a/drivers/net/ethernet/mediatek/mtk_ppe.h
-+++ b/drivers/net/ethernet/mediatek/mtk_ppe.h
-@@ -57,6 +57,7 @@ enum {
- #define MTK_FOE_IB2_MULTICAST         BIT(8)
- #define MTK_FOE_IB2_WDMA_QID2         GENMASK(13, 12)
-+#define MTK_FOE_IB2_MIB_CNT           BIT(15)
- #define MTK_FOE_IB2_WDMA_DEVIDX               BIT(16)
- #define MTK_FOE_IB2_WDMA_WINFO                BIT(17)
-@@ -285,16 +286,34 @@ struct mtk_flow_entry {
-       unsigned long cookie;
- };
-+struct mtk_mib_entry {
-+      u32     byt_cnt_l;
-+      u16     byt_cnt_h;
-+      u32     pkt_cnt_l;
-+      u8      pkt_cnt_h;
-+      u8      _rsv0;
-+      u32     _rsv1;
-+} __packed;
-+
-+struct mtk_foe_accounting {
-+      u64     bytes;
-+      u64     packets;
-+};
-+
- struct mtk_ppe {
-       struct mtk_eth *eth;
-       struct device *dev;
-       void __iomem *base;
-       int version;
-       char dirname[5];
-+      bool accounting;
-       void *foe_table;
-       dma_addr_t foe_phys;
-+      struct mtk_mib_entry *mib_table;
-+      dma_addr_t mib_phys;
-+
-       u16 foe_check_time[MTK_PPE_ENTRIES];
-       struct hlist_head *foe_flow;
-@@ -303,8 +322,7 @@ struct mtk_ppe {
-       void *acct_table;
- };
--struct mtk_ppe *mtk_ppe_init(struct mtk_eth *eth, void __iomem *base,
--                           int version, int index);
-+struct mtk_ppe *mtk_ppe_init(struct mtk_eth *eth, void __iomem *base, int index);
- void mtk_ppe_deinit(struct mtk_eth *eth);
- void mtk_ppe_start(struct mtk_ppe *ppe);
- int mtk_ppe_stop(struct mtk_ppe *ppe);
-@@ -359,5 +377,7 @@ int mtk_foe_entry_commit(struct mtk_ppe
- void mtk_foe_entry_clear(struct mtk_ppe *ppe, struct mtk_flow_entry *entry);
- int mtk_foe_entry_idle_time(struct mtk_ppe *ppe, struct mtk_flow_entry *entry);
- int mtk_ppe_debugfs_init(struct mtk_ppe *ppe, int index);
-+struct mtk_foe_accounting *mtk_foe_entry_get_mib(struct mtk_ppe *ppe, u32 index,
-+                                               struct mtk_foe_accounting *diff);
- #endif
---- a/drivers/net/ethernet/mediatek/mtk_ppe_debugfs.c
-+++ b/drivers/net/ethernet/mediatek/mtk_ppe_debugfs.c
-@@ -82,6 +82,7 @@ mtk_ppe_debugfs_foe_show(struct seq_file
-               struct mtk_foe_entry *entry = mtk_foe_get_entry(ppe, i);
-               struct mtk_foe_mac_info *l2;
-               struct mtk_flow_addr_info ai = {};
-+              struct mtk_foe_accounting *acct;
-               unsigned char h_source[ETH_ALEN];
-               unsigned char h_dest[ETH_ALEN];
-               int type, state;
-@@ -95,6 +96,8 @@ mtk_ppe_debugfs_foe_show(struct seq_file
-               if (bind && state != MTK_FOE_STATE_BIND)
-                       continue;
-+              acct = mtk_foe_entry_get_mib(ppe, i, NULL);
-+
-               type = FIELD_GET(MTK_FOE_IB1_PACKET_TYPE, entry->ib1);
-               seq_printf(m, "%05x %s %7s", i,
-                          mtk_foe_entry_state_str(state),
-@@ -153,9 +156,11 @@ mtk_ppe_debugfs_foe_show(struct seq_file
-               *((__be16 *)&h_dest[4]) = htons(l2->dest_mac_lo);
-               seq_printf(m, " eth=%pM->%pM etype=%04x"
--                            " vlan=%d,%d ib1=%08x ib2=%08x\n",
-+                            " vlan=%d,%d ib1=%08x ib2=%08x"
-+                            " packets=%llu bytes=%llu\n",
-                          h_source, h_dest, ntohs(l2->etype),
--                         l2->vlan1, l2->vlan2, entry->ib1, ib2);
-+                         l2->vlan1, l2->vlan2, entry->ib1, ib2,
-+                         acct ? acct->packets : 0, acct ? acct->bytes : 0);
-       }
-       return 0;
---- a/drivers/net/ethernet/mediatek/mtk_ppe_offload.c
-+++ b/drivers/net/ethernet/mediatek/mtk_ppe_offload.c
-@@ -497,6 +497,7 @@ static int
- mtk_flow_offload_stats(struct mtk_eth *eth, struct flow_cls_offload *f)
- {
-       struct mtk_flow_entry *entry;
-+      struct mtk_foe_accounting diff;
-       u32 idle;
-       entry = rhashtable_lookup(&eth->flow_table, &f->cookie,
-@@ -507,6 +508,13 @@ mtk_flow_offload_stats(struct mtk_eth *e
-       idle = mtk_foe_entry_idle_time(eth->ppe[entry->ppe_index], entry);
-       f->stats.lastused = jiffies - idle * HZ;
-+      if (entry->hash != 0xFFFF &&
-+          mtk_foe_entry_get_mib(eth->ppe[entry->ppe_index], entry->hash,
-+                                &diff)) {
-+              f->stats.pkts += diff.packets;
-+              f->stats.bytes += diff.bytes;
-+      }
-+
-       return 0;
- }
---- a/drivers/net/ethernet/mediatek/mtk_ppe_regs.h
-+++ b/drivers/net/ethernet/mediatek/mtk_ppe_regs.h
-@@ -149,6 +149,20 @@ enum {
- #define MTK_PPE_MIB_TB_BASE                   0x338
-+#define MTK_PPE_MIB_SER_CR                    0x33C
-+#define MTK_PPE_MIB_SER_CR_ST                 BIT(16)
-+#define MTK_PPE_MIB_SER_CR_ADDR                       GENMASK(13, 0)
-+
-+#define MTK_PPE_MIB_SER_R0                    0x340
-+#define MTK_PPE_MIB_SER_R0_BYTE_CNT_LOW               GENMASK(31, 0)
-+
-+#define MTK_PPE_MIB_SER_R1                    0x344
-+#define MTK_PPE_MIB_SER_R1_PKT_CNT_LOW                GENMASK(31, 16)
-+#define MTK_PPE_MIB_SER_R1_BYTE_CNT_HIGH      GENMASK(15, 0)
-+
-+#define MTK_PPE_MIB_SER_R2                    0x348
-+#define MTK_PPE_MIB_SER_R2_PKT_CNT_HIGH               GENMASK(23, 0)
-+
- #define MTK_PPE_MIB_CACHE_CTL                 0x350
- #define MTK_PPE_MIB_CACHE_CTL_EN              BIT(0)
- #define MTK_PPE_MIB_CACHE_CTL_FLUSH           BIT(2)
diff --git a/target/linux/generic/backport-5.15/733-v6.4-25-net-ethernet-mediatek-fix-ppe-flow-accounting-for-v1.patch b/target/linux/generic/backport-5.15/733-v6.4-25-net-ethernet-mediatek-fix-ppe-flow-accounting-for-v1.patch
deleted file mode 100644 (file)
index 3a02c3a..0000000
+++ /dev/null
@@ -1,51 +0,0 @@
-From: Felix Fietkau <[email protected]>
-Date: Thu, 23 Mar 2023 21:45:43 +0100
-Subject: [PATCH] net: ethernet: mediatek: fix ppe flow accounting for v1
- hardware
-
-Older chips (like MT7622) use a different bit in ib2 to enable hardware
-counter support.
-
-Signed-off-by: Felix Fietkau <[email protected]>
----
-
---- a/drivers/net/ethernet/mediatek/mtk_ppe.c
-+++ b/drivers/net/ethernet/mediatek/mtk_ppe.c
-@@ -605,6 +605,7 @@ __mtk_foe_entry_commit(struct mtk_ppe *p
-       struct mtk_eth *eth = ppe->eth;
-       u16 timestamp = mtk_eth_timestamp(eth);
-       struct mtk_foe_entry *hwe;
-+      u32 val;
-       if (MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2)) {
-               entry->ib1 &= ~MTK_FOE_IB1_BIND_TIMESTAMP_V2;
-@@ -621,8 +622,13 @@ __mtk_foe_entry_commit(struct mtk_ppe *p
-       wmb();
-       hwe->ib1 = entry->ib1;
--      if (ppe->accounting)
--              *mtk_foe_entry_ib2(eth, hwe) |= MTK_FOE_IB2_MIB_CNT;
-+      if (ppe->accounting) {
-+              if (MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2))
-+                      val = MTK_FOE_IB2_MIB_CNT_V2;
-+              else
-+                      val = MTK_FOE_IB2_MIB_CNT;
-+              *mtk_foe_entry_ib2(eth, hwe) |= val;
-+      }
-       dma_wmb();
---- a/drivers/net/ethernet/mediatek/mtk_ppe.h
-+++ b/drivers/net/ethernet/mediatek/mtk_ppe.h
-@@ -55,9 +55,10 @@ enum {
- #define MTK_FOE_IB2_PSE_QOS           BIT(4)
- #define MTK_FOE_IB2_DEST_PORT         GENMASK(7, 5)
- #define MTK_FOE_IB2_MULTICAST         BIT(8)
-+#define MTK_FOE_IB2_MIB_CNT           BIT(10)
- #define MTK_FOE_IB2_WDMA_QID2         GENMASK(13, 12)
--#define MTK_FOE_IB2_MIB_CNT           BIT(15)
-+#define MTK_FOE_IB2_MIB_CNT_V2                BIT(15)
- #define MTK_FOE_IB2_WDMA_DEVIDX               BIT(16)
- #define MTK_FOE_IB2_WDMA_WINFO                BIT(17)
diff --git a/target/linux/generic/backport-5.15/733-v6.4-26-net-ethernet-mtk_eth_soc-drop-generic-vlan-rx-offloa.patch b/target/linux/generic/backport-5.15/733-v6.4-26-net-ethernet-mtk_eth_soc-drop-generic-vlan-rx-offloa.patch
deleted file mode 100644 (file)
index 8be6a69..0000000
+++ /dev/null
@@ -1,201 +0,0 @@
-From: Felix Fietkau <[email protected]>
-Date: Sun, 20 Nov 2022 23:01:00 +0100
-Subject: [PATCH] net: ethernet: mtk_eth_soc: drop generic vlan rx offload,
- only use DSA untagging
-
-Through testing I found out that hardware vlan rx offload support seems to
-have some hardware issues. At least when using multiple MACs and when receiving
-tagged packets on the secondary MAC, the hardware can sometimes start to emit
-wrong tags on the first MAC as well.
-
-In order to avoid such issues, drop the feature configuration and use the
-offload feature only for DSA hardware untagging on MT7621/MT7622 devices which
-only use one MAC.
-
-Signed-off-by: Felix Fietkau <[email protected]>
----
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-@@ -1849,9 +1849,7 @@ static int mtk_poll_rx(struct napi_struc
-       while (done < budget) {
-               unsigned int pktlen, *rxdcsum;
--              bool has_hwaccel_tag = false;
-               struct net_device *netdev;
--              u16 vlan_proto, vlan_tci;
-               dma_addr_t dma_addr;
-               u32 hash, reason;
-               int mac = 0;
-@@ -1986,36 +1984,21 @@ static int mtk_poll_rx(struct napi_struc
-                       skb_checksum_none_assert(skb);
-               skb->protocol = eth_type_trans(skb, netdev);
--              if (reason == MTK_PPE_CPU_REASON_HIT_UNBIND_RATE_REACHED)
--                      mtk_ppe_check_skb(eth->ppe[0], skb, hash);
--
--              if (netdev->features & NETIF_F_HW_VLAN_CTAG_RX) {
--                      if (MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2)) {
--                              if (trxd.rxd3 & RX_DMA_VTAG_V2) {
--                                      vlan_proto = RX_DMA_VPID(trxd.rxd4);
--                                      vlan_tci = RX_DMA_VID(trxd.rxd4);
--                                      has_hwaccel_tag = true;
--                              }
--                      } else if (trxd.rxd2 & RX_DMA_VTAG) {
--                              vlan_proto = RX_DMA_VPID(trxd.rxd3);
--                              vlan_tci = RX_DMA_VID(trxd.rxd3);
--                              has_hwaccel_tag = true;
--                      }
--              }
--
-               /* When using VLAN untagging in combination with DSA, the
-                * hardware treats the MTK special tag as a VLAN and untags it.
-                */
--              if (has_hwaccel_tag && netdev_uses_dsa(netdev)) {
--                      unsigned int port = vlan_proto & GENMASK(2, 0);
-+              if (!MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2) &&
-+                  (trxd.rxd2 & RX_DMA_VTAG) && netdev_uses_dsa(netdev)) {
-+                      unsigned int port = RX_DMA_VPID(trxd.rxd3) & GENMASK(2, 0);
-                       if (port < ARRAY_SIZE(eth->dsa_meta) &&
-                           eth->dsa_meta[port])
-                               skb_dst_set_noref(skb, &eth->dsa_meta[port]->dst);
--              } else if (has_hwaccel_tag) {
--                      __vlan_hwaccel_put_tag(skb, htons(vlan_proto), vlan_tci);
-               }
-+              if (reason == MTK_PPE_CPU_REASON_HIT_UNBIND_RATE_REACHED)
-+                      mtk_ppe_check_skb(eth->ppe[0], skb, hash);
-+
-               skb_record_rx_queue(skb, 0);
-               napi_gro_receive(napi, skb);
-@@ -2833,29 +2816,11 @@ static netdev_features_t mtk_fix_feature
- static int mtk_set_features(struct net_device *dev, netdev_features_t features)
- {
--      struct mtk_mac *mac = netdev_priv(dev);
--      struct mtk_eth *eth = mac->hw;
-       netdev_features_t diff = dev->features ^ features;
--      int i;
-       if ((diff & NETIF_F_LRO) && !(features & NETIF_F_LRO))
-               mtk_hwlro_netdev_disable(dev);
--      /* Set RX VLAN offloading */
--      if (!(diff & NETIF_F_HW_VLAN_CTAG_RX))
--              return 0;
--
--      mtk_w32(eth, !!(features & NETIF_F_HW_VLAN_CTAG_RX),
--              MTK_CDMP_EG_CTRL);
--
--      /* sync features with other MAC */
--      for (i = 0; i < MTK_MAC_COUNT; i++) {
--              if (!eth->netdev[i] || eth->netdev[i] == dev)
--                      continue;
--              eth->netdev[i]->features &= ~NETIF_F_HW_VLAN_CTAG_RX;
--              eth->netdev[i]->features |= features & NETIF_F_HW_VLAN_CTAG_RX;
--      }
--
-       return 0;
- }
-@@ -3169,30 +3134,6 @@ static int mtk_open(struct net_device *d
-       struct mtk_eth *eth = mac->hw;
-       int i, err;
--      if (mtk_uses_dsa(dev) && !eth->prog) {
--              for (i = 0; i < ARRAY_SIZE(eth->dsa_meta); i++) {
--                      struct metadata_dst *md_dst = eth->dsa_meta[i];
--
--                      if (md_dst)
--                              continue;
--
--                      md_dst = metadata_dst_alloc(0, METADATA_HW_PORT_MUX,
--                                                  GFP_KERNEL);
--                      if (!md_dst)
--                              return -ENOMEM;
--
--                      md_dst->u.port_info.port_id = i;
--                      eth->dsa_meta[i] = md_dst;
--              }
--      } else {
--              /* Hardware special tag parsing needs to be disabled if at least
--               * one MAC does not use DSA.
--               */
--              u32 val = mtk_r32(eth, MTK_CDMP_IG_CTRL);
--              val &= ~MTK_CDMP_STAG_EN;
--              mtk_w32(eth, val, MTK_CDMP_IG_CTRL);
--      }
--
-       err = phylink_of_phy_connect(mac->phylink, mac->of_node, 0);
-       if (err) {
-               netdev_err(dev, "%s: could not attach PHY: %d\n", __func__,
-@@ -3233,6 +3174,35 @@ static int mtk_open(struct net_device *d
-       phylink_start(mac->phylink);
-       netif_tx_start_all_queues(dev);
-+      if (MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2))
-+              return 0;
-+
-+      if (mtk_uses_dsa(dev) && !eth->prog) {
-+              for (i = 0; i < ARRAY_SIZE(eth->dsa_meta); i++) {
-+                      struct metadata_dst *md_dst = eth->dsa_meta[i];
-+
-+                      if (md_dst)
-+                              continue;
-+
-+                      md_dst = metadata_dst_alloc(0, METADATA_HW_PORT_MUX,
-+                                                  GFP_KERNEL);
-+                      if (!md_dst)
-+                              return -ENOMEM;
-+
-+                      md_dst->u.port_info.port_id = i;
-+                      eth->dsa_meta[i] = md_dst;
-+              }
-+      } else {
-+              /* Hardware special tag parsing needs to be disabled if at least
-+               * one MAC does not use DSA.
-+               */
-+              u32 val = mtk_r32(eth, MTK_CDMP_IG_CTRL);
-+              val &= ~MTK_CDMP_STAG_EN;
-+              mtk_w32(eth, val, MTK_CDMP_IG_CTRL);
-+
-+              mtk_w32(eth, 0, MTK_CDMP_EG_CTRL);
-+      }
-+
-       return 0;
- }
-@@ -3717,10 +3687,9 @@ static int mtk_hw_init(struct mtk_eth *e
-       if (!MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2)) {
-               val = mtk_r32(eth, MTK_CDMP_IG_CTRL);
-               mtk_w32(eth, val | MTK_CDMP_STAG_EN, MTK_CDMP_IG_CTRL);
--      }
--      /* Enable RX VLan Offloading */
--      mtk_w32(eth, 1, MTK_CDMP_EG_CTRL);
-+              mtk_w32(eth, 1, MTK_CDMP_EG_CTRL);
-+      }
-       /* set interrupt delays based on current Net DIM sample */
-       mtk_dim_rx(&eth->rx_dim.work);
-@@ -4360,7 +4329,7 @@ static int mtk_add_mac(struct mtk_eth *e
-               eth->netdev[id]->hw_features |= NETIF_F_LRO;
-       eth->netdev[id]->vlan_features = eth->soc->hw_features &
--              ~(NETIF_F_HW_VLAN_CTAG_TX | NETIF_F_HW_VLAN_CTAG_RX);
-+              ~NETIF_F_HW_VLAN_CTAG_TX;
-       eth->netdev[id]->features |= eth->soc->hw_features;
-       eth->netdev[id]->ethtool_ops = &mtk_ethtool_ops;
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-@@ -48,7 +48,6 @@
- #define MTK_HW_FEATURES               (NETIF_F_IP_CSUM | \
-                                NETIF_F_RXCSUM | \
-                                NETIF_F_HW_VLAN_CTAG_TX | \
--                               NETIF_F_HW_VLAN_CTAG_RX | \
-                                NETIF_F_SG | NETIF_F_TSO | \
-                                NETIF_F_TSO6 | \
-                                NETIF_F_IPV6_CSUM |\
diff --git a/target/linux/generic/backport-5.15/733-v6.5-27-net-ethernet-mtk_eth_soc-always-mtk_get_ib1_pkt_type.patch b/target/linux/generic/backport-5.15/733-v6.5-27-net-ethernet-mtk_eth_soc-always-mtk_get_ib1_pkt_type.patch
deleted file mode 100644 (file)
index 2704fae..0000000
+++ /dev/null
@@ -1,31 +0,0 @@
-From b804f765485109f9644cc05d1e8fc79ca6c6e4aa Mon Sep 17 00:00:00 2001
-From: Daniel Golle <[email protected]>
-Date: Wed, 19 Jul 2023 01:39:36 +0100
-Subject: [PATCH 094/250] net: ethernet: mtk_eth_soc: always
- mtk_get_ib1_pkt_type
-
-entries and bind debugfs files would display wrong data on NETSYS_V2 and
-later because instead of using mtk_get_ib1_pkt_type the driver would use
-MTK_FOE_IB1_PACKET_TYPE which corresponds to NETSYS_V1(.x) SoCs.
-Use mtk_get_ib1_pkt_type so entries and bind records display correctly.
-
-Fixes: 03a3180e5c09e ("net: ethernet: mtk_eth_soc: introduce flow offloading support for mt7986")
-Signed-off-by: Daniel Golle <[email protected]>
-Acked-by: Lorenzo Bianconi <[email protected]>
-Link: https://lore.kernel.org/r/c0ae03d0182f4d27b874cbdf0059bc972c317f3c.1689727134.git.daniel@makrotopia.org
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- drivers/net/ethernet/mediatek/mtk_ppe_debugfs.c | 2 +-
- 1 file changed, 1 insertion(+), 1 deletion(-)
-
---- a/drivers/net/ethernet/mediatek/mtk_ppe_debugfs.c
-+++ b/drivers/net/ethernet/mediatek/mtk_ppe_debugfs.c
-@@ -98,7 +98,7 @@ mtk_ppe_debugfs_foe_show(struct seq_file
-               acct = mtk_foe_entry_get_mib(ppe, i, NULL);
--              type = FIELD_GET(MTK_FOE_IB1_PACKET_TYPE, entry->ib1);
-+              type = mtk_get_ib1_pkt_type(ppe->eth, entry->ib1);
-               seq_printf(m, "%05x %s %7s", i,
-                          mtk_foe_entry_state_str(state),
-                          mtk_foe_pkt_type_str(type));
diff --git a/target/linux/generic/backport-5.15/734-v5.16-0001-net-bgmac-improve-handling-PHY.patch b/target/linux/generic/backport-5.15/734-v5.16-0001-net-bgmac-improve-handling-PHY.patch
deleted file mode 100644 (file)
index 6788a2e..0000000
+++ /dev/null
@@ -1,84 +0,0 @@
-From b5375509184dc23d2b7fa0c5ed8763899ccc9674 Mon Sep 17 00:00:00 2001
-From: =?UTF-8?q?Rafa=C5=82=20Mi=C5=82ecki?= <[email protected]>
-Date: Sat, 2 Oct 2021 19:58:11 +0200
-Subject: [PATCH] net: bgmac: improve handling PHY
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-1. Use info from DT if available
-
-It allows describing for example a fixed link. It's more accurate than
-just guessing there may be one (depending on a chipset).
-
-2. Verify PHY ID before trying to connect PHY
-
-PHY addr 0x1e (30) is special in Broadcom routers and means a switch
-connected as MDIO devices instead of a real PHY. Don't try connecting to
-it.
-
-Signed-off-by: Rafał Miłecki <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/ethernet/broadcom/bgmac-bcma.c | 33 ++++++++++++++--------
- 1 file changed, 21 insertions(+), 12 deletions(-)
-
---- a/drivers/net/ethernet/broadcom/bgmac-bcma.c
-+++ b/drivers/net/ethernet/broadcom/bgmac-bcma.c
-@@ -11,6 +11,7 @@
- #include <linux/bcma/bcma.h>
- #include <linux/brcmphy.h>
- #include <linux/etherdevice.h>
-+#include <linux/of_mdio.h>
- #include <linux/of_net.h>
- #include "bgmac.h"
-@@ -86,17 +87,28 @@ static int bcma_phy_connect(struct bgmac
-       struct phy_device *phy_dev;
-       char bus_id[MII_BUS_ID_SIZE + 3];
-+      /* DT info should be the most accurate */
-+      phy_dev = of_phy_get_and_connect(bgmac->net_dev, bgmac->dev->of_node,
-+                                       bgmac_adjust_link);
-+      if (phy_dev)
-+              return 0;
-+
-       /* Connect to the PHY */
--      snprintf(bus_id, sizeof(bus_id), PHY_ID_FMT, bgmac->mii_bus->id,
--               bgmac->phyaddr);
--      phy_dev = phy_connect(bgmac->net_dev, bus_id, bgmac_adjust_link,
--                            PHY_INTERFACE_MODE_MII);
--      if (IS_ERR(phy_dev)) {
--              dev_err(bgmac->dev, "PHY connection failed\n");
--              return PTR_ERR(phy_dev);
-+      if (bgmac->mii_bus && bgmac->phyaddr != BGMAC_PHY_NOREGS) {
-+              snprintf(bus_id, sizeof(bus_id), PHY_ID_FMT, bgmac->mii_bus->id,
-+                       bgmac->phyaddr);
-+              phy_dev = phy_connect(bgmac->net_dev, bus_id, bgmac_adjust_link,
-+                                    PHY_INTERFACE_MODE_MII);
-+              if (IS_ERR(phy_dev)) {
-+                      dev_err(bgmac->dev, "PHY connection failed\n");
-+                      return PTR_ERR(phy_dev);
-+              }
-+
-+              return 0;
-       }
--      return 0;
-+      /* Assume a fixed link to the switch port */
-+      return bgmac_phy_connect_direct(bgmac);
- }
- static const struct bcma_device_id bgmac_bcma_tbl[] = {
-@@ -297,10 +309,7 @@ static int bgmac_probe(struct bcma_devic
-       bgmac->cco_ctl_maskset = bcma_bgmac_cco_ctl_maskset;
-       bgmac->get_bus_clock = bcma_bgmac_get_bus_clock;
-       bgmac->cmn_maskset32 = bcma_bgmac_cmn_maskset32;
--      if (bgmac->mii_bus)
--              bgmac->phy_connect = bcma_phy_connect;
--      else
--              bgmac->phy_connect = bgmac_phy_connect_direct;
-+      bgmac->phy_connect = bcma_phy_connect;
-       err = bgmac_enet_probe(bgmac);
-       if (err)
diff --git a/target/linux/generic/backport-5.15/734-v5.16-0002-net-bgmac-support-MDIO-described-in-DT.patch b/target/linux/generic/backport-5.15/734-v5.16-0002-net-bgmac-support-MDIO-described-in-DT.patch
deleted file mode 100644 (file)
index f134828..0000000
+++ /dev/null
@@ -1,54 +0,0 @@
-From 45c9d966688e7fad7f24bfc450547d91e4304d0b Mon Sep 17 00:00:00 2001
-From: =?UTF-8?q?Rafa=C5=82=20Mi=C5=82ecki?= <[email protected]>
-Date: Sat, 2 Oct 2021 19:58:12 +0200
-Subject: [PATCH] net: bgmac: support MDIO described in DT
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-Check ethernet controller DT node for "mdio" subnode and use it with
-of_mdiobus_register() when present. That allows specifying MDIO and its
-PHY devices in a standard DT based way.
-
-This is required for BCM53573 SoC support. That family is sometimes
-called Northstar (by marketing?) but is quite different from it. It uses
-different CPU(s) and many different hw blocks.
-
-One of shared blocks in BCM53573 is Ethernet controller. Switch however
-is not SRAB accessible (as it Northstar) but is MDIO attached.
-
-Signed-off-by: Rafał Miłecki <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/ethernet/broadcom/bgmac-bcma-mdio.c | 6 +++++-
- 1 file changed, 5 insertions(+), 1 deletion(-)
-
---- a/drivers/net/ethernet/broadcom/bgmac-bcma-mdio.c
-+++ b/drivers/net/ethernet/broadcom/bgmac-bcma-mdio.c
-@@ -10,6 +10,7 @@
- #include <linux/bcma/bcma.h>
- #include <linux/brcmphy.h>
-+#include <linux/of_mdio.h>
- #include "bgmac.h"
- static bool bcma_mdio_wait_value(struct bcma_device *core, u16 reg, u32 mask,
-@@ -211,6 +212,7 @@ struct mii_bus *bcma_mdio_mii_register(s
- {
-       struct bcma_device *core = bgmac->bcma.core;
-       struct mii_bus *mii_bus;
-+      struct device_node *np;
-       int err;
-       mii_bus = mdiobus_alloc();
-@@ -229,7 +231,9 @@ struct mii_bus *bcma_mdio_mii_register(s
-       mii_bus->parent = &core->dev;
-       mii_bus->phy_mask = ~(1 << bgmac->phyaddr);
--      err = mdiobus_register(mii_bus);
-+      np = of_get_child_by_name(core->dev.of_node, "mdio");
-+
-+      err = of_mdiobus_register(mii_bus, np);
-       if (err) {
-               dev_err(&core->dev, "Registration of mii bus failed\n");
-               goto err_free_bus;
diff --git a/target/linux/generic/backport-5.15/735-v6.0-0001-net-phy-Add-support-for-AQR113C-EPHY.patch b/target/linux/generic/backport-5.15/735-v6.0-0001-net-phy-Add-support-for-AQR113C-EPHY.patch
deleted file mode 100644 (file)
index 6090a40..0000000
+++ /dev/null
@@ -1,58 +0,0 @@
-From 12cf1b89a66828719b2135891b65bd5d03eedea9 Mon Sep 17 00:00:00 2001
-From: Bhadram Varka <[email protected]>
-Date: Tue, 21 Jun 2022 09:10:27 +0530
-Subject: [PATCH] net: phy: Add support for AQR113C EPHY
-
-Add support multi-gigabit and single-port Ethernet
-PHY transceiver (AQR113C).
-
-Signed-off-by: Bhadram Varka <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- drivers/net/phy/aquantia_main.c | 20 ++++++++++++++++++++
- 1 file changed, 20 insertions(+)
-
---- a/drivers/net/phy/aquantia_main.c
-+++ b/drivers/net/phy/aquantia_main.c
-@@ -22,6 +22,7 @@
- #define PHY_ID_AQR107 0x03a1b4e0
- #define PHY_ID_AQCS109        0x03a1b5c2
- #define PHY_ID_AQR405 0x03a1b4b0
-+#define PHY_ID_AQR113C        0x31c31c12
- #define MDIO_PHYXS_VEND_IF_STATUS             0xe812
- #define MDIO_PHYXS_VEND_IF_STATUS_TYPE_MASK   GENMASK(7, 3)
-@@ -744,6 +745,24 @@ static struct phy_driver aqr_driver[] =
-       .handle_interrupt = aqr_handle_interrupt,
-       .read_status    = aqr_read_status,
- },
-+{
-+      PHY_ID_MATCH_MODEL(PHY_ID_AQR113C),
-+      .name           = "Aquantia AQR113C",
-+      .probe          = aqr107_probe,
-+      .config_init    = aqr107_config_init,
-+      .config_aneg    = aqr_config_aneg,
-+      .config_intr    = aqr_config_intr,
-+      .handle_interrupt       = aqr_handle_interrupt,
-+      .read_status    = aqr107_read_status,
-+      .get_tunable    = aqr107_get_tunable,
-+      .set_tunable    = aqr107_set_tunable,
-+      .suspend        = aqr107_suspend,
-+      .resume         = aqr107_resume,
-+      .get_sset_count = aqr107_get_sset_count,
-+      .get_strings    = aqr107_get_strings,
-+      .get_stats      = aqr107_get_stats,
-+      .link_change_notify = aqr107_link_change_notify,
-+},
- };
- module_phy_driver(aqr_driver);
-@@ -756,6 +775,7 @@ static struct mdio_device_id __maybe_unu
-       { PHY_ID_MATCH_MODEL(PHY_ID_AQR107) },
-       { PHY_ID_MATCH_MODEL(PHY_ID_AQCS109) },
-       { PHY_ID_MATCH_MODEL(PHY_ID_AQR405) },
-+      { PHY_ID_MATCH_MODEL(PHY_ID_AQR113C) },
-       { }
- };
diff --git a/target/linux/generic/backport-5.15/736-v6.1-0001-net-phy-aquantia-Add-some-additional-phy-interfaces.patch b/target/linux/generic/backport-5.15/736-v6.1-0001-net-phy-aquantia-Add-some-additional-phy-interfaces.patch
deleted file mode 100644 (file)
index ec8485e..0000000
+++ /dev/null
@@ -1,71 +0,0 @@
-From 7de26bf144f6a72858ab60afb2bd2b43265ee0ad Mon Sep 17 00:00:00 2001
-From: Sean Anderson <[email protected]>
-Date: Tue, 20 Sep 2022 18:12:34 -0400
-Subject: [PATCH] net: phy: aquantia: Add some additional phy interfaces
-
-These are documented in the AQR115 register reference. I haven't tested
-them, but perhaps they'll be useful to someone.
-
-Signed-off-by: Sean Anderson <[email protected]>
-Reviewed-by: Andrew Lunn <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/phy/aquantia_main.c | 17 ++++++++++++++++-
- 1 file changed, 16 insertions(+), 1 deletion(-)
-
---- a/drivers/net/phy/aquantia_main.c
-+++ b/drivers/net/phy/aquantia_main.c
-@@ -27,9 +27,12 @@
- #define MDIO_PHYXS_VEND_IF_STATUS             0xe812
- #define MDIO_PHYXS_VEND_IF_STATUS_TYPE_MASK   GENMASK(7, 3)
- #define MDIO_PHYXS_VEND_IF_STATUS_TYPE_KR     0
-+#define MDIO_PHYXS_VEND_IF_STATUS_TYPE_KX     1
- #define MDIO_PHYXS_VEND_IF_STATUS_TYPE_XFI    2
- #define MDIO_PHYXS_VEND_IF_STATUS_TYPE_USXGMII        3
-+#define MDIO_PHYXS_VEND_IF_STATUS_TYPE_XAUI   4
- #define MDIO_PHYXS_VEND_IF_STATUS_TYPE_SGMII  6
-+#define MDIO_PHYXS_VEND_IF_STATUS_TYPE_RXAUI  7
- #define MDIO_PHYXS_VEND_IF_STATUS_TYPE_OCSGMII        10
- #define MDIO_AN_VEND_PROV                     0xc400
-@@ -401,15 +404,24 @@ static int aqr107_read_status(struct phy
-       case MDIO_PHYXS_VEND_IF_STATUS_TYPE_KR:
-               phydev->interface = PHY_INTERFACE_MODE_10GKR;
-               break;
-+      case MDIO_PHYXS_VEND_IF_STATUS_TYPE_KX:
-+              phydev->interface = PHY_INTERFACE_MODE_1000BASEKX;
-+              break;
-       case MDIO_PHYXS_VEND_IF_STATUS_TYPE_XFI:
-               phydev->interface = PHY_INTERFACE_MODE_10GBASER;
-               break;
-       case MDIO_PHYXS_VEND_IF_STATUS_TYPE_USXGMII:
-               phydev->interface = PHY_INTERFACE_MODE_USXGMII;
-               break;
-+      case MDIO_PHYXS_VEND_IF_STATUS_TYPE_XAUI:
-+              phydev->interface = PHY_INTERFACE_MODE_XAUI;
-+              break;
-       case MDIO_PHYXS_VEND_IF_STATUS_TYPE_SGMII:
-               phydev->interface = PHY_INTERFACE_MODE_SGMII;
-               break;
-+      case MDIO_PHYXS_VEND_IF_STATUS_TYPE_RXAUI:
-+              phydev->interface = PHY_INTERFACE_MODE_RXAUI;
-+              break;
-       case MDIO_PHYXS_VEND_IF_STATUS_TYPE_OCSGMII:
-               phydev->interface = PHY_INTERFACE_MODE_2500BASEX;
-               break;
-@@ -522,11 +534,14 @@ static int aqr107_config_init(struct phy
-       /* Check that the PHY interface type is compatible */
-       if (phydev->interface != PHY_INTERFACE_MODE_SGMII &&
-+          phydev->interface != PHY_INTERFACE_MODE_1000BASEKX &&
-           phydev->interface != PHY_INTERFACE_MODE_2500BASEX &&
-           phydev->interface != PHY_INTERFACE_MODE_XGMII &&
-           phydev->interface != PHY_INTERFACE_MODE_USXGMII &&
-           phydev->interface != PHY_INTERFACE_MODE_10GKR &&
--          phydev->interface != PHY_INTERFACE_MODE_10GBASER)
-+          phydev->interface != PHY_INTERFACE_MODE_10GBASER &&
-+          phydev->interface != PHY_INTERFACE_MODE_XAUI &&
-+          phydev->interface != PHY_INTERFACE_MODE_RXAUI)
-               return -ENODEV;
-       WARN(phydev->interface == PHY_INTERFACE_MODE_XGMII,
diff --git a/target/linux/generic/backport-5.15/736-v6.1-0002-net-phy-aquantia-Add-support-for-rate-matching.patch b/target/linux/generic/backport-5.15/736-v6.1-0002-net-phy-aquantia-Add-support-for-rate-matching.patch
deleted file mode 100644 (file)
index d5d5876..0000000
+++ /dev/null
@@ -1,148 +0,0 @@
-From 3c42563b30417afc8855a3b4c1b38c2f36f78657 Mon Sep 17 00:00:00 2001
-From: Sean Anderson <[email protected]>
-Date: Tue, 20 Sep 2022 18:12:35 -0400
-Subject: [PATCH] net: phy: aquantia: Add support for rate matching
-
-This adds support for rate matching for phys similar to the AQR107. We
-assume that all phys using aqr107_read_status support rate matching.
-However, it could be possible to determine support based on the firmware
-revision if there are phys discovered which do not support rate
-matching.  However, as rate matching is advertised in the datasheets for
-these phys, I suspect it is supported most boards.
-
-Despite the name, the "config" registers are updated with the current
-rate matching method (if any). Because they appear to be updated
-automatically, I don't know if these registers can be used to disable
-rate matching.
-
-Signed-off-by: Sean Anderson <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/phy/aquantia_main.c | 51 ++++++++++++++++++++++++++++++---
- 1 file changed, 47 insertions(+), 4 deletions(-)
-
---- a/drivers/net/phy/aquantia_main.c
-+++ b/drivers/net/phy/aquantia_main.c
-@@ -97,6 +97,19 @@
- #define VEND1_GLOBAL_GEN_STAT2                        0xc831
- #define VEND1_GLOBAL_GEN_STAT2_OP_IN_PROG     BIT(15)
-+/* The following registers all have similar layouts; first the registers... */
-+#define VEND1_GLOBAL_CFG_10M                  0x0310
-+#define VEND1_GLOBAL_CFG_100M                 0x031b
-+#define VEND1_GLOBAL_CFG_1G                   0x031c
-+#define VEND1_GLOBAL_CFG_2_5G                 0x031d
-+#define VEND1_GLOBAL_CFG_5G                   0x031e
-+#define VEND1_GLOBAL_CFG_10G                  0x031f
-+/* ...and now the fields */
-+#define VEND1_GLOBAL_CFG_RATE_ADAPT           GENMASK(8, 7)
-+#define VEND1_GLOBAL_CFG_RATE_ADAPT_NONE      0
-+#define VEND1_GLOBAL_CFG_RATE_ADAPT_USX               1
-+#define VEND1_GLOBAL_CFG_RATE_ADAPT_PAUSE     2
-+
- #define VEND1_GLOBAL_RSVD_STAT1                       0xc885
- #define VEND1_GLOBAL_RSVD_STAT1_FW_BUILD_ID   GENMASK(7, 4)
- #define VEND1_GLOBAL_RSVD_STAT1_PROV_ID               GENMASK(3, 0)
-@@ -347,40 +360,57 @@ static int aqr_read_status(struct phy_de
- static int aqr107_read_rate(struct phy_device *phydev)
- {
-+      u32 config_reg;
-       int val;
-       val = phy_read_mmd(phydev, MDIO_MMD_AN, MDIO_AN_TX_VEND_STATUS1);
-       if (val < 0)
-               return val;
-+      if (val & MDIO_AN_TX_VEND_STATUS1_FULL_DUPLEX)
-+              phydev->duplex = DUPLEX_FULL;
-+      else
-+              phydev->duplex = DUPLEX_HALF;
-+
-       switch (FIELD_GET(MDIO_AN_TX_VEND_STATUS1_RATE_MASK, val)) {
-       case MDIO_AN_TX_VEND_STATUS1_10BASET:
-               phydev->speed = SPEED_10;
-+              config_reg = VEND1_GLOBAL_CFG_10M;
-               break;
-       case MDIO_AN_TX_VEND_STATUS1_100BASETX:
-               phydev->speed = SPEED_100;
-+              config_reg = VEND1_GLOBAL_CFG_100M;
-               break;
-       case MDIO_AN_TX_VEND_STATUS1_1000BASET:
-               phydev->speed = SPEED_1000;
-+              config_reg = VEND1_GLOBAL_CFG_1G;
-               break;
-       case MDIO_AN_TX_VEND_STATUS1_2500BASET:
-               phydev->speed = SPEED_2500;
-+              config_reg = VEND1_GLOBAL_CFG_2_5G;
-               break;
-       case MDIO_AN_TX_VEND_STATUS1_5000BASET:
-               phydev->speed = SPEED_5000;
-+              config_reg = VEND1_GLOBAL_CFG_5G;
-               break;
-       case MDIO_AN_TX_VEND_STATUS1_10GBASET:
-               phydev->speed = SPEED_10000;
-+              config_reg = VEND1_GLOBAL_CFG_10G;
-               break;
-       default:
-               phydev->speed = SPEED_UNKNOWN;
--              break;
-+              return 0;
-       }
--      if (val & MDIO_AN_TX_VEND_STATUS1_FULL_DUPLEX)
--              phydev->duplex = DUPLEX_FULL;
-+      val = phy_read_mmd(phydev, MDIO_MMD_VEND1, config_reg);
-+      if (val < 0)
-+              return val;
-+
-+      if (FIELD_GET(VEND1_GLOBAL_CFG_RATE_ADAPT, val) ==
-+          VEND1_GLOBAL_CFG_RATE_ADAPT_PAUSE)
-+              phydev->rate_matching = RATE_MATCH_PAUSE;
-       else
--              phydev->duplex = DUPLEX_HALF;
-+              phydev->rate_matching = RATE_MATCH_NONE;
-       return 0;
- }
-@@ -647,6 +677,16 @@ static int aqr107_wait_processor_intensi
-       return 0;
- }
-+static int aqr107_get_rate_matching(struct phy_device *phydev,
-+                                  phy_interface_t iface)
-+{
-+      if (iface == PHY_INTERFACE_MODE_10GBASER ||
-+          iface == PHY_INTERFACE_MODE_2500BASEX ||
-+          iface == PHY_INTERFACE_MODE_NA)
-+              return RATE_MATCH_PAUSE;
-+      return RATE_MATCH_NONE;
-+}
-+
- static int aqr107_suspend(struct phy_device *phydev)
- {
-       int err;
-@@ -720,6 +760,7 @@ static struct phy_driver aqr_driver[] =
-       PHY_ID_MATCH_MODEL(PHY_ID_AQR107),
-       .name           = "Aquantia AQR107",
-       .probe          = aqr107_probe,
-+      .get_rate_matching = aqr107_get_rate_matching,
-       .config_init    = aqr107_config_init,
-       .config_aneg    = aqr_config_aneg,
-       .config_intr    = aqr_config_intr,
-@@ -738,6 +779,7 @@ static struct phy_driver aqr_driver[] =
-       PHY_ID_MATCH_MODEL(PHY_ID_AQCS109),
-       .name           = "Aquantia AQCS109",
-       .probe          = aqr107_probe,
-+      .get_rate_matching = aqr107_get_rate_matching,
-       .config_init    = aqcs109_config_init,
-       .config_aneg    = aqr_config_aneg,
-       .config_intr    = aqr_config_intr,
-@@ -764,6 +806,7 @@ static struct phy_driver aqr_driver[] =
-       PHY_ID_MATCH_MODEL(PHY_ID_AQR113C),
-       .name           = "Aquantia AQR113C",
-       .probe          = aqr107_probe,
-+      .get_rate_matching = aqr107_get_rate_matching,
-       .config_init    = aqr107_config_init,
-       .config_aneg    = aqr_config_aneg,
-       .config_intr    = aqr_config_intr,
diff --git a/target/linux/generic/backport-5.15/737-01-v6.7-net-phy-aquantia-move-to-separate-directory.patch b/target/linux/generic/backport-5.15/737-01-v6.7-net-phy-aquantia-move-to-separate-directory.patch
deleted file mode 100644 (file)
index 4bb786e..0000000
+++ /dev/null
@@ -1,2310 +0,0 @@
-From d2213db3f49bce8e7a87c8de05b9a091f78f654e Mon Sep 17 00:00:00 2001
-From: Christian Marangi <[email protected]>
-Date: Tue, 14 Nov 2023 15:08:41 +0100
-Subject: [PATCH 1/3] net: phy: aquantia: move to separate directory
-
-Move aquantia PHY driver to separate driectory in preparation for
-firmware loading support to keep things tidy.
-
-Signed-off-by: Christian Marangi <[email protected]>
-Reviewed-by: Andrew Lunn <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/phy/Kconfig                         | 5 +----
- drivers/net/phy/Makefile                        | 6 +-----
- drivers/net/phy/aquantia/Kconfig                | 5 +++++
- drivers/net/phy/aquantia/Makefile               | 6 ++++++
- drivers/net/phy/{ => aquantia}/aquantia.h       | 0
- drivers/net/phy/{ => aquantia}/aquantia_hwmon.c | 0
- drivers/net/phy/{ => aquantia}/aquantia_main.c  | 0
- 7 files changed, 13 insertions(+), 9 deletions(-)
- create mode 100644 drivers/net/phy/aquantia/Kconfig
- create mode 100644 drivers/net/phy/aquantia/Makefile
- rename drivers/net/phy/{ => aquantia}/aquantia.h (100%)
- rename drivers/net/phy/{ => aquantia}/aquantia_hwmon.c (100%)
- rename drivers/net/phy/{ => aquantia}/aquantia_main.c (100%)
-
---- a/drivers/net/phy/Kconfig
-+++ b/drivers/net/phy/Kconfig
-@@ -83,10 +83,7 @@ config ADIN_PHY
-         - ADIN1300 - Robust,Industrial, Low Latency 10/100/1000 Gigabit
-           Ethernet PHY
--config AQUANTIA_PHY
--      tristate "Aquantia PHYs"
--      help
--        Currently supports the Aquantia AQ1202, AQ2104, AQR105, AQR405
-+source "drivers/net/phy/aquantia/Kconfig"
- config AX88796B_PHY
-       tristate "Asix PHYs"
---- a/drivers/net/phy/Makefile
-+++ b/drivers/net/phy/Makefile
-@@ -32,11 +32,7 @@ obj-y                               += $(sfp-obj-y) $(sfp-obj-m)
- obj-$(CONFIG_ADIN_PHY)                += adin.o
- obj-$(CONFIG_AMD_PHY)         += amd.o
--aquantia-objs                 += aquantia_main.o
--ifdef CONFIG_HWMON
--aquantia-objs                 += aquantia_hwmon.o
--endif
--obj-$(CONFIG_AQUANTIA_PHY)    += aquantia.o
-+obj-$(CONFIG_AQUANTIA_PHY)    += aquantia/
- obj-$(CONFIG_AT803X_PHY)      += at803x.o
- obj-$(CONFIG_AX88796B_PHY)    += ax88796b.o
- obj-$(CONFIG_BCM54140_PHY)    += bcm54140.o
---- /dev/null
-+++ b/drivers/net/phy/aquantia/Kconfig
-@@ -0,0 +1,5 @@
-+# SPDX-License-Identifier: GPL-2.0-only
-+config AQUANTIA_PHY
-+      tristate "Aquantia PHYs"
-+      help
-+        Currently supports the Aquantia AQ1202, AQ2104, AQR105, AQR405
---- /dev/null
-+++ b/drivers/net/phy/aquantia/Makefile
-@@ -0,0 +1,6 @@
-+# SPDX-License-Identifier: GPL-2.0
-+aquantia-objs                 += aquantia_main.o
-+ifdef CONFIG_HWMON
-+aquantia-objs                 += aquantia_hwmon.o
-+endif
-+obj-$(CONFIG_AQUANTIA_PHY)    += aquantia.o
---- a/drivers/net/phy/aquantia.h
-+++ /dev/null
-@@ -1,16 +0,0 @@
--/* SPDX-License-Identifier: GPL-2.0 */
--/* HWMON driver for Aquantia PHY
-- *
-- * Author: Nikita Yushchenko <[email protected]>
-- * Author: Andrew Lunn <[email protected]>
-- * Author: Heiner Kallweit <[email protected]>
-- */
--
--#include <linux/device.h>
--#include <linux/phy.h>
--
--#if IS_REACHABLE(CONFIG_HWMON)
--int aqr_hwmon_probe(struct phy_device *phydev);
--#else
--static inline int aqr_hwmon_probe(struct phy_device *phydev) { return 0; }
--#endif
---- /dev/null
-+++ b/drivers/net/phy/aquantia/aquantia.h
-@@ -0,0 +1,16 @@
-+/* SPDX-License-Identifier: GPL-2.0 */
-+/* HWMON driver for Aquantia PHY
-+ *
-+ * Author: Nikita Yushchenko <[email protected]>
-+ * Author: Andrew Lunn <[email protected]>
-+ * Author: Heiner Kallweit <[email protected]>
-+ */
-+
-+#include <linux/device.h>
-+#include <linux/phy.h>
-+
-+#if IS_REACHABLE(CONFIG_HWMON)
-+int aqr_hwmon_probe(struct phy_device *phydev);
-+#else
-+static inline int aqr_hwmon_probe(struct phy_device *phydev) { return 0; }
-+#endif
---- /dev/null
-+++ b/drivers/net/phy/aquantia/aquantia_hwmon.c
-@@ -0,0 +1,250 @@
-+// SPDX-License-Identifier: GPL-2.0
-+/* HWMON driver for Aquantia PHY
-+ *
-+ * Author: Nikita Yushchenko <[email protected]>
-+ * Author: Andrew Lunn <[email protected]>
-+ * Author: Heiner Kallweit <[email protected]>
-+ */
-+
-+#include <linux/phy.h>
-+#include <linux/device.h>
-+#include <linux/ctype.h>
-+#include <linux/hwmon.h>
-+
-+#include "aquantia.h"
-+
-+/* Vendor specific 1, MDIO_MMD_VEND2 */
-+#define VEND1_THERMAL_PROV_HIGH_TEMP_FAIL     0xc421
-+#define VEND1_THERMAL_PROV_LOW_TEMP_FAIL      0xc422
-+#define VEND1_THERMAL_PROV_HIGH_TEMP_WARN     0xc423
-+#define VEND1_THERMAL_PROV_LOW_TEMP_WARN      0xc424
-+#define VEND1_THERMAL_STAT1                   0xc820
-+#define VEND1_THERMAL_STAT2                   0xc821
-+#define VEND1_THERMAL_STAT2_VALID             BIT(0)
-+#define VEND1_GENERAL_STAT1                   0xc830
-+#define VEND1_GENERAL_STAT1_HIGH_TEMP_FAIL    BIT(14)
-+#define VEND1_GENERAL_STAT1_LOW_TEMP_FAIL     BIT(13)
-+#define VEND1_GENERAL_STAT1_HIGH_TEMP_WARN    BIT(12)
-+#define VEND1_GENERAL_STAT1_LOW_TEMP_WARN     BIT(11)
-+
-+#if IS_REACHABLE(CONFIG_HWMON)
-+
-+static umode_t aqr_hwmon_is_visible(const void *data,
-+                                  enum hwmon_sensor_types type,
-+                                  u32 attr, int channel)
-+{
-+      if (type != hwmon_temp)
-+              return 0;
-+
-+      switch (attr) {
-+      case hwmon_temp_input:
-+      case hwmon_temp_min_alarm:
-+      case hwmon_temp_max_alarm:
-+      case hwmon_temp_lcrit_alarm:
-+      case hwmon_temp_crit_alarm:
-+              return 0444;
-+      case hwmon_temp_min:
-+      case hwmon_temp_max:
-+      case hwmon_temp_lcrit:
-+      case hwmon_temp_crit:
-+              return 0644;
-+      default:
-+              return 0;
-+      }
-+}
-+
-+static int aqr_hwmon_get(struct phy_device *phydev, int reg, long *value)
-+{
-+      int temp = phy_read_mmd(phydev, MDIO_MMD_VEND1, reg);
-+
-+      if (temp < 0)
-+              return temp;
-+
-+      /* 16 bit value is 2's complement with LSB = 1/256th degree Celsius */
-+      *value = (s16)temp * 1000 / 256;
-+
-+      return 0;
-+}
-+
-+static int aqr_hwmon_set(struct phy_device *phydev, int reg, long value)
-+{
-+      int temp;
-+
-+      if (value >= 128000 || value < -128000)
-+              return -ERANGE;
-+
-+      temp = value * 256 / 1000;
-+
-+      /* temp is in s16 range and we're interested in lower 16 bits only */
-+      return phy_write_mmd(phydev, MDIO_MMD_VEND1, reg, (u16)temp);
-+}
-+
-+static int aqr_hwmon_test_bit(struct phy_device *phydev, int reg, int bit)
-+{
-+      int val = phy_read_mmd(phydev, MDIO_MMD_VEND1, reg);
-+
-+      if (val < 0)
-+              return val;
-+
-+      return !!(val & bit);
-+}
-+
-+static int aqr_hwmon_status1(struct phy_device *phydev, int bit, long *value)
-+{
-+      int val = aqr_hwmon_test_bit(phydev, VEND1_GENERAL_STAT1, bit);
-+
-+      if (val < 0)
-+              return val;
-+
-+      *value = val;
-+
-+      return 0;
-+}
-+
-+static int aqr_hwmon_read(struct device *dev, enum hwmon_sensor_types type,
-+                        u32 attr, int channel, long *value)
-+{
-+      struct phy_device *phydev = dev_get_drvdata(dev);
-+      int reg;
-+
-+      if (type != hwmon_temp)
-+              return -EOPNOTSUPP;
-+
-+      switch (attr) {
-+      case hwmon_temp_input:
-+              reg = aqr_hwmon_test_bit(phydev, VEND1_THERMAL_STAT2,
-+                                       VEND1_THERMAL_STAT2_VALID);
-+              if (reg < 0)
-+                      return reg;
-+              if (!reg)
-+                      return -EBUSY;
-+
-+              return aqr_hwmon_get(phydev, VEND1_THERMAL_STAT1, value);
-+
-+      case hwmon_temp_lcrit:
-+              return aqr_hwmon_get(phydev, VEND1_THERMAL_PROV_LOW_TEMP_FAIL,
-+                                   value);
-+      case hwmon_temp_min:
-+              return aqr_hwmon_get(phydev, VEND1_THERMAL_PROV_LOW_TEMP_WARN,
-+                                   value);
-+      case hwmon_temp_max:
-+              return aqr_hwmon_get(phydev, VEND1_THERMAL_PROV_HIGH_TEMP_WARN,
-+                                   value);
-+      case hwmon_temp_crit:
-+              return aqr_hwmon_get(phydev, VEND1_THERMAL_PROV_HIGH_TEMP_FAIL,
-+                                   value);
-+      case hwmon_temp_lcrit_alarm:
-+              return aqr_hwmon_status1(phydev,
-+                                       VEND1_GENERAL_STAT1_LOW_TEMP_FAIL,
-+                                       value);
-+      case hwmon_temp_min_alarm:
-+              return aqr_hwmon_status1(phydev,
-+                                       VEND1_GENERAL_STAT1_LOW_TEMP_WARN,
-+                                       value);
-+      case hwmon_temp_max_alarm:
-+              return aqr_hwmon_status1(phydev,
-+                                       VEND1_GENERAL_STAT1_HIGH_TEMP_WARN,
-+                                       value);
-+      case hwmon_temp_crit_alarm:
-+              return aqr_hwmon_status1(phydev,
-+                                       VEND1_GENERAL_STAT1_HIGH_TEMP_FAIL,
-+                                       value);
-+      default:
-+              return -EOPNOTSUPP;
-+      }
-+}
-+
-+static int aqr_hwmon_write(struct device *dev, enum hwmon_sensor_types type,
-+                         u32 attr, int channel, long value)
-+{
-+      struct phy_device *phydev = dev_get_drvdata(dev);
-+
-+      if (type != hwmon_temp)
-+              return -EOPNOTSUPP;
-+
-+      switch (attr) {
-+      case hwmon_temp_lcrit:
-+              return aqr_hwmon_set(phydev, VEND1_THERMAL_PROV_LOW_TEMP_FAIL,
-+                                   value);
-+      case hwmon_temp_min:
-+              return aqr_hwmon_set(phydev, VEND1_THERMAL_PROV_LOW_TEMP_WARN,
-+                                   value);
-+      case hwmon_temp_max:
-+              return aqr_hwmon_set(phydev, VEND1_THERMAL_PROV_HIGH_TEMP_WARN,
-+                                   value);
-+      case hwmon_temp_crit:
-+              return aqr_hwmon_set(phydev, VEND1_THERMAL_PROV_HIGH_TEMP_FAIL,
-+                                   value);
-+      default:
-+              return -EOPNOTSUPP;
-+      }
-+}
-+
-+static const struct hwmon_ops aqr_hwmon_ops = {
-+      .is_visible = aqr_hwmon_is_visible,
-+      .read = aqr_hwmon_read,
-+      .write = aqr_hwmon_write,
-+};
-+
-+static u32 aqr_hwmon_chip_config[] = {
-+      HWMON_C_REGISTER_TZ,
-+      0,
-+};
-+
-+static const struct hwmon_channel_info aqr_hwmon_chip = {
-+      .type = hwmon_chip,
-+      .config = aqr_hwmon_chip_config,
-+};
-+
-+static u32 aqr_hwmon_temp_config[] = {
-+      HWMON_T_INPUT |
-+      HWMON_T_MAX | HWMON_T_MIN |
-+      HWMON_T_MAX_ALARM | HWMON_T_MIN_ALARM |
-+      HWMON_T_CRIT | HWMON_T_LCRIT |
-+      HWMON_T_CRIT_ALARM | HWMON_T_LCRIT_ALARM,
-+      0,
-+};
-+
-+static const struct hwmon_channel_info aqr_hwmon_temp = {
-+      .type = hwmon_temp,
-+      .config = aqr_hwmon_temp_config,
-+};
-+
-+static const struct hwmon_channel_info *aqr_hwmon_info[] = {
-+      &aqr_hwmon_chip,
-+      &aqr_hwmon_temp,
-+      NULL,
-+};
-+
-+static const struct hwmon_chip_info aqr_hwmon_chip_info = {
-+      .ops = &aqr_hwmon_ops,
-+      .info = aqr_hwmon_info,
-+};
-+
-+int aqr_hwmon_probe(struct phy_device *phydev)
-+{
-+      struct device *dev = &phydev->mdio.dev;
-+      struct device *hwmon_dev;
-+      char *hwmon_name;
-+      int i, j;
-+
-+      hwmon_name = devm_kstrdup(dev, dev_name(dev), GFP_KERNEL);
-+      if (!hwmon_name)
-+              return -ENOMEM;
-+
-+      for (i = j = 0; hwmon_name[i]; i++) {
-+              if (isalnum(hwmon_name[i])) {
-+                      if (i != j)
-+                              hwmon_name[j] = hwmon_name[i];
-+                      j++;
-+              }
-+      }
-+      hwmon_name[j] = '\0';
-+
-+      hwmon_dev = devm_hwmon_device_register_with_info(dev, hwmon_name,
-+                                      phydev, &aqr_hwmon_chip_info, NULL);
-+
-+      return PTR_ERR_OR_ZERO(hwmon_dev);
-+}
-+
-+#endif
---- /dev/null
-+++ b/drivers/net/phy/aquantia/aquantia_main.c
-@@ -0,0 +1,844 @@
-+// SPDX-License-Identifier: GPL-2.0
-+/*
-+ * Driver for Aquantia PHY
-+ *
-+ * Author: Shaohui Xie <[email protected]>
-+ *
-+ * Copyright 2015 Freescale Semiconductor, Inc.
-+ */
-+
-+#include <linux/kernel.h>
-+#include <linux/module.h>
-+#include <linux/delay.h>
-+#include <linux/bitfield.h>
-+#include <linux/phy.h>
-+
-+#include "aquantia.h"
-+
-+#define PHY_ID_AQ1202 0x03a1b445
-+#define PHY_ID_AQ2104 0x03a1b460
-+#define PHY_ID_AQR105 0x03a1b4a2
-+#define PHY_ID_AQR106 0x03a1b4d0
-+#define PHY_ID_AQR107 0x03a1b4e0
-+#define PHY_ID_AQCS109        0x03a1b5c2
-+#define PHY_ID_AQR405 0x03a1b4b0
-+#define PHY_ID_AQR113C        0x31c31c12
-+
-+#define MDIO_PHYXS_VEND_IF_STATUS             0xe812
-+#define MDIO_PHYXS_VEND_IF_STATUS_TYPE_MASK   GENMASK(7, 3)
-+#define MDIO_PHYXS_VEND_IF_STATUS_TYPE_KR     0
-+#define MDIO_PHYXS_VEND_IF_STATUS_TYPE_KX     1
-+#define MDIO_PHYXS_VEND_IF_STATUS_TYPE_XFI    2
-+#define MDIO_PHYXS_VEND_IF_STATUS_TYPE_USXGMII        3
-+#define MDIO_PHYXS_VEND_IF_STATUS_TYPE_XAUI   4
-+#define MDIO_PHYXS_VEND_IF_STATUS_TYPE_SGMII  6
-+#define MDIO_PHYXS_VEND_IF_STATUS_TYPE_RXAUI  7
-+#define MDIO_PHYXS_VEND_IF_STATUS_TYPE_OCSGMII        10
-+
-+#define MDIO_AN_VEND_PROV                     0xc400
-+#define MDIO_AN_VEND_PROV_1000BASET_FULL      BIT(15)
-+#define MDIO_AN_VEND_PROV_1000BASET_HALF      BIT(14)
-+#define MDIO_AN_VEND_PROV_5000BASET_FULL      BIT(11)
-+#define MDIO_AN_VEND_PROV_2500BASET_FULL      BIT(10)
-+#define MDIO_AN_VEND_PROV_DOWNSHIFT_EN                BIT(4)
-+#define MDIO_AN_VEND_PROV_DOWNSHIFT_MASK      GENMASK(3, 0)
-+#define MDIO_AN_VEND_PROV_DOWNSHIFT_DFLT      4
-+
-+#define MDIO_AN_TX_VEND_STATUS1                       0xc800
-+#define MDIO_AN_TX_VEND_STATUS1_RATE_MASK     GENMASK(3, 1)
-+#define MDIO_AN_TX_VEND_STATUS1_10BASET               0
-+#define MDIO_AN_TX_VEND_STATUS1_100BASETX     1
-+#define MDIO_AN_TX_VEND_STATUS1_1000BASET     2
-+#define MDIO_AN_TX_VEND_STATUS1_10GBASET      3
-+#define MDIO_AN_TX_VEND_STATUS1_2500BASET     4
-+#define MDIO_AN_TX_VEND_STATUS1_5000BASET     5
-+#define MDIO_AN_TX_VEND_STATUS1_FULL_DUPLEX   BIT(0)
-+
-+#define MDIO_AN_TX_VEND_INT_STATUS1           0xcc00
-+#define MDIO_AN_TX_VEND_INT_STATUS1_DOWNSHIFT BIT(1)
-+
-+#define MDIO_AN_TX_VEND_INT_STATUS2           0xcc01
-+#define MDIO_AN_TX_VEND_INT_STATUS2_MASK      BIT(0)
-+
-+#define MDIO_AN_TX_VEND_INT_MASK2             0xd401
-+#define MDIO_AN_TX_VEND_INT_MASK2_LINK                BIT(0)
-+
-+#define MDIO_AN_RX_LP_STAT1                   0xe820
-+#define MDIO_AN_RX_LP_STAT1_1000BASET_FULL    BIT(15)
-+#define MDIO_AN_RX_LP_STAT1_1000BASET_HALF    BIT(14)
-+#define MDIO_AN_RX_LP_STAT1_SHORT_REACH               BIT(13)
-+#define MDIO_AN_RX_LP_STAT1_AQRATE_DOWNSHIFT  BIT(12)
-+#define MDIO_AN_RX_LP_STAT1_AQ_PHY            BIT(2)
-+
-+#define MDIO_AN_RX_LP_STAT4                   0xe823
-+#define MDIO_AN_RX_LP_STAT4_FW_MAJOR          GENMASK(15, 8)
-+#define MDIO_AN_RX_LP_STAT4_FW_MINOR          GENMASK(7, 0)
-+
-+#define MDIO_AN_RX_VEND_STAT3                 0xe832
-+#define MDIO_AN_RX_VEND_STAT3_AFR             BIT(0)
-+
-+/* MDIO_MMD_C22EXT */
-+#define MDIO_C22EXT_STAT_SGMII_RX_GOOD_FRAMES         0xd292
-+#define MDIO_C22EXT_STAT_SGMII_RX_BAD_FRAMES          0xd294
-+#define MDIO_C22EXT_STAT_SGMII_RX_FALSE_CARRIER               0xd297
-+#define MDIO_C22EXT_STAT_SGMII_TX_GOOD_FRAMES         0xd313
-+#define MDIO_C22EXT_STAT_SGMII_TX_BAD_FRAMES          0xd315
-+#define MDIO_C22EXT_STAT_SGMII_TX_FALSE_CARRIER               0xd317
-+#define MDIO_C22EXT_STAT_SGMII_TX_COLLISIONS          0xd318
-+#define MDIO_C22EXT_STAT_SGMII_TX_LINE_COLLISIONS     0xd319
-+#define MDIO_C22EXT_STAT_SGMII_TX_FRAME_ALIGN_ERR     0xd31a
-+#define MDIO_C22EXT_STAT_SGMII_TX_RUNT_FRAMES         0xd31b
-+
-+/* Vendor specific 1, MDIO_MMD_VEND1 */
-+#define VEND1_GLOBAL_FW_ID                    0x0020
-+#define VEND1_GLOBAL_FW_ID_MAJOR              GENMASK(15, 8)
-+#define VEND1_GLOBAL_FW_ID_MINOR              GENMASK(7, 0)
-+
-+#define VEND1_GLOBAL_GEN_STAT2                        0xc831
-+#define VEND1_GLOBAL_GEN_STAT2_OP_IN_PROG     BIT(15)
-+
-+/* The following registers all have similar layouts; first the registers... */
-+#define VEND1_GLOBAL_CFG_10M                  0x0310
-+#define VEND1_GLOBAL_CFG_100M                 0x031b
-+#define VEND1_GLOBAL_CFG_1G                   0x031c
-+#define VEND1_GLOBAL_CFG_2_5G                 0x031d
-+#define VEND1_GLOBAL_CFG_5G                   0x031e
-+#define VEND1_GLOBAL_CFG_10G                  0x031f
-+/* ...and now the fields */
-+#define VEND1_GLOBAL_CFG_RATE_ADAPT           GENMASK(8, 7)
-+#define VEND1_GLOBAL_CFG_RATE_ADAPT_NONE      0
-+#define VEND1_GLOBAL_CFG_RATE_ADAPT_USX               1
-+#define VEND1_GLOBAL_CFG_RATE_ADAPT_PAUSE     2
-+
-+#define VEND1_GLOBAL_RSVD_STAT1                       0xc885
-+#define VEND1_GLOBAL_RSVD_STAT1_FW_BUILD_ID   GENMASK(7, 4)
-+#define VEND1_GLOBAL_RSVD_STAT1_PROV_ID               GENMASK(3, 0)
-+
-+#define VEND1_GLOBAL_RSVD_STAT9                       0xc88d
-+#define VEND1_GLOBAL_RSVD_STAT9_MODE          GENMASK(7, 0)
-+#define VEND1_GLOBAL_RSVD_STAT9_1000BT2               0x23
-+
-+#define VEND1_GLOBAL_INT_STD_STATUS           0xfc00
-+#define VEND1_GLOBAL_INT_VEND_STATUS          0xfc01
-+
-+#define VEND1_GLOBAL_INT_STD_MASK             0xff00
-+#define VEND1_GLOBAL_INT_STD_MASK_PMA1                BIT(15)
-+#define VEND1_GLOBAL_INT_STD_MASK_PMA2                BIT(14)
-+#define VEND1_GLOBAL_INT_STD_MASK_PCS1                BIT(13)
-+#define VEND1_GLOBAL_INT_STD_MASK_PCS2                BIT(12)
-+#define VEND1_GLOBAL_INT_STD_MASK_PCS3                BIT(11)
-+#define VEND1_GLOBAL_INT_STD_MASK_PHY_XS1     BIT(10)
-+#define VEND1_GLOBAL_INT_STD_MASK_PHY_XS2     BIT(9)
-+#define VEND1_GLOBAL_INT_STD_MASK_AN1         BIT(8)
-+#define VEND1_GLOBAL_INT_STD_MASK_AN2         BIT(7)
-+#define VEND1_GLOBAL_INT_STD_MASK_GBE         BIT(6)
-+#define VEND1_GLOBAL_INT_STD_MASK_ALL         BIT(0)
-+
-+#define VEND1_GLOBAL_INT_VEND_MASK            0xff01
-+#define VEND1_GLOBAL_INT_VEND_MASK_PMA                BIT(15)
-+#define VEND1_GLOBAL_INT_VEND_MASK_PCS                BIT(14)
-+#define VEND1_GLOBAL_INT_VEND_MASK_PHY_XS     BIT(13)
-+#define VEND1_GLOBAL_INT_VEND_MASK_AN         BIT(12)
-+#define VEND1_GLOBAL_INT_VEND_MASK_GBE                BIT(11)
-+#define VEND1_GLOBAL_INT_VEND_MASK_GLOBAL1    BIT(2)
-+#define VEND1_GLOBAL_INT_VEND_MASK_GLOBAL2    BIT(1)
-+#define VEND1_GLOBAL_INT_VEND_MASK_GLOBAL3    BIT(0)
-+
-+/* Sleep and timeout for checking if the Processor-Intensive
-+ * MDIO operation is finished
-+ */
-+#define AQR107_OP_IN_PROG_SLEEP               1000
-+#define AQR107_OP_IN_PROG_TIMEOUT     100000
-+
-+struct aqr107_hw_stat {
-+      const char *name;
-+      int reg;
-+      int size;
-+};
-+
-+#define SGMII_STAT(n, r, s) { n, MDIO_C22EXT_STAT_SGMII_ ## r, s }
-+static const struct aqr107_hw_stat aqr107_hw_stats[] = {
-+      SGMII_STAT("sgmii_rx_good_frames",          RX_GOOD_FRAMES,     26),
-+      SGMII_STAT("sgmii_rx_bad_frames",           RX_BAD_FRAMES,      26),
-+      SGMII_STAT("sgmii_rx_false_carrier_events", RX_FALSE_CARRIER,    8),
-+      SGMII_STAT("sgmii_tx_good_frames",          TX_GOOD_FRAMES,     26),
-+      SGMII_STAT("sgmii_tx_bad_frames",           TX_BAD_FRAMES,      26),
-+      SGMII_STAT("sgmii_tx_false_carrier_events", TX_FALSE_CARRIER,    8),
-+      SGMII_STAT("sgmii_tx_collisions",           TX_COLLISIONS,       8),
-+      SGMII_STAT("sgmii_tx_line_collisions",      TX_LINE_COLLISIONS,  8),
-+      SGMII_STAT("sgmii_tx_frame_alignment_err",  TX_FRAME_ALIGN_ERR, 16),
-+      SGMII_STAT("sgmii_tx_runt_frames",          TX_RUNT_FRAMES,     22),
-+};
-+#define AQR107_SGMII_STAT_SZ ARRAY_SIZE(aqr107_hw_stats)
-+
-+struct aqr107_priv {
-+      u64 sgmii_stats[AQR107_SGMII_STAT_SZ];
-+};
-+
-+static int aqr107_get_sset_count(struct phy_device *phydev)
-+{
-+      return AQR107_SGMII_STAT_SZ;
-+}
-+
-+static void aqr107_get_strings(struct phy_device *phydev, u8 *data)
-+{
-+      int i;
-+
-+      for (i = 0; i < AQR107_SGMII_STAT_SZ; i++)
-+              strscpy(data + i * ETH_GSTRING_LEN, aqr107_hw_stats[i].name,
-+                      ETH_GSTRING_LEN);
-+}
-+
-+static u64 aqr107_get_stat(struct phy_device *phydev, int index)
-+{
-+      const struct aqr107_hw_stat *stat = aqr107_hw_stats + index;
-+      int len_l = min(stat->size, 16);
-+      int len_h = stat->size - len_l;
-+      u64 ret;
-+      int val;
-+
-+      val = phy_read_mmd(phydev, MDIO_MMD_C22EXT, stat->reg);
-+      if (val < 0)
-+              return U64_MAX;
-+
-+      ret = val & GENMASK(len_l - 1, 0);
-+      if (len_h) {
-+              val = phy_read_mmd(phydev, MDIO_MMD_C22EXT, stat->reg + 1);
-+              if (val < 0)
-+                      return U64_MAX;
-+
-+              ret += (val & GENMASK(len_h - 1, 0)) << 16;
-+      }
-+
-+      return ret;
-+}
-+
-+static void aqr107_get_stats(struct phy_device *phydev,
-+                           struct ethtool_stats *stats, u64 *data)
-+{
-+      struct aqr107_priv *priv = phydev->priv;
-+      u64 val;
-+      int i;
-+
-+      for (i = 0; i < AQR107_SGMII_STAT_SZ; i++) {
-+              val = aqr107_get_stat(phydev, i);
-+              if (val == U64_MAX)
-+                      phydev_err(phydev, "Reading HW Statistics failed for %s\n",
-+                                 aqr107_hw_stats[i].name);
-+              else
-+                      priv->sgmii_stats[i] += val;
-+
-+              data[i] = priv->sgmii_stats[i];
-+      }
-+}
-+
-+static int aqr_config_aneg(struct phy_device *phydev)
-+{
-+      bool changed = false;
-+      u16 reg;
-+      int ret;
-+
-+      if (phydev->autoneg == AUTONEG_DISABLE)
-+              return genphy_c45_pma_setup_forced(phydev);
-+
-+      ret = genphy_c45_an_config_aneg(phydev);
-+      if (ret < 0)
-+              return ret;
-+      if (ret > 0)
-+              changed = true;
-+
-+      /* Clause 45 has no standardized support for 1000BaseT, therefore
-+       * use vendor registers for this mode.
-+       */
-+      reg = 0;
-+      if (linkmode_test_bit(ETHTOOL_LINK_MODE_1000baseT_Full_BIT,
-+                            phydev->advertising))
-+              reg |= MDIO_AN_VEND_PROV_1000BASET_FULL;
-+
-+      if (linkmode_test_bit(ETHTOOL_LINK_MODE_1000baseT_Half_BIT,
-+                            phydev->advertising))
-+              reg |= MDIO_AN_VEND_PROV_1000BASET_HALF;
-+
-+      /* Handle the case when the 2.5G and 5G speeds are not advertised */
-+      if (linkmode_test_bit(ETHTOOL_LINK_MODE_2500baseT_Full_BIT,
-+                            phydev->advertising))
-+              reg |= MDIO_AN_VEND_PROV_2500BASET_FULL;
-+
-+      if (linkmode_test_bit(ETHTOOL_LINK_MODE_5000baseT_Full_BIT,
-+                            phydev->advertising))
-+              reg |= MDIO_AN_VEND_PROV_5000BASET_FULL;
-+
-+      ret = phy_modify_mmd_changed(phydev, MDIO_MMD_AN, MDIO_AN_VEND_PROV,
-+                                   MDIO_AN_VEND_PROV_1000BASET_HALF |
-+                                   MDIO_AN_VEND_PROV_1000BASET_FULL |
-+                                   MDIO_AN_VEND_PROV_2500BASET_FULL |
-+                                   MDIO_AN_VEND_PROV_5000BASET_FULL, reg);
-+      if (ret < 0)
-+              return ret;
-+      if (ret > 0)
-+              changed = true;
-+
-+      return genphy_c45_check_and_restart_aneg(phydev, changed);
-+}
-+
-+static int aqr_config_intr(struct phy_device *phydev)
-+{
-+      bool en = phydev->interrupts == PHY_INTERRUPT_ENABLED;
-+      int err;
-+
-+      if (en) {
-+              /* Clear any pending interrupts before enabling them */
-+              err = phy_read_mmd(phydev, MDIO_MMD_AN, MDIO_AN_TX_VEND_INT_STATUS2);
-+              if (err < 0)
-+                      return err;
-+      }
-+
-+      err = phy_write_mmd(phydev, MDIO_MMD_AN, MDIO_AN_TX_VEND_INT_MASK2,
-+                          en ? MDIO_AN_TX_VEND_INT_MASK2_LINK : 0);
-+      if (err < 0)
-+              return err;
-+
-+      err = phy_write_mmd(phydev, MDIO_MMD_VEND1, VEND1_GLOBAL_INT_STD_MASK,
-+                          en ? VEND1_GLOBAL_INT_STD_MASK_ALL : 0);
-+      if (err < 0)
-+              return err;
-+
-+      err = phy_write_mmd(phydev, MDIO_MMD_VEND1, VEND1_GLOBAL_INT_VEND_MASK,
-+                          en ? VEND1_GLOBAL_INT_VEND_MASK_GLOBAL3 |
-+                          VEND1_GLOBAL_INT_VEND_MASK_AN : 0);
-+      if (err < 0)
-+              return err;
-+
-+      if (!en) {
-+              /* Clear any pending interrupts after we have disabled them */
-+              err = phy_read_mmd(phydev, MDIO_MMD_AN, MDIO_AN_TX_VEND_INT_STATUS2);
-+              if (err < 0)
-+                      return err;
-+      }
-+
-+      return 0;
-+}
-+
-+static irqreturn_t aqr_handle_interrupt(struct phy_device *phydev)
-+{
-+      int irq_status;
-+
-+      irq_status = phy_read_mmd(phydev, MDIO_MMD_AN,
-+                                MDIO_AN_TX_VEND_INT_STATUS2);
-+      if (irq_status < 0) {
-+              phy_error(phydev);
-+              return IRQ_NONE;
-+      }
-+
-+      if (!(irq_status & MDIO_AN_TX_VEND_INT_STATUS2_MASK))
-+              return IRQ_NONE;
-+
-+      phy_trigger_machine(phydev);
-+
-+      return IRQ_HANDLED;
-+}
-+
-+static int aqr_read_status(struct phy_device *phydev)
-+{
-+      int val;
-+
-+      if (phydev->autoneg == AUTONEG_ENABLE) {
-+              val = phy_read_mmd(phydev, MDIO_MMD_AN, MDIO_AN_RX_LP_STAT1);
-+              if (val < 0)
-+                      return val;
-+
-+              linkmode_mod_bit(ETHTOOL_LINK_MODE_1000baseT_Full_BIT,
-+                               phydev->lp_advertising,
-+                               val & MDIO_AN_RX_LP_STAT1_1000BASET_FULL);
-+              linkmode_mod_bit(ETHTOOL_LINK_MODE_1000baseT_Half_BIT,
-+                               phydev->lp_advertising,
-+                               val & MDIO_AN_RX_LP_STAT1_1000BASET_HALF);
-+      }
-+
-+      return genphy_c45_read_status(phydev);
-+}
-+
-+static int aqr107_read_rate(struct phy_device *phydev)
-+{
-+      u32 config_reg;
-+      int val;
-+
-+      val = phy_read_mmd(phydev, MDIO_MMD_AN, MDIO_AN_TX_VEND_STATUS1);
-+      if (val < 0)
-+              return val;
-+
-+      if (val & MDIO_AN_TX_VEND_STATUS1_FULL_DUPLEX)
-+              phydev->duplex = DUPLEX_FULL;
-+      else
-+              phydev->duplex = DUPLEX_HALF;
-+
-+      switch (FIELD_GET(MDIO_AN_TX_VEND_STATUS1_RATE_MASK, val)) {
-+      case MDIO_AN_TX_VEND_STATUS1_10BASET:
-+              phydev->speed = SPEED_10;
-+              config_reg = VEND1_GLOBAL_CFG_10M;
-+              break;
-+      case MDIO_AN_TX_VEND_STATUS1_100BASETX:
-+              phydev->speed = SPEED_100;
-+              config_reg = VEND1_GLOBAL_CFG_100M;
-+              break;
-+      case MDIO_AN_TX_VEND_STATUS1_1000BASET:
-+              phydev->speed = SPEED_1000;
-+              config_reg = VEND1_GLOBAL_CFG_1G;
-+              break;
-+      case MDIO_AN_TX_VEND_STATUS1_2500BASET:
-+              phydev->speed = SPEED_2500;
-+              config_reg = VEND1_GLOBAL_CFG_2_5G;
-+              break;
-+      case MDIO_AN_TX_VEND_STATUS1_5000BASET:
-+              phydev->speed = SPEED_5000;
-+              config_reg = VEND1_GLOBAL_CFG_5G;
-+              break;
-+      case MDIO_AN_TX_VEND_STATUS1_10GBASET:
-+              phydev->speed = SPEED_10000;
-+              config_reg = VEND1_GLOBAL_CFG_10G;
-+              break;
-+      default:
-+              phydev->speed = SPEED_UNKNOWN;
-+              return 0;
-+      }
-+
-+      val = phy_read_mmd(phydev, MDIO_MMD_VEND1, config_reg);
-+      if (val < 0)
-+              return val;
-+
-+      if (FIELD_GET(VEND1_GLOBAL_CFG_RATE_ADAPT, val) ==
-+          VEND1_GLOBAL_CFG_RATE_ADAPT_PAUSE)
-+              phydev->rate_matching = RATE_MATCH_PAUSE;
-+      else
-+              phydev->rate_matching = RATE_MATCH_NONE;
-+
-+      return 0;
-+}
-+
-+static int aqr107_read_status(struct phy_device *phydev)
-+{
-+      int val, ret;
-+
-+      ret = aqr_read_status(phydev);
-+      if (ret)
-+              return ret;
-+
-+      if (!phydev->link || phydev->autoneg == AUTONEG_DISABLE)
-+              return 0;
-+
-+      val = phy_read_mmd(phydev, MDIO_MMD_PHYXS, MDIO_PHYXS_VEND_IF_STATUS);
-+      if (val < 0)
-+              return val;
-+
-+      switch (FIELD_GET(MDIO_PHYXS_VEND_IF_STATUS_TYPE_MASK, val)) {
-+      case MDIO_PHYXS_VEND_IF_STATUS_TYPE_KR:
-+              phydev->interface = PHY_INTERFACE_MODE_10GKR;
-+              break;
-+      case MDIO_PHYXS_VEND_IF_STATUS_TYPE_KX:
-+              phydev->interface = PHY_INTERFACE_MODE_1000BASEKX;
-+              break;
-+      case MDIO_PHYXS_VEND_IF_STATUS_TYPE_XFI:
-+              phydev->interface = PHY_INTERFACE_MODE_10GBASER;
-+              break;
-+      case MDIO_PHYXS_VEND_IF_STATUS_TYPE_USXGMII:
-+              phydev->interface = PHY_INTERFACE_MODE_USXGMII;
-+              break;
-+      case MDIO_PHYXS_VEND_IF_STATUS_TYPE_XAUI:
-+              phydev->interface = PHY_INTERFACE_MODE_XAUI;
-+              break;
-+      case MDIO_PHYXS_VEND_IF_STATUS_TYPE_SGMII:
-+              phydev->interface = PHY_INTERFACE_MODE_SGMII;
-+              break;
-+      case MDIO_PHYXS_VEND_IF_STATUS_TYPE_RXAUI:
-+              phydev->interface = PHY_INTERFACE_MODE_RXAUI;
-+              break;
-+      case MDIO_PHYXS_VEND_IF_STATUS_TYPE_OCSGMII:
-+              phydev->interface = PHY_INTERFACE_MODE_2500BASEX;
-+              break;
-+      default:
-+              phydev->interface = PHY_INTERFACE_MODE_NA;
-+              break;
-+      }
-+
-+      /* Read possibly downshifted rate from vendor register */
-+      return aqr107_read_rate(phydev);
-+}
-+
-+static int aqr107_get_downshift(struct phy_device *phydev, u8 *data)
-+{
-+      int val, cnt, enable;
-+
-+      val = phy_read_mmd(phydev, MDIO_MMD_AN, MDIO_AN_VEND_PROV);
-+      if (val < 0)
-+              return val;
-+
-+      enable = FIELD_GET(MDIO_AN_VEND_PROV_DOWNSHIFT_EN, val);
-+      cnt = FIELD_GET(MDIO_AN_VEND_PROV_DOWNSHIFT_MASK, val);
-+
-+      *data = enable && cnt ? cnt : DOWNSHIFT_DEV_DISABLE;
-+
-+      return 0;
-+}
-+
-+static int aqr107_set_downshift(struct phy_device *phydev, u8 cnt)
-+{
-+      int val = 0;
-+
-+      if (!FIELD_FIT(MDIO_AN_VEND_PROV_DOWNSHIFT_MASK, cnt))
-+              return -E2BIG;
-+
-+      if (cnt != DOWNSHIFT_DEV_DISABLE) {
-+              val = MDIO_AN_VEND_PROV_DOWNSHIFT_EN;
-+              val |= FIELD_PREP(MDIO_AN_VEND_PROV_DOWNSHIFT_MASK, cnt);
-+      }
-+
-+      return phy_modify_mmd(phydev, MDIO_MMD_AN, MDIO_AN_VEND_PROV,
-+                            MDIO_AN_VEND_PROV_DOWNSHIFT_EN |
-+                            MDIO_AN_VEND_PROV_DOWNSHIFT_MASK, val);
-+}
-+
-+static int aqr107_get_tunable(struct phy_device *phydev,
-+                            struct ethtool_tunable *tuna, void *data)
-+{
-+      switch (tuna->id) {
-+      case ETHTOOL_PHY_DOWNSHIFT:
-+              return aqr107_get_downshift(phydev, data);
-+      default:
-+              return -EOPNOTSUPP;
-+      }
-+}
-+
-+static int aqr107_set_tunable(struct phy_device *phydev,
-+                            struct ethtool_tunable *tuna, const void *data)
-+{
-+      switch (tuna->id) {
-+      case ETHTOOL_PHY_DOWNSHIFT:
-+              return aqr107_set_downshift(phydev, *(const u8 *)data);
-+      default:
-+              return -EOPNOTSUPP;
-+      }
-+}
-+
-+/* If we configure settings whilst firmware is still initializing the chip,
-+ * then these settings may be overwritten. Therefore make sure chip
-+ * initialization has completed. Use presence of the firmware ID as
-+ * indicator for initialization having completed.
-+ * The chip also provides a "reset completed" bit, but it's cleared after
-+ * read. Therefore function would time out if called again.
-+ */
-+static int aqr107_wait_reset_complete(struct phy_device *phydev)
-+{
-+      int val;
-+
-+      return phy_read_mmd_poll_timeout(phydev, MDIO_MMD_VEND1,
-+                                       VEND1_GLOBAL_FW_ID, val, val != 0,
-+                                       20000, 2000000, false);
-+}
-+
-+static void aqr107_chip_info(struct phy_device *phydev)
-+{
-+      u8 fw_major, fw_minor, build_id, prov_id;
-+      int val;
-+
-+      val = phy_read_mmd(phydev, MDIO_MMD_VEND1, VEND1_GLOBAL_FW_ID);
-+      if (val < 0)
-+              return;
-+
-+      fw_major = FIELD_GET(VEND1_GLOBAL_FW_ID_MAJOR, val);
-+      fw_minor = FIELD_GET(VEND1_GLOBAL_FW_ID_MINOR, val);
-+
-+      val = phy_read_mmd(phydev, MDIO_MMD_VEND1, VEND1_GLOBAL_RSVD_STAT1);
-+      if (val < 0)
-+              return;
-+
-+      build_id = FIELD_GET(VEND1_GLOBAL_RSVD_STAT1_FW_BUILD_ID, val);
-+      prov_id = FIELD_GET(VEND1_GLOBAL_RSVD_STAT1_PROV_ID, val);
-+
-+      phydev_dbg(phydev, "FW %u.%u, Build %u, Provisioning %u\n",
-+                 fw_major, fw_minor, build_id, prov_id);
-+}
-+
-+static int aqr107_config_init(struct phy_device *phydev)
-+{
-+      int ret;
-+
-+      /* Check that the PHY interface type is compatible */
-+      if (phydev->interface != PHY_INTERFACE_MODE_SGMII &&
-+          phydev->interface != PHY_INTERFACE_MODE_1000BASEKX &&
-+          phydev->interface != PHY_INTERFACE_MODE_2500BASEX &&
-+          phydev->interface != PHY_INTERFACE_MODE_XGMII &&
-+          phydev->interface != PHY_INTERFACE_MODE_USXGMII &&
-+          phydev->interface != PHY_INTERFACE_MODE_10GKR &&
-+          phydev->interface != PHY_INTERFACE_MODE_10GBASER &&
-+          phydev->interface != PHY_INTERFACE_MODE_XAUI &&
-+          phydev->interface != PHY_INTERFACE_MODE_RXAUI)
-+              return -ENODEV;
-+
-+      WARN(phydev->interface == PHY_INTERFACE_MODE_XGMII,
-+           "Your devicetree is out of date, please update it. The AQR107 family doesn't support XGMII, maybe you mean USXGMII.\n");
-+
-+      ret = aqr107_wait_reset_complete(phydev);
-+      if (!ret)
-+              aqr107_chip_info(phydev);
-+
-+      return aqr107_set_downshift(phydev, MDIO_AN_VEND_PROV_DOWNSHIFT_DFLT);
-+}
-+
-+static int aqcs109_config_init(struct phy_device *phydev)
-+{
-+      int ret;
-+
-+      /* Check that the PHY interface type is compatible */
-+      if (phydev->interface != PHY_INTERFACE_MODE_SGMII &&
-+          phydev->interface != PHY_INTERFACE_MODE_2500BASEX)
-+              return -ENODEV;
-+
-+      ret = aqr107_wait_reset_complete(phydev);
-+      if (!ret)
-+              aqr107_chip_info(phydev);
-+
-+      /* AQCS109 belongs to a chip family partially supporting 10G and 5G.
-+       * PMA speed ability bits are the same for all members of the family,
-+       * AQCS109 however supports speeds up to 2.5G only.
-+       */
-+      ret = phy_set_max_speed(phydev, SPEED_2500);
-+      if (ret)
-+              return ret;
-+
-+      return aqr107_set_downshift(phydev, MDIO_AN_VEND_PROV_DOWNSHIFT_DFLT);
-+}
-+
-+static void aqr107_link_change_notify(struct phy_device *phydev)
-+{
-+      u8 fw_major, fw_minor;
-+      bool downshift, short_reach, afr;
-+      int mode, val;
-+
-+      if (phydev->state != PHY_RUNNING || phydev->autoneg == AUTONEG_DISABLE)
-+              return;
-+
-+      val = phy_read_mmd(phydev, MDIO_MMD_AN, MDIO_AN_RX_LP_STAT1);
-+      /* call failed or link partner is no Aquantia PHY */
-+      if (val < 0 || !(val & MDIO_AN_RX_LP_STAT1_AQ_PHY))
-+              return;
-+
-+      short_reach = val & MDIO_AN_RX_LP_STAT1_SHORT_REACH;
-+      downshift = val & MDIO_AN_RX_LP_STAT1_AQRATE_DOWNSHIFT;
-+
-+      val = phy_read_mmd(phydev, MDIO_MMD_AN, MDIO_AN_RX_LP_STAT4);
-+      if (val < 0)
-+              return;
-+
-+      fw_major = FIELD_GET(MDIO_AN_RX_LP_STAT4_FW_MAJOR, val);
-+      fw_minor = FIELD_GET(MDIO_AN_RX_LP_STAT4_FW_MINOR, val);
-+
-+      val = phy_read_mmd(phydev, MDIO_MMD_AN, MDIO_AN_RX_VEND_STAT3);
-+      if (val < 0)
-+              return;
-+
-+      afr = val & MDIO_AN_RX_VEND_STAT3_AFR;
-+
-+      phydev_dbg(phydev, "Link partner is Aquantia PHY, FW %u.%u%s%s%s\n",
-+                 fw_major, fw_minor,
-+                 short_reach ? ", short reach mode" : "",
-+                 downshift ? ", fast-retrain downshift advertised" : "",
-+                 afr ? ", fast reframe advertised" : "");
-+
-+      val = phy_read_mmd(phydev, MDIO_MMD_VEND1, VEND1_GLOBAL_RSVD_STAT9);
-+      if (val < 0)
-+              return;
-+
-+      mode = FIELD_GET(VEND1_GLOBAL_RSVD_STAT9_MODE, val);
-+      if (mode == VEND1_GLOBAL_RSVD_STAT9_1000BT2)
-+              phydev_info(phydev, "Aquantia 1000Base-T2 mode active\n");
-+}
-+
-+static int aqr107_wait_processor_intensive_op(struct phy_device *phydev)
-+{
-+      int val, err;
-+
-+      /* The datasheet notes to wait at least 1ms after issuing a
-+       * processor intensive operation before checking.
-+       * We cannot use the 'sleep_before_read' parameter of read_poll_timeout
-+       * because that just determines the maximum time slept, not the minimum.
-+       */
-+      usleep_range(1000, 5000);
-+
-+      err = phy_read_mmd_poll_timeout(phydev, MDIO_MMD_VEND1,
-+                                      VEND1_GLOBAL_GEN_STAT2, val,
-+                                      !(val & VEND1_GLOBAL_GEN_STAT2_OP_IN_PROG),
-+                                      AQR107_OP_IN_PROG_SLEEP,
-+                                      AQR107_OP_IN_PROG_TIMEOUT, false);
-+      if (err) {
-+              phydev_err(phydev, "timeout: processor-intensive MDIO operation\n");
-+              return err;
-+      }
-+
-+      return 0;
-+}
-+
-+static int aqr107_get_rate_matching(struct phy_device *phydev,
-+                                  phy_interface_t iface)
-+{
-+      if (iface == PHY_INTERFACE_MODE_10GBASER ||
-+          iface == PHY_INTERFACE_MODE_2500BASEX ||
-+          iface == PHY_INTERFACE_MODE_NA)
-+              return RATE_MATCH_PAUSE;
-+      return RATE_MATCH_NONE;
-+}
-+
-+static int aqr107_suspend(struct phy_device *phydev)
-+{
-+      int err;
-+
-+      err = phy_set_bits_mmd(phydev, MDIO_MMD_VEND1, MDIO_CTRL1,
-+                             MDIO_CTRL1_LPOWER);
-+      if (err)
-+              return err;
-+
-+      return aqr107_wait_processor_intensive_op(phydev);
-+}
-+
-+static int aqr107_resume(struct phy_device *phydev)
-+{
-+      int err;
-+
-+      err = phy_clear_bits_mmd(phydev, MDIO_MMD_VEND1, MDIO_CTRL1,
-+                               MDIO_CTRL1_LPOWER);
-+      if (err)
-+              return err;
-+
-+      return aqr107_wait_processor_intensive_op(phydev);
-+}
-+
-+static int aqr107_probe(struct phy_device *phydev)
-+{
-+      phydev->priv = devm_kzalloc(&phydev->mdio.dev,
-+                                  sizeof(struct aqr107_priv), GFP_KERNEL);
-+      if (!phydev->priv)
-+              return -ENOMEM;
-+
-+      return aqr_hwmon_probe(phydev);
-+}
-+
-+static struct phy_driver aqr_driver[] = {
-+{
-+      PHY_ID_MATCH_MODEL(PHY_ID_AQ1202),
-+      .name           = "Aquantia AQ1202",
-+      .config_aneg    = aqr_config_aneg,
-+      .config_intr    = aqr_config_intr,
-+      .handle_interrupt = aqr_handle_interrupt,
-+      .read_status    = aqr_read_status,
-+},
-+{
-+      PHY_ID_MATCH_MODEL(PHY_ID_AQ2104),
-+      .name           = "Aquantia AQ2104",
-+      .config_aneg    = aqr_config_aneg,
-+      .config_intr    = aqr_config_intr,
-+      .handle_interrupt = aqr_handle_interrupt,
-+      .read_status    = aqr_read_status,
-+},
-+{
-+      PHY_ID_MATCH_MODEL(PHY_ID_AQR105),
-+      .name           = "Aquantia AQR105",
-+      .config_aneg    = aqr_config_aneg,
-+      .config_intr    = aqr_config_intr,
-+      .handle_interrupt = aqr_handle_interrupt,
-+      .read_status    = aqr_read_status,
-+      .suspend        = aqr107_suspend,
-+      .resume         = aqr107_resume,
-+},
-+{
-+      PHY_ID_MATCH_MODEL(PHY_ID_AQR106),
-+      .name           = "Aquantia AQR106",
-+      .config_aneg    = aqr_config_aneg,
-+      .config_intr    = aqr_config_intr,
-+      .handle_interrupt = aqr_handle_interrupt,
-+      .read_status    = aqr_read_status,
-+},
-+{
-+      PHY_ID_MATCH_MODEL(PHY_ID_AQR107),
-+      .name           = "Aquantia AQR107",
-+      .probe          = aqr107_probe,
-+      .get_rate_matching = aqr107_get_rate_matching,
-+      .config_init    = aqr107_config_init,
-+      .config_aneg    = aqr_config_aneg,
-+      .config_intr    = aqr_config_intr,
-+      .handle_interrupt = aqr_handle_interrupt,
-+      .read_status    = aqr107_read_status,
-+      .get_tunable    = aqr107_get_tunable,
-+      .set_tunable    = aqr107_set_tunable,
-+      .suspend        = aqr107_suspend,
-+      .resume         = aqr107_resume,
-+      .get_sset_count = aqr107_get_sset_count,
-+      .get_strings    = aqr107_get_strings,
-+      .get_stats      = aqr107_get_stats,
-+      .link_change_notify = aqr107_link_change_notify,
-+},
-+{
-+      PHY_ID_MATCH_MODEL(PHY_ID_AQCS109),
-+      .name           = "Aquantia AQCS109",
-+      .probe          = aqr107_probe,
-+      .get_rate_matching = aqr107_get_rate_matching,
-+      .config_init    = aqcs109_config_init,
-+      .config_aneg    = aqr_config_aneg,
-+      .config_intr    = aqr_config_intr,
-+      .handle_interrupt = aqr_handle_interrupt,
-+      .read_status    = aqr107_read_status,
-+      .get_tunable    = aqr107_get_tunable,
-+      .set_tunable    = aqr107_set_tunable,
-+      .suspend        = aqr107_suspend,
-+      .resume         = aqr107_resume,
-+      .get_sset_count = aqr107_get_sset_count,
-+      .get_strings    = aqr107_get_strings,
-+      .get_stats      = aqr107_get_stats,
-+      .link_change_notify = aqr107_link_change_notify,
-+},
-+{
-+      PHY_ID_MATCH_MODEL(PHY_ID_AQR405),
-+      .name           = "Aquantia AQR405",
-+      .config_aneg    = aqr_config_aneg,
-+      .config_intr    = aqr_config_intr,
-+      .handle_interrupt = aqr_handle_interrupt,
-+      .read_status    = aqr_read_status,
-+},
-+{
-+      PHY_ID_MATCH_MODEL(PHY_ID_AQR113C),
-+      .name           = "Aquantia AQR113C",
-+      .probe          = aqr107_probe,
-+      .get_rate_matching = aqr107_get_rate_matching,
-+      .config_init    = aqr107_config_init,
-+      .config_aneg    = aqr_config_aneg,
-+      .config_intr    = aqr_config_intr,
-+      .handle_interrupt       = aqr_handle_interrupt,
-+      .read_status    = aqr107_read_status,
-+      .get_tunable    = aqr107_get_tunable,
-+      .set_tunable    = aqr107_set_tunable,
-+      .suspend        = aqr107_suspend,
-+      .resume         = aqr107_resume,
-+      .get_sset_count = aqr107_get_sset_count,
-+      .get_strings    = aqr107_get_strings,
-+      .get_stats      = aqr107_get_stats,
-+      .link_change_notify = aqr107_link_change_notify,
-+},
-+};
-+
-+module_phy_driver(aqr_driver);
-+
-+static struct mdio_device_id __maybe_unused aqr_tbl[] = {
-+      { PHY_ID_MATCH_MODEL(PHY_ID_AQ1202) },
-+      { PHY_ID_MATCH_MODEL(PHY_ID_AQ2104) },
-+      { PHY_ID_MATCH_MODEL(PHY_ID_AQR105) },
-+      { PHY_ID_MATCH_MODEL(PHY_ID_AQR106) },
-+      { PHY_ID_MATCH_MODEL(PHY_ID_AQR107) },
-+      { PHY_ID_MATCH_MODEL(PHY_ID_AQCS109) },
-+      { PHY_ID_MATCH_MODEL(PHY_ID_AQR405) },
-+      { PHY_ID_MATCH_MODEL(PHY_ID_AQR113C) },
-+      { }
-+};
-+
-+MODULE_DEVICE_TABLE(mdio, aqr_tbl);
-+
-+MODULE_DESCRIPTION("Aquantia PHY driver");
-+MODULE_AUTHOR("Shaohui Xie <[email protected]>");
-+MODULE_LICENSE("GPL v2");
---- a/drivers/net/phy/aquantia_hwmon.c
-+++ /dev/null
-@@ -1,250 +0,0 @@
--// SPDX-License-Identifier: GPL-2.0
--/* HWMON driver for Aquantia PHY
-- *
-- * Author: Nikita Yushchenko <[email protected]>
-- * Author: Andrew Lunn <[email protected]>
-- * Author: Heiner Kallweit <[email protected]>
-- */
--
--#include <linux/phy.h>
--#include <linux/device.h>
--#include <linux/ctype.h>
--#include <linux/hwmon.h>
--
--#include "aquantia.h"
--
--/* Vendor specific 1, MDIO_MMD_VEND2 */
--#define VEND1_THERMAL_PROV_HIGH_TEMP_FAIL     0xc421
--#define VEND1_THERMAL_PROV_LOW_TEMP_FAIL      0xc422
--#define VEND1_THERMAL_PROV_HIGH_TEMP_WARN     0xc423
--#define VEND1_THERMAL_PROV_LOW_TEMP_WARN      0xc424
--#define VEND1_THERMAL_STAT1                   0xc820
--#define VEND1_THERMAL_STAT2                   0xc821
--#define VEND1_THERMAL_STAT2_VALID             BIT(0)
--#define VEND1_GENERAL_STAT1                   0xc830
--#define VEND1_GENERAL_STAT1_HIGH_TEMP_FAIL    BIT(14)
--#define VEND1_GENERAL_STAT1_LOW_TEMP_FAIL     BIT(13)
--#define VEND1_GENERAL_STAT1_HIGH_TEMP_WARN    BIT(12)
--#define VEND1_GENERAL_STAT1_LOW_TEMP_WARN     BIT(11)
--
--#if IS_REACHABLE(CONFIG_HWMON)
--
--static umode_t aqr_hwmon_is_visible(const void *data,
--                                  enum hwmon_sensor_types type,
--                                  u32 attr, int channel)
--{
--      if (type != hwmon_temp)
--              return 0;
--
--      switch (attr) {
--      case hwmon_temp_input:
--      case hwmon_temp_min_alarm:
--      case hwmon_temp_max_alarm:
--      case hwmon_temp_lcrit_alarm:
--      case hwmon_temp_crit_alarm:
--              return 0444;
--      case hwmon_temp_min:
--      case hwmon_temp_max:
--      case hwmon_temp_lcrit:
--      case hwmon_temp_crit:
--              return 0644;
--      default:
--              return 0;
--      }
--}
--
--static int aqr_hwmon_get(struct phy_device *phydev, int reg, long *value)
--{
--      int temp = phy_read_mmd(phydev, MDIO_MMD_VEND1, reg);
--
--      if (temp < 0)
--              return temp;
--
--      /* 16 bit value is 2's complement with LSB = 1/256th degree Celsius */
--      *value = (s16)temp * 1000 / 256;
--
--      return 0;
--}
--
--static int aqr_hwmon_set(struct phy_device *phydev, int reg, long value)
--{
--      int temp;
--
--      if (value >= 128000 || value < -128000)
--              return -ERANGE;
--
--      temp = value * 256 / 1000;
--
--      /* temp is in s16 range and we're interested in lower 16 bits only */
--      return phy_write_mmd(phydev, MDIO_MMD_VEND1, reg, (u16)temp);
--}
--
--static int aqr_hwmon_test_bit(struct phy_device *phydev, int reg, int bit)
--{
--      int val = phy_read_mmd(phydev, MDIO_MMD_VEND1, reg);
--
--      if (val < 0)
--              return val;
--
--      return !!(val & bit);
--}
--
--static int aqr_hwmon_status1(struct phy_device *phydev, int bit, long *value)
--{
--      int val = aqr_hwmon_test_bit(phydev, VEND1_GENERAL_STAT1, bit);
--
--      if (val < 0)
--              return val;
--
--      *value = val;
--
--      return 0;
--}
--
--static int aqr_hwmon_read(struct device *dev, enum hwmon_sensor_types type,
--                        u32 attr, int channel, long *value)
--{
--      struct phy_device *phydev = dev_get_drvdata(dev);
--      int reg;
--
--      if (type != hwmon_temp)
--              return -EOPNOTSUPP;
--
--      switch (attr) {
--      case hwmon_temp_input:
--              reg = aqr_hwmon_test_bit(phydev, VEND1_THERMAL_STAT2,
--                                       VEND1_THERMAL_STAT2_VALID);
--              if (reg < 0)
--                      return reg;
--              if (!reg)
--                      return -EBUSY;
--
--              return aqr_hwmon_get(phydev, VEND1_THERMAL_STAT1, value);
--
--      case hwmon_temp_lcrit:
--              return aqr_hwmon_get(phydev, VEND1_THERMAL_PROV_LOW_TEMP_FAIL,
--                                   value);
--      case hwmon_temp_min:
--              return aqr_hwmon_get(phydev, VEND1_THERMAL_PROV_LOW_TEMP_WARN,
--                                   value);
--      case hwmon_temp_max:
--              return aqr_hwmon_get(phydev, VEND1_THERMAL_PROV_HIGH_TEMP_WARN,
--                                   value);
--      case hwmon_temp_crit:
--              return aqr_hwmon_get(phydev, VEND1_THERMAL_PROV_HIGH_TEMP_FAIL,
--                                   value);
--      case hwmon_temp_lcrit_alarm:
--              return aqr_hwmon_status1(phydev,
--                                       VEND1_GENERAL_STAT1_LOW_TEMP_FAIL,
--                                       value);
--      case hwmon_temp_min_alarm:
--              return aqr_hwmon_status1(phydev,
--                                       VEND1_GENERAL_STAT1_LOW_TEMP_WARN,
--                                       value);
--      case hwmon_temp_max_alarm:
--              return aqr_hwmon_status1(phydev,
--                                       VEND1_GENERAL_STAT1_HIGH_TEMP_WARN,
--                                       value);
--      case hwmon_temp_crit_alarm:
--              return aqr_hwmon_status1(phydev,
--                                       VEND1_GENERAL_STAT1_HIGH_TEMP_FAIL,
--                                       value);
--      default:
--              return -EOPNOTSUPP;
--      }
--}
--
--static int aqr_hwmon_write(struct device *dev, enum hwmon_sensor_types type,
--                         u32 attr, int channel, long value)
--{
--      struct phy_device *phydev = dev_get_drvdata(dev);
--
--      if (type != hwmon_temp)
--              return -EOPNOTSUPP;
--
--      switch (attr) {
--      case hwmon_temp_lcrit:
--              return aqr_hwmon_set(phydev, VEND1_THERMAL_PROV_LOW_TEMP_FAIL,
--                                   value);
--      case hwmon_temp_min:
--              return aqr_hwmon_set(phydev, VEND1_THERMAL_PROV_LOW_TEMP_WARN,
--                                   value);
--      case hwmon_temp_max:
--              return aqr_hwmon_set(phydev, VEND1_THERMAL_PROV_HIGH_TEMP_WARN,
--                                   value);
--      case hwmon_temp_crit:
--              return aqr_hwmon_set(phydev, VEND1_THERMAL_PROV_HIGH_TEMP_FAIL,
--                                   value);
--      default:
--              return -EOPNOTSUPP;
--      }
--}
--
--static const struct hwmon_ops aqr_hwmon_ops = {
--      .is_visible = aqr_hwmon_is_visible,
--      .read = aqr_hwmon_read,
--      .write = aqr_hwmon_write,
--};
--
--static u32 aqr_hwmon_chip_config[] = {
--      HWMON_C_REGISTER_TZ,
--      0,
--};
--
--static const struct hwmon_channel_info aqr_hwmon_chip = {
--      .type = hwmon_chip,
--      .config = aqr_hwmon_chip_config,
--};
--
--static u32 aqr_hwmon_temp_config[] = {
--      HWMON_T_INPUT |
--      HWMON_T_MAX | HWMON_T_MIN |
--      HWMON_T_MAX_ALARM | HWMON_T_MIN_ALARM |
--      HWMON_T_CRIT | HWMON_T_LCRIT |
--      HWMON_T_CRIT_ALARM | HWMON_T_LCRIT_ALARM,
--      0,
--};
--
--static const struct hwmon_channel_info aqr_hwmon_temp = {
--      .type = hwmon_temp,
--      .config = aqr_hwmon_temp_config,
--};
--
--static const struct hwmon_channel_info *aqr_hwmon_info[] = {
--      &aqr_hwmon_chip,
--      &aqr_hwmon_temp,
--      NULL,
--};
--
--static const struct hwmon_chip_info aqr_hwmon_chip_info = {
--      .ops = &aqr_hwmon_ops,
--      .info = aqr_hwmon_info,
--};
--
--int aqr_hwmon_probe(struct phy_device *phydev)
--{
--      struct device *dev = &phydev->mdio.dev;
--      struct device *hwmon_dev;
--      char *hwmon_name;
--      int i, j;
--
--      hwmon_name = devm_kstrdup(dev, dev_name(dev), GFP_KERNEL);
--      if (!hwmon_name)
--              return -ENOMEM;
--
--      for (i = j = 0; hwmon_name[i]; i++) {
--              if (isalnum(hwmon_name[i])) {
--                      if (i != j)
--                              hwmon_name[j] = hwmon_name[i];
--                      j++;
--              }
--      }
--      hwmon_name[j] = '\0';
--
--      hwmon_dev = devm_hwmon_device_register_with_info(dev, hwmon_name,
--                                      phydev, &aqr_hwmon_chip_info, NULL);
--
--      return PTR_ERR_OR_ZERO(hwmon_dev);
--}
--
--#endif
---- a/drivers/net/phy/aquantia_main.c
-+++ /dev/null
-@@ -1,844 +0,0 @@
--// SPDX-License-Identifier: GPL-2.0
--/*
-- * Driver for Aquantia PHY
-- *
-- * Author: Shaohui Xie <[email protected]>
-- *
-- * Copyright 2015 Freescale Semiconductor, Inc.
-- */
--
--#include <linux/kernel.h>
--#include <linux/module.h>
--#include <linux/delay.h>
--#include <linux/bitfield.h>
--#include <linux/phy.h>
--
--#include "aquantia.h"
--
--#define PHY_ID_AQ1202 0x03a1b445
--#define PHY_ID_AQ2104 0x03a1b460
--#define PHY_ID_AQR105 0x03a1b4a2
--#define PHY_ID_AQR106 0x03a1b4d0
--#define PHY_ID_AQR107 0x03a1b4e0
--#define PHY_ID_AQCS109        0x03a1b5c2
--#define PHY_ID_AQR405 0x03a1b4b0
--#define PHY_ID_AQR113C        0x31c31c12
--
--#define MDIO_PHYXS_VEND_IF_STATUS             0xe812
--#define MDIO_PHYXS_VEND_IF_STATUS_TYPE_MASK   GENMASK(7, 3)
--#define MDIO_PHYXS_VEND_IF_STATUS_TYPE_KR     0
--#define MDIO_PHYXS_VEND_IF_STATUS_TYPE_KX     1
--#define MDIO_PHYXS_VEND_IF_STATUS_TYPE_XFI    2
--#define MDIO_PHYXS_VEND_IF_STATUS_TYPE_USXGMII        3
--#define MDIO_PHYXS_VEND_IF_STATUS_TYPE_XAUI   4
--#define MDIO_PHYXS_VEND_IF_STATUS_TYPE_SGMII  6
--#define MDIO_PHYXS_VEND_IF_STATUS_TYPE_RXAUI  7
--#define MDIO_PHYXS_VEND_IF_STATUS_TYPE_OCSGMII        10
--
--#define MDIO_AN_VEND_PROV                     0xc400
--#define MDIO_AN_VEND_PROV_1000BASET_FULL      BIT(15)
--#define MDIO_AN_VEND_PROV_1000BASET_HALF      BIT(14)
--#define MDIO_AN_VEND_PROV_5000BASET_FULL      BIT(11)
--#define MDIO_AN_VEND_PROV_2500BASET_FULL      BIT(10)
--#define MDIO_AN_VEND_PROV_DOWNSHIFT_EN                BIT(4)
--#define MDIO_AN_VEND_PROV_DOWNSHIFT_MASK      GENMASK(3, 0)
--#define MDIO_AN_VEND_PROV_DOWNSHIFT_DFLT      4
--
--#define MDIO_AN_TX_VEND_STATUS1                       0xc800
--#define MDIO_AN_TX_VEND_STATUS1_RATE_MASK     GENMASK(3, 1)
--#define MDIO_AN_TX_VEND_STATUS1_10BASET               0
--#define MDIO_AN_TX_VEND_STATUS1_100BASETX     1
--#define MDIO_AN_TX_VEND_STATUS1_1000BASET     2
--#define MDIO_AN_TX_VEND_STATUS1_10GBASET      3
--#define MDIO_AN_TX_VEND_STATUS1_2500BASET     4
--#define MDIO_AN_TX_VEND_STATUS1_5000BASET     5
--#define MDIO_AN_TX_VEND_STATUS1_FULL_DUPLEX   BIT(0)
--
--#define MDIO_AN_TX_VEND_INT_STATUS1           0xcc00
--#define MDIO_AN_TX_VEND_INT_STATUS1_DOWNSHIFT BIT(1)
--
--#define MDIO_AN_TX_VEND_INT_STATUS2           0xcc01
--#define MDIO_AN_TX_VEND_INT_STATUS2_MASK      BIT(0)
--
--#define MDIO_AN_TX_VEND_INT_MASK2             0xd401
--#define MDIO_AN_TX_VEND_INT_MASK2_LINK                BIT(0)
--
--#define MDIO_AN_RX_LP_STAT1                   0xe820
--#define MDIO_AN_RX_LP_STAT1_1000BASET_FULL    BIT(15)
--#define MDIO_AN_RX_LP_STAT1_1000BASET_HALF    BIT(14)
--#define MDIO_AN_RX_LP_STAT1_SHORT_REACH               BIT(13)
--#define MDIO_AN_RX_LP_STAT1_AQRATE_DOWNSHIFT  BIT(12)
--#define MDIO_AN_RX_LP_STAT1_AQ_PHY            BIT(2)
--
--#define MDIO_AN_RX_LP_STAT4                   0xe823
--#define MDIO_AN_RX_LP_STAT4_FW_MAJOR          GENMASK(15, 8)
--#define MDIO_AN_RX_LP_STAT4_FW_MINOR          GENMASK(7, 0)
--
--#define MDIO_AN_RX_VEND_STAT3                 0xe832
--#define MDIO_AN_RX_VEND_STAT3_AFR             BIT(0)
--
--/* MDIO_MMD_C22EXT */
--#define MDIO_C22EXT_STAT_SGMII_RX_GOOD_FRAMES         0xd292
--#define MDIO_C22EXT_STAT_SGMII_RX_BAD_FRAMES          0xd294
--#define MDIO_C22EXT_STAT_SGMII_RX_FALSE_CARRIER               0xd297
--#define MDIO_C22EXT_STAT_SGMII_TX_GOOD_FRAMES         0xd313
--#define MDIO_C22EXT_STAT_SGMII_TX_BAD_FRAMES          0xd315
--#define MDIO_C22EXT_STAT_SGMII_TX_FALSE_CARRIER               0xd317
--#define MDIO_C22EXT_STAT_SGMII_TX_COLLISIONS          0xd318
--#define MDIO_C22EXT_STAT_SGMII_TX_LINE_COLLISIONS     0xd319
--#define MDIO_C22EXT_STAT_SGMII_TX_FRAME_ALIGN_ERR     0xd31a
--#define MDIO_C22EXT_STAT_SGMII_TX_RUNT_FRAMES         0xd31b
--
--/* Vendor specific 1, MDIO_MMD_VEND1 */
--#define VEND1_GLOBAL_FW_ID                    0x0020
--#define VEND1_GLOBAL_FW_ID_MAJOR              GENMASK(15, 8)
--#define VEND1_GLOBAL_FW_ID_MINOR              GENMASK(7, 0)
--
--#define VEND1_GLOBAL_GEN_STAT2                        0xc831
--#define VEND1_GLOBAL_GEN_STAT2_OP_IN_PROG     BIT(15)
--
--/* The following registers all have similar layouts; first the registers... */
--#define VEND1_GLOBAL_CFG_10M                  0x0310
--#define VEND1_GLOBAL_CFG_100M                 0x031b
--#define VEND1_GLOBAL_CFG_1G                   0x031c
--#define VEND1_GLOBAL_CFG_2_5G                 0x031d
--#define VEND1_GLOBAL_CFG_5G                   0x031e
--#define VEND1_GLOBAL_CFG_10G                  0x031f
--/* ...and now the fields */
--#define VEND1_GLOBAL_CFG_RATE_ADAPT           GENMASK(8, 7)
--#define VEND1_GLOBAL_CFG_RATE_ADAPT_NONE      0
--#define VEND1_GLOBAL_CFG_RATE_ADAPT_USX               1
--#define VEND1_GLOBAL_CFG_RATE_ADAPT_PAUSE     2
--
--#define VEND1_GLOBAL_RSVD_STAT1                       0xc885
--#define VEND1_GLOBAL_RSVD_STAT1_FW_BUILD_ID   GENMASK(7, 4)
--#define VEND1_GLOBAL_RSVD_STAT1_PROV_ID               GENMASK(3, 0)
--
--#define VEND1_GLOBAL_RSVD_STAT9                       0xc88d
--#define VEND1_GLOBAL_RSVD_STAT9_MODE          GENMASK(7, 0)
--#define VEND1_GLOBAL_RSVD_STAT9_1000BT2               0x23
--
--#define VEND1_GLOBAL_INT_STD_STATUS           0xfc00
--#define VEND1_GLOBAL_INT_VEND_STATUS          0xfc01
--
--#define VEND1_GLOBAL_INT_STD_MASK             0xff00
--#define VEND1_GLOBAL_INT_STD_MASK_PMA1                BIT(15)
--#define VEND1_GLOBAL_INT_STD_MASK_PMA2                BIT(14)
--#define VEND1_GLOBAL_INT_STD_MASK_PCS1                BIT(13)
--#define VEND1_GLOBAL_INT_STD_MASK_PCS2                BIT(12)
--#define VEND1_GLOBAL_INT_STD_MASK_PCS3                BIT(11)
--#define VEND1_GLOBAL_INT_STD_MASK_PHY_XS1     BIT(10)
--#define VEND1_GLOBAL_INT_STD_MASK_PHY_XS2     BIT(9)
--#define VEND1_GLOBAL_INT_STD_MASK_AN1         BIT(8)
--#define VEND1_GLOBAL_INT_STD_MASK_AN2         BIT(7)
--#define VEND1_GLOBAL_INT_STD_MASK_GBE         BIT(6)
--#define VEND1_GLOBAL_INT_STD_MASK_ALL         BIT(0)
--
--#define VEND1_GLOBAL_INT_VEND_MASK            0xff01
--#define VEND1_GLOBAL_INT_VEND_MASK_PMA                BIT(15)
--#define VEND1_GLOBAL_INT_VEND_MASK_PCS                BIT(14)
--#define VEND1_GLOBAL_INT_VEND_MASK_PHY_XS     BIT(13)
--#define VEND1_GLOBAL_INT_VEND_MASK_AN         BIT(12)
--#define VEND1_GLOBAL_INT_VEND_MASK_GBE                BIT(11)
--#define VEND1_GLOBAL_INT_VEND_MASK_GLOBAL1    BIT(2)
--#define VEND1_GLOBAL_INT_VEND_MASK_GLOBAL2    BIT(1)
--#define VEND1_GLOBAL_INT_VEND_MASK_GLOBAL3    BIT(0)
--
--/* Sleep and timeout for checking if the Processor-Intensive
-- * MDIO operation is finished
-- */
--#define AQR107_OP_IN_PROG_SLEEP               1000
--#define AQR107_OP_IN_PROG_TIMEOUT     100000
--
--struct aqr107_hw_stat {
--      const char *name;
--      int reg;
--      int size;
--};
--
--#define SGMII_STAT(n, r, s) { n, MDIO_C22EXT_STAT_SGMII_ ## r, s }
--static const struct aqr107_hw_stat aqr107_hw_stats[] = {
--      SGMII_STAT("sgmii_rx_good_frames",          RX_GOOD_FRAMES,     26),
--      SGMII_STAT("sgmii_rx_bad_frames",           RX_BAD_FRAMES,      26),
--      SGMII_STAT("sgmii_rx_false_carrier_events", RX_FALSE_CARRIER,    8),
--      SGMII_STAT("sgmii_tx_good_frames",          TX_GOOD_FRAMES,     26),
--      SGMII_STAT("sgmii_tx_bad_frames",           TX_BAD_FRAMES,      26),
--      SGMII_STAT("sgmii_tx_false_carrier_events", TX_FALSE_CARRIER,    8),
--      SGMII_STAT("sgmii_tx_collisions",           TX_COLLISIONS,       8),
--      SGMII_STAT("sgmii_tx_line_collisions",      TX_LINE_COLLISIONS,  8),
--      SGMII_STAT("sgmii_tx_frame_alignment_err",  TX_FRAME_ALIGN_ERR, 16),
--      SGMII_STAT("sgmii_tx_runt_frames",          TX_RUNT_FRAMES,     22),
--};
--#define AQR107_SGMII_STAT_SZ ARRAY_SIZE(aqr107_hw_stats)
--
--struct aqr107_priv {
--      u64 sgmii_stats[AQR107_SGMII_STAT_SZ];
--};
--
--static int aqr107_get_sset_count(struct phy_device *phydev)
--{
--      return AQR107_SGMII_STAT_SZ;
--}
--
--static void aqr107_get_strings(struct phy_device *phydev, u8 *data)
--{
--      int i;
--
--      for (i = 0; i < AQR107_SGMII_STAT_SZ; i++)
--              strscpy(data + i * ETH_GSTRING_LEN, aqr107_hw_stats[i].name,
--                      ETH_GSTRING_LEN);
--}
--
--static u64 aqr107_get_stat(struct phy_device *phydev, int index)
--{
--      const struct aqr107_hw_stat *stat = aqr107_hw_stats + index;
--      int len_l = min(stat->size, 16);
--      int len_h = stat->size - len_l;
--      u64 ret;
--      int val;
--
--      val = phy_read_mmd(phydev, MDIO_MMD_C22EXT, stat->reg);
--      if (val < 0)
--              return U64_MAX;
--
--      ret = val & GENMASK(len_l - 1, 0);
--      if (len_h) {
--              val = phy_read_mmd(phydev, MDIO_MMD_C22EXT, stat->reg + 1);
--              if (val < 0)
--                      return U64_MAX;
--
--              ret += (val & GENMASK(len_h - 1, 0)) << 16;
--      }
--
--      return ret;
--}
--
--static void aqr107_get_stats(struct phy_device *phydev,
--                           struct ethtool_stats *stats, u64 *data)
--{
--      struct aqr107_priv *priv = phydev->priv;
--      u64 val;
--      int i;
--
--      for (i = 0; i < AQR107_SGMII_STAT_SZ; i++) {
--              val = aqr107_get_stat(phydev, i);
--              if (val == U64_MAX)
--                      phydev_err(phydev, "Reading HW Statistics failed for %s\n",
--                                 aqr107_hw_stats[i].name);
--              else
--                      priv->sgmii_stats[i] += val;
--
--              data[i] = priv->sgmii_stats[i];
--      }
--}
--
--static int aqr_config_aneg(struct phy_device *phydev)
--{
--      bool changed = false;
--      u16 reg;
--      int ret;
--
--      if (phydev->autoneg == AUTONEG_DISABLE)
--              return genphy_c45_pma_setup_forced(phydev);
--
--      ret = genphy_c45_an_config_aneg(phydev);
--      if (ret < 0)
--              return ret;
--      if (ret > 0)
--              changed = true;
--
--      /* Clause 45 has no standardized support for 1000BaseT, therefore
--       * use vendor registers for this mode.
--       */
--      reg = 0;
--      if (linkmode_test_bit(ETHTOOL_LINK_MODE_1000baseT_Full_BIT,
--                            phydev->advertising))
--              reg |= MDIO_AN_VEND_PROV_1000BASET_FULL;
--
--      if (linkmode_test_bit(ETHTOOL_LINK_MODE_1000baseT_Half_BIT,
--                            phydev->advertising))
--              reg |= MDIO_AN_VEND_PROV_1000BASET_HALF;
--
--      /* Handle the case when the 2.5G and 5G speeds are not advertised */
--      if (linkmode_test_bit(ETHTOOL_LINK_MODE_2500baseT_Full_BIT,
--                            phydev->advertising))
--              reg |= MDIO_AN_VEND_PROV_2500BASET_FULL;
--
--      if (linkmode_test_bit(ETHTOOL_LINK_MODE_5000baseT_Full_BIT,
--                            phydev->advertising))
--              reg |= MDIO_AN_VEND_PROV_5000BASET_FULL;
--
--      ret = phy_modify_mmd_changed(phydev, MDIO_MMD_AN, MDIO_AN_VEND_PROV,
--                                   MDIO_AN_VEND_PROV_1000BASET_HALF |
--                                   MDIO_AN_VEND_PROV_1000BASET_FULL |
--                                   MDIO_AN_VEND_PROV_2500BASET_FULL |
--                                   MDIO_AN_VEND_PROV_5000BASET_FULL, reg);
--      if (ret < 0)
--              return ret;
--      if (ret > 0)
--              changed = true;
--
--      return genphy_c45_check_and_restart_aneg(phydev, changed);
--}
--
--static int aqr_config_intr(struct phy_device *phydev)
--{
--      bool en = phydev->interrupts == PHY_INTERRUPT_ENABLED;
--      int err;
--
--      if (en) {
--              /* Clear any pending interrupts before enabling them */
--              err = phy_read_mmd(phydev, MDIO_MMD_AN, MDIO_AN_TX_VEND_INT_STATUS2);
--              if (err < 0)
--                      return err;
--      }
--
--      err = phy_write_mmd(phydev, MDIO_MMD_AN, MDIO_AN_TX_VEND_INT_MASK2,
--                          en ? MDIO_AN_TX_VEND_INT_MASK2_LINK : 0);
--      if (err < 0)
--              return err;
--
--      err = phy_write_mmd(phydev, MDIO_MMD_VEND1, VEND1_GLOBAL_INT_STD_MASK,
--                          en ? VEND1_GLOBAL_INT_STD_MASK_ALL : 0);
--      if (err < 0)
--              return err;
--
--      err = phy_write_mmd(phydev, MDIO_MMD_VEND1, VEND1_GLOBAL_INT_VEND_MASK,
--                          en ? VEND1_GLOBAL_INT_VEND_MASK_GLOBAL3 |
--                          VEND1_GLOBAL_INT_VEND_MASK_AN : 0);
--      if (err < 0)
--              return err;
--
--      if (!en) {
--              /* Clear any pending interrupts after we have disabled them */
--              err = phy_read_mmd(phydev, MDIO_MMD_AN, MDIO_AN_TX_VEND_INT_STATUS2);
--              if (err < 0)
--                      return err;
--      }
--
--      return 0;
--}
--
--static irqreturn_t aqr_handle_interrupt(struct phy_device *phydev)
--{
--      int irq_status;
--
--      irq_status = phy_read_mmd(phydev, MDIO_MMD_AN,
--                                MDIO_AN_TX_VEND_INT_STATUS2);
--      if (irq_status < 0) {
--              phy_error(phydev);
--              return IRQ_NONE;
--      }
--
--      if (!(irq_status & MDIO_AN_TX_VEND_INT_STATUS2_MASK))
--              return IRQ_NONE;
--
--      phy_trigger_machine(phydev);
--
--      return IRQ_HANDLED;
--}
--
--static int aqr_read_status(struct phy_device *phydev)
--{
--      int val;
--
--      if (phydev->autoneg == AUTONEG_ENABLE) {
--              val = phy_read_mmd(phydev, MDIO_MMD_AN, MDIO_AN_RX_LP_STAT1);
--              if (val < 0)
--                      return val;
--
--              linkmode_mod_bit(ETHTOOL_LINK_MODE_1000baseT_Full_BIT,
--                               phydev->lp_advertising,
--                               val & MDIO_AN_RX_LP_STAT1_1000BASET_FULL);
--              linkmode_mod_bit(ETHTOOL_LINK_MODE_1000baseT_Half_BIT,
--                               phydev->lp_advertising,
--                               val & MDIO_AN_RX_LP_STAT1_1000BASET_HALF);
--      }
--
--      return genphy_c45_read_status(phydev);
--}
--
--static int aqr107_read_rate(struct phy_device *phydev)
--{
--      u32 config_reg;
--      int val;
--
--      val = phy_read_mmd(phydev, MDIO_MMD_AN, MDIO_AN_TX_VEND_STATUS1);
--      if (val < 0)
--              return val;
--
--      if (val & MDIO_AN_TX_VEND_STATUS1_FULL_DUPLEX)
--              phydev->duplex = DUPLEX_FULL;
--      else
--              phydev->duplex = DUPLEX_HALF;
--
--      switch (FIELD_GET(MDIO_AN_TX_VEND_STATUS1_RATE_MASK, val)) {
--      case MDIO_AN_TX_VEND_STATUS1_10BASET:
--              phydev->speed = SPEED_10;
--              config_reg = VEND1_GLOBAL_CFG_10M;
--              break;
--      case MDIO_AN_TX_VEND_STATUS1_100BASETX:
--              phydev->speed = SPEED_100;
--              config_reg = VEND1_GLOBAL_CFG_100M;
--              break;
--      case MDIO_AN_TX_VEND_STATUS1_1000BASET:
--              phydev->speed = SPEED_1000;
--              config_reg = VEND1_GLOBAL_CFG_1G;
--              break;
--      case MDIO_AN_TX_VEND_STATUS1_2500BASET:
--              phydev->speed = SPEED_2500;
--              config_reg = VEND1_GLOBAL_CFG_2_5G;
--              break;
--      case MDIO_AN_TX_VEND_STATUS1_5000BASET:
--              phydev->speed = SPEED_5000;
--              config_reg = VEND1_GLOBAL_CFG_5G;
--              break;
--      case MDIO_AN_TX_VEND_STATUS1_10GBASET:
--              phydev->speed = SPEED_10000;
--              config_reg = VEND1_GLOBAL_CFG_10G;
--              break;
--      default:
--              phydev->speed = SPEED_UNKNOWN;
--              return 0;
--      }
--
--      val = phy_read_mmd(phydev, MDIO_MMD_VEND1, config_reg);
--      if (val < 0)
--              return val;
--
--      if (FIELD_GET(VEND1_GLOBAL_CFG_RATE_ADAPT, val) ==
--          VEND1_GLOBAL_CFG_RATE_ADAPT_PAUSE)
--              phydev->rate_matching = RATE_MATCH_PAUSE;
--      else
--              phydev->rate_matching = RATE_MATCH_NONE;
--
--      return 0;
--}
--
--static int aqr107_read_status(struct phy_device *phydev)
--{
--      int val, ret;
--
--      ret = aqr_read_status(phydev);
--      if (ret)
--              return ret;
--
--      if (!phydev->link || phydev->autoneg == AUTONEG_DISABLE)
--              return 0;
--
--      val = phy_read_mmd(phydev, MDIO_MMD_PHYXS, MDIO_PHYXS_VEND_IF_STATUS);
--      if (val < 0)
--              return val;
--
--      switch (FIELD_GET(MDIO_PHYXS_VEND_IF_STATUS_TYPE_MASK, val)) {
--      case MDIO_PHYXS_VEND_IF_STATUS_TYPE_KR:
--              phydev->interface = PHY_INTERFACE_MODE_10GKR;
--              break;
--      case MDIO_PHYXS_VEND_IF_STATUS_TYPE_KX:
--              phydev->interface = PHY_INTERFACE_MODE_1000BASEKX;
--              break;
--      case MDIO_PHYXS_VEND_IF_STATUS_TYPE_XFI:
--              phydev->interface = PHY_INTERFACE_MODE_10GBASER;
--              break;
--      case MDIO_PHYXS_VEND_IF_STATUS_TYPE_USXGMII:
--              phydev->interface = PHY_INTERFACE_MODE_USXGMII;
--              break;
--      case MDIO_PHYXS_VEND_IF_STATUS_TYPE_XAUI:
--              phydev->interface = PHY_INTERFACE_MODE_XAUI;
--              break;
--      case MDIO_PHYXS_VEND_IF_STATUS_TYPE_SGMII:
--              phydev->interface = PHY_INTERFACE_MODE_SGMII;
--              break;
--      case MDIO_PHYXS_VEND_IF_STATUS_TYPE_RXAUI:
--              phydev->interface = PHY_INTERFACE_MODE_RXAUI;
--              break;
--      case MDIO_PHYXS_VEND_IF_STATUS_TYPE_OCSGMII:
--              phydev->interface = PHY_INTERFACE_MODE_2500BASEX;
--              break;
--      default:
--              phydev->interface = PHY_INTERFACE_MODE_NA;
--              break;
--      }
--
--      /* Read possibly downshifted rate from vendor register */
--      return aqr107_read_rate(phydev);
--}
--
--static int aqr107_get_downshift(struct phy_device *phydev, u8 *data)
--{
--      int val, cnt, enable;
--
--      val = phy_read_mmd(phydev, MDIO_MMD_AN, MDIO_AN_VEND_PROV);
--      if (val < 0)
--              return val;
--
--      enable = FIELD_GET(MDIO_AN_VEND_PROV_DOWNSHIFT_EN, val);
--      cnt = FIELD_GET(MDIO_AN_VEND_PROV_DOWNSHIFT_MASK, val);
--
--      *data = enable && cnt ? cnt : DOWNSHIFT_DEV_DISABLE;
--
--      return 0;
--}
--
--static int aqr107_set_downshift(struct phy_device *phydev, u8 cnt)
--{
--      int val = 0;
--
--      if (!FIELD_FIT(MDIO_AN_VEND_PROV_DOWNSHIFT_MASK, cnt))
--              return -E2BIG;
--
--      if (cnt != DOWNSHIFT_DEV_DISABLE) {
--              val = MDIO_AN_VEND_PROV_DOWNSHIFT_EN;
--              val |= FIELD_PREP(MDIO_AN_VEND_PROV_DOWNSHIFT_MASK, cnt);
--      }
--
--      return phy_modify_mmd(phydev, MDIO_MMD_AN, MDIO_AN_VEND_PROV,
--                            MDIO_AN_VEND_PROV_DOWNSHIFT_EN |
--                            MDIO_AN_VEND_PROV_DOWNSHIFT_MASK, val);
--}
--
--static int aqr107_get_tunable(struct phy_device *phydev,
--                            struct ethtool_tunable *tuna, void *data)
--{
--      switch (tuna->id) {
--      case ETHTOOL_PHY_DOWNSHIFT:
--              return aqr107_get_downshift(phydev, data);
--      default:
--              return -EOPNOTSUPP;
--      }
--}
--
--static int aqr107_set_tunable(struct phy_device *phydev,
--                            struct ethtool_tunable *tuna, const void *data)
--{
--      switch (tuna->id) {
--      case ETHTOOL_PHY_DOWNSHIFT:
--              return aqr107_set_downshift(phydev, *(const u8 *)data);
--      default:
--              return -EOPNOTSUPP;
--      }
--}
--
--/* If we configure settings whilst firmware is still initializing the chip,
-- * then these settings may be overwritten. Therefore make sure chip
-- * initialization has completed. Use presence of the firmware ID as
-- * indicator for initialization having completed.
-- * The chip also provides a "reset completed" bit, but it's cleared after
-- * read. Therefore function would time out if called again.
-- */
--static int aqr107_wait_reset_complete(struct phy_device *phydev)
--{
--      int val;
--
--      return phy_read_mmd_poll_timeout(phydev, MDIO_MMD_VEND1,
--                                       VEND1_GLOBAL_FW_ID, val, val != 0,
--                                       20000, 2000000, false);
--}
--
--static void aqr107_chip_info(struct phy_device *phydev)
--{
--      u8 fw_major, fw_minor, build_id, prov_id;
--      int val;
--
--      val = phy_read_mmd(phydev, MDIO_MMD_VEND1, VEND1_GLOBAL_FW_ID);
--      if (val < 0)
--              return;
--
--      fw_major = FIELD_GET(VEND1_GLOBAL_FW_ID_MAJOR, val);
--      fw_minor = FIELD_GET(VEND1_GLOBAL_FW_ID_MINOR, val);
--
--      val = phy_read_mmd(phydev, MDIO_MMD_VEND1, VEND1_GLOBAL_RSVD_STAT1);
--      if (val < 0)
--              return;
--
--      build_id = FIELD_GET(VEND1_GLOBAL_RSVD_STAT1_FW_BUILD_ID, val);
--      prov_id = FIELD_GET(VEND1_GLOBAL_RSVD_STAT1_PROV_ID, val);
--
--      phydev_dbg(phydev, "FW %u.%u, Build %u, Provisioning %u\n",
--                 fw_major, fw_minor, build_id, prov_id);
--}
--
--static int aqr107_config_init(struct phy_device *phydev)
--{
--      int ret;
--
--      /* Check that the PHY interface type is compatible */
--      if (phydev->interface != PHY_INTERFACE_MODE_SGMII &&
--          phydev->interface != PHY_INTERFACE_MODE_1000BASEKX &&
--          phydev->interface != PHY_INTERFACE_MODE_2500BASEX &&
--          phydev->interface != PHY_INTERFACE_MODE_XGMII &&
--          phydev->interface != PHY_INTERFACE_MODE_USXGMII &&
--          phydev->interface != PHY_INTERFACE_MODE_10GKR &&
--          phydev->interface != PHY_INTERFACE_MODE_10GBASER &&
--          phydev->interface != PHY_INTERFACE_MODE_XAUI &&
--          phydev->interface != PHY_INTERFACE_MODE_RXAUI)
--              return -ENODEV;
--
--      WARN(phydev->interface == PHY_INTERFACE_MODE_XGMII,
--           "Your devicetree is out of date, please update it. The AQR107 family doesn't support XGMII, maybe you mean USXGMII.\n");
--
--      ret = aqr107_wait_reset_complete(phydev);
--      if (!ret)
--              aqr107_chip_info(phydev);
--
--      return aqr107_set_downshift(phydev, MDIO_AN_VEND_PROV_DOWNSHIFT_DFLT);
--}
--
--static int aqcs109_config_init(struct phy_device *phydev)
--{
--      int ret;
--
--      /* Check that the PHY interface type is compatible */
--      if (phydev->interface != PHY_INTERFACE_MODE_SGMII &&
--          phydev->interface != PHY_INTERFACE_MODE_2500BASEX)
--              return -ENODEV;
--
--      ret = aqr107_wait_reset_complete(phydev);
--      if (!ret)
--              aqr107_chip_info(phydev);
--
--      /* AQCS109 belongs to a chip family partially supporting 10G and 5G.
--       * PMA speed ability bits are the same for all members of the family,
--       * AQCS109 however supports speeds up to 2.5G only.
--       */
--      ret = phy_set_max_speed(phydev, SPEED_2500);
--      if (ret)
--              return ret;
--
--      return aqr107_set_downshift(phydev, MDIO_AN_VEND_PROV_DOWNSHIFT_DFLT);
--}
--
--static void aqr107_link_change_notify(struct phy_device *phydev)
--{
--      u8 fw_major, fw_minor;
--      bool downshift, short_reach, afr;
--      int mode, val;
--
--      if (phydev->state != PHY_RUNNING || phydev->autoneg == AUTONEG_DISABLE)
--              return;
--
--      val = phy_read_mmd(phydev, MDIO_MMD_AN, MDIO_AN_RX_LP_STAT1);
--      /* call failed or link partner is no Aquantia PHY */
--      if (val < 0 || !(val & MDIO_AN_RX_LP_STAT1_AQ_PHY))
--              return;
--
--      short_reach = val & MDIO_AN_RX_LP_STAT1_SHORT_REACH;
--      downshift = val & MDIO_AN_RX_LP_STAT1_AQRATE_DOWNSHIFT;
--
--      val = phy_read_mmd(phydev, MDIO_MMD_AN, MDIO_AN_RX_LP_STAT4);
--      if (val < 0)
--              return;
--
--      fw_major = FIELD_GET(MDIO_AN_RX_LP_STAT4_FW_MAJOR, val);
--      fw_minor = FIELD_GET(MDIO_AN_RX_LP_STAT4_FW_MINOR, val);
--
--      val = phy_read_mmd(phydev, MDIO_MMD_AN, MDIO_AN_RX_VEND_STAT3);
--      if (val < 0)
--              return;
--
--      afr = val & MDIO_AN_RX_VEND_STAT3_AFR;
--
--      phydev_dbg(phydev, "Link partner is Aquantia PHY, FW %u.%u%s%s%s\n",
--                 fw_major, fw_minor,
--                 short_reach ? ", short reach mode" : "",
--                 downshift ? ", fast-retrain downshift advertised" : "",
--                 afr ? ", fast reframe advertised" : "");
--
--      val = phy_read_mmd(phydev, MDIO_MMD_VEND1, VEND1_GLOBAL_RSVD_STAT9);
--      if (val < 0)
--              return;
--
--      mode = FIELD_GET(VEND1_GLOBAL_RSVD_STAT9_MODE, val);
--      if (mode == VEND1_GLOBAL_RSVD_STAT9_1000BT2)
--              phydev_info(phydev, "Aquantia 1000Base-T2 mode active\n");
--}
--
--static int aqr107_wait_processor_intensive_op(struct phy_device *phydev)
--{
--      int val, err;
--
--      /* The datasheet notes to wait at least 1ms after issuing a
--       * processor intensive operation before checking.
--       * We cannot use the 'sleep_before_read' parameter of read_poll_timeout
--       * because that just determines the maximum time slept, not the minimum.
--       */
--      usleep_range(1000, 5000);
--
--      err = phy_read_mmd_poll_timeout(phydev, MDIO_MMD_VEND1,
--                                      VEND1_GLOBAL_GEN_STAT2, val,
--                                      !(val & VEND1_GLOBAL_GEN_STAT2_OP_IN_PROG),
--                                      AQR107_OP_IN_PROG_SLEEP,
--                                      AQR107_OP_IN_PROG_TIMEOUT, false);
--      if (err) {
--              phydev_err(phydev, "timeout: processor-intensive MDIO operation\n");
--              return err;
--      }
--
--      return 0;
--}
--
--static int aqr107_get_rate_matching(struct phy_device *phydev,
--                                  phy_interface_t iface)
--{
--      if (iface == PHY_INTERFACE_MODE_10GBASER ||
--          iface == PHY_INTERFACE_MODE_2500BASEX ||
--          iface == PHY_INTERFACE_MODE_NA)
--              return RATE_MATCH_PAUSE;
--      return RATE_MATCH_NONE;
--}
--
--static int aqr107_suspend(struct phy_device *phydev)
--{
--      int err;
--
--      err = phy_set_bits_mmd(phydev, MDIO_MMD_VEND1, MDIO_CTRL1,
--                             MDIO_CTRL1_LPOWER);
--      if (err)
--              return err;
--
--      return aqr107_wait_processor_intensive_op(phydev);
--}
--
--static int aqr107_resume(struct phy_device *phydev)
--{
--      int err;
--
--      err = phy_clear_bits_mmd(phydev, MDIO_MMD_VEND1, MDIO_CTRL1,
--                               MDIO_CTRL1_LPOWER);
--      if (err)
--              return err;
--
--      return aqr107_wait_processor_intensive_op(phydev);
--}
--
--static int aqr107_probe(struct phy_device *phydev)
--{
--      phydev->priv = devm_kzalloc(&phydev->mdio.dev,
--                                  sizeof(struct aqr107_priv), GFP_KERNEL);
--      if (!phydev->priv)
--              return -ENOMEM;
--
--      return aqr_hwmon_probe(phydev);
--}
--
--static struct phy_driver aqr_driver[] = {
--{
--      PHY_ID_MATCH_MODEL(PHY_ID_AQ1202),
--      .name           = "Aquantia AQ1202",
--      .config_aneg    = aqr_config_aneg,
--      .config_intr    = aqr_config_intr,
--      .handle_interrupt = aqr_handle_interrupt,
--      .read_status    = aqr_read_status,
--},
--{
--      PHY_ID_MATCH_MODEL(PHY_ID_AQ2104),
--      .name           = "Aquantia AQ2104",
--      .config_aneg    = aqr_config_aneg,
--      .config_intr    = aqr_config_intr,
--      .handle_interrupt = aqr_handle_interrupt,
--      .read_status    = aqr_read_status,
--},
--{
--      PHY_ID_MATCH_MODEL(PHY_ID_AQR105),
--      .name           = "Aquantia AQR105",
--      .config_aneg    = aqr_config_aneg,
--      .config_intr    = aqr_config_intr,
--      .handle_interrupt = aqr_handle_interrupt,
--      .read_status    = aqr_read_status,
--      .suspend        = aqr107_suspend,
--      .resume         = aqr107_resume,
--},
--{
--      PHY_ID_MATCH_MODEL(PHY_ID_AQR106),
--      .name           = "Aquantia AQR106",
--      .config_aneg    = aqr_config_aneg,
--      .config_intr    = aqr_config_intr,
--      .handle_interrupt = aqr_handle_interrupt,
--      .read_status    = aqr_read_status,
--},
--{
--      PHY_ID_MATCH_MODEL(PHY_ID_AQR107),
--      .name           = "Aquantia AQR107",
--      .probe          = aqr107_probe,
--      .get_rate_matching = aqr107_get_rate_matching,
--      .config_init    = aqr107_config_init,
--      .config_aneg    = aqr_config_aneg,
--      .config_intr    = aqr_config_intr,
--      .handle_interrupt = aqr_handle_interrupt,
--      .read_status    = aqr107_read_status,
--      .get_tunable    = aqr107_get_tunable,
--      .set_tunable    = aqr107_set_tunable,
--      .suspend        = aqr107_suspend,
--      .resume         = aqr107_resume,
--      .get_sset_count = aqr107_get_sset_count,
--      .get_strings    = aqr107_get_strings,
--      .get_stats      = aqr107_get_stats,
--      .link_change_notify = aqr107_link_change_notify,
--},
--{
--      PHY_ID_MATCH_MODEL(PHY_ID_AQCS109),
--      .name           = "Aquantia AQCS109",
--      .probe          = aqr107_probe,
--      .get_rate_matching = aqr107_get_rate_matching,
--      .config_init    = aqcs109_config_init,
--      .config_aneg    = aqr_config_aneg,
--      .config_intr    = aqr_config_intr,
--      .handle_interrupt = aqr_handle_interrupt,
--      .read_status    = aqr107_read_status,
--      .get_tunable    = aqr107_get_tunable,
--      .set_tunable    = aqr107_set_tunable,
--      .suspend        = aqr107_suspend,
--      .resume         = aqr107_resume,
--      .get_sset_count = aqr107_get_sset_count,
--      .get_strings    = aqr107_get_strings,
--      .get_stats      = aqr107_get_stats,
--      .link_change_notify = aqr107_link_change_notify,
--},
--{
--      PHY_ID_MATCH_MODEL(PHY_ID_AQR405),
--      .name           = "Aquantia AQR405",
--      .config_aneg    = aqr_config_aneg,
--      .config_intr    = aqr_config_intr,
--      .handle_interrupt = aqr_handle_interrupt,
--      .read_status    = aqr_read_status,
--},
--{
--      PHY_ID_MATCH_MODEL(PHY_ID_AQR113C),
--      .name           = "Aquantia AQR113C",
--      .probe          = aqr107_probe,
--      .get_rate_matching = aqr107_get_rate_matching,
--      .config_init    = aqr107_config_init,
--      .config_aneg    = aqr_config_aneg,
--      .config_intr    = aqr_config_intr,
--      .handle_interrupt       = aqr_handle_interrupt,
--      .read_status    = aqr107_read_status,
--      .get_tunable    = aqr107_get_tunable,
--      .set_tunable    = aqr107_set_tunable,
--      .suspend        = aqr107_suspend,
--      .resume         = aqr107_resume,
--      .get_sset_count = aqr107_get_sset_count,
--      .get_strings    = aqr107_get_strings,
--      .get_stats      = aqr107_get_stats,
--      .link_change_notify = aqr107_link_change_notify,
--},
--};
--
--module_phy_driver(aqr_driver);
--
--static struct mdio_device_id __maybe_unused aqr_tbl[] = {
--      { PHY_ID_MATCH_MODEL(PHY_ID_AQ1202) },
--      { PHY_ID_MATCH_MODEL(PHY_ID_AQ2104) },
--      { PHY_ID_MATCH_MODEL(PHY_ID_AQR105) },
--      { PHY_ID_MATCH_MODEL(PHY_ID_AQR106) },
--      { PHY_ID_MATCH_MODEL(PHY_ID_AQR107) },
--      { PHY_ID_MATCH_MODEL(PHY_ID_AQCS109) },
--      { PHY_ID_MATCH_MODEL(PHY_ID_AQR405) },
--      { PHY_ID_MATCH_MODEL(PHY_ID_AQR113C) },
--      { }
--};
--
--MODULE_DEVICE_TABLE(mdio, aqr_tbl);
--
--MODULE_DESCRIPTION("Aquantia PHY driver");
--MODULE_AUTHOR("Shaohui Xie <[email protected]>");
--MODULE_LICENSE("GPL v2");
diff --git a/target/linux/generic/backport-5.15/737-02-v6.7-net-phy-aquantia-move-MMD_VEND-define-to-header.patch b/target/linux/generic/backport-5.15/737-02-v6.7-net-phy-aquantia-move-MMD_VEND-define-to-header.patch
deleted file mode 100644 (file)
index 2b94522..0000000
+++ /dev/null
@@ -1,183 +0,0 @@
-From e1fbfa4a995d42e02e22b0dff2f8b4fdee1504b3 Mon Sep 17 00:00:00 2001
-From: Christian Marangi <[email protected]>
-Date: Tue, 14 Nov 2023 15:08:42 +0100
-Subject: [PATCH 2/3] net: phy: aquantia: move MMD_VEND define to header
-
-Move MMD_VEND define to header to clean things up and in preparation for
-firmware loading support that require some define placed in
-aquantia_main.
-
-Signed-off-by: Christian Marangi <[email protected]>
-Reviewed-by: Andrew Lunn <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/phy/aquantia/aquantia.h       | 69 +++++++++++++++++++++++
- drivers/net/phy/aquantia/aquantia_hwmon.c | 14 -----
- drivers/net/phy/aquantia/aquantia_main.c  | 55 ------------------
- 3 files changed, 69 insertions(+), 69 deletions(-)
-
---- a/drivers/net/phy/aquantia/aquantia.h
-+++ b/drivers/net/phy/aquantia/aquantia.h
-@@ -9,6 +9,75 @@
- #include <linux/device.h>
- #include <linux/phy.h>
-+/* Vendor specific 1, MDIO_MMD_VEND1 */
-+#define VEND1_GLOBAL_FW_ID                    0x0020
-+#define VEND1_GLOBAL_FW_ID_MAJOR              GENMASK(15, 8)
-+#define VEND1_GLOBAL_FW_ID_MINOR              GENMASK(7, 0)
-+
-+/* The following registers all have similar layouts; first the registers... */
-+#define VEND1_GLOBAL_CFG_10M                  0x0310
-+#define VEND1_GLOBAL_CFG_100M                 0x031b
-+#define VEND1_GLOBAL_CFG_1G                   0x031c
-+#define VEND1_GLOBAL_CFG_2_5G                 0x031d
-+#define VEND1_GLOBAL_CFG_5G                   0x031e
-+#define VEND1_GLOBAL_CFG_10G                  0x031f
-+/* ...and now the fields */
-+#define VEND1_GLOBAL_CFG_RATE_ADAPT           GENMASK(8, 7)
-+#define VEND1_GLOBAL_CFG_RATE_ADAPT_NONE      0
-+#define VEND1_GLOBAL_CFG_RATE_ADAPT_USX               1
-+#define VEND1_GLOBAL_CFG_RATE_ADAPT_PAUSE     2
-+
-+/* Vendor specific 1, MDIO_MMD_VEND2 */
-+#define VEND1_THERMAL_PROV_HIGH_TEMP_FAIL     0xc421
-+#define VEND1_THERMAL_PROV_LOW_TEMP_FAIL      0xc422
-+#define VEND1_THERMAL_PROV_HIGH_TEMP_WARN     0xc423
-+#define VEND1_THERMAL_PROV_LOW_TEMP_WARN      0xc424
-+#define VEND1_THERMAL_STAT1                   0xc820
-+#define VEND1_THERMAL_STAT2                   0xc821
-+#define VEND1_THERMAL_STAT2_VALID             BIT(0)
-+#define VEND1_GENERAL_STAT1                   0xc830
-+#define VEND1_GENERAL_STAT1_HIGH_TEMP_FAIL    BIT(14)
-+#define VEND1_GENERAL_STAT1_LOW_TEMP_FAIL     BIT(13)
-+#define VEND1_GENERAL_STAT1_HIGH_TEMP_WARN    BIT(12)
-+#define VEND1_GENERAL_STAT1_LOW_TEMP_WARN     BIT(11)
-+
-+#define VEND1_GLOBAL_GEN_STAT2                        0xc831
-+#define VEND1_GLOBAL_GEN_STAT2_OP_IN_PROG     BIT(15)
-+
-+#define VEND1_GLOBAL_RSVD_STAT1                       0xc885
-+#define VEND1_GLOBAL_RSVD_STAT1_FW_BUILD_ID   GENMASK(7, 4)
-+#define VEND1_GLOBAL_RSVD_STAT1_PROV_ID               GENMASK(3, 0)
-+
-+#define VEND1_GLOBAL_RSVD_STAT9                       0xc88d
-+#define VEND1_GLOBAL_RSVD_STAT9_MODE          GENMASK(7, 0)
-+#define VEND1_GLOBAL_RSVD_STAT9_1000BT2               0x23
-+
-+#define VEND1_GLOBAL_INT_STD_STATUS           0xfc00
-+#define VEND1_GLOBAL_INT_VEND_STATUS          0xfc01
-+
-+#define VEND1_GLOBAL_INT_STD_MASK             0xff00
-+#define VEND1_GLOBAL_INT_STD_MASK_PMA1                BIT(15)
-+#define VEND1_GLOBAL_INT_STD_MASK_PMA2                BIT(14)
-+#define VEND1_GLOBAL_INT_STD_MASK_PCS1                BIT(13)
-+#define VEND1_GLOBAL_INT_STD_MASK_PCS2                BIT(12)
-+#define VEND1_GLOBAL_INT_STD_MASK_PCS3                BIT(11)
-+#define VEND1_GLOBAL_INT_STD_MASK_PHY_XS1     BIT(10)
-+#define VEND1_GLOBAL_INT_STD_MASK_PHY_XS2     BIT(9)
-+#define VEND1_GLOBAL_INT_STD_MASK_AN1         BIT(8)
-+#define VEND1_GLOBAL_INT_STD_MASK_AN2         BIT(7)
-+#define VEND1_GLOBAL_INT_STD_MASK_GBE         BIT(6)
-+#define VEND1_GLOBAL_INT_STD_MASK_ALL         BIT(0)
-+
-+#define VEND1_GLOBAL_INT_VEND_MASK            0xff01
-+#define VEND1_GLOBAL_INT_VEND_MASK_PMA                BIT(15)
-+#define VEND1_GLOBAL_INT_VEND_MASK_PCS                BIT(14)
-+#define VEND1_GLOBAL_INT_VEND_MASK_PHY_XS     BIT(13)
-+#define VEND1_GLOBAL_INT_VEND_MASK_AN         BIT(12)
-+#define VEND1_GLOBAL_INT_VEND_MASK_GBE                BIT(11)
-+#define VEND1_GLOBAL_INT_VEND_MASK_GLOBAL1    BIT(2)
-+#define VEND1_GLOBAL_INT_VEND_MASK_GLOBAL2    BIT(1)
-+#define VEND1_GLOBAL_INT_VEND_MASK_GLOBAL3    BIT(0)
-+
- #if IS_REACHABLE(CONFIG_HWMON)
- int aqr_hwmon_probe(struct phy_device *phydev);
- #else
---- a/drivers/net/phy/aquantia/aquantia_hwmon.c
-+++ b/drivers/net/phy/aquantia/aquantia_hwmon.c
-@@ -13,20 +13,6 @@
- #include "aquantia.h"
--/* Vendor specific 1, MDIO_MMD_VEND2 */
--#define VEND1_THERMAL_PROV_HIGH_TEMP_FAIL     0xc421
--#define VEND1_THERMAL_PROV_LOW_TEMP_FAIL      0xc422
--#define VEND1_THERMAL_PROV_HIGH_TEMP_WARN     0xc423
--#define VEND1_THERMAL_PROV_LOW_TEMP_WARN      0xc424
--#define VEND1_THERMAL_STAT1                   0xc820
--#define VEND1_THERMAL_STAT2                   0xc821
--#define VEND1_THERMAL_STAT2_VALID             BIT(0)
--#define VEND1_GENERAL_STAT1                   0xc830
--#define VEND1_GENERAL_STAT1_HIGH_TEMP_FAIL    BIT(14)
--#define VEND1_GENERAL_STAT1_LOW_TEMP_FAIL     BIT(13)
--#define VEND1_GENERAL_STAT1_HIGH_TEMP_WARN    BIT(12)
--#define VEND1_GENERAL_STAT1_LOW_TEMP_WARN     BIT(11)
--
- #if IS_REACHABLE(CONFIG_HWMON)
- static umode_t aqr_hwmon_is_visible(const void *data,
---- a/drivers/net/phy/aquantia/aquantia_main.c
-+++ b/drivers/net/phy/aquantia/aquantia_main.c
-@@ -89,61 +89,6 @@
- #define MDIO_C22EXT_STAT_SGMII_TX_FRAME_ALIGN_ERR     0xd31a
- #define MDIO_C22EXT_STAT_SGMII_TX_RUNT_FRAMES         0xd31b
--/* Vendor specific 1, MDIO_MMD_VEND1 */
--#define VEND1_GLOBAL_FW_ID                    0x0020
--#define VEND1_GLOBAL_FW_ID_MAJOR              GENMASK(15, 8)
--#define VEND1_GLOBAL_FW_ID_MINOR              GENMASK(7, 0)
--
--#define VEND1_GLOBAL_GEN_STAT2                        0xc831
--#define VEND1_GLOBAL_GEN_STAT2_OP_IN_PROG     BIT(15)
--
--/* The following registers all have similar layouts; first the registers... */
--#define VEND1_GLOBAL_CFG_10M                  0x0310
--#define VEND1_GLOBAL_CFG_100M                 0x031b
--#define VEND1_GLOBAL_CFG_1G                   0x031c
--#define VEND1_GLOBAL_CFG_2_5G                 0x031d
--#define VEND1_GLOBAL_CFG_5G                   0x031e
--#define VEND1_GLOBAL_CFG_10G                  0x031f
--/* ...and now the fields */
--#define VEND1_GLOBAL_CFG_RATE_ADAPT           GENMASK(8, 7)
--#define VEND1_GLOBAL_CFG_RATE_ADAPT_NONE      0
--#define VEND1_GLOBAL_CFG_RATE_ADAPT_USX               1
--#define VEND1_GLOBAL_CFG_RATE_ADAPT_PAUSE     2
--
--#define VEND1_GLOBAL_RSVD_STAT1                       0xc885
--#define VEND1_GLOBAL_RSVD_STAT1_FW_BUILD_ID   GENMASK(7, 4)
--#define VEND1_GLOBAL_RSVD_STAT1_PROV_ID               GENMASK(3, 0)
--
--#define VEND1_GLOBAL_RSVD_STAT9                       0xc88d
--#define VEND1_GLOBAL_RSVD_STAT9_MODE          GENMASK(7, 0)
--#define VEND1_GLOBAL_RSVD_STAT9_1000BT2               0x23
--
--#define VEND1_GLOBAL_INT_STD_STATUS           0xfc00
--#define VEND1_GLOBAL_INT_VEND_STATUS          0xfc01
--
--#define VEND1_GLOBAL_INT_STD_MASK             0xff00
--#define VEND1_GLOBAL_INT_STD_MASK_PMA1                BIT(15)
--#define VEND1_GLOBAL_INT_STD_MASK_PMA2                BIT(14)
--#define VEND1_GLOBAL_INT_STD_MASK_PCS1                BIT(13)
--#define VEND1_GLOBAL_INT_STD_MASK_PCS2                BIT(12)
--#define VEND1_GLOBAL_INT_STD_MASK_PCS3                BIT(11)
--#define VEND1_GLOBAL_INT_STD_MASK_PHY_XS1     BIT(10)
--#define VEND1_GLOBAL_INT_STD_MASK_PHY_XS2     BIT(9)
--#define VEND1_GLOBAL_INT_STD_MASK_AN1         BIT(8)
--#define VEND1_GLOBAL_INT_STD_MASK_AN2         BIT(7)
--#define VEND1_GLOBAL_INT_STD_MASK_GBE         BIT(6)
--#define VEND1_GLOBAL_INT_STD_MASK_ALL         BIT(0)
--
--#define VEND1_GLOBAL_INT_VEND_MASK            0xff01
--#define VEND1_GLOBAL_INT_VEND_MASK_PMA                BIT(15)
--#define VEND1_GLOBAL_INT_VEND_MASK_PCS                BIT(14)
--#define VEND1_GLOBAL_INT_VEND_MASK_PHY_XS     BIT(13)
--#define VEND1_GLOBAL_INT_VEND_MASK_AN         BIT(12)
--#define VEND1_GLOBAL_INT_VEND_MASK_GBE                BIT(11)
--#define VEND1_GLOBAL_INT_VEND_MASK_GLOBAL1    BIT(2)
--#define VEND1_GLOBAL_INT_VEND_MASK_GLOBAL2    BIT(1)
--#define VEND1_GLOBAL_INT_VEND_MASK_GLOBAL3    BIT(0)
--
- /* Sleep and timeout for checking if the Processor-Intensive
-  * MDIO operation is finished
-  */
diff --git a/target/linux/generic/backport-5.15/737-03-v6.7-net-phy-aquantia-add-firmware-load-support.patch b/target/linux/generic/backport-5.15/737-03-v6.7-net-phy-aquantia-add-firmware-load-support.patch
deleted file mode 100644 (file)
index 1ae5966..0000000
+++ /dev/null
@@ -1,504 +0,0 @@
-From e93984ebc1c82bd34f7a1b3391efaceee0a8ae96 Mon Sep 17 00:00:00 2001
-From: Robert Marko <[email protected]>
-Date: Tue, 14 Nov 2023 15:08:43 +0100
-Subject: [PATCH 3/3] net: phy: aquantia: add firmware load support
-
-Aquantia PHY-s require firmware to be loaded before they start operating.
-It can be automatically loaded in case when there is a SPI-NOR connected
-to Aquantia PHY-s or can be loaded from the host via MDIO.
-
-This patch adds support for loading the firmware via MDIO as in most cases
-there is no SPI-NOR being used to save on cost.
-Firmware loading code itself is ported from mainline U-boot with cleanups.
-
-The firmware has mixed values both in big and little endian.
-PHY core itself is big-endian but it expects values to be in little-endian.
-The firmware is little-endian but CRC-16 value for it is stored at the end
-of firmware in big-endian.
-
-It seems the PHY does the conversion internally from firmware that is
-little-endian to the PHY that is big-endian on using the mailbox
-but mailbox returns a big-endian CRC-16 to verify the written data
-integrity.
-
-Co-developed-by: Christian Marangi <[email protected]>
-Signed-off-by: Robert Marko <[email protected]>
-Signed-off-by: Christian Marangi <[email protected]>
-Reviewed-by: Andrew Lunn <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/phy/aquantia/Kconfig             |   1 +
- drivers/net/phy/aquantia/Makefile            |   2 +-
- drivers/net/phy/aquantia/aquantia.h          |  32 ++
- drivers/net/phy/aquantia/aquantia_firmware.c | 370 +++++++++++++++++++
- drivers/net/phy/aquantia/aquantia_main.c     |   6 +
- 5 files changed, 410 insertions(+), 1 deletion(-)
- create mode 100644 drivers/net/phy/aquantia/aquantia_firmware.c
-
---- a/drivers/net/phy/aquantia/Kconfig
-+++ b/drivers/net/phy/aquantia/Kconfig
-@@ -1,5 +1,6 @@
- # SPDX-License-Identifier: GPL-2.0-only
- config AQUANTIA_PHY
-       tristate "Aquantia PHYs"
-+      select CRC_CCITT
-       help
-         Currently supports the Aquantia AQ1202, AQ2104, AQR105, AQR405
---- a/drivers/net/phy/aquantia/Makefile
-+++ b/drivers/net/phy/aquantia/Makefile
-@@ -1,5 +1,5 @@
- # SPDX-License-Identifier: GPL-2.0
--aquantia-objs                 += aquantia_main.o
-+aquantia-objs                 += aquantia_main.o aquantia_firmware.o
- ifdef CONFIG_HWMON
- aquantia-objs                 += aquantia_hwmon.o
- endif
---- a/drivers/net/phy/aquantia/aquantia.h
-+++ b/drivers/net/phy/aquantia/aquantia.h
-@@ -10,10 +10,35 @@
- #include <linux/phy.h>
- /* Vendor specific 1, MDIO_MMD_VEND1 */
-+#define VEND1_GLOBAL_SC                               0x0
-+#define VEND1_GLOBAL_SC_SOFT_RESET            BIT(15)
-+#define VEND1_GLOBAL_SC_LOW_POWER             BIT(11)
-+
- #define VEND1_GLOBAL_FW_ID                    0x0020
- #define VEND1_GLOBAL_FW_ID_MAJOR              GENMASK(15, 8)
- #define VEND1_GLOBAL_FW_ID_MINOR              GENMASK(7, 0)
-+#define VEND1_GLOBAL_MAILBOX_INTERFACE1                       0x0200
-+#define VEND1_GLOBAL_MAILBOX_INTERFACE1_EXECUTE               BIT(15)
-+#define VEND1_GLOBAL_MAILBOX_INTERFACE1_WRITE         BIT(14)
-+#define VEND1_GLOBAL_MAILBOX_INTERFACE1_CRC_RESET     BIT(12)
-+#define VEND1_GLOBAL_MAILBOX_INTERFACE1_BUSY          BIT(8)
-+
-+#define VEND1_GLOBAL_MAILBOX_INTERFACE2                       0x0201
-+#define VEND1_GLOBAL_MAILBOX_INTERFACE3                       0x0202
-+#define VEND1_GLOBAL_MAILBOX_INTERFACE3_MSW_ADDR_MASK GENMASK(15, 0)
-+#define VEND1_GLOBAL_MAILBOX_INTERFACE3_MSW_ADDR(x)   FIELD_PREP(VEND1_GLOBAL_MAILBOX_INTERFACE3_MSW_ADDR_MASK, (u16)((x) >> 16))
-+#define VEND1_GLOBAL_MAILBOX_INTERFACE4                       0x0203
-+#define VEND1_GLOBAL_MAILBOX_INTERFACE4_LSW_ADDR_MASK GENMASK(15, 2)
-+#define VEND1_GLOBAL_MAILBOX_INTERFACE4_LSW_ADDR(x)   FIELD_PREP(VEND1_GLOBAL_MAILBOX_INTERFACE4_LSW_ADDR_MASK, (u16)(x))
-+
-+#define VEND1_GLOBAL_MAILBOX_INTERFACE5                       0x0204
-+#define VEND1_GLOBAL_MAILBOX_INTERFACE5_MSW_DATA_MASK GENMASK(15, 0)
-+#define VEND1_GLOBAL_MAILBOX_INTERFACE5_MSW_DATA(x)   FIELD_PREP(VEND1_GLOBAL_MAILBOX_INTERFACE5_MSW_DATA_MASK, (u16)((x) >> 16))
-+#define VEND1_GLOBAL_MAILBOX_INTERFACE6                       0x0205
-+#define VEND1_GLOBAL_MAILBOX_INTERFACE6_LSW_DATA_MASK GENMASK(15, 0)
-+#define VEND1_GLOBAL_MAILBOX_INTERFACE6_LSW_DATA(x)   FIELD_PREP(VEND1_GLOBAL_MAILBOX_INTERFACE6_LSW_DATA_MASK, (u16)(x))
-+
- /* The following registers all have similar layouts; first the registers... */
- #define VEND1_GLOBAL_CFG_10M                  0x0310
- #define VEND1_GLOBAL_CFG_100M                 0x031b
-@@ -28,6 +53,11 @@
- #define VEND1_GLOBAL_CFG_RATE_ADAPT_PAUSE     2
- /* Vendor specific 1, MDIO_MMD_VEND2 */
-+#define VEND1_GLOBAL_CONTROL2                 0xc001
-+#define VEND1_GLOBAL_CONTROL2_UP_RUN_STALL_RST        BIT(15)
-+#define VEND1_GLOBAL_CONTROL2_UP_RUN_STALL_OVD        BIT(6)
-+#define VEND1_GLOBAL_CONTROL2_UP_RUN_STALL    BIT(0)
-+
- #define VEND1_THERMAL_PROV_HIGH_TEMP_FAIL     0xc421
- #define VEND1_THERMAL_PROV_LOW_TEMP_FAIL      0xc422
- #define VEND1_THERMAL_PROV_HIGH_TEMP_WARN     0xc423
-@@ -83,3 +113,5 @@ int aqr_hwmon_probe(struct phy_device *p
- #else
- static inline int aqr_hwmon_probe(struct phy_device *phydev) { return 0; }
- #endif
-+
-+int aqr_firmware_load(struct phy_device *phydev);
---- /dev/null
-+++ b/drivers/net/phy/aquantia/aquantia_firmware.c
-@@ -0,0 +1,370 @@
-+// SPDX-License-Identifier: GPL-2.0
-+
-+#include <linux/bitfield.h>
-+#include <linux/of.h>
-+#include <linux/firmware.h>
-+#include <linux/crc-ccitt.h>
-+#include <linux/nvmem-consumer.h>
-+
-+#include <asm/unaligned.h>
-+
-+#include "aquantia.h"
-+
-+#define UP_RESET_SLEEP                100
-+
-+/* addresses of memory segments in the phy */
-+#define DRAM_BASE_ADDR                0x3FFE0000
-+#define IRAM_BASE_ADDR                0x40000000
-+
-+/* firmware image format constants */
-+#define VERSION_STRING_SIZE           0x40
-+#define VERSION_STRING_OFFSET         0x0200
-+/* primary offset is written at an offset from the start of the fw blob */
-+#define PRIMARY_OFFSET_OFFSET         0x8
-+/* primary offset needs to be then added to a base offset */
-+#define PRIMARY_OFFSET_SHIFT          12
-+#define PRIMARY_OFFSET(x)             ((x) << PRIMARY_OFFSET_SHIFT)
-+#define HEADER_OFFSET                 0x300
-+
-+struct aqr_fw_header {
-+      u32 padding;
-+      u8 iram_offset[3];
-+      u8 iram_size[3];
-+      u8 dram_offset[3];
-+      u8 dram_size[3];
-+} __packed;
-+
-+enum aqr_fw_src {
-+      AQR_FW_SRC_NVMEM = 0,
-+      AQR_FW_SRC_FS,
-+};
-+
-+static const char * const aqr_fw_src_string[] = {
-+      [AQR_FW_SRC_NVMEM] = "NVMEM",
-+      [AQR_FW_SRC_FS] = "FS",
-+};
-+
-+/* AQR firmware doesn't have fixed offsets for iram and dram section
-+ * but instead provide an header with the offset to use on reading
-+ * and parsing the firmware.
-+ *
-+ * AQR firmware can't be trusted and each offset is validated to be
-+ * not negative and be in the size of the firmware itself.
-+ */
-+static bool aqr_fw_validate_get(size_t size, size_t offset, size_t get_size)
-+{
-+      return offset + get_size <= size;
-+}
-+
-+static int aqr_fw_get_be16(const u8 *data, size_t offset, size_t size, u16 *value)
-+{
-+      if (!aqr_fw_validate_get(size, offset, sizeof(u16)))
-+              return -EINVAL;
-+
-+      *value = get_unaligned_be16(data + offset);
-+
-+      return 0;
-+}
-+
-+static int aqr_fw_get_le16(const u8 *data, size_t offset, size_t size, u16 *value)
-+{
-+      if (!aqr_fw_validate_get(size, offset, sizeof(u16)))
-+              return -EINVAL;
-+
-+      *value = get_unaligned_le16(data + offset);
-+
-+      return 0;
-+}
-+
-+static int aqr_fw_get_le24(const u8 *data, size_t offset, size_t size, u32 *value)
-+{
-+      if (!aqr_fw_validate_get(size, offset, sizeof(u8) * 3))
-+              return -EINVAL;
-+
-+      *value = get_unaligned_le24(data + offset);
-+
-+      return 0;
-+}
-+
-+/* load data into the phy's memory */
-+static int aqr_fw_load_memory(struct phy_device *phydev, u32 addr,
-+                            const u8 *data, size_t len)
-+{
-+      u16 crc = 0, up_crc;
-+      size_t pos;
-+
-+      /* PHY expect addr in LE */
-+      addr = (__force u32)cpu_to_le32(addr);
-+
-+      phy_write_mmd(phydev, MDIO_MMD_VEND1,
-+                    VEND1_GLOBAL_MAILBOX_INTERFACE1,
-+                    VEND1_GLOBAL_MAILBOX_INTERFACE1_CRC_RESET);
-+      phy_write_mmd(phydev, MDIO_MMD_VEND1,
-+                    VEND1_GLOBAL_MAILBOX_INTERFACE3,
-+                    VEND1_GLOBAL_MAILBOX_INTERFACE3_MSW_ADDR(addr));
-+      phy_write_mmd(phydev, MDIO_MMD_VEND1,
-+                    VEND1_GLOBAL_MAILBOX_INTERFACE4,
-+                    VEND1_GLOBAL_MAILBOX_INTERFACE4_LSW_ADDR(addr));
-+
-+      /* We assume and enforce the size to be word aligned.
-+       * If a firmware that is not word aligned is found, please report upstream.
-+       */
-+      for (pos = 0; pos < len; pos += sizeof(u32)) {
-+              u32 word;
-+
-+              /* FW data is always stored in little-endian */
-+              word = get_unaligned((const u32 *)(data + pos));
-+
-+              phy_write_mmd(phydev, MDIO_MMD_VEND1, VEND1_GLOBAL_MAILBOX_INTERFACE5,
-+                            VEND1_GLOBAL_MAILBOX_INTERFACE5_MSW_DATA(word));
-+              phy_write_mmd(phydev, MDIO_MMD_VEND1, VEND1_GLOBAL_MAILBOX_INTERFACE6,
-+                            VEND1_GLOBAL_MAILBOX_INTERFACE6_LSW_DATA(word));
-+
-+              phy_write_mmd(phydev, MDIO_MMD_VEND1, VEND1_GLOBAL_MAILBOX_INTERFACE1,
-+                            VEND1_GLOBAL_MAILBOX_INTERFACE1_EXECUTE |
-+                            VEND1_GLOBAL_MAILBOX_INTERFACE1_WRITE);
-+
-+              /* calculate CRC as we load data to the mailbox.
-+               * We convert word to big-endian as PHY is BE and mailbox will
-+               * return a BE CRC.
-+               */
-+              word = (__force u32)cpu_to_be32(word);
-+              crc = crc_ccitt_false(crc, (u8 *)&word, sizeof(word));
-+      }
-+
-+      up_crc = phy_read_mmd(phydev, MDIO_MMD_VEND1, VEND1_GLOBAL_MAILBOX_INTERFACE2);
-+      if (crc != up_crc) {
-+              phydev_err(phydev, "CRC mismatch: calculated 0x%04x PHY 0x%04x\n",
-+                         crc, up_crc);
-+              return -EINVAL;
-+      }
-+
-+      return 0;
-+}
-+
-+static int aqr_fw_boot(struct phy_device *phydev, const u8 *data, size_t size,
-+                     enum aqr_fw_src fw_src)
-+{
-+      u16 calculated_crc, read_crc, read_primary_offset;
-+      u32 iram_offset = 0, iram_size = 0;
-+      u32 dram_offset = 0, dram_size = 0;
-+      char version[VERSION_STRING_SIZE];
-+      u32 primary_offset = 0;
-+      int ret;
-+
-+      /* extract saved CRC at the end of the fw
-+       * CRC is saved in big-endian as PHY is BE
-+       */
-+      ret = aqr_fw_get_be16(data, size - sizeof(u16), size, &read_crc);
-+      if (ret) {
-+              phydev_err(phydev, "bad firmware CRC in firmware\n");
-+              return ret;
-+      }
-+      calculated_crc = crc_ccitt_false(0, data, size - sizeof(u16));
-+      if (read_crc != calculated_crc) {
-+              phydev_err(phydev, "bad firmware CRC: file 0x%04x calculated 0x%04x\n",
-+                         read_crc, calculated_crc);
-+              return -EINVAL;
-+      }
-+
-+      /* Get the primary offset to extract DRAM and IRAM sections. */
-+      ret = aqr_fw_get_le16(data, PRIMARY_OFFSET_OFFSET, size, &read_primary_offset);
-+      if (ret) {
-+              phydev_err(phydev, "bad primary offset in firmware\n");
-+              return ret;
-+      }
-+      primary_offset = PRIMARY_OFFSET(read_primary_offset);
-+
-+      /* Find the DRAM and IRAM sections within the firmware file.
-+       * Make sure the fw_header is correctly in the firmware.
-+       */
-+      if (!aqr_fw_validate_get(size, primary_offset + HEADER_OFFSET,
-+                               sizeof(struct aqr_fw_header))) {
-+              phydev_err(phydev, "bad fw_header in firmware\n");
-+              return -EINVAL;
-+      }
-+
-+      /* offset are in LE and values needs to be converted to cpu endian */
-+      ret = aqr_fw_get_le24(data, primary_offset + HEADER_OFFSET +
-+                            offsetof(struct aqr_fw_header, iram_offset),
-+                            size, &iram_offset);
-+      if (ret) {
-+              phydev_err(phydev, "bad iram offset in firmware\n");
-+              return ret;
-+      }
-+      ret = aqr_fw_get_le24(data, primary_offset + HEADER_OFFSET +
-+                            offsetof(struct aqr_fw_header, iram_size),
-+                            size, &iram_size);
-+      if (ret) {
-+              phydev_err(phydev, "invalid iram size in firmware\n");
-+              return ret;
-+      }
-+      ret = aqr_fw_get_le24(data, primary_offset + HEADER_OFFSET +
-+                            offsetof(struct aqr_fw_header, dram_offset),
-+                            size, &dram_offset);
-+      if (ret) {
-+              phydev_err(phydev, "bad dram offset in firmware\n");
-+              return ret;
-+      }
-+      ret = aqr_fw_get_le24(data, primary_offset + HEADER_OFFSET +
-+                            offsetof(struct aqr_fw_header, dram_size),
-+                            size, &dram_size);
-+      if (ret) {
-+              phydev_err(phydev, "invalid dram size in firmware\n");
-+              return ret;
-+      }
-+
-+      /* Increment the offset with the primary offset.
-+       * Validate iram/dram offset and size.
-+       */
-+      iram_offset += primary_offset;
-+      if (iram_size % sizeof(u32)) {
-+              phydev_err(phydev, "iram size if not aligned to word size. Please report this upstream!\n");
-+              return -EINVAL;
-+      }
-+      if (!aqr_fw_validate_get(size, iram_offset, iram_size)) {
-+              phydev_err(phydev, "invalid iram offset for iram size\n");
-+              return -EINVAL;
-+      }
-+
-+      dram_offset += primary_offset;
-+      if (dram_size % sizeof(u32)) {
-+              phydev_err(phydev, "dram size if not aligned to word size. Please report this upstream!\n");
-+              return -EINVAL;
-+      }
-+      if (!aqr_fw_validate_get(size, dram_offset, dram_size)) {
-+              phydev_err(phydev, "invalid iram offset for iram size\n");
-+              return -EINVAL;
-+      }
-+
-+      phydev_dbg(phydev, "primary %d IRAM offset=%d size=%d DRAM offset=%d size=%d\n",
-+                 primary_offset, iram_offset, iram_size, dram_offset, dram_size);
-+
-+      if (!aqr_fw_validate_get(size, dram_offset + VERSION_STRING_OFFSET,
-+                               VERSION_STRING_SIZE)) {
-+              phydev_err(phydev, "invalid version in firmware\n");
-+              return -EINVAL;
-+      }
-+      strscpy(version, (char *)data + dram_offset + VERSION_STRING_OFFSET,
-+              VERSION_STRING_SIZE);
-+      if (version[0] == '\0') {
-+              phydev_err(phydev, "invalid version in firmware\n");
-+              return -EINVAL;
-+      }
-+      phydev_info(phydev, "loading firmware version '%s' from '%s'\n", version,
-+                  aqr_fw_src_string[fw_src]);
-+
-+      /* stall the microcprocessor */
-+      phy_write_mmd(phydev, MDIO_MMD_VEND1, VEND1_GLOBAL_CONTROL2,
-+                    VEND1_GLOBAL_CONTROL2_UP_RUN_STALL | VEND1_GLOBAL_CONTROL2_UP_RUN_STALL_OVD);
-+
-+      phydev_dbg(phydev, "loading DRAM 0x%08x from offset=%d size=%d\n",
-+                 DRAM_BASE_ADDR, dram_offset, dram_size);
-+      ret = aqr_fw_load_memory(phydev, DRAM_BASE_ADDR, data + dram_offset,
-+                               dram_size);
-+      if (ret)
-+              return ret;
-+
-+      phydev_dbg(phydev, "loading IRAM 0x%08x from offset=%d size=%d\n",
-+                 IRAM_BASE_ADDR, iram_offset, iram_size);
-+      ret = aqr_fw_load_memory(phydev, IRAM_BASE_ADDR, data + iram_offset,
-+                               iram_size);
-+      if (ret)
-+              return ret;
-+
-+      /* make sure soft reset and low power mode are clear */
-+      phy_clear_bits_mmd(phydev, MDIO_MMD_VEND1, VEND1_GLOBAL_SC,
-+                         VEND1_GLOBAL_SC_SOFT_RESET | VEND1_GLOBAL_SC_LOW_POWER);
-+
-+      /* Release the microprocessor. UP_RESET must be held for 100 usec. */
-+      phy_write_mmd(phydev, MDIO_MMD_VEND1, VEND1_GLOBAL_CONTROL2,
-+                    VEND1_GLOBAL_CONTROL2_UP_RUN_STALL |
-+                    VEND1_GLOBAL_CONTROL2_UP_RUN_STALL_OVD |
-+                    VEND1_GLOBAL_CONTROL2_UP_RUN_STALL_RST);
-+      usleep_range(UP_RESET_SLEEP, UP_RESET_SLEEP * 2);
-+
-+      phy_write_mmd(phydev, MDIO_MMD_VEND1, VEND1_GLOBAL_CONTROL2,
-+                    VEND1_GLOBAL_CONTROL2_UP_RUN_STALL_OVD);
-+
-+      return 0;
-+}
-+
-+static int aqr_firmware_load_nvmem(struct phy_device *phydev)
-+{
-+      struct nvmem_cell *cell;
-+      size_t size;
-+      u8 *buf;
-+      int ret;
-+
-+      cell = nvmem_cell_get(&phydev->mdio.dev, "firmware");
-+      if (IS_ERR(cell))
-+              return PTR_ERR(cell);
-+
-+      buf = nvmem_cell_read(cell, &size);
-+      if (IS_ERR(buf)) {
-+              ret = PTR_ERR(buf);
-+              goto exit;
-+      }
-+
-+      ret = aqr_fw_boot(phydev, buf, size, AQR_FW_SRC_NVMEM);
-+      if (ret)
-+              phydev_err(phydev, "firmware loading failed: %d\n", ret);
-+
-+      kfree(buf);
-+exit:
-+      nvmem_cell_put(cell);
-+
-+      return ret;
-+}
-+
-+static int aqr_firmware_load_fs(struct phy_device *phydev)
-+{
-+      struct device *dev = &phydev->mdio.dev;
-+      const struct firmware *fw;
-+      const char *fw_name;
-+      int ret;
-+
-+      ret = of_property_read_string(dev->of_node, "firmware-name",
-+                                    &fw_name);
-+      if (ret)
-+              return ret;
-+
-+      ret = request_firmware(&fw, fw_name, dev);
-+      if (ret) {
-+              phydev_err(phydev, "failed to find FW file %s (%d)\n",
-+                         fw_name, ret);
-+              return ret;
-+      }
-+
-+      ret = aqr_fw_boot(phydev, fw->data, fw->size, AQR_FW_SRC_FS);
-+      if (ret)
-+              phydev_err(phydev, "firmware loading failed: %d\n", ret);
-+
-+      release_firmware(fw);
-+
-+      return ret;
-+}
-+
-+int aqr_firmware_load(struct phy_device *phydev)
-+{
-+      int ret;
-+
-+      /* Check if the firmware is not already loaded by pooling
-+       * the current version returned by the PHY. If 0 is returned,
-+       * no firmware is loaded.
-+       */
-+      ret = phy_read_mmd(phydev, MDIO_MMD_VEND1, VEND1_GLOBAL_FW_ID);
-+      if (ret > 0)
-+              goto exit;
-+
-+      ret = aqr_firmware_load_nvmem(phydev);
-+      if (!ret)
-+              goto exit;
-+
-+      ret = aqr_firmware_load_fs(phydev);
-+      if (ret)
-+              return ret;
-+
-+exit:
-+      return 0;
-+}
---- a/drivers/net/phy/aquantia/aquantia_main.c
-+++ b/drivers/net/phy/aquantia/aquantia_main.c
-@@ -658,11 +658,17 @@ static int aqr107_resume(struct phy_devi
- static int aqr107_probe(struct phy_device *phydev)
- {
-+      int ret;
-+
-       phydev->priv = devm_kzalloc(&phydev->mdio.dev,
-                                   sizeof(struct aqr107_priv), GFP_KERNEL);
-       if (!phydev->priv)
-               return -ENOMEM;
-+      ret = aqr_firmware_load(phydev);
-+      if (ret)
-+              return ret;
-+
-       return aqr_hwmon_probe(phydev);
- }
diff --git a/target/linux/generic/backport-5.15/738-v6.9-net-phy-aquantia-add-AQR111-and-AQR111B0-PHY-ID.patch b/target/linux/generic/backport-5.15/738-v6.9-net-phy-aquantia-add-AQR111-and-AQR111B0-PHY-ID.patch
deleted file mode 100644 (file)
index d130794..0000000
+++ /dev/null
@@ -1,100 +0,0 @@
-From 038ba1dc4e54d51d953f5618d8eb5dd39bd9de25 Mon Sep 17 00:00:00 2001
-From: Christian Marangi <[email protected]>
-Date: Tue, 13 Feb 2024 14:35:51 +0100
-Subject: [PATCH] net: phy: aquantia: add AQR111 and AQR111B0 PHY ID
-
-Add Aquantia AQR111 and AQR111B0 PHY ID. These PHY advertise 10G speed
-but actually supports up to 5G speed, hence some manual fixup is needed.
-
-The Aquantia AQR111B0 PHY is just a variant of the AQR111 with smaller
-chip size.
-
-Signed-off-by: Christian Marangi <[email protected]>
-Reviewed-by: Andrew Lunn <[email protected]>
-Reviewed-by: Andrew Lunn <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Paolo Abeni <[email protected]>
----
- drivers/net/phy/aquantia/aquantia_main.c | 52 ++++++++++++++++++++++++
- 1 file changed, 52 insertions(+)
-
---- a/drivers/net/phy/aquantia/aquantia_main.c
-+++ b/drivers/net/phy/aquantia/aquantia_main.c
-@@ -22,6 +22,8 @@
- #define PHY_ID_AQR107 0x03a1b4e0
- #define PHY_ID_AQCS109        0x03a1b5c2
- #define PHY_ID_AQR405 0x03a1b4b0
-+#define PHY_ID_AQR111 0x03a1b610
-+#define PHY_ID_AQR111B0       0x03a1b612
- #define PHY_ID_AQR113C        0x31c31c12
- #define MDIO_PHYXS_VEND_IF_STATUS             0xe812
-@@ -672,6 +674,16 @@ static int aqr107_probe(struct phy_devic
-       return aqr_hwmon_probe(phydev);
- }
-+static int aqr111_config_init(struct phy_device *phydev)
-+{
-+      /* AQR111 reports supporting speed up to 10G,
-+       * however only speeds up to 5G are supported.
-+       */
-+      phy_set_max_speed(phydev, SPEED_5000);
-+
-+      return aqr107_config_init(phydev);
-+}
-+
- static struct phy_driver aqr_driver[] = {
- {
-       PHY_ID_MATCH_MODEL(PHY_ID_AQ1202),
-@@ -746,6 +758,42 @@ static struct phy_driver aqr_driver[] =
-       .link_change_notify = aqr107_link_change_notify,
- },
- {
-+      PHY_ID_MATCH_MODEL(PHY_ID_AQR111),
-+      .name           = "Aquantia AQR111",
-+      .probe          = aqr107_probe,
-+      .config_init    = aqr111_config_init,
-+      .config_aneg    = aqr_config_aneg,
-+      .config_intr    = aqr_config_intr,
-+      .handle_interrupt = aqr_handle_interrupt,
-+      .read_status    = aqr107_read_status,
-+      .get_tunable    = aqr107_get_tunable,
-+      .set_tunable    = aqr107_set_tunable,
-+      .suspend        = aqr107_suspend,
-+      .resume         = aqr107_resume,
-+      .get_sset_count = aqr107_get_sset_count,
-+      .get_strings    = aqr107_get_strings,
-+      .get_stats      = aqr107_get_stats,
-+      .link_change_notify = aqr107_link_change_notify,
-+},
-+{
-+      PHY_ID_MATCH_MODEL(PHY_ID_AQR111B0),
-+      .name           = "Aquantia AQR111B0",
-+      .probe          = aqr107_probe,
-+      .config_init    = aqr111_config_init,
-+      .config_aneg    = aqr_config_aneg,
-+      .config_intr    = aqr_config_intr,
-+      .handle_interrupt = aqr_handle_interrupt,
-+      .read_status    = aqr107_read_status,
-+      .get_tunable    = aqr107_get_tunable,
-+      .set_tunable    = aqr107_set_tunable,
-+      .suspend        = aqr107_suspend,
-+      .resume         = aqr107_resume,
-+      .get_sset_count = aqr107_get_sset_count,
-+      .get_strings    = aqr107_get_strings,
-+      .get_stats      = aqr107_get_stats,
-+      .link_change_notify = aqr107_link_change_notify,
-+},
-+{
-       PHY_ID_MATCH_MODEL(PHY_ID_AQR405),
-       .name           = "Aquantia AQR405",
-       .config_aneg    = aqr_config_aneg,
-@@ -784,6 +832,8 @@ static struct mdio_device_id __maybe_unu
-       { PHY_ID_MATCH_MODEL(PHY_ID_AQR107) },
-       { PHY_ID_MATCH_MODEL(PHY_ID_AQCS109) },
-       { PHY_ID_MATCH_MODEL(PHY_ID_AQR405) },
-+      { PHY_ID_MATCH_MODEL(PHY_ID_AQR111) },
-+      { PHY_ID_MATCH_MODEL(PHY_ID_AQR111B0) },
-       { PHY_ID_MATCH_MODEL(PHY_ID_AQR113C) },
-       { }
- };
diff --git a/target/linux/generic/backport-5.15/739-v6.9-net-phy-aquantia-add-AQR113-PHY-ID.patch b/target/linux/generic/backport-5.15/739-v6.9-net-phy-aquantia-add-AQR113-PHY-ID.patch
deleted file mode 100644 (file)
index 5a46ab3..0000000
+++ /dev/null
@@ -1,59 +0,0 @@
-From 71b605d32017e5b8d257db7344bc2f8e8fcc973e Mon Sep 17 00:00:00 2001
-From: Christian Marangi <[email protected]>
-Date: Thu, 15 Feb 2024 16:30:05 +0100
-Subject: [PATCH] net: phy: aquantia: add AQR113 PHY ID
-
-Add Aquantia AQR113 PHY ID. Aquantia AQR113 is just a chip size variant of
-the already supported AQR133C where the only difference is the PHY ID
-and the hw chip size.
-
-Signed-off-by: Christian Marangi <[email protected]>
-Reviewed-by: Andrew Lunn <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/phy/aquantia/aquantia_main.c | 21 +++++++++++++++++++++
- 1 file changed, 21 insertions(+)
-
---- a/drivers/net/phy/aquantia/aquantia_main.c
-+++ b/drivers/net/phy/aquantia/aquantia_main.c
-@@ -24,6 +24,7 @@
- #define PHY_ID_AQR405 0x03a1b4b0
- #define PHY_ID_AQR111 0x03a1b610
- #define PHY_ID_AQR111B0       0x03a1b612
-+#define PHY_ID_AQR113 0x31c31c40
- #define PHY_ID_AQR113C        0x31c31c12
- #define MDIO_PHYXS_VEND_IF_STATUS             0xe812
-@@ -802,6 +803,24 @@ static struct phy_driver aqr_driver[] =
-       .read_status    = aqr_read_status,
- },
- {
-+      PHY_ID_MATCH_MODEL(PHY_ID_AQR113),
-+      .name           = "Aquantia AQR113",
-+      .probe          = aqr107_probe,
-+      .config_init    = aqr107_config_init,
-+      .config_aneg    = aqr_config_aneg,
-+      .config_intr    = aqr_config_intr,
-+      .handle_interrupt       = aqr_handle_interrupt,
-+      .read_status    = aqr107_read_status,
-+      .get_tunable    = aqr107_get_tunable,
-+      .set_tunable    = aqr107_set_tunable,
-+      .suspend        = aqr107_suspend,
-+      .resume         = aqr107_resume,
-+      .get_sset_count = aqr107_get_sset_count,
-+      .get_strings    = aqr107_get_strings,
-+      .get_stats      = aqr107_get_stats,
-+      .link_change_notify = aqr107_link_change_notify,
-+},
-+{
-       PHY_ID_MATCH_MODEL(PHY_ID_AQR113C),
-       .name           = "Aquantia AQR113C",
-       .probe          = aqr107_probe,
-@@ -834,6 +853,7 @@ static struct mdio_device_id __maybe_unu
-       { PHY_ID_MATCH_MODEL(PHY_ID_AQR405) },
-       { PHY_ID_MATCH_MODEL(PHY_ID_AQR111) },
-       { PHY_ID_MATCH_MODEL(PHY_ID_AQR111B0) },
-+      { PHY_ID_MATCH_MODEL(PHY_ID_AQR113) },
-       { PHY_ID_MATCH_MODEL(PHY_ID_AQR113C) },
-       { }
- };
diff --git a/target/linux/generic/backport-5.15/740-v6.9-net-phy-aquantia-add-AQR813-PHY-ID.patch b/target/linux/generic/backport-5.15/740-v6.9-net-phy-aquantia-add-AQR813-PHY-ID.patch
deleted file mode 100644 (file)
index 49651a5..0000000
+++ /dev/null
@@ -1,58 +0,0 @@
-From 6d47302a3f0ba31445478d518d98bd55918bc8ab Mon Sep 17 00:00:00 2001
-From: Christian Marangi <[email protected]>
-Date: Thu, 15 Feb 2024 22:43:30 +0100
-Subject: [PATCH] net: phy: aquantia: add AQR813 PHY ID
-
-Aquantia AQR813 is the Octal Port variant of the AQR113. Add PHY ID for
-it to provide support for it.
-
-Signed-off-by: Christian Marangi <[email protected]>
-Reviewed-by: Andrew Lunn <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/phy/aquantia/aquantia_main.c | 21 +++++++++++++++++++++
- 1 file changed, 21 insertions(+)
-
---- a/drivers/net/phy/aquantia/aquantia_main.c
-+++ b/drivers/net/phy/aquantia/aquantia_main.c
-@@ -26,6 +26,7 @@
- #define PHY_ID_AQR111B0       0x03a1b612
- #define PHY_ID_AQR113 0x31c31c40
- #define PHY_ID_AQR113C        0x31c31c12
-+#define PHY_ID_AQR813 0x31c31cb2
- #define MDIO_PHYXS_VEND_IF_STATUS             0xe812
- #define MDIO_PHYXS_VEND_IF_STATUS_TYPE_MASK   GENMASK(7, 3)
-@@ -839,6 +840,24 @@ static struct phy_driver aqr_driver[] =
-       .get_stats      = aqr107_get_stats,
-       .link_change_notify = aqr107_link_change_notify,
- },
-+{
-+      PHY_ID_MATCH_MODEL(PHY_ID_AQR813),
-+      .name           = "Aquantia AQR813",
-+      .probe          = aqr107_probe,
-+      .config_init    = aqr107_config_init,
-+      .config_aneg    = aqr_config_aneg,
-+      .config_intr    = aqr_config_intr,
-+      .handle_interrupt = aqr_handle_interrupt,
-+      .read_status    = aqr107_read_status,
-+      .get_tunable    = aqr107_get_tunable,
-+      .set_tunable    = aqr107_set_tunable,
-+      .suspend        = aqr107_suspend,
-+      .resume         = aqr107_resume,
-+      .get_sset_count = aqr107_get_sset_count,
-+      .get_strings    = aqr107_get_strings,
-+      .get_stats      = aqr107_get_stats,
-+      .link_change_notify = aqr107_link_change_notify,
-+},
- };
- module_phy_driver(aqr_driver);
-@@ -855,6 +874,7 @@ static struct mdio_device_id __maybe_unu
-       { PHY_ID_MATCH_MODEL(PHY_ID_AQR111B0) },
-       { PHY_ID_MATCH_MODEL(PHY_ID_AQR113) },
-       { PHY_ID_MATCH_MODEL(PHY_ID_AQR113C) },
-+      { PHY_ID_MATCH_MODEL(PHY_ID_AQR813) },
-       { }
- };
diff --git a/target/linux/generic/backport-5.15/742-v5.16-net-phy-at803x-add-support-for-qca-8327-internal-phy.patch b/target/linux/generic/backport-5.15/742-v5.16-net-phy-at803x-add-support-for-qca-8327-internal-phy.patch
deleted file mode 100644 (file)
index 03171d7..0000000
+++ /dev/null
@@ -1,48 +0,0 @@
-From 0ccf8511182436183c031e8a2f740ae91a02c625 Mon Sep 17 00:00:00 2001
-From: Ansuel Smith <[email protected]>
-Date: Tue, 14 Sep 2021 14:33:45 +0200
-Subject: net: phy: at803x: add support for qca 8327 internal phy
-
-Add support for qca8327 internal phy needed for correct init of the
-switch port. It does use the same qca8337 function and reg just with a
-different id.
-
-Signed-off-by: Ansuel Smith <[email protected]>
-Tested-by: Rosen Penev <[email protected]>
-Tested-by: Andrew Lunn <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/phy/at803x.c | 15 +++++++++++++++
- 1 file changed, 15 insertions(+)
-
---- a/drivers/net/phy/at803x.c
-+++ b/drivers/net/phy/at803x.c
-@@ -1410,6 +1410,19 @@ static struct phy_driver at803x_driver[]
-       .get_sset_count = at803x_get_sset_count,
-       .get_strings = at803x_get_strings,
-       .get_stats = at803x_get_stats,
-+}, {
-+      /* QCA8327 */
-+      .phy_id = QCA8327_PHY_ID,
-+      .phy_id_mask = QCA8K_PHY_ID_MASK,
-+      .name = "QCA PHY 8327",
-+      /* PHY_GBIT_FEATURES */
-+      .probe = at803x_probe,
-+      .flags = PHY_IS_INTERNAL,
-+      .config_init = qca83xx_config_init,
-+      .soft_reset = genphy_soft_reset,
-+      .get_sset_count = at803x_get_sset_count,
-+      .get_strings = at803x_get_strings,
-+      .get_stats = at803x_get_stats,
- }, };
- module_phy_driver(at803x_driver);
-@@ -1420,6 +1433,8 @@ static struct mdio_device_id __maybe_unu
-       { PHY_ID_MATCH_EXACT(ATH8032_PHY_ID) },
-       { PHY_ID_MATCH_EXACT(ATH8035_PHY_ID) },
-       { PHY_ID_MATCH_EXACT(ATH9331_PHY_ID) },
-+      { PHY_ID_MATCH_EXACT(QCA8337_PHY_ID) },
-+      { PHY_ID_MATCH_EXACT(QCA8327_PHY_ID) },
-       { }
- };
diff --git a/target/linux/generic/backport-5.15/743-v5.16-0001-net-dsa-b53-Include-all-ports-in-enabled_ports.patch b/target/linux/generic/backport-5.15/743-v5.16-0001-net-dsa-b53-Include-all-ports-in-enabled_ports.patch
deleted file mode 100644 (file)
index dc149a7..0000000
+++ /dev/null
@@ -1,131 +0,0 @@
-From 983d96a9116a328668601555d96736261d33170c Mon Sep 17 00:00:00 2001
-From: =?UTF-8?q?Rafa=C5=82=20Mi=C5=82ecki?= <[email protected]>
-Date: Thu, 16 Sep 2021 14:03:51 +0200
-Subject: [PATCH] net: dsa: b53: Include all ports in "enabled_ports"
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-Make "enabled_ports" bitfield contain all available switch ports
-including a CPU port. This way there is no need for fixup during
-initialization.
-
-For BCM53010, BCM53018 and BCM53019 include also other available ports.
-
-Signed-off-by: Rafał Miłecki <[email protected]>
-Reviewed-by: Florian Fainelli <[email protected]>
-Tested-by: Florian Fainelli <[email protected]>
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- drivers/net/dsa/b53/b53_common.c | 23 +++++++++++------------
- 1 file changed, 11 insertions(+), 12 deletions(-)
-
---- a/drivers/net/dsa/b53/b53_common.c
-+++ b/drivers/net/dsa/b53/b53_common.c
-@@ -2300,7 +2300,7 @@ static const struct b53_chip_data b53_sw
-               .chip_id = BCM5325_DEVICE_ID,
-               .dev_name = "BCM5325",
-               .vlans = 16,
--              .enabled_ports = 0x1f,
-+              .enabled_ports = 0x3f,
-               .arl_bins = 2,
-               .arl_buckets = 1024,
-               .imp_port = 5,
-@@ -2311,7 +2311,7 @@ static const struct b53_chip_data b53_sw
-               .chip_id = BCM5365_DEVICE_ID,
-               .dev_name = "BCM5365",
-               .vlans = 256,
--              .enabled_ports = 0x1f,
-+              .enabled_ports = 0x3f,
-               .arl_bins = 2,
-               .arl_buckets = 1024,
-               .imp_port = 5,
-@@ -2322,7 +2322,7 @@ static const struct b53_chip_data b53_sw
-               .chip_id = BCM5389_DEVICE_ID,
-               .dev_name = "BCM5389",
-               .vlans = 4096,
--              .enabled_ports = 0x1f,
-+              .enabled_ports = 0x11f,
-               .arl_bins = 4,
-               .arl_buckets = 1024,
-               .imp_port = 8,
-@@ -2336,7 +2336,7 @@ static const struct b53_chip_data b53_sw
-               .chip_id = BCM5395_DEVICE_ID,
-               .dev_name = "BCM5395",
-               .vlans = 4096,
--              .enabled_ports = 0x1f,
-+              .enabled_ports = 0x11f,
-               .arl_bins = 4,
-               .arl_buckets = 1024,
-               .imp_port = 8,
-@@ -2350,7 +2350,7 @@ static const struct b53_chip_data b53_sw
-               .chip_id = BCM5397_DEVICE_ID,
-               .dev_name = "BCM5397",
-               .vlans = 4096,
--              .enabled_ports = 0x1f,
-+              .enabled_ports = 0x11f,
-               .arl_bins = 4,
-               .arl_buckets = 1024,
-               .imp_port = 8,
-@@ -2364,7 +2364,7 @@ static const struct b53_chip_data b53_sw
-               .chip_id = BCM5398_DEVICE_ID,
-               .dev_name = "BCM5398",
-               .vlans = 4096,
--              .enabled_ports = 0x7f,
-+              .enabled_ports = 0x17f,
-               .arl_bins = 4,
-               .arl_buckets = 1024,
-               .imp_port = 8,
-@@ -2378,7 +2378,7 @@ static const struct b53_chip_data b53_sw
-               .chip_id = BCM53115_DEVICE_ID,
-               .dev_name = "BCM53115",
-               .vlans = 4096,
--              .enabled_ports = 0x1f,
-+              .enabled_ports = 0x11f,
-               .arl_bins = 4,
-               .arl_buckets = 1024,
-               .vta_regs = B53_VTA_REGS,
-@@ -2392,7 +2392,7 @@ static const struct b53_chip_data b53_sw
-               .chip_id = BCM53125_DEVICE_ID,
-               .dev_name = "BCM53125",
-               .vlans = 4096,
--              .enabled_ports = 0xff,
-+              .enabled_ports = 0x1ff,
-               .arl_bins = 4,
-               .arl_buckets = 1024,
-               .imp_port = 8,
-@@ -2434,7 +2434,7 @@ static const struct b53_chip_data b53_sw
-               .chip_id = BCM53010_DEVICE_ID,
-               .dev_name = "BCM53010",
-               .vlans = 4096,
--              .enabled_ports = 0x1f,
-+              .enabled_ports = 0x1bf,
-               .arl_bins = 4,
-               .arl_buckets = 1024,
-               .imp_port = 8,
-@@ -2476,7 +2476,7 @@ static const struct b53_chip_data b53_sw
-               .chip_id = BCM53018_DEVICE_ID,
-               .dev_name = "BCM53018",
-               .vlans = 4096,
--              .enabled_ports = 0x1f,
-+              .enabled_ports = 0x1bf,
-               .arl_bins = 4,
-               .arl_buckets = 1024,
-               .imp_port = 8,
-@@ -2490,7 +2490,7 @@ static const struct b53_chip_data b53_sw
-               .chip_id = BCM53019_DEVICE_ID,
-               .dev_name = "BCM53019",
-               .vlans = 4096,
--              .enabled_ports = 0x1f,
-+              .enabled_ports = 0x1bf,
-               .arl_bins = 4,
-               .arl_buckets = 1024,
-               .imp_port = 8,
-@@ -2632,7 +2632,6 @@ static int b53_switch_init(struct b53_de
-                       dev->cpu_port = 5;
-       }
--      dev->enabled_ports |= BIT(dev->cpu_port);
-       dev->num_ports = fls(dev->enabled_ports);
-       dev->ds->num_ports = min_t(unsigned int, dev->num_ports, DSA_MAX_PORTS);
diff --git a/target/linux/generic/backport-5.15/743-v5.16-0002-net-dsa-b53-Drop-BCM5301x-workaround-for-a-wrong-CPU.patch b/target/linux/generic/backport-5.15/743-v5.16-0002-net-dsa-b53-Drop-BCM5301x-workaround-for-a-wrong-CPU.patch
deleted file mode 100644 (file)
index 23805a9..0000000
+++ /dev/null
@@ -1,42 +0,0 @@
-From b290c6384afabbca5ae6e2af72fb1b2bc37922be Mon Sep 17 00:00:00 2001
-From: =?UTF-8?q?Rafa=C5=82=20Mi=C5=82ecki?= <[email protected]>
-Date: Thu, 16 Sep 2021 14:03:52 +0200
-Subject: [PATCH] net: dsa: b53: Drop BCM5301x workaround for a wrong CPU/IMP
- port
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-On BCM5301x port 8 requires a fixed link when used.
-
-Years ago when b53 was an OpenWrt downstream driver (with configuration
-based on sometimes bugged NVRAM) there was a need for a fixup. In case
-of forcing fixed link for (incorrectly specified) port 5 the code had to
-actually setup port 8 link.
-
-For upstream b53 driver with setup based on DT there is no need for that
-workaround. In DT we have and require correct ports setup.
-
-Signed-off-by: Rafał Miłecki <[email protected]>
-Reviewed-by: Florian Fainelli <[email protected]>
-Tested-by: Florian Fainelli <[email protected]>
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- drivers/net/dsa/b53/b53_common.c | 6 ------
- 1 file changed, 6 deletions(-)
-
---- a/drivers/net/dsa/b53/b53_common.c
-+++ b/drivers/net/dsa/b53/b53_common.c
-@@ -1291,12 +1291,6 @@ static void b53_adjust_link(struct dsa_s
-                               return;
-                       }
-               }
--      } else if (is5301x(dev)) {
--              if (port != dev->cpu_port) {
--                      b53_force_port_config(dev, dev->cpu_port, 2000,
--                                            DUPLEX_FULL, true, true);
--                      b53_force_link(dev, dev->cpu_port, 1);
--              }
-       }
-       /* Re-negotiate EEE if it was enabled already */
diff --git a/target/linux/generic/backport-5.15/743-v5.16-0003-net-dsa-b53-Improve-flow-control-setup-on-BCM5301x.patch b/target/linux/generic/backport-5.15/743-v5.16-0003-net-dsa-b53-Improve-flow-control-setup-on-BCM5301x.patch
deleted file mode 100644 (file)
index 941fa23..0000000
+++ /dev/null
@@ -1,32 +0,0 @@
-From 3ff26b29230c54fea2353b63124c589b61953e14 Mon Sep 17 00:00:00 2001
-From: =?UTF-8?q?Rafa=C5=82=20Mi=C5=82ecki?= <[email protected]>
-Date: Thu, 16 Sep 2021 14:03:53 +0200
-Subject: [PATCH] net: dsa: b53: Improve flow control setup on BCM5301x
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-According to the Broadcom's reference driver flow control needs to be
-enabled for any CPU switch port (5, 7 or 8 - depending on which one is
-used). Current code makes it work only for the port 5. Use
-dsa_is_cpu_port() which solved that problem.
-
-Signed-off-by: Rafał Miłecki <[email protected]>
-Reviewed-by: Florian Fainelli <[email protected]>
-Tested-by: Florian Fainelli <[email protected]>
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- drivers/net/dsa/b53/b53_common.c | 2 +-
- 1 file changed, 1 insertion(+), 1 deletion(-)
-
---- a/drivers/net/dsa/b53/b53_common.c
-+++ b/drivers/net/dsa/b53/b53_common.c
-@@ -1222,7 +1222,7 @@ static void b53_adjust_link(struct dsa_s
-               return;
-       /* Enable flow control on BCM5301x's CPU port */
--      if (is5301x(dev) && port == dev->cpu_port)
-+      if (is5301x(dev) && dsa_is_cpu_port(ds, port))
-               tx_pause = rx_pause = true;
-       if (phydev->pause) {
diff --git a/target/linux/generic/backport-5.15/743-v5.16-0004-net-dsa-b53-Drop-unused-cpu_port-field.patch b/target/linux/generic/backport-5.15/743-v5.16-0004-net-dsa-b53-Drop-unused-cpu_port-field.patch
deleted file mode 100644 (file)
index 07d0ec0..0000000
+++ /dev/null
@@ -1,205 +0,0 @@
-From 7d5af56418d7d01e43247a33b6fe6492ea871923 Mon Sep 17 00:00:00 2001
-From: =?UTF-8?q?Rafa=C5=82=20Mi=C5=82ecki?= <[email protected]>
-Date: Thu, 16 Sep 2021 14:03:54 +0200
-Subject: [PATCH] net: dsa: b53: Drop unused "cpu_port" field
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-It's set but never used anymore.
-
-Signed-off-by: Rafał Miłecki <[email protected]>
-Reviewed-by: Florian Fainelli <[email protected]>
-Tested-by: Florian Fainelli <[email protected]>
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- drivers/net/dsa/b53/b53_common.c | 28 ----------------------------
- drivers/net/dsa/b53/b53_priv.h   |  1 -
- 2 files changed, 29 deletions(-)
-
---- a/drivers/net/dsa/b53/b53_common.c
-+++ b/drivers/net/dsa/b53/b53_common.c
-@@ -2298,7 +2298,6 @@ static const struct b53_chip_data b53_sw
-               .arl_bins = 2,
-               .arl_buckets = 1024,
-               .imp_port = 5,
--              .cpu_port = B53_CPU_PORT_25,
-               .duplex_reg = B53_DUPLEX_STAT_FE,
-       },
-       {
-@@ -2309,7 +2308,6 @@ static const struct b53_chip_data b53_sw
-               .arl_bins = 2,
-               .arl_buckets = 1024,
-               .imp_port = 5,
--              .cpu_port = B53_CPU_PORT_25,
-               .duplex_reg = B53_DUPLEX_STAT_FE,
-       },
-       {
-@@ -2320,7 +2318,6 @@ static const struct b53_chip_data b53_sw
-               .arl_bins = 4,
-               .arl_buckets = 1024,
-               .imp_port = 8,
--              .cpu_port = B53_CPU_PORT,
-               .vta_regs = B53_VTA_REGS,
-               .duplex_reg = B53_DUPLEX_STAT_GE,
-               .jumbo_pm_reg = B53_JUMBO_PORT_MASK,
-@@ -2334,7 +2331,6 @@ static const struct b53_chip_data b53_sw
-               .arl_bins = 4,
-               .arl_buckets = 1024,
-               .imp_port = 8,
--              .cpu_port = B53_CPU_PORT,
-               .vta_regs = B53_VTA_REGS,
-               .duplex_reg = B53_DUPLEX_STAT_GE,
-               .jumbo_pm_reg = B53_JUMBO_PORT_MASK,
-@@ -2348,7 +2344,6 @@ static const struct b53_chip_data b53_sw
-               .arl_bins = 4,
-               .arl_buckets = 1024,
-               .imp_port = 8,
--              .cpu_port = B53_CPU_PORT,
-               .vta_regs = B53_VTA_REGS_9798,
-               .duplex_reg = B53_DUPLEX_STAT_GE,
-               .jumbo_pm_reg = B53_JUMBO_PORT_MASK,
-@@ -2362,7 +2357,6 @@ static const struct b53_chip_data b53_sw
-               .arl_bins = 4,
-               .arl_buckets = 1024,
-               .imp_port = 8,
--              .cpu_port = B53_CPU_PORT,
-               .vta_regs = B53_VTA_REGS_9798,
-               .duplex_reg = B53_DUPLEX_STAT_GE,
-               .jumbo_pm_reg = B53_JUMBO_PORT_MASK,
-@@ -2377,7 +2371,6 @@ static const struct b53_chip_data b53_sw
-               .arl_buckets = 1024,
-               .vta_regs = B53_VTA_REGS,
-               .imp_port = 8,
--              .cpu_port = B53_CPU_PORT,
-               .duplex_reg = B53_DUPLEX_STAT_GE,
-               .jumbo_pm_reg = B53_JUMBO_PORT_MASK,
-               .jumbo_size_reg = B53_JUMBO_MAX_SIZE,
-@@ -2390,7 +2383,6 @@ static const struct b53_chip_data b53_sw
-               .arl_bins = 4,
-               .arl_buckets = 1024,
-               .imp_port = 8,
--              .cpu_port = B53_CPU_PORT,
-               .vta_regs = B53_VTA_REGS,
-               .duplex_reg = B53_DUPLEX_STAT_GE,
-               .jumbo_pm_reg = B53_JUMBO_PORT_MASK,
-@@ -2404,7 +2396,6 @@ static const struct b53_chip_data b53_sw
-               .arl_bins = 4,
-               .arl_buckets = 1024,
-               .imp_port = 8,
--              .cpu_port = B53_CPU_PORT,
-               .vta_regs = B53_VTA_REGS,
-               .duplex_reg = B53_DUPLEX_STAT_GE,
-               .jumbo_pm_reg = B53_JUMBO_PORT_MASK,
-@@ -2418,7 +2409,6 @@ static const struct b53_chip_data b53_sw
-               .arl_bins = 4,
-               .arl_buckets = 1024,
-               .imp_port = 8,
--              .cpu_port = B53_CPU_PORT,
-               .vta_regs = B53_VTA_REGS_63XX,
-               .duplex_reg = B53_DUPLEX_STAT_63XX,
-               .jumbo_pm_reg = B53_JUMBO_PORT_MASK_63XX,
-@@ -2432,7 +2422,6 @@ static const struct b53_chip_data b53_sw
-               .arl_bins = 4,
-               .arl_buckets = 1024,
-               .imp_port = 8,
--              .cpu_port = B53_CPU_PORT_25, /* TODO: auto detect */
-               .vta_regs = B53_VTA_REGS,
-               .duplex_reg = B53_DUPLEX_STAT_GE,
-               .jumbo_pm_reg = B53_JUMBO_PORT_MASK,
-@@ -2446,7 +2435,6 @@ static const struct b53_chip_data b53_sw
-               .arl_bins = 4,
-               .arl_buckets = 1024,
-               .imp_port = 8,
--              .cpu_port = B53_CPU_PORT_25, /* TODO: auto detect */
-               .vta_regs = B53_VTA_REGS,
-               .duplex_reg = B53_DUPLEX_STAT_GE,
-               .jumbo_pm_reg = B53_JUMBO_PORT_MASK,
-@@ -2460,7 +2448,6 @@ static const struct b53_chip_data b53_sw
-               .arl_bins = 4,
-               .arl_buckets = 1024,
-               .imp_port = 8,
--              .cpu_port = B53_CPU_PORT_25, /* TODO: auto detect */
-               .vta_regs = B53_VTA_REGS,
-               .duplex_reg = B53_DUPLEX_STAT_GE,
-               .jumbo_pm_reg = B53_JUMBO_PORT_MASK,
-@@ -2474,7 +2461,6 @@ static const struct b53_chip_data b53_sw
-               .arl_bins = 4,
-               .arl_buckets = 1024,
-               .imp_port = 8,
--              .cpu_port = B53_CPU_PORT_25, /* TODO: auto detect */
-               .vta_regs = B53_VTA_REGS,
-               .duplex_reg = B53_DUPLEX_STAT_GE,
-               .jumbo_pm_reg = B53_JUMBO_PORT_MASK,
-@@ -2488,7 +2474,6 @@ static const struct b53_chip_data b53_sw
-               .arl_bins = 4,
-               .arl_buckets = 1024,
-               .imp_port = 8,
--              .cpu_port = B53_CPU_PORT_25, /* TODO: auto detect */
-               .vta_regs = B53_VTA_REGS,
-               .duplex_reg = B53_DUPLEX_STAT_GE,
-               .jumbo_pm_reg = B53_JUMBO_PORT_MASK,
-@@ -2502,7 +2487,6 @@ static const struct b53_chip_data b53_sw
-               .arl_bins = 4,
-               .arl_buckets = 1024,
-               .imp_port = 8,
--              .cpu_port = B53_CPU_PORT,
-               .vta_regs = B53_VTA_REGS,
-               .duplex_reg = B53_DUPLEX_STAT_GE,
-               .jumbo_pm_reg = B53_JUMBO_PORT_MASK,
-@@ -2516,7 +2500,6 @@ static const struct b53_chip_data b53_sw
-               .arl_bins = 4,
-               .arl_buckets = 1024,
-               .imp_port = 8,
--              .cpu_port = B53_CPU_PORT,
-               .vta_regs = B53_VTA_REGS,
-               .duplex_reg = B53_DUPLEX_STAT_GE,
-               .jumbo_pm_reg = B53_JUMBO_PORT_MASK,
-@@ -2545,7 +2528,6 @@ static const struct b53_chip_data b53_sw
-               .arl_bins = 4,
-               .arl_buckets = 1024,
-               .imp_port = 8,
--              .cpu_port = B53_CPU_PORT,
-               .vta_regs = B53_VTA_REGS,
-               .duplex_reg = B53_DUPLEX_STAT_GE,
-               .jumbo_pm_reg = B53_JUMBO_PORT_MASK,
-@@ -2559,7 +2541,6 @@ static const struct b53_chip_data b53_sw
-               .arl_bins = 4,
-               .arl_buckets = 256,
-               .imp_port = 8,
--              .cpu_port = B53_CPU_PORT,
-               .vta_regs = B53_VTA_REGS,
-               .duplex_reg = B53_DUPLEX_STAT_GE,
-               .jumbo_pm_reg = B53_JUMBO_PORT_MASK,
-@@ -2585,7 +2566,6 @@ static int b53_switch_init(struct b53_de
-                       dev->vta_regs[2] = chip->vta_regs[2];
-                       dev->jumbo_pm_reg = chip->jumbo_pm_reg;
-                       dev->imp_port = chip->imp_port;
--                      dev->cpu_port = chip->cpu_port;
-                       dev->num_vlans = chip->vlans;
-                       dev->num_arl_bins = chip->arl_bins;
-                       dev->num_arl_buckets = chip->arl_buckets;
-@@ -2617,13 +2597,6 @@ static int b53_switch_init(struct b53_de
-                       break;
- #endif
-               }
--      } else if (dev->chip_id == BCM53115_DEVICE_ID) {
--              u64 strap_value;
--
--              b53_read48(dev, B53_STAT_PAGE, B53_STRAP_VALUE, &strap_value);
--              /* use second IMP port if GMII is enabled */
--              if (strap_value & SV_GMII_CTRL_115)
--                      dev->cpu_port = 5;
-       }
-       dev->num_ports = fls(dev->enabled_ports);
---- a/drivers/net/dsa/b53/b53_priv.h
-+++ b/drivers/net/dsa/b53/b53_priv.h
-@@ -124,7 +124,6 @@ struct b53_device {
-       /* used ports mask */
-       u16 enabled_ports;
-       unsigned int imp_port;
--      unsigned int cpu_port;
-       /* connect specific data */
-       u8 current_page;
diff --git a/target/linux/generic/backport-5.15/745-v5.16-01-net-phy-at803x-add-support-for-qca-8327-A-variant.patch b/target/linux/generic/backport-5.15/745-v5.16-01-net-phy-at803x-add-support-for-qca-8327-A-variant.patch
deleted file mode 100644 (file)
index 7e4e946..0000000
+++ /dev/null
@@ -1,65 +0,0 @@
-From b4df02b562f4aa14ff6811f30e1b4d2159585c59 Mon Sep 17 00:00:00 2001
-From: Ansuel Smith <[email protected]>
-Date: Sun, 19 Sep 2021 18:28:15 +0200
-Subject: net: phy: at803x: add support for qca 8327 A variant internal phy
-
-For qca8327 internal phy there are 2 different switch variant with 2
-different phy id. Add this missing variant so the internal phy can be
-correctly identified and fixed.
-
-Signed-off-by: Ansuel Smith <[email protected]>
-Reviewed-by: Andrew Lunn <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/phy/at803x.c | 25 ++++++++++++++++++++-----
- 1 file changed, 20 insertions(+), 5 deletions(-)
-
---- a/drivers/net/phy/at803x.c
-+++ b/drivers/net/phy/at803x.c
-@@ -150,7 +150,8 @@
- #define ATH8035_PHY_ID                                0x004dd072
- #define AT8030_PHY_ID_MASK                    0xffffffef
--#define QCA8327_PHY_ID                                0x004dd034
-+#define QCA8327_A_PHY_ID                      0x004dd033
-+#define QCA8327_B_PHY_ID                      0x004dd034
- #define QCA8337_PHY_ID                                0x004dd036
- #define QCA8K_PHY_ID_MASK                     0xffffffff
-@@ -1411,10 +1412,23 @@ static struct phy_driver at803x_driver[]
-       .get_strings = at803x_get_strings,
-       .get_stats = at803x_get_stats,
- }, {
--      /* QCA8327 */
--      .phy_id = QCA8327_PHY_ID,
-+      /* QCA8327-A from switch QCA8327-AL1A */
-+      .phy_id = QCA8327_A_PHY_ID,
-       .phy_id_mask = QCA8K_PHY_ID_MASK,
--      .name = "QCA PHY 8327",
-+      .name = "QCA PHY 8327-A",
-+      /* PHY_GBIT_FEATURES */
-+      .probe = at803x_probe,
-+      .flags = PHY_IS_INTERNAL,
-+      .config_init = qca83xx_config_init,
-+      .soft_reset = genphy_soft_reset,
-+      .get_sset_count = at803x_get_sset_count,
-+      .get_strings = at803x_get_strings,
-+      .get_stats = at803x_get_stats,
-+}, {
-+      /* QCA8327-B from switch QCA8327-BL1A */
-+      .phy_id = QCA8327_B_PHY_ID,
-+      .phy_id_mask = QCA8K_PHY_ID_MASK,
-+      .name = "QCA PHY 8327-B",
-       /* PHY_GBIT_FEATURES */
-       .probe = at803x_probe,
-       .flags = PHY_IS_INTERNAL,
-@@ -1434,7 +1448,8 @@ static struct mdio_device_id __maybe_unu
-       { PHY_ID_MATCH_EXACT(ATH8035_PHY_ID) },
-       { PHY_ID_MATCH_EXACT(ATH9331_PHY_ID) },
-       { PHY_ID_MATCH_EXACT(QCA8337_PHY_ID) },
--      { PHY_ID_MATCH_EXACT(QCA8327_PHY_ID) },
-+      { PHY_ID_MATCH_EXACT(QCA8327_A_PHY_ID) },
-+      { PHY_ID_MATCH_EXACT(QCA8327_B_PHY_ID) },
-       { }
- };
diff --git a/target/linux/generic/backport-5.15/745-v5.16-02-net-phy-at803x-add-resume-suspend-function-to-qca83x.patch b/target/linux/generic/backport-5.15/745-v5.16-02-net-phy-at803x-add-resume-suspend-function-to-qca83x.patch
deleted file mode 100644 (file)
index 89aca23..0000000
+++ /dev/null
@@ -1,45 +0,0 @@
-From 15b9df4ece17d084f14eb0ca1cf05f2ad497e425 Mon Sep 17 00:00:00 2001
-From: Ansuel Smith <[email protected]>
-Date: Sun, 19 Sep 2021 18:28:16 +0200
-Subject: net: phy: at803x: add resume/suspend function to qca83xx phy
-
-Add resume/suspend function to qca83xx internal phy.
-We can't use the at803x generic function as the documentation lacks of
-any support for WoL regs.
-
-Signed-off-by: Ansuel Smith <[email protected]>
-Reviewed-by: Andrew Lunn <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/phy/at803x.c | 6 ++++++
- 1 file changed, 6 insertions(+)
-
---- a/drivers/net/phy/at803x.c
-+++ b/drivers/net/phy/at803x.c
-@@ -1411,6 +1411,8 @@ static struct phy_driver at803x_driver[]
-       .get_sset_count = at803x_get_sset_count,
-       .get_strings = at803x_get_strings,
-       .get_stats = at803x_get_stats,
-+      .suspend                = genphy_suspend,
-+      .resume                 = genphy_resume,
- }, {
-       /* QCA8327-A from switch QCA8327-AL1A */
-       .phy_id = QCA8327_A_PHY_ID,
-@@ -1424,6 +1426,8 @@ static struct phy_driver at803x_driver[]
-       .get_sset_count = at803x_get_sset_count,
-       .get_strings = at803x_get_strings,
-       .get_stats = at803x_get_stats,
-+      .suspend                = genphy_suspend,
-+      .resume                 = genphy_resume,
- }, {
-       /* QCA8327-B from switch QCA8327-BL1A */
-       .phy_id = QCA8327_B_PHY_ID,
-@@ -1437,6 +1441,8 @@ static struct phy_driver at803x_driver[]
-       .get_sset_count = at803x_get_sset_count,
-       .get_strings = at803x_get_strings,
-       .get_stats = at803x_get_stats,
-+      .suspend                = genphy_suspend,
-+      .resume                 = genphy_resume,
- }, };
- module_phy_driver(at803x_driver);
diff --git a/target/linux/generic/backport-5.15/745-v5.16-03-net-phy-at803x-fix-spacing-and-improve-name-for-83xx.patch b/target/linux/generic/backport-5.15/745-v5.16-03-net-phy-at803x-fix-spacing-and-improve-name-for-83xx.patch
deleted file mode 100644 (file)
index 920bef2..0000000
+++ /dev/null
@@ -1,95 +0,0 @@
-From d44fd8604a4ab92119adb35f05fd87612af722b5 Mon Sep 17 00:00:00 2001
-From: Ansuel Smith <[email protected]>
-Date: Sun, 19 Sep 2021 18:28:17 +0200
-Subject: net: phy: at803x: fix spacing and improve name for 83xx phy
-
-Fix spacing and improve name for 83xx phy following other phy in the
-same driver.
-
-Signed-off-by: Ansuel Smith <[email protected]>
-Reviewed-by: Andrew Lunn <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/phy/at803x.c | 60 ++++++++++++++++++++++++------------------------
- 1 file changed, 30 insertions(+), 30 deletions(-)
-
---- a/drivers/net/phy/at803x.c
-+++ b/drivers/net/phy/at803x.c
-@@ -1400,47 +1400,47 @@ static struct phy_driver at803x_driver[]
-       .config_aneg            = at803x_config_aneg,
- }, {
-       /* QCA8337 */
--      .phy_id = QCA8337_PHY_ID,
--      .phy_id_mask = QCA8K_PHY_ID_MASK,
--      .name = "QCA PHY 8337",
-+      .phy_id                 = QCA8337_PHY_ID,
-+      .phy_id_mask            = QCA8K_PHY_ID_MASK,
-+      .name                   = "Qualcomm Atheros 8337 internal PHY",
-       /* PHY_GBIT_FEATURES */
--      .probe = at803x_probe,
--      .flags = PHY_IS_INTERNAL,
--      .config_init = qca83xx_config_init,
--      .soft_reset = genphy_soft_reset,
--      .get_sset_count = at803x_get_sset_count,
--      .get_strings = at803x_get_strings,
--      .get_stats = at803x_get_stats,
-+      .probe                  = at803x_probe,
-+      .flags                  = PHY_IS_INTERNAL,
-+      .config_init            = qca83xx_config_init,
-+      .soft_reset             = genphy_soft_reset,
-+      .get_sset_count         = at803x_get_sset_count,
-+      .get_strings            = at803x_get_strings,
-+      .get_stats              = at803x_get_stats,
-       .suspend                = genphy_suspend,
-       .resume                 = genphy_resume,
- }, {
-       /* QCA8327-A from switch QCA8327-AL1A */
--      .phy_id = QCA8327_A_PHY_ID,
--      .phy_id_mask = QCA8K_PHY_ID_MASK,
--      .name = "QCA PHY 8327-A",
-+      .phy_id                 = QCA8327_A_PHY_ID,
-+      .phy_id_mask            = QCA8K_PHY_ID_MASK,
-+      .name                   = "Qualcomm Atheros 8327-A internal PHY",
-       /* PHY_GBIT_FEATURES */
--      .probe = at803x_probe,
--      .flags = PHY_IS_INTERNAL,
--      .config_init = qca83xx_config_init,
--      .soft_reset = genphy_soft_reset,
--      .get_sset_count = at803x_get_sset_count,
--      .get_strings = at803x_get_strings,
--      .get_stats = at803x_get_stats,
-+      .probe                  = at803x_probe,
-+      .flags                  = PHY_IS_INTERNAL,
-+      .config_init            = qca83xx_config_init,
-+      .soft_reset             = genphy_soft_reset,
-+      .get_sset_count         = at803x_get_sset_count,
-+      .get_strings            = at803x_get_strings,
-+      .get_stats              = at803x_get_stats,
-       .suspend                = genphy_suspend,
-       .resume                 = genphy_resume,
- }, {
-       /* QCA8327-B from switch QCA8327-BL1A */
--      .phy_id = QCA8327_B_PHY_ID,
--      .phy_id_mask = QCA8K_PHY_ID_MASK,
--      .name = "QCA PHY 8327-B",
-+      .phy_id                 = QCA8327_B_PHY_ID,
-+      .phy_id_mask            = QCA8K_PHY_ID_MASK,
-+      .name                   = "Qualcomm Atheros 8327-B internal PHY",
-       /* PHY_GBIT_FEATURES */
--      .probe = at803x_probe,
--      .flags = PHY_IS_INTERNAL,
--      .config_init = qca83xx_config_init,
--      .soft_reset = genphy_soft_reset,
--      .get_sset_count = at803x_get_sset_count,
--      .get_strings = at803x_get_strings,
--      .get_stats = at803x_get_stats,
-+      .probe                  = at803x_probe,
-+      .flags                  = PHY_IS_INTERNAL,
-+      .config_init            = qca83xx_config_init,
-+      .soft_reset             = genphy_soft_reset,
-+      .get_sset_count         = at803x_get_sset_count,
-+      .get_strings            = at803x_get_strings,
-+      .get_stats              = at803x_get_stats,
-       .suspend                = genphy_suspend,
-       .resume                 = genphy_resume,
- }, };
diff --git a/target/linux/generic/backport-5.15/746-v5.16-01-net-phy-at803x-fix-resume-for-QCA8327-phy.patch b/target/linux/generic/backport-5.15/746-v5.16-01-net-phy-at803x-fix-resume-for-QCA8327-phy.patch
deleted file mode 100644 (file)
index 1029420..0000000
+++ /dev/null
@@ -1,131 +0,0 @@
-From ba3c01ee02ed0d821c9f241f179bbc9457542b8f Mon Sep 17 00:00:00 2001
-From: Ansuel Smith <[email protected]>
-Date: Sun, 10 Oct 2021 00:46:15 +0200
-Subject: net: phy: at803x: fix resume for QCA8327 phy
-
-From Documentation phy resume triggers phy reset and restart
-auto-negotiation. Add a dedicated function to wait reset to finish as
-it was notice a regression where port sometime are not reliable after a
-suspend/resume session. The reset wait logic is copied from phy_poll_reset.
-Add dedicated suspend function to use genphy_suspend only with QCA8337
-phy and set only additional debug settings for QCA8327. With more test
-it was reported that QCA8327 doesn't proprely support this mode and
-using this cause the unreliability of the switch ports, especially the
-malfunction of the port0.
-
-Fixes: 15b9df4ece17 ("net: phy: at803x: add resume/suspend function to qca83xx phy")
-Signed-off-by: Ansuel Smith <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/phy/at803x.c | 69 +++++++++++++++++++++++++++++++++++++++++++-----
- 1 file changed, 63 insertions(+), 6 deletions(-)
-
---- a/drivers/net/phy/at803x.c
-+++ b/drivers/net/phy/at803x.c
-@@ -92,9 +92,14 @@
- #define AT803X_DEBUG_REG_5                    0x05
- #define AT803X_DEBUG_TX_CLK_DLY_EN            BIT(8)
-+#define AT803X_DEBUG_REG_HIB_CTRL             0x0b
-+#define   AT803X_DEBUG_HIB_CTRL_SEL_RST_80U   BIT(10)
-+#define   AT803X_DEBUG_HIB_CTRL_EN_ANY_CHANGE BIT(13)
-+
- #define AT803X_DEBUG_REG_3C                   0x3C
- #define AT803X_DEBUG_REG_3D                   0x3D
-+#define   AT803X_DEBUG_GATE_CLK_IN1000                BIT(6)
- #define AT803X_DEBUG_REG_1F                   0x1F
- #define AT803X_DEBUG_PLL_ON                   BIT(2)
-@@ -1304,6 +1309,58 @@ static int qca83xx_config_init(struct ph
-       return 0;
- }
-+static int qca83xx_resume(struct phy_device *phydev)
-+{
-+      int ret, val;
-+
-+      /* Skip reset if not suspended */
-+      if (!phydev->suspended)
-+              return 0;
-+
-+      /* Reinit the port, reset values set by suspend */
-+      qca83xx_config_init(phydev);
-+
-+      /* Reset the port on port resume */
-+      phy_set_bits(phydev, MII_BMCR, BMCR_RESET | BMCR_ANENABLE);
-+
-+      /* On resume from suspend the switch execute a reset and
-+       * restart auto-negotiation. Wait for reset to complete.
-+       */
-+      ret = phy_read_poll_timeout(phydev, MII_BMCR, val, !(val & BMCR_RESET),
-+                                  50000, 600000, true);
-+      if (ret)
-+              return ret;
-+
-+      msleep(1);
-+
-+      return 0;
-+}
-+
-+static int qca83xx_suspend(struct phy_device *phydev)
-+{
-+      u16 mask = 0;
-+
-+      /* Only QCA8337 support actual suspend.
-+       * QCA8327 cause port unreliability when phy suspend
-+       * is set.
-+       */
-+      if (phydev->drv->phy_id == QCA8337_PHY_ID) {
-+              genphy_suspend(phydev);
-+      } else {
-+              mask |= ~(BMCR_SPEED1000 | BMCR_FULLDPLX);
-+              phy_modify(phydev, MII_BMCR, mask, 0);
-+      }
-+
-+      at803x_debug_reg_mask(phydev, AT803X_DEBUG_REG_3D,
-+                            AT803X_DEBUG_GATE_CLK_IN1000, 0);
-+
-+      at803x_debug_reg_mask(phydev, AT803X_DEBUG_REG_HIB_CTRL,
-+                            AT803X_DEBUG_HIB_CTRL_EN_ANY_CHANGE |
-+                            AT803X_DEBUG_HIB_CTRL_SEL_RST_80U, 0);
-+
-+      return 0;
-+}
-+
- static struct phy_driver at803x_driver[] = {
- {
-       /* Qualcomm Atheros AR8035 */
-@@ -1411,8 +1468,8 @@ static struct phy_driver at803x_driver[]
-       .get_sset_count         = at803x_get_sset_count,
-       .get_strings            = at803x_get_strings,
-       .get_stats              = at803x_get_stats,
--      .suspend                = genphy_suspend,
--      .resume                 = genphy_resume,
-+      .suspend                = qca83xx_suspend,
-+      .resume                 = qca83xx_resume,
- }, {
-       /* QCA8327-A from switch QCA8327-AL1A */
-       .phy_id                 = QCA8327_A_PHY_ID,
-@@ -1426,8 +1483,8 @@ static struct phy_driver at803x_driver[]
-       .get_sset_count         = at803x_get_sset_count,
-       .get_strings            = at803x_get_strings,
-       .get_stats              = at803x_get_stats,
--      .suspend                = genphy_suspend,
--      .resume                 = genphy_resume,
-+      .suspend                = qca83xx_suspend,
-+      .resume                 = qca83xx_resume,
- }, {
-       /* QCA8327-B from switch QCA8327-BL1A */
-       .phy_id                 = QCA8327_B_PHY_ID,
-@@ -1441,8 +1498,8 @@ static struct phy_driver at803x_driver[]
-       .get_sset_count         = at803x_get_sset_count,
-       .get_strings            = at803x_get_strings,
-       .get_stats              = at803x_get_stats,
--      .suspend                = genphy_suspend,
--      .resume                 = genphy_resume,
-+      .suspend                = qca83xx_suspend,
-+      .resume                 = qca83xx_resume,
- }, };
- module_phy_driver(at803x_driver);
diff --git a/target/linux/generic/backport-5.15/746-v5.16-02-net-phy-at803x-add-DAC-amplitude-fix-for-8327-phy.patch b/target/linux/generic/backport-5.15/746-v5.16-02-net-phy-at803x-add-DAC-amplitude-fix-for-8327-phy.patch
deleted file mode 100644 (file)
index 5813619..0000000
+++ /dev/null
@@ -1,91 +0,0 @@
-From 1ca8311949aec5c9447645731ef1c6bc5bd71350 Mon Sep 17 00:00:00 2001
-From: Ansuel Smith <[email protected]>
-Date: Sun, 10 Oct 2021 00:46:16 +0200
-Subject: net: phy: at803x: add DAC amplitude fix for 8327 phy
-
-QCA8327 internal phy require DAC amplitude adjustement set to +6% with
-100m speed. Also add additional define to report a change of the same
-reg in QCA8337. (different scope it does set 1000m voltage)
-Add link_change_notify function to set the proper amplitude adjustement
-on PHY_RUNNING state and disable on any other state.
-
-Fixes: b4df02b562f4 ("net: phy: at803x: add support for qca 8327 A variant internal phy")
-Signed-off-by: Ansuel Smith <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/phy/at803x.c | 33 +++++++++++++++++++++++++++++++++
- 1 file changed, 33 insertions(+)
-
---- a/drivers/net/phy/at803x.c
-+++ b/drivers/net/phy/at803x.c
-@@ -87,6 +87,8 @@
- #define AT803X_PSSR_MR_AN_COMPLETE            0x0200
- #define AT803X_DEBUG_REG_0                    0x00
-+#define QCA8327_DEBUG_MANU_CTRL_EN            BIT(2)
-+#define QCA8337_DEBUG_MANU_CTRL_EN            GENMASK(3, 2)
- #define AT803X_DEBUG_RX_CLK_DLY_EN            BIT(15)
- #define AT803X_DEBUG_REG_5                    0x05
-@@ -1306,9 +1308,37 @@ static int qca83xx_config_init(struct ph
-               break;
-       }
-+      /* QCA8327 require DAC amplitude adjustment for 100m set to +6%.
-+       * Disable on init and enable only with 100m speed following
-+       * qca original source code.
-+       */
-+      if (phydev->drv->phy_id == QCA8327_A_PHY_ID ||
-+          phydev->drv->phy_id == QCA8327_B_PHY_ID)
-+              at803x_debug_reg_mask(phydev, AT803X_DEBUG_REG_0,
-+                                    QCA8327_DEBUG_MANU_CTRL_EN, 0);
-+
-       return 0;
- }
-+static void qca83xx_link_change_notify(struct phy_device *phydev)
-+{
-+      /* QCA8337 doesn't require DAC Amplitude adjustement */
-+      if (phydev->drv->phy_id == QCA8337_PHY_ID)
-+              return;
-+
-+      /* Set DAC Amplitude adjustment to +6% for 100m on link running */
-+      if (phydev->state == PHY_RUNNING) {
-+              if (phydev->speed == SPEED_100)
-+                      at803x_debug_reg_mask(phydev, AT803X_DEBUG_REG_0,
-+                                            QCA8327_DEBUG_MANU_CTRL_EN,
-+                                            QCA8327_DEBUG_MANU_CTRL_EN);
-+      } else {
-+              /* Reset DAC Amplitude adjustment */
-+              at803x_debug_reg_mask(phydev, AT803X_DEBUG_REG_0,
-+                                    QCA8327_DEBUG_MANU_CTRL_EN, 0);
-+      }
-+}
-+
- static int qca83xx_resume(struct phy_device *phydev)
- {
-       int ret, val;
-@@ -1461,6 +1491,7 @@ static struct phy_driver at803x_driver[]
-       .phy_id_mask            = QCA8K_PHY_ID_MASK,
-       .name                   = "Qualcomm Atheros 8337 internal PHY",
-       /* PHY_GBIT_FEATURES */
-+      .link_change_notify     = qca83xx_link_change_notify,
-       .probe                  = at803x_probe,
-       .flags                  = PHY_IS_INTERNAL,
-       .config_init            = qca83xx_config_init,
-@@ -1476,6 +1507,7 @@ static struct phy_driver at803x_driver[]
-       .phy_id_mask            = QCA8K_PHY_ID_MASK,
-       .name                   = "Qualcomm Atheros 8327-A internal PHY",
-       /* PHY_GBIT_FEATURES */
-+      .link_change_notify     = qca83xx_link_change_notify,
-       .probe                  = at803x_probe,
-       .flags                  = PHY_IS_INTERNAL,
-       .config_init            = qca83xx_config_init,
-@@ -1491,6 +1523,7 @@ static struct phy_driver at803x_driver[]
-       .phy_id_mask            = QCA8K_PHY_ID_MASK,
-       .name                   = "Qualcomm Atheros 8327-B internal PHY",
-       /* PHY_GBIT_FEATURES */
-+      .link_change_notify     = qca83xx_link_change_notify,
-       .probe                  = at803x_probe,
-       .flags                  = PHY_IS_INTERNAL,
-       .config_init            = qca83xx_config_init,
diff --git a/target/linux/generic/backport-5.15/746-v5.16-03-net-phy-at803x-enable-prefer-master-for-83xx-interna.patch b/target/linux/generic/backport-5.15/746-v5.16-03-net-phy-at803x-enable-prefer-master-for-83xx-interna.patch
deleted file mode 100644 (file)
index 9f88059..0000000
+++ /dev/null
@@ -1,27 +0,0 @@
-From 9d1c29b4028557a496be9c5eb2b4b86063700636 Mon Sep 17 00:00:00 2001
-From: Ansuel Smith <[email protected]>
-Date: Sun, 10 Oct 2021 00:46:17 +0200
-Subject: net: phy: at803x: enable prefer master for 83xx internal phy
-
-From original QCA source code the port was set to prefer master as port
-type in 1000BASE-T mode. Apply the same settings also here.
-
-Signed-off-by: Ansuel Smith <[email protected]>
-Reviewed-by: Andrew Lunn <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/phy/at803x.c | 3 +++
- 1 file changed, 3 insertions(+)
-
---- a/drivers/net/phy/at803x.c
-+++ b/drivers/net/phy/at803x.c
-@@ -1317,6 +1317,9 @@ static int qca83xx_config_init(struct ph
-               at803x_debug_reg_mask(phydev, AT803X_DEBUG_REG_0,
-                                     QCA8327_DEBUG_MANU_CTRL_EN, 0);
-+      /* Following original QCA sourcecode set port to prefer master */
-+      phy_set_bits(phydev, MII_CTRL1000, CTL1000_PREFER_MASTER);
-+
-       return 0;
- }
diff --git a/target/linux/generic/backport-5.15/746-v5.16-04-net-phy-at803x-better-describe-debug-regs.patch b/target/linux/generic/backport-5.15/746-v5.16-04-net-phy-at803x-better-describe-debug-regs.patch
deleted file mode 100644 (file)
index 89e9b3f..0000000
+++ /dev/null
@@ -1,127 +0,0 @@
-From 67999555ff42e91de7654488d9a7735bd9e84555 Mon Sep 17 00:00:00 2001
-From: Ansuel Smith <[email protected]>
-Date: Sun, 10 Oct 2021 00:46:18 +0200
-Subject: net: phy: at803x: better describe debug regs
-
-Give a name to known debug regs from Documentation instead of using
-unknown hex values.
-
-Signed-off-by: Ansuel Smith <[email protected]>
-Reviewed-by: Andrew Lunn <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/phy/at803x.c | 30 +++++++++++++++---------------
- 1 file changed, 15 insertions(+), 15 deletions(-)
-
---- a/drivers/net/phy/at803x.c
-+++ b/drivers/net/phy/at803x.c
-@@ -86,12 +86,12 @@
- #define AT803X_PSSR                           0x11    /*PHY-Specific Status Register*/
- #define AT803X_PSSR_MR_AN_COMPLETE            0x0200
--#define AT803X_DEBUG_REG_0                    0x00
-+#define AT803X_DEBUG_ANALOG_TEST_CTRL         0x00
- #define QCA8327_DEBUG_MANU_CTRL_EN            BIT(2)
- #define QCA8337_DEBUG_MANU_CTRL_EN            GENMASK(3, 2)
- #define AT803X_DEBUG_RX_CLK_DLY_EN            BIT(15)
--#define AT803X_DEBUG_REG_5                    0x05
-+#define AT803X_DEBUG_SYSTEM_CTRL_MODE         0x05
- #define AT803X_DEBUG_TX_CLK_DLY_EN            BIT(8)
- #define AT803X_DEBUG_REG_HIB_CTRL             0x0b
-@@ -100,7 +100,7 @@
- #define AT803X_DEBUG_REG_3C                   0x3C
--#define AT803X_DEBUG_REG_3D                   0x3D
-+#define AT803X_DEBUG_REG_GREEN                        0x3D
- #define   AT803X_DEBUG_GATE_CLK_IN1000                BIT(6)
- #define AT803X_DEBUG_REG_1F                   0x1F
-@@ -284,25 +284,25 @@ static int at803x_read_page(struct phy_d
- static int at803x_enable_rx_delay(struct phy_device *phydev)
- {
--      return at803x_debug_reg_mask(phydev, AT803X_DEBUG_REG_0, 0,
-+      return at803x_debug_reg_mask(phydev, AT803X_DEBUG_ANALOG_TEST_CTRL, 0,
-                                    AT803X_DEBUG_RX_CLK_DLY_EN);
- }
- static int at803x_enable_tx_delay(struct phy_device *phydev)
- {
--      return at803x_debug_reg_mask(phydev, AT803X_DEBUG_REG_5, 0,
-+      return at803x_debug_reg_mask(phydev, AT803X_DEBUG_SYSTEM_CTRL_MODE, 0,
-                                    AT803X_DEBUG_TX_CLK_DLY_EN);
- }
- static int at803x_disable_rx_delay(struct phy_device *phydev)
- {
--      return at803x_debug_reg_mask(phydev, AT803X_DEBUG_REG_0,
-+      return at803x_debug_reg_mask(phydev, AT803X_DEBUG_ANALOG_TEST_CTRL,
-                                    AT803X_DEBUG_RX_CLK_DLY_EN, 0);
- }
- static int at803x_disable_tx_delay(struct phy_device *phydev)
- {
--      return at803x_debug_reg_mask(phydev, AT803X_DEBUG_REG_5,
-+      return at803x_debug_reg_mask(phydev, AT803X_DEBUG_SYSTEM_CTRL_MODE,
-                                    AT803X_DEBUG_TX_CLK_DLY_EN, 0);
- }
-@@ -1292,9 +1292,9 @@ static int qca83xx_config_init(struct ph
-       switch (switch_revision) {
-       case 1:
-               /* For 100M waveform */
--              at803x_debug_reg_write(phydev, AT803X_DEBUG_REG_0, 0x02ea);
-+              at803x_debug_reg_write(phydev, AT803X_DEBUG_ANALOG_TEST_CTRL, 0x02ea);
-               /* Turn on Gigabit clock */
--              at803x_debug_reg_write(phydev, AT803X_DEBUG_REG_3D, 0x68a0);
-+              at803x_debug_reg_write(phydev, AT803X_DEBUG_REG_GREEN, 0x68a0);
-               break;
-       case 2:
-@@ -1302,8 +1302,8 @@ static int qca83xx_config_init(struct ph
-               fallthrough;
-       case 4:
-               phy_write_mmd(phydev, MDIO_MMD_PCS, MDIO_AZ_DEBUG, 0x803f);
--              at803x_debug_reg_write(phydev, AT803X_DEBUG_REG_3D, 0x6860);
--              at803x_debug_reg_write(phydev, AT803X_DEBUG_REG_5, 0x2c46);
-+              at803x_debug_reg_write(phydev, AT803X_DEBUG_REG_GREEN, 0x6860);
-+              at803x_debug_reg_write(phydev, AT803X_DEBUG_SYSTEM_CTRL_MODE, 0x2c46);
-               at803x_debug_reg_write(phydev, AT803X_DEBUG_REG_3C, 0x6000);
-               break;
-       }
-@@ -1314,7 +1314,7 @@ static int qca83xx_config_init(struct ph
-        */
-       if (phydev->drv->phy_id == QCA8327_A_PHY_ID ||
-           phydev->drv->phy_id == QCA8327_B_PHY_ID)
--              at803x_debug_reg_mask(phydev, AT803X_DEBUG_REG_0,
-+              at803x_debug_reg_mask(phydev, AT803X_DEBUG_ANALOG_TEST_CTRL,
-                                     QCA8327_DEBUG_MANU_CTRL_EN, 0);
-       /* Following original QCA sourcecode set port to prefer master */
-@@ -1332,12 +1332,12 @@ static void qca83xx_link_change_notify(s
-       /* Set DAC Amplitude adjustment to +6% for 100m on link running */
-       if (phydev->state == PHY_RUNNING) {
-               if (phydev->speed == SPEED_100)
--                      at803x_debug_reg_mask(phydev, AT803X_DEBUG_REG_0,
-+                      at803x_debug_reg_mask(phydev, AT803X_DEBUG_ANALOG_TEST_CTRL,
-                                             QCA8327_DEBUG_MANU_CTRL_EN,
-                                             QCA8327_DEBUG_MANU_CTRL_EN);
-       } else {
-               /* Reset DAC Amplitude adjustment */
--              at803x_debug_reg_mask(phydev, AT803X_DEBUG_REG_0,
-+              at803x_debug_reg_mask(phydev, AT803X_DEBUG_ANALOG_TEST_CTRL,
-                                     QCA8327_DEBUG_MANU_CTRL_EN, 0);
-       }
- }
-@@ -1384,7 +1384,7 @@ static int qca83xx_suspend(struct phy_de
-               phy_modify(phydev, MII_BMCR, mask, 0);
-       }
--      at803x_debug_reg_mask(phydev, AT803X_DEBUG_REG_3D,
-+      at803x_debug_reg_mask(phydev, AT803X_DEBUG_REG_GREEN,
-                             AT803X_DEBUG_GATE_CLK_IN1000, 0);
-       at803x_debug_reg_mask(phydev, AT803X_DEBUG_REG_HIB_CTRL,
diff --git a/target/linux/generic/backport-5.15/747-v5.16-01-dsa-qca8k-add-mac-power-sel-support.patch b/target/linux/generic/backport-5.15/747-v5.16-01-dsa-qca8k-add-mac-power-sel-support.patch
deleted file mode 100644 (file)
index c8d424d..0000000
+++ /dev/null
@@ -1,80 +0,0 @@
-From d8b6f5bae6d3b648a67b6958cb98e4e97256d652 Mon Sep 17 00:00:00 2001
-From: Ansuel Smith <[email protected]>
-Date: Thu, 14 Oct 2021 00:39:06 +0200
-Subject: dsa: qca8k: add mac_power_sel support
-
-Add missing mac power sel support needed for ipq8064/5 SoC that require
-1.8v for the internal regulator port instead of the default 1.5v.
-If other device needs this, consider adding a dedicated binding to
-support this.
-
-Signed-off-by: Ansuel Smith <[email protected]>
-Reviewed-by: Vladimir Oltean <[email protected]>
-Reviewed-by: Florian Fainelli <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/dsa/qca8k.c | 31 +++++++++++++++++++++++++++++++
- drivers/net/dsa/qca8k.h |  5 +++++
- 2 files changed, 36 insertions(+)
-
---- a/drivers/net/dsa/qca8k.c
-+++ b/drivers/net/dsa/qca8k.c
-@@ -951,6 +951,33 @@ qca8k_setup_of_rgmii_delay(struct qca8k_
- }
- static int
-+qca8k_setup_mac_pwr_sel(struct qca8k_priv *priv)
-+{
-+      u32 mask = 0;
-+      int ret = 0;
-+
-+      /* SoC specific settings for ipq8064.
-+       * If more device require this consider adding
-+       * a dedicated binding.
-+       */
-+      if (of_machine_is_compatible("qcom,ipq8064"))
-+              mask |= QCA8K_MAC_PWR_RGMII0_1_8V;
-+
-+      /* SoC specific settings for ipq8065 */
-+      if (of_machine_is_compatible("qcom,ipq8065"))
-+              mask |= QCA8K_MAC_PWR_RGMII1_1_8V;
-+
-+      if (mask) {
-+              ret = qca8k_rmw(priv, QCA8K_REG_MAC_PWR_SEL,
-+                              QCA8K_MAC_PWR_RGMII0_1_8V |
-+                              QCA8K_MAC_PWR_RGMII1_1_8V,
-+                              mask);
-+      }
-+
-+      return ret;
-+}
-+
-+static int
- qca8k_setup(struct dsa_switch *ds)
- {
-       struct qca8k_priv *priv = (struct qca8k_priv *)ds->priv;
-@@ -979,6 +1006,10 @@ qca8k_setup(struct dsa_switch *ds)
-       if (ret)
-               return ret;
-+      ret = qca8k_setup_mac_pwr_sel(priv);
-+      if (ret)
-+              return ret;
-+
-       /* Enable CPU Port */
-       ret = qca8k_reg_set(priv, QCA8K_REG_GLOBAL_FW_CTRL0,
-                           QCA8K_GLOBAL_FW_CTRL0_CPU_PORT_EN);
---- a/drivers/net/dsa/qca8k.h
-+++ b/drivers/net/dsa/qca8k.h
-@@ -100,6 +100,11 @@
- #define   QCA8K_SGMII_MODE_CTRL_PHY                   (1 << 22)
- #define   QCA8K_SGMII_MODE_CTRL_MAC                   (2 << 22)
-+/* MAC_PWR_SEL registers */
-+#define QCA8K_REG_MAC_PWR_SEL                         0x0e4
-+#define   QCA8K_MAC_PWR_RGMII1_1_8V                   BIT(18)
-+#define   QCA8K_MAC_PWR_RGMII0_1_8V                   BIT(19)
-+
- /* EEE control registers */
- #define QCA8K_REG_EEE_CTRL                            0x100
- #define  QCA8K_REG_EEE_CTRL_LPI_EN(_i)                        ((_i + 1) * 2)
diff --git a/target/linux/generic/backport-5.15/747-v5.16-02-dt-bindings-net-dsa-qca8k-Add-SGMII-clock-phase-prop.patch b/target/linux/generic/backport-5.15/747-v5.16-02-dt-bindings-net-dsa-qca8k-Add-SGMII-clock-phase-prop.patch
deleted file mode 100644 (file)
index bd768ec..0000000
+++ /dev/null
@@ -1,30 +0,0 @@
-From fdbf35df9c091db9c46e57e9938e3f7a4f603a7c Mon Sep 17 00:00:00 2001
-From: Ansuel Smith <[email protected]>
-Date: Thu, 14 Oct 2021 00:39:07 +0200
-Subject: dt-bindings: net: dsa: qca8k: Add SGMII clock phase properties
-
-Add names and descriptions of additional PORT0_PAD_CTRL properties.
-qca,sgmii-(rx|tx)clk-falling-edge are for setting the respective clock
-phase to failling edge.
-
-Co-developed-by: Matthew Hagan <[email protected]>
-Signed-off-by: Matthew Hagan <[email protected]>
-Signed-off-by: Ansuel Smith <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- Documentation/devicetree/bindings/net/dsa/qca8k.txt | 4 ++++
- 1 file changed, 4 insertions(+)
-
---- a/Documentation/devicetree/bindings/net/dsa/qca8k.txt
-+++ b/Documentation/devicetree/bindings/net/dsa/qca8k.txt
-@@ -37,6 +37,10 @@ A CPU port node has the following option
-                           managed entity. See
-                           Documentation/devicetree/bindings/net/fixed-link.txt
-                           for details.
-+- qca,sgmii-rxclk-falling-edge: Set the receive clock phase to falling edge.
-+                                Mostly used in qca8327 with CPU port 0 set to
-+                                sgmii.
-+- qca,sgmii-txclk-falling-edge: Set the transmit clock phase to falling edge.
- For QCA8K the 'fixed-link' sub-node supports only the following properties:
diff --git a/target/linux/generic/backport-5.15/747-v5.16-03-net-dsa-qca8k-add-support-for-sgmii-falling-edge.patch b/target/linux/generic/backport-5.15/747-v5.16-03-net-dsa-qca8k-add-support-for-sgmii-falling-edge.patch
deleted file mode 100644 (file)
index e464452..0000000
+++ /dev/null
@@ -1,127 +0,0 @@
-From 6c43809bf1bee76c434e365a26546a92a5fbec14 Mon Sep 17 00:00:00 2001
-From: Ansuel Smith <[email protected]>
-Date: Thu, 14 Oct 2021 00:39:08 +0200
-Subject: net: dsa: qca8k: add support for sgmii falling edge
-
-Add support for this in the qca8k driver. Also add support for SGMII
-rx/tx clock falling edge. This is only present for pad0, pad5 and
-pad6 have these bit reserved from Documentation. Add a comment that this
-is hardcoded to PAD0 as qca8327/28/34/37 have an unique sgmii line and
-setting falling in port0 applies to both configuration with sgmii used
-for port0 or port6.
-
-Co-developed-by: Matthew Hagan <[email protected]>
-Signed-off-by: Matthew Hagan <[email protected]>
-Signed-off-by: Ansuel Smith <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/dsa/qca8k.c | 63 +++++++++++++++++++++++++++++++++++++++++++++++++
- drivers/net/dsa/qca8k.h |  4 ++++
- 2 files changed, 67 insertions(+)
-
---- a/drivers/net/dsa/qca8k.c
-+++ b/drivers/net/dsa/qca8k.c
-@@ -978,6 +978,42 @@ qca8k_setup_mac_pwr_sel(struct qca8k_pri
- }
- static int
-+qca8k_parse_port_config(struct qca8k_priv *priv)
-+{
-+      struct device_node *port_dn;
-+      phy_interface_t mode;
-+      struct dsa_port *dp;
-+      int port, ret;
-+
-+      /* We have 2 CPU port. Check them */
-+      for (port = 0; port < QCA8K_NUM_PORTS; port++) {
-+              /* Skip every other port */
-+              if (port != 0 && port != 6)
-+                      continue;
-+
-+              dp = dsa_to_port(priv->ds, port);
-+              port_dn = dp->dn;
-+
-+              if (!of_device_is_available(port_dn))
-+                      continue;
-+
-+              ret = of_get_phy_mode(port_dn, &mode);
-+              if (ret)
-+                      continue;
-+
-+              if (mode == PHY_INTERFACE_MODE_SGMII) {
-+                      if (of_property_read_bool(port_dn, "qca,sgmii-txclk-falling-edge"))
-+                              priv->sgmii_tx_clk_falling_edge = true;
-+
-+                      if (of_property_read_bool(port_dn, "qca,sgmii-rxclk-falling-edge"))
-+                              priv->sgmii_rx_clk_falling_edge = true;
-+              }
-+      }
-+
-+      return 0;
-+}
-+
-+static int
- qca8k_setup(struct dsa_switch *ds)
- {
-       struct qca8k_priv *priv = (struct qca8k_priv *)ds->priv;
-@@ -990,6 +1026,11 @@ qca8k_setup(struct dsa_switch *ds)
-               return -EINVAL;
-       }
-+      /* Parse CPU port config to be later used in phy_link mac_config */
-+      ret = qca8k_parse_port_config(priv);
-+      if (ret)
-+              return ret;
-+
-       mutex_init(&priv->reg_mutex);
-       /* Start by setting up the register mapping */
-@@ -1274,6 +1315,28 @@ qca8k_phylink_mac_config(struct dsa_swit
-               }
-               qca8k_write(priv, QCA8K_REG_SGMII_CTRL, val);
-+
-+              /* For qca8327/qca8328/qca8334/qca8338 sgmii is unique and
-+               * falling edge is set writing in the PORT0 PAD reg
-+               */
-+              if (priv->switch_id == QCA8K_ID_QCA8327 ||
-+                  priv->switch_id == QCA8K_ID_QCA8337)
-+                      reg = QCA8K_REG_PORT0_PAD_CTRL;
-+
-+              val = 0;
-+
-+              /* SGMII Clock phase configuration */
-+              if (priv->sgmii_rx_clk_falling_edge)
-+                      val |= QCA8K_PORT0_PAD_SGMII_RXCLK_FALLING_EDGE;
-+
-+              if (priv->sgmii_tx_clk_falling_edge)
-+                      val |= QCA8K_PORT0_PAD_SGMII_TXCLK_FALLING_EDGE;
-+
-+              if (val)
-+                      ret = qca8k_rmw(priv, reg,
-+                                      QCA8K_PORT0_PAD_SGMII_RXCLK_FALLING_EDGE |
-+                                      QCA8K_PORT0_PAD_SGMII_TXCLK_FALLING_EDGE,
-+                                      val);
-               break;
-       default:
-               dev_err(ds->dev, "xMII mode %s not supported for port %d\n",
---- a/drivers/net/dsa/qca8k.h
-+++ b/drivers/net/dsa/qca8k.h
-@@ -35,6 +35,8 @@
- #define   QCA8K_MASK_CTRL_DEVICE_ID_MASK              GENMASK(15, 8)
- #define   QCA8K_MASK_CTRL_DEVICE_ID(x)                        ((x) >> 8)
- #define QCA8K_REG_PORT0_PAD_CTRL                      0x004
-+#define   QCA8K_PORT0_PAD_SGMII_RXCLK_FALLING_EDGE    BIT(19)
-+#define   QCA8K_PORT0_PAD_SGMII_TXCLK_FALLING_EDGE    BIT(18)
- #define QCA8K_REG_PORT5_PAD_CTRL                      0x008
- #define QCA8K_REG_PORT6_PAD_CTRL                      0x00c
- #define   QCA8K_PORT_PAD_RGMII_EN                     BIT(26)
-@@ -260,6 +262,8 @@ struct qca8k_priv {
-       u8 switch_revision;
-       u8 rgmii_tx_delay;
-       u8 rgmii_rx_delay;
-+      bool sgmii_rx_clk_falling_edge;
-+      bool sgmii_tx_clk_falling_edge;
-       bool legacy_phy_port_mapping;
-       struct regmap *regmap;
-       struct mii_bus *bus;
diff --git a/target/linux/generic/backport-5.15/747-v5.16-04-dt-bindings-net-dsa-qca8k-Document-support-for-CPU-p.patch b/target/linux/generic/backport-5.15/747-v5.16-04-dt-bindings-net-dsa-qca8k-Document-support-for-CPU-p.patch
deleted file mode 100644 (file)
index 606ac0a..0000000
+++ /dev/null
@@ -1,29 +0,0 @@
-From 731d613338ec6de482053ffa3f71be2325b0f8eb Mon Sep 17 00:00:00 2001
-From: Ansuel Smith <[email protected]>
-Date: Thu, 14 Oct 2021 00:39:09 +0200
-Subject: dt-bindings: net: dsa: qca8k: Document support for CPU port 6
-
-The switch now support CPU port to be set 6 instead of be hardcoded to
-0. Document support for it and describe logic selection.
-
-Signed-off-by: Ansuel Smith <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- Documentation/devicetree/bindings/net/dsa/qca8k.txt | 6 +++++-
- 1 file changed, 5 insertions(+), 1 deletion(-)
-
---- a/Documentation/devicetree/bindings/net/dsa/qca8k.txt
-+++ b/Documentation/devicetree/bindings/net/dsa/qca8k.txt
-@@ -29,7 +29,11 @@ the mdio MASTER is used as communication
- Don't use mixed external and internal mdio-bus configurations, as this is
- not supported by the hardware.
--The CPU port of this switch is always port 0.
-+This switch support 2 CPU port. Normally and advised configuration is with
-+CPU port set to port 0. It is also possible to set the CPU port to port 6
-+if the device requires it. The driver will configure the switch to the defined
-+port. With both CPU port declared the first CPU port is selected as primary
-+and the secondary CPU ignored.
- A CPU port node has the following optional node:
diff --git a/target/linux/generic/backport-5.15/747-v5.16-05-net-dsa-qca8k-add-support-for-cpu-port-6.patch b/target/linux/generic/backport-5.15/747-v5.16-05-net-dsa-qca8k-add-support-for-cpu-port-6.patch
deleted file mode 100644 (file)
index 320db8f..0000000
+++ /dev/null
@@ -1,153 +0,0 @@
-From 3fcf734aa482487df83cf8f18608438fcf59127f Mon Sep 17 00:00:00 2001
-From: Ansuel Smith <[email protected]>
-Date: Thu, 14 Oct 2021 00:39:10 +0200
-Subject: net: dsa: qca8k: add support for cpu port 6
-
-Currently CPU port is always hardcoded to port 0. This switch have 2 CPU
-ports. The original intention of this driver seems to be use the
-mac06_exchange bit to swap MAC0 with MAC6 in the strange configuration
-where device have connected only the CPU port 6. To skip the
-introduction of a new binding, rework the driver to address the
-secondary CPU port as primary and drop any reference of hardcoded port.
-With configuration of mac06 exchange, just skip the definition of port0
-and define the CPU port as a secondary. The driver will autoconfigure
-the switch to use that as the primary CPU port.
-
-Signed-off-by: Ansuel Smith <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/dsa/qca8k.c | 51 ++++++++++++++++++++++++++++++++++---------------
- drivers/net/dsa/qca8k.h |  2 --
- 2 files changed, 36 insertions(+), 17 deletions(-)
-
---- a/drivers/net/dsa/qca8k.c
-+++ b/drivers/net/dsa/qca8k.c
-@@ -977,6 +977,22 @@ qca8k_setup_mac_pwr_sel(struct qca8k_pri
-       return ret;
- }
-+static int qca8k_find_cpu_port(struct dsa_switch *ds)
-+{
-+      struct qca8k_priv *priv = ds->priv;
-+
-+      /* Find the connected cpu port. Valid port are 0 or 6 */
-+      if (dsa_is_cpu_port(ds, 0))
-+              return 0;
-+
-+      dev_dbg(priv->dev, "port 0 is not the CPU port. Checking port 6");
-+
-+      if (dsa_is_cpu_port(ds, 6))
-+              return 6;
-+
-+      return -EINVAL;
-+}
-+
- static int
- qca8k_parse_port_config(struct qca8k_priv *priv)
- {
-@@ -1017,13 +1033,13 @@ static int
- qca8k_setup(struct dsa_switch *ds)
- {
-       struct qca8k_priv *priv = (struct qca8k_priv *)ds->priv;
--      int ret, i;
-+      int cpu_port, ret, i;
-       u32 mask;
--      /* Make sure that port 0 is the cpu port */
--      if (!dsa_is_cpu_port(ds, 0)) {
--              dev_err(priv->dev, "port 0 is not the CPU port");
--              return -EINVAL;
-+      cpu_port = qca8k_find_cpu_port(ds);
-+      if (cpu_port < 0) {
-+              dev_err(priv->dev, "No cpu port configured in both cpu port0 and port6");
-+              return cpu_port;
-       }
-       /* Parse CPU port config to be later used in phy_link mac_config */
-@@ -1065,7 +1081,7 @@ qca8k_setup(struct dsa_switch *ds)
-               dev_warn(priv->dev, "mib init failed");
-       /* Enable QCA header mode on the cpu port */
--      ret = qca8k_write(priv, QCA8K_REG_PORT_HDR_CTRL(QCA8K_CPU_PORT),
-+      ret = qca8k_write(priv, QCA8K_REG_PORT_HDR_CTRL(cpu_port),
-                         QCA8K_PORT_HDR_CTRL_ALL << QCA8K_PORT_HDR_CTRL_TX_S |
-                         QCA8K_PORT_HDR_CTRL_ALL << QCA8K_PORT_HDR_CTRL_RX_S);
-       if (ret) {
-@@ -1087,10 +1103,10 @@ qca8k_setup(struct dsa_switch *ds)
-       /* Forward all unknown frames to CPU port for Linux processing */
-       ret = qca8k_write(priv, QCA8K_REG_GLOBAL_FW_CTRL1,
--                        BIT(0) << QCA8K_GLOBAL_FW_CTRL1_IGMP_DP_S |
--                        BIT(0) << QCA8K_GLOBAL_FW_CTRL1_BC_DP_S |
--                        BIT(0) << QCA8K_GLOBAL_FW_CTRL1_MC_DP_S |
--                        BIT(0) << QCA8K_GLOBAL_FW_CTRL1_UC_DP_S);
-+                        BIT(cpu_port) << QCA8K_GLOBAL_FW_CTRL1_IGMP_DP_S |
-+                        BIT(cpu_port) << QCA8K_GLOBAL_FW_CTRL1_BC_DP_S |
-+                        BIT(cpu_port) << QCA8K_GLOBAL_FW_CTRL1_MC_DP_S |
-+                        BIT(cpu_port) << QCA8K_GLOBAL_FW_CTRL1_UC_DP_S);
-       if (ret)
-               return ret;
-@@ -1098,7 +1114,7 @@ qca8k_setup(struct dsa_switch *ds)
-       for (i = 0; i < QCA8K_NUM_PORTS; i++) {
-               /* CPU port gets connected to all user ports of the switch */
-               if (dsa_is_cpu_port(ds, i)) {
--                      ret = qca8k_rmw(priv, QCA8K_PORT_LOOKUP_CTRL(QCA8K_CPU_PORT),
-+                      ret = qca8k_rmw(priv, QCA8K_PORT_LOOKUP_CTRL(cpu_port),
-                                       QCA8K_PORT_LOOKUP_MEMBER, dsa_user_ports(ds));
-                       if (ret)
-                               return ret;
-@@ -1110,7 +1126,7 @@ qca8k_setup(struct dsa_switch *ds)
-                       ret = qca8k_rmw(priv, QCA8K_PORT_LOOKUP_CTRL(i),
-                                       QCA8K_PORT_LOOKUP_MEMBER,
--                                      BIT(QCA8K_CPU_PORT));
-+                                      BIT(cpu_port));
-                       if (ret)
-                               return ret;
-@@ -1616,9 +1632,12 @@ static int
- qca8k_port_bridge_join(struct dsa_switch *ds, int port, struct net_device *br)
- {
-       struct qca8k_priv *priv = (struct qca8k_priv *)ds->priv;
--      int port_mask = BIT(QCA8K_CPU_PORT);
-+      int port_mask, cpu_port;
-       int i, ret;
-+      cpu_port = dsa_to_port(ds, port)->cpu_dp->index;
-+      port_mask = BIT(cpu_port);
-+
-       for (i = 1; i < QCA8K_NUM_PORTS; i++) {
-               if (dsa_to_port(ds, i)->bridge_dev != br)
-                       continue;
-@@ -1645,7 +1664,9 @@ static void
- qca8k_port_bridge_leave(struct dsa_switch *ds, int port, struct net_device *br)
- {
-       struct qca8k_priv *priv = (struct qca8k_priv *)ds->priv;
--      int i;
-+      int cpu_port, i;
-+
-+      cpu_port = dsa_to_port(ds, port)->cpu_dp->index;
-       for (i = 1; i < QCA8K_NUM_PORTS; i++) {
-               if (dsa_to_port(ds, i)->bridge_dev != br)
-@@ -1662,7 +1683,7 @@ qca8k_port_bridge_leave(struct dsa_switc
-        * this port
-        */
-       qca8k_rmw(priv, QCA8K_PORT_LOOKUP_CTRL(port),
--                QCA8K_PORT_LOOKUP_MEMBER, BIT(QCA8K_CPU_PORT));
-+                QCA8K_PORT_LOOKUP_MEMBER, BIT(cpu_port));
- }
- static int
---- a/drivers/net/dsa/qca8k.h
-+++ b/drivers/net/dsa/qca8k.h
-@@ -24,8 +24,6 @@
- #define QCA8K_NUM_FDB_RECORDS                         2048
--#define QCA8K_CPU_PORT                                        0
--
- #define QCA8K_PORT_VID_DEF                            1
- /* Global control registers */
diff --git a/target/linux/generic/backport-5.15/747-v5.16-06-net-dsa-qca8k-rework-rgmii-delay-logic-and-scan-for-.patch b/target/linux/generic/backport-5.15/747-v5.16-06-net-dsa-qca8k-rework-rgmii-delay-logic-and-scan-for-.patch
deleted file mode 100644 (file)
index de20176..0000000
+++ /dev/null
@@ -1,295 +0,0 @@
-From 5654ec78dd7e64b1e04777b24007344329e6a63b Mon Sep 17 00:00:00 2001
-From: Ansuel Smith <[email protected]>
-Date: Thu, 14 Oct 2021 00:39:11 +0200
-Subject: net: dsa: qca8k: rework rgmii delay logic and scan for cpu port 6
-
-Future proof commit. This switch have 2 CPU ports and one valid
-configuration is first CPU port set to sgmii and second CPU port set to
-rgmii-id. The current implementation detects delay only for CPU port
-zero set to rgmii and doesn't count any delay set in a secondary CPU
-port. Drop the current delay scan function and move it to the sgmii
-parser function to generalize and implicitly add support for secondary
-CPU port set to rgmii-id. Introduce new logic where delay is enabled
-also with internal delay binding declared and rgmii set as PHY mode.
-
-Signed-off-by: Ansuel Smith <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/dsa/qca8k.c | 165 ++++++++++++++++++++++++------------------------
- drivers/net/dsa/qca8k.h |  10 ++-
- 2 files changed, 89 insertions(+), 86 deletions(-)
-
---- a/drivers/net/dsa/qca8k.c
-+++ b/drivers/net/dsa/qca8k.c
-@@ -889,68 +889,6 @@ qca8k_setup_mdio_bus(struct qca8k_priv *
- }
- static int
--qca8k_setup_of_rgmii_delay(struct qca8k_priv *priv)
--{
--      struct device_node *port_dn;
--      phy_interface_t mode;
--      struct dsa_port *dp;
--      u32 val;
--
--      /* CPU port is already checked */
--      dp = dsa_to_port(priv->ds, 0);
--
--      port_dn = dp->dn;
--
--      /* Check if port 0 is set to the correct type */
--      of_get_phy_mode(port_dn, &mode);
--      if (mode != PHY_INTERFACE_MODE_RGMII_ID &&
--          mode != PHY_INTERFACE_MODE_RGMII_RXID &&
--          mode != PHY_INTERFACE_MODE_RGMII_TXID) {
--              return 0;
--      }
--
--      switch (mode) {
--      case PHY_INTERFACE_MODE_RGMII_ID:
--      case PHY_INTERFACE_MODE_RGMII_RXID:
--              if (of_property_read_u32(port_dn, "rx-internal-delay-ps", &val))
--                      val = 2;
--              else
--                      /* Switch regs accept value in ns, convert ps to ns */
--                      val = val / 1000;
--
--              if (val > QCA8K_MAX_DELAY) {
--                      dev_err(priv->dev, "rgmii rx delay is limited to a max value of 3ns, setting to the max value");
--                      val = 3;
--              }
--
--              priv->rgmii_rx_delay = val;
--              /* Stop here if we need to check only for rx delay */
--              if (mode != PHY_INTERFACE_MODE_RGMII_ID)
--                      break;
--
--              fallthrough;
--      case PHY_INTERFACE_MODE_RGMII_TXID:
--              if (of_property_read_u32(port_dn, "tx-internal-delay-ps", &val))
--                      val = 1;
--              else
--                      /* Switch regs accept value in ns, convert ps to ns */
--                      val = val / 1000;
--
--              if (val > QCA8K_MAX_DELAY) {
--                      dev_err(priv->dev, "rgmii tx delay is limited to a max value of 3ns, setting to the max value");
--                      val = 3;
--              }
--
--              priv->rgmii_tx_delay = val;
--              break;
--      default:
--              return 0;
--      }
--
--      return 0;
--}
--
--static int
- qca8k_setup_mac_pwr_sel(struct qca8k_priv *priv)
- {
-       u32 mask = 0;
-@@ -996,19 +934,21 @@ static int qca8k_find_cpu_port(struct ds
- static int
- qca8k_parse_port_config(struct qca8k_priv *priv)
- {
-+      int port, cpu_port_index = 0, ret;
-       struct device_node *port_dn;
-       phy_interface_t mode;
-       struct dsa_port *dp;
--      int port, ret;
-+      u32 delay;
-       /* We have 2 CPU port. Check them */
--      for (port = 0; port < QCA8K_NUM_PORTS; port++) {
-+      for (port = 0; port < QCA8K_NUM_PORTS && cpu_port_index < QCA8K_NUM_CPU_PORTS; port++) {
-               /* Skip every other port */
-               if (port != 0 && port != 6)
-                       continue;
-               dp = dsa_to_port(priv->ds, port);
-               port_dn = dp->dn;
-+              cpu_port_index++;
-               if (!of_device_is_available(port_dn))
-                       continue;
-@@ -1017,12 +957,54 @@ qca8k_parse_port_config(struct qca8k_pri
-               if (ret)
-                       continue;
--              if (mode == PHY_INTERFACE_MODE_SGMII) {
-+              switch (mode) {
-+              case PHY_INTERFACE_MODE_RGMII:
-+              case PHY_INTERFACE_MODE_RGMII_ID:
-+              case PHY_INTERFACE_MODE_RGMII_TXID:
-+              case PHY_INTERFACE_MODE_RGMII_RXID:
-+                      delay = 0;
-+
-+                      if (!of_property_read_u32(port_dn, "tx-internal-delay-ps", &delay))
-+                              /* Switch regs accept value in ns, convert ps to ns */
-+                              delay = delay / 1000;
-+                      else if (mode == PHY_INTERFACE_MODE_RGMII_ID ||
-+                               mode == PHY_INTERFACE_MODE_RGMII_TXID)
-+                              delay = 1;
-+
-+                      if (delay > QCA8K_MAX_DELAY) {
-+                              dev_err(priv->dev, "rgmii tx delay is limited to a max value of 3ns, setting to the max value");
-+                              delay = 3;
-+                      }
-+
-+                      priv->rgmii_tx_delay[cpu_port_index] = delay;
-+
-+                      delay = 0;
-+
-+                      if (!of_property_read_u32(port_dn, "rx-internal-delay-ps", &delay))
-+                              /* Switch regs accept value in ns, convert ps to ns */
-+                              delay = delay / 1000;
-+                      else if (mode == PHY_INTERFACE_MODE_RGMII_ID ||
-+                               mode == PHY_INTERFACE_MODE_RGMII_RXID)
-+                              delay = 2;
-+
-+                      if (delay > QCA8K_MAX_DELAY) {
-+                              dev_err(priv->dev, "rgmii rx delay is limited to a max value of 3ns, setting to the max value");
-+                              delay = 3;
-+                      }
-+
-+                      priv->rgmii_rx_delay[cpu_port_index] = delay;
-+
-+                      break;
-+              case PHY_INTERFACE_MODE_SGMII:
-                       if (of_property_read_bool(port_dn, "qca,sgmii-txclk-falling-edge"))
-                               priv->sgmii_tx_clk_falling_edge = true;
-                       if (of_property_read_bool(port_dn, "qca,sgmii-rxclk-falling-edge"))
-                               priv->sgmii_rx_clk_falling_edge = true;
-+
-+                      break;
-+              default:
-+                      continue;
-               }
-       }
-@@ -1059,10 +1041,6 @@ qca8k_setup(struct dsa_switch *ds)
-       if (ret)
-               return ret;
--      ret = qca8k_setup_of_rgmii_delay(priv);
--      if (ret)
--              return ret;
--
-       ret = qca8k_setup_mac_pwr_sel(priv);
-       if (ret)
-               return ret;
-@@ -1229,8 +1207,8 @@ qca8k_phylink_mac_config(struct dsa_swit
-                        const struct phylink_link_state *state)
- {
-       struct qca8k_priv *priv = ds->priv;
--      u32 reg, val;
--      int ret;
-+      int cpu_port_index, ret;
-+      u32 reg, val, delay;
-       switch (port) {
-       case 0: /* 1st CPU port */
-@@ -1242,6 +1220,7 @@ qca8k_phylink_mac_config(struct dsa_swit
-                       return;
-               reg = QCA8K_REG_PORT0_PAD_CTRL;
-+              cpu_port_index = QCA8K_CPU_PORT0;
-               break;
-       case 1:
-       case 2:
-@@ -1260,6 +1239,7 @@ qca8k_phylink_mac_config(struct dsa_swit
-                       return;
-               reg = QCA8K_REG_PORT6_PAD_CTRL;
-+              cpu_port_index = QCA8K_CPU_PORT6;
-               break;
-       default:
-               dev_err(ds->dev, "%s: unsupported port: %i\n", __func__, port);
-@@ -1274,23 +1254,40 @@ qca8k_phylink_mac_config(struct dsa_swit
-       switch (state->interface) {
-       case PHY_INTERFACE_MODE_RGMII:
--              /* RGMII mode means no delay so don't enable the delay */
--              qca8k_write(priv, reg, QCA8K_PORT_PAD_RGMII_EN);
--              break;
-       case PHY_INTERFACE_MODE_RGMII_ID:
-       case PHY_INTERFACE_MODE_RGMII_TXID:
-       case PHY_INTERFACE_MODE_RGMII_RXID:
--              /* RGMII_ID needs internal delay. This is enabled through
--               * PORT5_PAD_CTRL for all ports, rather than individual port
--               * registers
-+              val = QCA8K_PORT_PAD_RGMII_EN;
-+
-+              /* Delay can be declared in 3 different way.
-+               * Mode to rgmii and internal-delay standard binding defined
-+               * rgmii-id or rgmii-tx/rx phy mode set.
-+               * The parse logic set a delay different than 0 only when one
-+               * of the 3 different way is used. In all other case delay is
-+               * not enabled. With ID or TX/RXID delay is enabled and set
-+               * to the default and recommended value.
-+               */
-+              if (priv->rgmii_tx_delay[cpu_port_index]) {
-+                      delay = priv->rgmii_tx_delay[cpu_port_index];
-+
-+                      val |= QCA8K_PORT_PAD_RGMII_TX_DELAY(delay) |
-+                             QCA8K_PORT_PAD_RGMII_TX_DELAY_EN;
-+              }
-+
-+              if (priv->rgmii_rx_delay[cpu_port_index]) {
-+                      delay = priv->rgmii_rx_delay[cpu_port_index];
-+
-+                      val |= QCA8K_PORT_PAD_RGMII_RX_DELAY(delay) |
-+                             QCA8K_PORT_PAD_RGMII_RX_DELAY_EN;
-+              }
-+
-+              /* Set RGMII delay based on the selected values */
-+              qca8k_write(priv, reg, val);
-+
-+              /* QCA8337 requires to set rgmii rx delay for all ports.
-+               * This is enabled through PORT5_PAD_CTRL for all ports,
-+               * rather than individual port registers.
-                */
--              qca8k_write(priv, reg,
--                          QCA8K_PORT_PAD_RGMII_EN |
--                          QCA8K_PORT_PAD_RGMII_TX_DELAY(priv->rgmii_tx_delay) |
--                          QCA8K_PORT_PAD_RGMII_RX_DELAY(priv->rgmii_rx_delay) |
--                          QCA8K_PORT_PAD_RGMII_TX_DELAY_EN |
--                          QCA8K_PORT_PAD_RGMII_RX_DELAY_EN);
--              /* QCA8337 requires to set rgmii rx delay */
-               if (priv->switch_id == QCA8K_ID_QCA8337)
-                       qca8k_write(priv, QCA8K_REG_PORT5_PAD_CTRL,
-                                   QCA8K_PORT_PAD_RGMII_RX_DELAY_EN);
---- a/drivers/net/dsa/qca8k.h
-+++ b/drivers/net/dsa/qca8k.h
-@@ -13,6 +13,7 @@
- #include <linux/gpio.h>
- #define QCA8K_NUM_PORTS                                       7
-+#define QCA8K_NUM_CPU_PORTS                           2
- #define QCA8K_MAX_MTU                                 9000
- #define PHY_ID_QCA8327                                        0x004dd034
-@@ -255,13 +256,18 @@ struct qca8k_match_data {
-       u8 id;
- };
-+enum {
-+      QCA8K_CPU_PORT0,
-+      QCA8K_CPU_PORT6,
-+};
-+
- struct qca8k_priv {
-       u8 switch_id;
-       u8 switch_revision;
--      u8 rgmii_tx_delay;
--      u8 rgmii_rx_delay;
-       bool sgmii_rx_clk_falling_edge;
-       bool sgmii_tx_clk_falling_edge;
-+      u8 rgmii_rx_delay[QCA8K_NUM_CPU_PORTS]; /* 0: CPU port0, 1: CPU port6 */
-+      u8 rgmii_tx_delay[QCA8K_NUM_CPU_PORTS]; /* 0: CPU port0, 1: CPU port6 */
-       bool legacy_phy_port_mapping;
-       struct regmap *regmap;
-       struct mii_bus *bus;
diff --git a/target/linux/generic/backport-5.15/747-v5.16-07-dt-bindings-net-dsa-qca8k-Document-qca-sgmii-enable-.patch b/target/linux/generic/backport-5.15/747-v5.16-07-dt-bindings-net-dsa-qca8k-Document-qca-sgmii-enable-.patch
deleted file mode 100644 (file)
index 8abd264..0000000
+++ /dev/null
@@ -1,33 +0,0 @@
-From 13ad5ccc093ff448b99ac7e138e91e78796adb48 Mon Sep 17 00:00:00 2001
-From: Ansuel Smith <[email protected]>
-Date: Thu, 14 Oct 2021 00:39:12 +0200
-Subject: dt-bindings: net: dsa: qca8k: Document qca,sgmii-enable-pll
-
-Document qca,sgmii-enable-pll binding used in the CPU nodes to
-enable SGMII PLL on MAC config.
-
-Signed-off-by: Ansuel Smith <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- Documentation/devicetree/bindings/net/dsa/qca8k.txt | 10 ++++++++++
- 1 file changed, 10 insertions(+)
-
---- a/Documentation/devicetree/bindings/net/dsa/qca8k.txt
-+++ b/Documentation/devicetree/bindings/net/dsa/qca8k.txt
-@@ -45,6 +45,16 @@ A CPU port node has the following option
-                                 Mostly used in qca8327 with CPU port 0 set to
-                                 sgmii.
- - qca,sgmii-txclk-falling-edge: Set the transmit clock phase to falling edge.
-+- qca,sgmii-enable-pll  : For SGMII CPU port, explicitly enable PLL, TX and RX
-+                          chain along with Signal Detection.
-+                          This should NOT be enabled for qca8327. If enabled with
-+                          qca8327 the sgmii port won't correctly init and an err
-+                          is printed.
-+                          This can be required for qca8337 switch with revision 2.
-+                          A warning is displayed when used with revision greater
-+                          2.
-+                          With CPU port set to sgmii and qca8337 it is advised
-+                          to set this unless a communication problem is observed.
- For QCA8K the 'fixed-link' sub-node supports only the following properties:
diff --git a/target/linux/generic/backport-5.15/747-v5.16-08-net-dsa-qca8k-add-explicit-SGMII-PLL-enable.patch b/target/linux/generic/backport-5.15/747-v5.16-08-net-dsa-qca8k-add-explicit-SGMII-PLL-enable.patch
deleted file mode 100644 (file)
index 2b5a84a..0000000
+++ /dev/null
@@ -1,65 +0,0 @@
-From bbc4799e8bb6c397e3b3fec13de68e179f5db9ff Mon Sep 17 00:00:00 2001
-From: Ansuel Smith <[email protected]>
-Date: Thu, 14 Oct 2021 00:39:13 +0200
-Subject: net: dsa: qca8k: add explicit SGMII PLL enable
-
-Support enabling PLL on the SGMII CPU port. Some device require this
-special configuration or no traffic is transmitted and the switch
-doesn't work at all. A dedicated binding is added to the CPU node
-port to apply the correct reg on mac config.
-Fail to correctly configure sgmii with qca8327 switch and warn if pll is
-used on qca8337 with a revision greater than 1.
-
-Signed-off-by: Ansuel Smith <[email protected]>
-Reviewed-by: Florian Fainelli <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/dsa/qca8k.c | 19 +++++++++++++++++--
- drivers/net/dsa/qca8k.h |  1 +
- 2 files changed, 18 insertions(+), 2 deletions(-)
-
---- a/drivers/net/dsa/qca8k.c
-+++ b/drivers/net/dsa/qca8k.c
-@@ -1002,6 +1002,18 @@ qca8k_parse_port_config(struct qca8k_pri
-                       if (of_property_read_bool(port_dn, "qca,sgmii-rxclk-falling-edge"))
-                               priv->sgmii_rx_clk_falling_edge = true;
-+                      if (of_property_read_bool(port_dn, "qca,sgmii-enable-pll")) {
-+                              priv->sgmii_enable_pll = true;
-+
-+                              if (priv->switch_id == QCA8K_ID_QCA8327) {
-+                                      dev_err(priv->dev, "SGMII PLL should NOT be enabled for qca8327. Aborting enabling");
-+                                      priv->sgmii_enable_pll = false;
-+                              }
-+
-+                              if (priv->switch_revision < 2)
-+                                      dev_warn(priv->dev, "SGMII PLL should NOT be enabled for qca8337 with revision 2 or more.");
-+                      }
-+
-                       break;
-               default:
-                       continue;
-@@ -1312,8 +1324,11 @@ qca8k_phylink_mac_config(struct dsa_swit
-               if (ret)
-                       return;
--              val |= QCA8K_SGMII_EN_PLL | QCA8K_SGMII_EN_RX |
--                      QCA8K_SGMII_EN_TX | QCA8K_SGMII_EN_SD;
-+              val |= QCA8K_SGMII_EN_SD;
-+
-+              if (priv->sgmii_enable_pll)
-+                      val |= QCA8K_SGMII_EN_PLL | QCA8K_SGMII_EN_RX |
-+                             QCA8K_SGMII_EN_TX;
-               if (dsa_is_cpu_port(ds, port)) {
-                       /* CPU port, we're talking to the CPU MAC, be a PHY */
---- a/drivers/net/dsa/qca8k.h
-+++ b/drivers/net/dsa/qca8k.h
-@@ -266,6 +266,7 @@ struct qca8k_priv {
-       u8 switch_revision;
-       bool sgmii_rx_clk_falling_edge;
-       bool sgmii_tx_clk_falling_edge;
-+      bool sgmii_enable_pll;
-       u8 rgmii_rx_delay[QCA8K_NUM_CPU_PORTS]; /* 0: CPU port0, 1: CPU port6 */
-       u8 rgmii_tx_delay[QCA8K_NUM_CPU_PORTS]; /* 0: CPU port0, 1: CPU port6 */
-       bool legacy_phy_port_mapping;
diff --git a/target/linux/generic/backport-5.15/747-v5.16-09-dt-bindings-net-dsa-qca8k-Document-qca-led-open-drai.patch b/target/linux/generic/backport-5.15/747-v5.16-09-dt-bindings-net-dsa-qca8k-Document-qca-led-open-drai.patch
deleted file mode 100644 (file)
index 38dc954..0000000
+++ /dev/null
@@ -1,37 +0,0 @@
-From 924087c5c3d41553700b0eb83ca2a53b91643dca Mon Sep 17 00:00:00 2001
-From: Ansuel Smith <[email protected]>
-Date: Thu, 14 Oct 2021 00:39:14 +0200
-Subject: dt-bindings: net: dsa: qca8k: Document qca,led-open-drain binding
-
-Document new binding qca,ignore-power-on-sel used to ignore
-power on strapping and use sw regs instead.
-Document qca,led-open.drain to set led to open drain mode, the
-qca,ignore-power-on-sel is mandatory with this enabled or an error will
-be reported.
-
-Signed-off-by: Ansuel Smith <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- Documentation/devicetree/bindings/net/dsa/qca8k.txt | 11 +++++++++++
- 1 file changed, 11 insertions(+)
-
---- a/Documentation/devicetree/bindings/net/dsa/qca8k.txt
-+++ b/Documentation/devicetree/bindings/net/dsa/qca8k.txt
-@@ -13,6 +13,17 @@ Required properties:
- Optional properties:
- - reset-gpios: GPIO to be used to reset the whole device
-+- qca,ignore-power-on-sel: Ignore power on pin strapping to configure led open
-+                           drain or eeprom presence. This is needed for broken
-+                           devices that have wrong configuration or when the oem
-+                           decided to not use pin strapping and fallback to sw
-+                           regs.
-+- qca,led-open-drain: Set leds to open-drain mode. This requires the
-+                      qca,ignore-power-on-sel to be set or the driver will fail
-+                      to probe. This is needed if the oem doesn't use pin
-+                      strapping to set this mode and prefers to set it using sw
-+                      regs. The pin strapping related to led open drain mode is
-+                      the pin B68 for QCA832x and B49 for QCA833x
- Subnodes:
diff --git a/target/linux/generic/backport-5.15/747-v5.16-10-net-dsa-qca8k-add-support-for-pws-config-reg.patch b/target/linux/generic/backport-5.15/747-v5.16-10-net-dsa-qca8k-add-support-for-pws-config-reg.patch
deleted file mode 100644 (file)
index aa5d92a..0000000
+++ /dev/null
@@ -1,92 +0,0 @@
-From 362bb238d8bf1470424214a8a5968d9c6cce68fa Mon Sep 17 00:00:00 2001
-From: Ansuel Smith <[email protected]>
-Date: Thu, 14 Oct 2021 00:39:15 +0200
-Subject: net: dsa: qca8k: add support for pws config reg
-
-Some qca8327 switch require to force the ignore of power on sel
-strapping. Some switch require to set the led open drain mode in regs
-instead of using strapping. While most of the device implements this
-using the correct way using pin strapping, there are still some broken
-device that require to be set using sw regs.
-Introduce a new binding and support these special configuration.
-As led open drain require to ignore pin strapping to work, the probe
-fails with EINVAL error with incorrect configuration.
-
-Signed-off-by: Ansuel Smith <[email protected]>
-Reviewed-by: Florian Fainelli <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/dsa/qca8k.c | 39 +++++++++++++++++++++++++++++++++++++++
- drivers/net/dsa/qca8k.h |  6 ++++++
- 2 files changed, 45 insertions(+)
-
---- a/drivers/net/dsa/qca8k.c
-+++ b/drivers/net/dsa/qca8k.c
-@@ -932,6 +932,41 @@ static int qca8k_find_cpu_port(struct ds
- }
- static int
-+qca8k_setup_of_pws_reg(struct qca8k_priv *priv)
-+{
-+      struct device_node *node = priv->dev->of_node;
-+      u32 val = 0;
-+      int ret;
-+
-+      /* QCA8327 require to set to the correct mode.
-+       * His bigger brother QCA8328 have the 172 pin layout.
-+       * Should be applied by default but we set this just to make sure.
-+       */
-+      if (priv->switch_id == QCA8K_ID_QCA8327) {
-+              ret = qca8k_rmw(priv, QCA8K_REG_PWS, QCA8327_PWS_PACKAGE148_EN,
-+                              QCA8327_PWS_PACKAGE148_EN);
-+              if (ret)
-+                      return ret;
-+      }
-+
-+      if (of_property_read_bool(node, "qca,ignore-power-on-sel"))
-+              val |= QCA8K_PWS_POWER_ON_SEL;
-+
-+      if (of_property_read_bool(node, "qca,led-open-drain")) {
-+              if (!(val & QCA8K_PWS_POWER_ON_SEL)) {
-+                      dev_err(priv->dev, "qca,led-open-drain require qca,ignore-power-on-sel to be set.");
-+                      return -EINVAL;
-+              }
-+
-+              val |= QCA8K_PWS_LED_OPEN_EN_CSR;
-+      }
-+
-+      return qca8k_rmw(priv, QCA8K_REG_PWS,
-+                      QCA8K_PWS_LED_OPEN_EN_CSR | QCA8K_PWS_POWER_ON_SEL,
-+                      val);
-+}
-+
-+static int
- qca8k_parse_port_config(struct qca8k_priv *priv)
- {
-       int port, cpu_port_index = 0, ret;
-@@ -1053,6 +1088,10 @@ qca8k_setup(struct dsa_switch *ds)
-       if (ret)
-               return ret;
-+      ret = qca8k_setup_of_pws_reg(priv);
-+      if (ret)
-+              return ret;
-+
-       ret = qca8k_setup_mac_pwr_sel(priv);
-       if (ret)
-               return ret;
---- a/drivers/net/dsa/qca8k.h
-+++ b/drivers/net/dsa/qca8k.h
-@@ -46,6 +46,12 @@
- #define   QCA8K_MAX_DELAY                             3
- #define   QCA8K_PORT_PAD_SGMII_EN                     BIT(7)
- #define QCA8K_REG_PWS                                 0x010
-+#define   QCA8K_PWS_POWER_ON_SEL                      BIT(31)
-+/* This reg is only valid for QCA832x and toggle the package
-+ * type from 176 pin (by default) to 148 pin used on QCA8327
-+ */
-+#define   QCA8327_PWS_PACKAGE148_EN                   BIT(30)
-+#define   QCA8K_PWS_LED_OPEN_EN_CSR                   BIT(24)
- #define   QCA8K_PWS_SERDES_AEN_DIS                    BIT(7)
- #define QCA8K_REG_MODULE_EN                           0x030
- #define   QCA8K_MODULE_EN_MIB                         BIT(0)
diff --git a/target/linux/generic/backport-5.15/747-v5.16-11-dt-bindings-net-dsa-qca8k-document-support-for-qca83.patch b/target/linux/generic/backport-5.15/747-v5.16-11-dt-bindings-net-dsa-qca8k-document-support-for-qca83.patch
deleted file mode 100644 (file)
index 1bfb00c..0000000
+++ /dev/null
@@ -1,32 +0,0 @@
-From ed7988d77fbfb79366b68f9e7fa60a6080da23d4 Mon Sep 17 00:00:00 2001
-From: Ansuel Smith <[email protected]>
-Date: Thu, 14 Oct 2021 00:39:16 +0200
-Subject: dt-bindings: net: dsa: qca8k: document support for qca8328
-
-QCA8328 is the bigger brother of qca8327. Document the new compatible
-binding and add some information to understand the various switch
-compatible.
-
-Signed-off-by: Ansuel Smith <[email protected]>
-Reviewed-by: Florian Fainelli <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- Documentation/devicetree/bindings/net/dsa/qca8k.txt | 7 ++++---
- 1 file changed, 4 insertions(+), 3 deletions(-)
-
---- a/Documentation/devicetree/bindings/net/dsa/qca8k.txt
-+++ b/Documentation/devicetree/bindings/net/dsa/qca8k.txt
-@@ -3,9 +3,10 @@
- Required properties:
- - compatible: should be one of:
--    "qca,qca8327"
--    "qca,qca8334"
--    "qca,qca8337"
-+    "qca,qca8328": referenced as AR8328(N)-AK1(A/B) QFN 176 pin package
-+    "qca,qca8327": referenced as AR8327(N)-AL1A DR-QFN 148 pin package
-+    "qca,qca8334": referenced as QCA8334-AL3C QFN 88 pin package
-+    "qca,qca8337": referenced as QCA8337N-AL3(B/C) DR-QFN 148 pin package
- - #size-cells: must be 0
- - #address-cells: must be 1
diff --git a/target/linux/generic/backport-5.15/747-v5.16-12-net-dsa-qca8k-add-support-for-QCA8328.patch b/target/linux/generic/backport-5.15/747-v5.16-12-net-dsa-qca8k-add-support-for-QCA8328.patch
deleted file mode 100644 (file)
index b300621..0000000
+++ /dev/null
@@ -1,78 +0,0 @@
-From f477d1c8bdbef4f400718238e350f16f521d2a3e Mon Sep 17 00:00:00 2001
-From: Ansuel Smith <[email protected]>
-Date: Thu, 14 Oct 2021 00:39:17 +0200
-Subject: net: dsa: qca8k: add support for QCA8328
-
-QCA8328 switch is the bigger brother of the qca8327. Same regs different
-chip. Change the function to set the correct pin layout and introduce a
-new match_data to differentiate the 2 switch as they have the same ID
-and their internal PHY have the same ID.
-
-Signed-off-by: Ansuel Smith <[email protected]>
-Reviewed-by: Florian Fainelli <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/dsa/qca8k.c | 19 ++++++++++++++++---
- drivers/net/dsa/qca8k.h |  1 +
- 2 files changed, 17 insertions(+), 3 deletions(-)
-
---- a/drivers/net/dsa/qca8k.c
-+++ b/drivers/net/dsa/qca8k.c
-@@ -935,6 +935,7 @@ static int
- qca8k_setup_of_pws_reg(struct qca8k_priv *priv)
- {
-       struct device_node *node = priv->dev->of_node;
-+      const struct qca8k_match_data *data;
-       u32 val = 0;
-       int ret;
-@@ -943,8 +944,14 @@ qca8k_setup_of_pws_reg(struct qca8k_priv
-        * Should be applied by default but we set this just to make sure.
-        */
-       if (priv->switch_id == QCA8K_ID_QCA8327) {
-+              data = of_device_get_match_data(priv->dev);
-+
-+              /* Set the correct package of 148 pin for QCA8327 */
-+              if (data->reduced_package)
-+                      val |= QCA8327_PWS_PACKAGE148_EN;
-+
-               ret = qca8k_rmw(priv, QCA8K_REG_PWS, QCA8327_PWS_PACKAGE148_EN,
--                              QCA8327_PWS_PACKAGE148_EN);
-+                              val);
-               if (ret)
-                       return ret;
-       }
-@@ -2124,7 +2131,12 @@ static int qca8k_resume(struct device *d
- static SIMPLE_DEV_PM_OPS(qca8k_pm_ops,
-                        qca8k_suspend, qca8k_resume);
--static const struct qca8k_match_data qca832x = {
-+static const struct qca8k_match_data qca8327 = {
-+      .id = QCA8K_ID_QCA8327,
-+      .reduced_package = true,
-+};
-+
-+static const struct qca8k_match_data qca8328 = {
-       .id = QCA8K_ID_QCA8327,
- };
-@@ -2133,7 +2145,8 @@ static const struct qca8k_match_data qca
- };
- static const struct of_device_id qca8k_of_match[] = {
--      { .compatible = "qca,qca8327", .data = &qca832x },
-+      { .compatible = "qca,qca8327", .data = &qca8327 },
-+      { .compatible = "qca,qca8328", .data = &qca8328 },
-       { .compatible = "qca,qca8334", .data = &qca833x },
-       { .compatible = "qca,qca8337", .data = &qca833x },
-       { /* sentinel */ },
---- a/drivers/net/dsa/qca8k.h
-+++ b/drivers/net/dsa/qca8k.h
-@@ -260,6 +260,7 @@ struct ar8xxx_port_status {
- struct qca8k_match_data {
-       u8 id;
-+      bool reduced_package;
- };
- enum {
diff --git a/target/linux/generic/backport-5.15/747-v5.16-13-net-dsa-qca8k-set-internal-delay-also-for-sgmii.patch b/target/linux/generic/backport-5.15/747-v5.16-13-net-dsa-qca8k-set-internal-delay-also-for-sgmii.patch
deleted file mode 100644 (file)
index 27f94dc..0000000
+++ /dev/null
@@ -1,159 +0,0 @@
-From cef08115846e581f80ff99abf7bf218da1840616 Mon Sep 17 00:00:00 2001
-From: Ansuel Smith <[email protected]>
-Date: Thu, 14 Oct 2021 00:39:18 +0200
-Subject: net: dsa: qca8k: set internal delay also for sgmii
-
-QCA original code report port instability and sa that SGMII also require
-to set internal delay. Generalize the rgmii delay function and apply the
-advised value if they are not defined in DT.
-
-Signed-off-by: Ansuel Smith <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/dsa/qca8k.c | 88 +++++++++++++++++++++++++++++++++----------------
- drivers/net/dsa/qca8k.h |  2 ++
- 2 files changed, 62 insertions(+), 28 deletions(-)
-
---- a/drivers/net/dsa/qca8k.c
-+++ b/drivers/net/dsa/qca8k.c
-@@ -1004,6 +1004,7 @@ qca8k_parse_port_config(struct qca8k_pri
-               case PHY_INTERFACE_MODE_RGMII_ID:
-               case PHY_INTERFACE_MODE_RGMII_TXID:
-               case PHY_INTERFACE_MODE_RGMII_RXID:
-+              case PHY_INTERFACE_MODE_SGMII:
-                       delay = 0;
-                       if (!of_property_read_u32(port_dn, "tx-internal-delay-ps", &delay))
-@@ -1036,8 +1037,13 @@ qca8k_parse_port_config(struct qca8k_pri
-                       priv->rgmii_rx_delay[cpu_port_index] = delay;
--                      break;
--              case PHY_INTERFACE_MODE_SGMII:
-+                      /* Skip sgmii parsing for rgmii* mode */
-+                      if (mode == PHY_INTERFACE_MODE_RGMII ||
-+                          mode == PHY_INTERFACE_MODE_RGMII_ID ||
-+                          mode == PHY_INTERFACE_MODE_RGMII_TXID ||
-+                          mode == PHY_INTERFACE_MODE_RGMII_RXID)
-+                              break;
-+
-                       if (of_property_read_bool(port_dn, "qca,sgmii-txclk-falling-edge"))
-                               priv->sgmii_tx_clk_falling_edge = true;
-@@ -1261,12 +1267,53 @@ qca8k_setup(struct dsa_switch *ds)
- }
- static void
-+qca8k_mac_config_setup_internal_delay(struct qca8k_priv *priv, int cpu_port_index,
-+                                    u32 reg)
-+{
-+      u32 delay, val = 0;
-+      int ret;
-+
-+      /* Delay can be declared in 3 different way.
-+       * Mode to rgmii and internal-delay standard binding defined
-+       * rgmii-id or rgmii-tx/rx phy mode set.
-+       * The parse logic set a delay different than 0 only when one
-+       * of the 3 different way is used. In all other case delay is
-+       * not enabled. With ID or TX/RXID delay is enabled and set
-+       * to the default and recommended value.
-+       */
-+      if (priv->rgmii_tx_delay[cpu_port_index]) {
-+              delay = priv->rgmii_tx_delay[cpu_port_index];
-+
-+              val |= QCA8K_PORT_PAD_RGMII_TX_DELAY(delay) |
-+                      QCA8K_PORT_PAD_RGMII_TX_DELAY_EN;
-+      }
-+
-+      if (priv->rgmii_rx_delay[cpu_port_index]) {
-+              delay = priv->rgmii_rx_delay[cpu_port_index];
-+
-+              val |= QCA8K_PORT_PAD_RGMII_RX_DELAY(delay) |
-+                      QCA8K_PORT_PAD_RGMII_RX_DELAY_EN;
-+      }
-+
-+      /* Set RGMII delay based on the selected values */
-+      ret = qca8k_rmw(priv, reg,
-+                      QCA8K_PORT_PAD_RGMII_TX_DELAY_MASK |
-+                      QCA8K_PORT_PAD_RGMII_RX_DELAY_MASK |
-+                      QCA8K_PORT_PAD_RGMII_TX_DELAY_EN |
-+                      QCA8K_PORT_PAD_RGMII_RX_DELAY_EN,
-+                      val);
-+      if (ret)
-+              dev_err(priv->dev, "Failed to set internal delay for CPU port%d",
-+                      cpu_port_index == QCA8K_CPU_PORT0 ? 0 : 6);
-+}
-+
-+static void
- qca8k_phylink_mac_config(struct dsa_switch *ds, int port, unsigned int mode,
-                        const struct phylink_link_state *state)
- {
-       struct qca8k_priv *priv = ds->priv;
-       int cpu_port_index, ret;
--      u32 reg, val, delay;
-+      u32 reg, val;
-       switch (port) {
-       case 0: /* 1st CPU port */
-@@ -1315,32 +1362,10 @@ qca8k_phylink_mac_config(struct dsa_swit
-       case PHY_INTERFACE_MODE_RGMII_ID:
-       case PHY_INTERFACE_MODE_RGMII_TXID:
-       case PHY_INTERFACE_MODE_RGMII_RXID:
--              val = QCA8K_PORT_PAD_RGMII_EN;
--
--              /* Delay can be declared in 3 different way.
--               * Mode to rgmii and internal-delay standard binding defined
--               * rgmii-id or rgmii-tx/rx phy mode set.
--               * The parse logic set a delay different than 0 only when one
--               * of the 3 different way is used. In all other case delay is
--               * not enabled. With ID or TX/RXID delay is enabled and set
--               * to the default and recommended value.
--               */
--              if (priv->rgmii_tx_delay[cpu_port_index]) {
--                      delay = priv->rgmii_tx_delay[cpu_port_index];
--
--                      val |= QCA8K_PORT_PAD_RGMII_TX_DELAY(delay) |
--                             QCA8K_PORT_PAD_RGMII_TX_DELAY_EN;
--              }
--
--              if (priv->rgmii_rx_delay[cpu_port_index]) {
--                      delay = priv->rgmii_rx_delay[cpu_port_index];
--
--                      val |= QCA8K_PORT_PAD_RGMII_RX_DELAY(delay) |
--                             QCA8K_PORT_PAD_RGMII_RX_DELAY_EN;
--              }
-+              qca8k_write(priv, reg, QCA8K_PORT_PAD_RGMII_EN);
--              /* Set RGMII delay based on the selected values */
--              qca8k_write(priv, reg, val);
-+              /* Configure rgmii delay */
-+              qca8k_mac_config_setup_internal_delay(priv, cpu_port_index, reg);
-               /* QCA8337 requires to set rgmii rx delay for all ports.
-                * This is enabled through PORT5_PAD_CTRL for all ports,
-@@ -1411,6 +1436,13 @@ qca8k_phylink_mac_config(struct dsa_swit
-                                       QCA8K_PORT0_PAD_SGMII_RXCLK_FALLING_EDGE |
-                                       QCA8K_PORT0_PAD_SGMII_TXCLK_FALLING_EDGE,
-                                       val);
-+
-+              /* From original code is reported port instability as SGMII also
-+               * require delay set. Apply advised values here or take them from DT.
-+               */
-+              if (state->interface == PHY_INTERFACE_MODE_SGMII)
-+                      qca8k_mac_config_setup_internal_delay(priv, cpu_port_index, reg);
-+
-               break;
-       default:
-               dev_err(ds->dev, "xMII mode %s not supported for port %d\n",
---- a/drivers/net/dsa/qca8k.h
-+++ b/drivers/net/dsa/qca8k.h
-@@ -39,7 +39,9 @@
- #define QCA8K_REG_PORT5_PAD_CTRL                      0x008
- #define QCA8K_REG_PORT6_PAD_CTRL                      0x00c
- #define   QCA8K_PORT_PAD_RGMII_EN                     BIT(26)
-+#define   QCA8K_PORT_PAD_RGMII_TX_DELAY_MASK          GENMASK(23, 22)
- #define   QCA8K_PORT_PAD_RGMII_TX_DELAY(x)            ((x) << 22)
-+#define   QCA8K_PORT_PAD_RGMII_RX_DELAY_MASK          GENMASK(21, 20)
- #define   QCA8K_PORT_PAD_RGMII_RX_DELAY(x)            ((x) << 20)
- #define         QCA8K_PORT_PAD_RGMII_TX_DELAY_EN              BIT(25)
- #define   QCA8K_PORT_PAD_RGMII_RX_DELAY_EN            BIT(24)
diff --git a/target/linux/generic/backport-5.15/747-v5.16-14-net-dsa-qca8k-move-port-config-to-dedicated-struct.patch b/target/linux/generic/backport-5.15/747-v5.16-14-net-dsa-qca8k-move-port-config-to-dedicated-struct.patch
deleted file mode 100644 (file)
index b991798..0000000
+++ /dev/null
@@ -1,124 +0,0 @@
-From fd0bb28c547f7c8affb1691128cece38f5b626a1 Mon Sep 17 00:00:00 2001
-From: Ansuel Smith <[email protected]>
-Date: Thu, 14 Oct 2021 00:39:19 +0200
-Subject: net: dsa: qca8k: move port config to dedicated struct
-
-Move ports related config to dedicated struct to keep things organized.
-
-Signed-off-by: Ansuel Smith <[email protected]>
-Reviewed-by: Florian Fainelli <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/dsa/qca8k.c | 26 +++++++++++++-------------
- drivers/net/dsa/qca8k.h | 10 +++++++---
- 2 files changed, 20 insertions(+), 16 deletions(-)
-
---- a/drivers/net/dsa/qca8k.c
-+++ b/drivers/net/dsa/qca8k.c
-@@ -1019,7 +1019,7 @@ qca8k_parse_port_config(struct qca8k_pri
-                               delay = 3;
-                       }
--                      priv->rgmii_tx_delay[cpu_port_index] = delay;
-+                      priv->ports_config.rgmii_tx_delay[cpu_port_index] = delay;
-                       delay = 0;
-@@ -1035,7 +1035,7 @@ qca8k_parse_port_config(struct qca8k_pri
-                               delay = 3;
-                       }
--                      priv->rgmii_rx_delay[cpu_port_index] = delay;
-+                      priv->ports_config.rgmii_rx_delay[cpu_port_index] = delay;
-                       /* Skip sgmii parsing for rgmii* mode */
-                       if (mode == PHY_INTERFACE_MODE_RGMII ||
-@@ -1045,17 +1045,17 @@ qca8k_parse_port_config(struct qca8k_pri
-                               break;
-                       if (of_property_read_bool(port_dn, "qca,sgmii-txclk-falling-edge"))
--                              priv->sgmii_tx_clk_falling_edge = true;
-+                              priv->ports_config.sgmii_tx_clk_falling_edge = true;
-                       if (of_property_read_bool(port_dn, "qca,sgmii-rxclk-falling-edge"))
--                              priv->sgmii_rx_clk_falling_edge = true;
-+                              priv->ports_config.sgmii_rx_clk_falling_edge = true;
-                       if (of_property_read_bool(port_dn, "qca,sgmii-enable-pll")) {
--                              priv->sgmii_enable_pll = true;
-+                              priv->ports_config.sgmii_enable_pll = true;
-                               if (priv->switch_id == QCA8K_ID_QCA8327) {
-                                       dev_err(priv->dev, "SGMII PLL should NOT be enabled for qca8327. Aborting enabling");
--                                      priv->sgmii_enable_pll = false;
-+                                      priv->ports_config.sgmii_enable_pll = false;
-                               }
-                               if (priv->switch_revision < 2)
-@@ -1281,15 +1281,15 @@ qca8k_mac_config_setup_internal_delay(st
-        * not enabled. With ID or TX/RXID delay is enabled and set
-        * to the default and recommended value.
-        */
--      if (priv->rgmii_tx_delay[cpu_port_index]) {
--              delay = priv->rgmii_tx_delay[cpu_port_index];
-+      if (priv->ports_config.rgmii_tx_delay[cpu_port_index]) {
-+              delay = priv->ports_config.rgmii_tx_delay[cpu_port_index];
-               val |= QCA8K_PORT_PAD_RGMII_TX_DELAY(delay) |
-                       QCA8K_PORT_PAD_RGMII_TX_DELAY_EN;
-       }
--      if (priv->rgmii_rx_delay[cpu_port_index]) {
--              delay = priv->rgmii_rx_delay[cpu_port_index];
-+      if (priv->ports_config.rgmii_rx_delay[cpu_port_index]) {
-+              delay = priv->ports_config.rgmii_rx_delay[cpu_port_index];
-               val |= QCA8K_PORT_PAD_RGMII_RX_DELAY(delay) |
-                       QCA8K_PORT_PAD_RGMII_RX_DELAY_EN;
-@@ -1397,7 +1397,7 @@ qca8k_phylink_mac_config(struct dsa_swit
-               val |= QCA8K_SGMII_EN_SD;
--              if (priv->sgmii_enable_pll)
-+              if (priv->ports_config.sgmii_enable_pll)
-                       val |= QCA8K_SGMII_EN_PLL | QCA8K_SGMII_EN_RX |
-                              QCA8K_SGMII_EN_TX;
-@@ -1425,10 +1425,10 @@ qca8k_phylink_mac_config(struct dsa_swit
-               val = 0;
-               /* SGMII Clock phase configuration */
--              if (priv->sgmii_rx_clk_falling_edge)
-+              if (priv->ports_config.sgmii_rx_clk_falling_edge)
-                       val |= QCA8K_PORT0_PAD_SGMII_RXCLK_FALLING_EDGE;
--              if (priv->sgmii_tx_clk_falling_edge)
-+              if (priv->ports_config.sgmii_tx_clk_falling_edge)
-                       val |= QCA8K_PORT0_PAD_SGMII_TXCLK_FALLING_EDGE;
-               if (val)
---- a/drivers/net/dsa/qca8k.h
-+++ b/drivers/net/dsa/qca8k.h
-@@ -270,15 +270,19 @@ enum {
-       QCA8K_CPU_PORT6,
- };
--struct qca8k_priv {
--      u8 switch_id;
--      u8 switch_revision;
-+struct qca8k_ports_config {
-       bool sgmii_rx_clk_falling_edge;
-       bool sgmii_tx_clk_falling_edge;
-       bool sgmii_enable_pll;
-       u8 rgmii_rx_delay[QCA8K_NUM_CPU_PORTS]; /* 0: CPU port0, 1: CPU port6 */
-       u8 rgmii_tx_delay[QCA8K_NUM_CPU_PORTS]; /* 0: CPU port0, 1: CPU port6 */
-+};
-+
-+struct qca8k_priv {
-+      u8 switch_id;
-+      u8 switch_revision;
-       bool legacy_phy_port_mapping;
-+      struct qca8k_ports_config ports_config;
-       struct regmap *regmap;
-       struct mii_bus *bus;
-       struct ar8xxx_port_status port_sts[QCA8K_NUM_PORTS];
diff --git a/target/linux/generic/backport-5.15/747-v5.16-15-dt-bindings-net-ipq8064-mdio-fix-warning-with-new-qc.patch b/target/linux/generic/backport-5.15/747-v5.16-15-dt-bindings-net-ipq8064-mdio-fix-warning-with-new-qc.patch
deleted file mode 100644 (file)
index f7cb514..0000000
+++ /dev/null
@@ -1,26 +0,0 @@
-From e52073a8e3086046a098b8a7cbeb282ff0cdb424 Mon Sep 17 00:00:00 2001
-From: Ansuel Smith <[email protected]>
-Date: Thu, 14 Oct 2021 00:39:20 +0200
-Subject: dt-bindings: net: ipq8064-mdio: fix warning with new qca8k switch
-
-Fix warning now that we have qca8k switch Documentation using yaml.
-
-Signed-off-by: Ansuel Smith <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- Documentation/devicetree/bindings/net/qcom,ipq8064-mdio.yaml | 5 ++++-
- 1 file changed, 4 insertions(+), 1 deletion(-)
-
---- a/Documentation/devicetree/bindings/net/qcom,ipq8064-mdio.yaml
-+++ b/Documentation/devicetree/bindings/net/qcom,ipq8064-mdio.yaml
-@@ -51,6 +51,9 @@ examples:
-         switch@10 {
-             compatible = "qca,qca8337";
-             reg = <0x10>;
--            /* ... */
-+
-+            ports {
-+              /* ... */
-+            };
-         };
-     };
diff --git a/target/linux/generic/backport-5.15/747-v5.16-16-dt-bindings-net-dsa-qca8k-convert-to-YAML-schema.patch b/target/linux/generic/backport-5.15/747-v5.16-16-dt-bindings-net-dsa-qca8k-convert-to-YAML-schema.patch
deleted file mode 100644 (file)
index b9bce97..0000000
+++ /dev/null
@@ -1,631 +0,0 @@
-From d291fbb8245d5ba04979fed85575860a5cea7196 Mon Sep 17 00:00:00 2001
-From: Matthew Hagan <[email protected]>
-Date: Thu, 14 Oct 2021 00:39:21 +0200
-Subject: dt-bindings: net: dsa: qca8k: convert to YAML schema
-
-Convert the qca8k bindings to YAML format.
-
-Signed-off-by: Matthew Hagan <[email protected]>
-Co-developed-by: Ansuel Smith <[email protected]>
-Signed-off-by: Ansuel Smith <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- .../devicetree/bindings/net/dsa/qca8k.txt          | 245 --------------
- .../devicetree/bindings/net/dsa/qca8k.yaml         | 362 +++++++++++++++++++++
- 2 files changed, 362 insertions(+), 245 deletions(-)
- delete mode 100644 Documentation/devicetree/bindings/net/dsa/qca8k.txt
- create mode 100644 Documentation/devicetree/bindings/net/dsa/qca8k.yaml
-
---- a/Documentation/devicetree/bindings/net/dsa/qca8k.txt
-+++ /dev/null
-@@ -1,245 +0,0 @@
--* Qualcomm Atheros QCA8xxx switch family
--
--Required properties:
--
--- compatible: should be one of:
--    "qca,qca8328": referenced as AR8328(N)-AK1(A/B) QFN 176 pin package
--    "qca,qca8327": referenced as AR8327(N)-AL1A DR-QFN 148 pin package
--    "qca,qca8334": referenced as QCA8334-AL3C QFN 88 pin package
--    "qca,qca8337": referenced as QCA8337N-AL3(B/C) DR-QFN 148 pin package
--
--- #size-cells: must be 0
--- #address-cells: must be 1
--
--Optional properties:
--
--- reset-gpios: GPIO to be used to reset the whole device
--- qca,ignore-power-on-sel: Ignore power on pin strapping to configure led open
--                           drain or eeprom presence. This is needed for broken
--                           devices that have wrong configuration or when the oem
--                           decided to not use pin strapping and fallback to sw
--                           regs.
--- qca,led-open-drain: Set leds to open-drain mode. This requires the
--                      qca,ignore-power-on-sel to be set or the driver will fail
--                      to probe. This is needed if the oem doesn't use pin
--                      strapping to set this mode and prefers to set it using sw
--                      regs. The pin strapping related to led open drain mode is
--                      the pin B68 for QCA832x and B49 for QCA833x
--
--Subnodes:
--
--The integrated switch subnode should be specified according to the binding
--described in dsa/dsa.txt. If the QCA8K switch is connect to a SoC's external
--mdio-bus each subnode describing a port needs to have a valid phandle
--referencing the internal PHY it is connected to. This is because there's no
--N:N mapping of port and PHY id.
--To declare the internal mdio-bus configuration, declare a mdio node in the
--switch node and declare the phandle for the port referencing the internal
--PHY is connected to. In this config a internal mdio-bus is registered and
--the mdio MASTER is used as communication.
--
--Don't use mixed external and internal mdio-bus configurations, as this is
--not supported by the hardware.
--
--This switch support 2 CPU port. Normally and advised configuration is with
--CPU port set to port 0. It is also possible to set the CPU port to port 6
--if the device requires it. The driver will configure the switch to the defined
--port. With both CPU port declared the first CPU port is selected as primary
--and the secondary CPU ignored.
--
--A CPU port node has the following optional node:
--
--- fixed-link            : Fixed-link subnode describing a link to a non-MDIO
--                          managed entity. See
--                          Documentation/devicetree/bindings/net/fixed-link.txt
--                          for details.
--- qca,sgmii-rxclk-falling-edge: Set the receive clock phase to falling edge.
--                                Mostly used in qca8327 with CPU port 0 set to
--                                sgmii.
--- qca,sgmii-txclk-falling-edge: Set the transmit clock phase to falling edge.
--- qca,sgmii-enable-pll  : For SGMII CPU port, explicitly enable PLL, TX and RX
--                          chain along with Signal Detection.
--                          This should NOT be enabled for qca8327. If enabled with
--                          qca8327 the sgmii port won't correctly init and an err
--                          is printed.
--                          This can be required for qca8337 switch with revision 2.
--                          A warning is displayed when used with revision greater
--                          2.
--                          With CPU port set to sgmii and qca8337 it is advised
--                          to set this unless a communication problem is observed.
--
--For QCA8K the 'fixed-link' sub-node supports only the following properties:
--
--- 'speed' (integer, mandatory), to indicate the link speed. Accepted
--  values are 10, 100 and 1000
--- 'full-duplex' (boolean, optional), to indicate that full duplex is
--  used. When absent, half duplex is assumed.
--
--Examples:
--
--for the external mdio-bus configuration:
--
--      &mdio0 {
--              phy_port1: phy@0 {
--                      reg = <0>;
--              };
--
--              phy_port2: phy@1 {
--                      reg = <1>;
--              };
--
--              phy_port3: phy@2 {
--                      reg = <2>;
--              };
--
--              phy_port4: phy@3 {
--                      reg = <3>;
--              };
--
--              phy_port5: phy@4 {
--                      reg = <4>;
--              };
--
--              switch@10 {
--                      compatible = "qca,qca8337";
--                      #address-cells = <1>;
--                      #size-cells = <0>;
--
--                      reset-gpios = <&gpio 42 GPIO_ACTIVE_LOW>;
--                      reg = <0x10>;
--
--                      ports {
--                              #address-cells = <1>;
--                              #size-cells = <0>;
--                              port@0 {
--                                      reg = <0>;
--                                      label = "cpu";
--                                      ethernet = <&gmac1>;
--                                      phy-mode = "rgmii";
--                                      fixed-link {
--                                              speed = 1000;
--                                              full-duplex;
--                                      };
--                              };
--
--                              port@1 {
--                                      reg = <1>;
--                                      label = "lan1";
--                                      phy-handle = <&phy_port1>;
--                              };
--
--                              port@2 {
--                                      reg = <2>;
--                                      label = "lan2";
--                                      phy-handle = <&phy_port2>;
--                              };
--
--                              port@3 {
--                                      reg = <3>;
--                                      label = "lan3";
--                                      phy-handle = <&phy_port3>;
--                              };
--
--                              port@4 {
--                                      reg = <4>;
--                                      label = "lan4";
--                                      phy-handle = <&phy_port4>;
--                              };
--
--                              port@5 {
--                                      reg = <5>;
--                                      label = "wan";
--                                      phy-handle = <&phy_port5>;
--                              };
--                      };
--              };
--      };
--
--for the internal master mdio-bus configuration:
--
--      &mdio0 {
--              switch@10 {
--                      compatible = "qca,qca8337";
--                      #address-cells = <1>;
--                      #size-cells = <0>;
--
--                      reset-gpios = <&gpio 42 GPIO_ACTIVE_LOW>;
--                      reg = <0x10>;
--
--                      ports {
--                              #address-cells = <1>;
--                              #size-cells = <0>;
--
--                              port@0 {
--                                      reg = <0>;
--                                      label = "cpu";
--                                      ethernet = <&gmac1>;
--                                      phy-mode = "rgmii";
--                                      fixed-link {
--                                              speed = 1000;
--                                              full-duplex;
--                                      };
--                              };
--
--                              port@1 {
--                                      reg = <1>;
--                                      label = "lan1";
--                                      phy-mode = "internal";
--                                      phy-handle = <&phy_port1>;
--                              };
--
--                              port@2 {
--                                      reg = <2>;
--                                      label = "lan2";
--                                      phy-mode = "internal";
--                                      phy-handle = <&phy_port2>;
--                              };
--
--                              port@3 {
--                                      reg = <3>;
--                                      label = "lan3";
--                                      phy-mode = "internal";
--                                      phy-handle = <&phy_port3>;
--                              };
--
--                              port@4 {
--                                      reg = <4>;
--                                      label = "lan4";
--                                      phy-mode = "internal";
--                                      phy-handle = <&phy_port4>;
--                              };
--
--                              port@5 {
--                                      reg = <5>;
--                                      label = "wan";
--                                      phy-mode = "internal";
--                                      phy-handle = <&phy_port5>;
--                              };
--                      };
--
--                      mdio {
--                              #address-cells = <1>;
--                              #size-cells = <0>;
--
--                              phy_port1: phy@0 {
--                                      reg = <0>;
--                              };
--
--                              phy_port2: phy@1 {
--                                      reg = <1>;
--                              };
--
--                              phy_port3: phy@2 {
--                                      reg = <2>;
--                              };
--
--                              phy_port4: phy@3 {
--                                      reg = <3>;
--                              };
--
--                              phy_port5: phy@4 {
--                                      reg = <4>;
--                              };
--                      };
--              };
--      };
---- /dev/null
-+++ b/Documentation/devicetree/bindings/net/dsa/qca8k.yaml
-@@ -0,0 +1,362 @@
-+# SPDX-License-Identifier: (GPL-2.0-only OR BSD-2-Clause)
-+%YAML 1.2
-+---
-+$id: http://devicetree.org/schemas/net/dsa/qca8k.yaml#
-+$schema: http://devicetree.org/meta-schemas/core.yaml#
-+
-+title: Qualcomm Atheros QCA83xx switch family
-+
-+maintainers:
-+  - John Crispin <[email protected]>
-+
-+description:
-+  If the QCA8K switch is connect to an SoC's external mdio-bus, each subnode
-+  describing a port needs to have a valid phandle referencing the internal PHY
-+  it is connected to. This is because there is no N:N mapping of port and PHY
-+  ID. To declare the internal mdio-bus configuration, declare an MDIO node in
-+  the switch node and declare the phandle for the port, referencing the internal
-+  PHY it is connected to. In this config, an internal mdio-bus is registered and
-+  the MDIO master is used for communication. Mixed external and internal
-+  mdio-bus configurations are not supported by the hardware.
-+
-+properties:
-+  compatible:
-+    oneOf:
-+      - enum:
-+          - qca,qca8327
-+          - qca,qca8328
-+          - qca,qca8334
-+          - qca,qca8337
-+    description: |
-+      qca,qca8328: referenced as AR8328(N)-AK1(A/B) QFN 176 pin package
-+      qca,qca8327: referenced as AR8327(N)-AL1A DR-QFN 148 pin package
-+      qca,qca8334: referenced as QCA8334-AL3C QFN 88 pin package
-+      qca,qca8337: referenced as QCA8337N-AL3(B/C) DR-QFN 148 pin package
-+
-+  reg:
-+    maxItems: 1
-+
-+  reset-gpios:
-+    description:
-+      GPIO to be used to reset the whole device
-+    maxItems: 1
-+
-+  qca,ignore-power-on-sel:
-+    $ref: /schemas/types.yaml#/definitions/flag
-+    description:
-+      Ignore power-on pin strapping to configure LED open-drain or EEPROM
-+      presence. This is needed for devices with incorrect configuration or when
-+      the OEM has decided not to use pin strapping and falls back to SW regs.
-+
-+  qca,led-open-drain:
-+    $ref: /schemas/types.yaml#/definitions/flag
-+    description:
-+      Set LEDs to open-drain mode. This requires the qca,ignore-power-on-sel to
-+      be set, otherwise the driver will fail at probe. This is required if the
-+      OEM does not use pin strapping to set this mode and prefers to set it
-+      using SW regs. The pin strappings related to LED open-drain mode are
-+      B68 on the QCA832x and B49 on the QCA833x.
-+
-+  mdio:
-+    type: object
-+    description: Qca8k switch have an internal mdio to access switch port.
-+                 If this is not present, the legacy mapping is used and the
-+                 internal mdio access is used.
-+                 With the legacy mapping the reg corresponding to the internal
-+                 mdio is the switch reg with an offset of -1.
-+
-+    properties:
-+      '#address-cells':
-+        const: 1
-+      '#size-cells':
-+        const: 0
-+
-+    patternProperties:
-+      "^(ethernet-)?phy@[0-4]$":
-+        type: object
-+
-+        allOf:
-+          - $ref: "http://devicetree.org/schemas/net/mdio.yaml#"
-+
-+        properties:
-+          reg:
-+            maxItems: 1
-+
-+        required:
-+          - reg
-+
-+patternProperties:
-+  "^(ethernet-)?ports$":
-+    type: object
-+    properties:
-+      '#address-cells':
-+        const: 1
-+      '#size-cells':
-+        const: 0
-+
-+    patternProperties:
-+      "^(ethernet-)?port@[0-6]$":
-+        type: object
-+        description: Ethernet switch ports
-+
-+        properties:
-+          reg:
-+            description: Port number
-+
-+          label:
-+            description:
-+              Describes the label associated with this port, which will become
-+              the netdev name
-+            $ref: /schemas/types.yaml#/definitions/string
-+
-+          link:
-+            description:
-+              Should be a list of phandles to other switch's DSA port. This
-+              port is used as the outgoing port towards the phandle ports. The
-+              full routing information must be given, not just the one hop
-+              routes to neighbouring switches
-+            $ref: /schemas/types.yaml#/definitions/phandle-array
-+
-+          ethernet:
-+            description:
-+              Should be a phandle to a valid Ethernet device node.  This host
-+              device is what the switch port is connected to
-+            $ref: /schemas/types.yaml#/definitions/phandle
-+
-+          phy-handle: true
-+
-+          phy-mode: true
-+
-+          fixed-link: true
-+
-+          mac-address: true
-+
-+          sfp: true
-+
-+          qca,sgmii-rxclk-falling-edge:
-+            $ref: /schemas/types.yaml#/definitions/flag
-+            description:
-+              Set the receive clock phase to falling edge. Mostly commonly used on
-+              the QCA8327 with CPU port 0 set to SGMII.
-+
-+          qca,sgmii-txclk-falling-edge:
-+            $ref: /schemas/types.yaml#/definitions/flag
-+            description:
-+              Set the transmit clock phase to falling edge.
-+
-+          qca,sgmii-enable-pll:
-+            $ref: /schemas/types.yaml#/definitions/flag
-+            description:
-+              For SGMII CPU port, explicitly enable PLL, TX and RX chain along with
-+              Signal Detection. On the QCA8327 this should not be enabled, otherwise
-+              the SGMII port will not initialize. When used on the QCA8337, revision 3
-+              or greater, a warning will be displayed. When the CPU port is set to
-+              SGMII on the QCA8337, it is advised to set this unless a communication
-+              issue is observed.
-+
-+        required:
-+          - reg
-+
-+        additionalProperties: false
-+
-+oneOf:
-+  - required:
-+      - ports
-+  - required:
-+      - ethernet-ports
-+
-+required:
-+  - compatible
-+  - reg
-+
-+additionalProperties: true
-+
-+examples:
-+  - |
-+    #include <dt-bindings/gpio/gpio.h>
-+
-+    mdio {
-+        #address-cells = <1>;
-+        #size-cells = <0>;
-+
-+        external_phy_port1: ethernet-phy@0 {
-+            reg = <0>;
-+        };
-+
-+        external_phy_port2: ethernet-phy@1 {
-+            reg = <1>;
-+        };
-+
-+        external_phy_port3: ethernet-phy@2 {
-+            reg = <2>;
-+        };
-+
-+        external_phy_port4: ethernet-phy@3 {
-+            reg = <3>;
-+        };
-+
-+        external_phy_port5: ethernet-phy@4 {
-+            reg = <4>;
-+        };
-+
-+        switch@10 {
-+            compatible = "qca,qca8337";
-+            #address-cells = <1>;
-+            #size-cells = <0>;
-+            reset-gpios = <&gpio 42 GPIO_ACTIVE_LOW>;
-+            reg = <0x10>;
-+
-+            ports {
-+                #address-cells = <1>;
-+                #size-cells = <0>;
-+
-+                port@0 {
-+                    reg = <0>;
-+                    label = "cpu";
-+                    ethernet = <&gmac1>;
-+                    phy-mode = "rgmii";
-+
-+                    fixed-link {
-+                        speed = <1000>;
-+                        full-duplex;
-+                    };
-+                };
-+
-+                port@1 {
-+                    reg = <1>;
-+                    label = "lan1";
-+                    phy-handle = <&external_phy_port1>;
-+                };
-+
-+                port@2 {
-+                    reg = <2>;
-+                    label = "lan2";
-+                    phy-handle = <&external_phy_port2>;
-+                };
-+
-+                port@3 {
-+                    reg = <3>;
-+                    label = "lan3";
-+                    phy-handle = <&external_phy_port3>;
-+                };
-+
-+                port@4 {
-+                    reg = <4>;
-+                    label = "lan4";
-+                    phy-handle = <&external_phy_port4>;
-+                };
-+
-+                port@5 {
-+                    reg = <5>;
-+                    label = "wan";
-+                    phy-handle = <&external_phy_port5>;
-+                };
-+            };
-+        };
-+    };
-+  - |
-+    #include <dt-bindings/gpio/gpio.h>
-+
-+    mdio {
-+        #address-cells = <1>;
-+        #size-cells = <0>;
-+
-+        switch@10 {
-+            compatible = "qca,qca8337";
-+            #address-cells = <1>;
-+            #size-cells = <0>;
-+            reset-gpios = <&gpio 42 GPIO_ACTIVE_LOW>;
-+            reg = <0x10>;
-+
-+            ports {
-+                #address-cells = <1>;
-+                #size-cells = <0>;
-+
-+                port@0 {
-+                    reg = <0>;
-+                    label = "cpu";
-+                    ethernet = <&gmac1>;
-+                    phy-mode = "rgmii";
-+
-+                    fixed-link {
-+                        speed = <1000>;
-+                        full-duplex;
-+                    };
-+                };
-+
-+                port@1 {
-+                    reg = <1>;
-+                    label = "lan1";
-+                    phy-mode = "internal";
-+                    phy-handle = <&internal_phy_port1>;
-+                };
-+
-+                port@2 {
-+                    reg = <2>;
-+                    label = "lan2";
-+                    phy-mode = "internal";
-+                    phy-handle = <&internal_phy_port2>;
-+                };
-+
-+                port@3 {
-+                    reg = <3>;
-+                    label = "lan3";
-+                    phy-mode = "internal";
-+                    phy-handle = <&internal_phy_port3>;
-+                };
-+
-+                port@4 {
-+                    reg = <4>;
-+                    label = "lan4";
-+                    phy-mode = "internal";
-+                    phy-handle = <&internal_phy_port4>;
-+                };
-+
-+                port@5 {
-+                    reg = <5>;
-+                    label = "wan";
-+                    phy-mode = "internal";
-+                    phy-handle = <&internal_phy_port5>;
-+                };
-+
-+                port@6 {
-+                    reg = <0>;
-+                    label = "cpu";
-+                    ethernet = <&gmac1>;
-+                    phy-mode = "sgmii";
-+
-+                    qca,sgmii-rxclk-falling-edge;
-+
-+                    fixed-link {
-+                        speed = <1000>;
-+                        full-duplex;
-+                    };
-+                };
-+            };
-+
-+            mdio {
-+                #address-cells = <1>;
-+                #size-cells = <0>;
-+
-+                internal_phy_port1: ethernet-phy@0 {
-+                    reg = <0>;
-+                };
-+
-+                internal_phy_port2: ethernet-phy@1 {
-+                    reg = <1>;
-+                };
-+
-+                internal_phy_port3: ethernet-phy@2 {
-+                    reg = <2>;
-+                };
-+
-+                internal_phy_port4: ethernet-phy@3 {
-+                    reg = <3>;
-+                };
-+
-+                internal_phy_port5: ethernet-phy@4 {
-+                    reg = <4>;
-+                };
-+            };
-+        };
-+    };
diff --git a/target/linux/generic/backport-5.15/748-v5.16-net-dsa-qca8k-fix-delay-applied-to-wrong-cpu-in-parse-p.patch b/target/linux/generic/backport-5.15/748-v5.16-net-dsa-qca8k-fix-delay-applied-to-wrong-cpu-in-parse-p.patch
deleted file mode 100644 (file)
index a510cfd..0000000
+++ /dev/null
@@ -1,28 +0,0 @@
-From 06dd34a628ae5b6a839b757e746de165d6789ca8 Mon Sep 17 00:00:00 2001
-From: Ansuel Smith <[email protected]>
-Date: Sun, 17 Oct 2021 16:56:46 +0200
-Subject: net: dsa: qca8k: fix delay applied to wrong cpu in parse_port_config
-
-Fix delay settings applied to wrong cpu in parse_port_config. The delay
-values is set to the wrong index as the cpu_port_index is incremented
-too early. Start the cpu_port_index to -1 so the correct value is
-applied to address also the case with invalid phy mode and not available
-port.
-
-Signed-off-by: Ansuel Smith <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/dsa/qca8k.c | 2 +-
- 1 file changed, 1 insertion(+), 1 deletion(-)
-
---- a/drivers/net/dsa/qca8k.c
-+++ b/drivers/net/dsa/qca8k.c
-@@ -976,7 +976,7 @@ qca8k_setup_of_pws_reg(struct qca8k_priv
- static int
- qca8k_parse_port_config(struct qca8k_priv *priv)
- {
--      int port, cpu_port_index = 0, ret;
-+      int port, cpu_port_index = -1, ret;
-       struct device_node *port_dn;
-       phy_interface_t mode;
-       struct dsa_port *dp;
diff --git a/target/linux/generic/backport-5.15/749-v5.16-net-dsa-qca8k-tidy-for-loop-in-setup-and-add-cpu-port-c.patch b/target/linux/generic/backport-5.15/749-v5.16-net-dsa-qca8k-tidy-for-loop-in-setup-and-add-cpu-port-c.patch
deleted file mode 100644 (file)
index 71fa302..0000000
+++ /dev/null
@@ -1,151 +0,0 @@
-From 040e926f5813a5f4cc18dbff7c942d1e52f368f2 Mon Sep 17 00:00:00 2001
-From: Ansuel Smith <[email protected]>
-Date: Tue, 19 Oct 2021 02:08:50 +0200
-Subject: net: dsa: qca8k: tidy for loop in setup and add cpu port check
-
-Tidy and organize qca8k setup function from multiple for loop.
-Change for loop in bridge leave/join to scan all port and skip cpu port.
-No functional change intended.
-
-Signed-off-by: Ansuel Smith <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/dsa/qca8k.c | 74 +++++++++++++++++++++++++++++--------------------
- 1 file changed, 44 insertions(+), 30 deletions(-)
-
---- a/drivers/net/dsa/qca8k.c
-+++ b/drivers/net/dsa/qca8k.c
-@@ -1122,28 +1122,34 @@ qca8k_setup(struct dsa_switch *ds)
-       if (ret)
-               dev_warn(priv->dev, "mib init failed");
--      /* Enable QCA header mode on the cpu port */
--      ret = qca8k_write(priv, QCA8K_REG_PORT_HDR_CTRL(cpu_port),
--                        QCA8K_PORT_HDR_CTRL_ALL << QCA8K_PORT_HDR_CTRL_TX_S |
--                        QCA8K_PORT_HDR_CTRL_ALL << QCA8K_PORT_HDR_CTRL_RX_S);
--      if (ret) {
--              dev_err(priv->dev, "failed enabling QCA header mode");
--              return ret;
--      }
--
--      /* Disable forwarding by default on all ports */
-+      /* Initial setup of all ports */
-       for (i = 0; i < QCA8K_NUM_PORTS; i++) {
-+              /* Disable forwarding by default on all ports */
-               ret = qca8k_rmw(priv, QCA8K_PORT_LOOKUP_CTRL(i),
-                               QCA8K_PORT_LOOKUP_MEMBER, 0);
-               if (ret)
-                       return ret;
--      }
--      /* Disable MAC by default on all ports */
--      for (i = 1; i < QCA8K_NUM_PORTS; i++)
--              qca8k_port_set_status(priv, i, 0);
-+              /* Enable QCA header mode on all cpu ports */
-+              if (dsa_is_cpu_port(ds, i)) {
-+                      ret = qca8k_write(priv, QCA8K_REG_PORT_HDR_CTRL(i),
-+                                        QCA8K_PORT_HDR_CTRL_ALL << QCA8K_PORT_HDR_CTRL_TX_S |
-+                                        QCA8K_PORT_HDR_CTRL_ALL << QCA8K_PORT_HDR_CTRL_RX_S);
-+                      if (ret) {
-+                              dev_err(priv->dev, "failed enabling QCA header mode");
-+                              return ret;
-+                      }
-+              }
-+
-+              /* Disable MAC by default on all user ports */
-+              if (dsa_is_user_port(ds, i))
-+                      qca8k_port_set_status(priv, i, 0);
-+      }
--      /* Forward all unknown frames to CPU port for Linux processing */
-+      /* Forward all unknown frames to CPU port for Linux processing
-+       * Notice that in multi-cpu config only one port should be set
-+       * for igmp, unknown, multicast and broadcast packet
-+       */
-       ret = qca8k_write(priv, QCA8K_REG_GLOBAL_FW_CTRL1,
-                         BIT(cpu_port) << QCA8K_GLOBAL_FW_CTRL1_IGMP_DP_S |
-                         BIT(cpu_port) << QCA8K_GLOBAL_FW_CTRL1_BC_DP_S |
-@@ -1152,11 +1158,13 @@ qca8k_setup(struct dsa_switch *ds)
-       if (ret)
-               return ret;
--      /* Setup connection between CPU port & user ports */
-+      /* Setup connection between CPU port & user ports
-+       * Configure specific switch configuration for ports
-+       */
-       for (i = 0; i < QCA8K_NUM_PORTS; i++) {
-               /* CPU port gets connected to all user ports of the switch */
-               if (dsa_is_cpu_port(ds, i)) {
--                      ret = qca8k_rmw(priv, QCA8K_PORT_LOOKUP_CTRL(cpu_port),
-+                      ret = qca8k_rmw(priv, QCA8K_PORT_LOOKUP_CTRL(i),
-                                       QCA8K_PORT_LOOKUP_MEMBER, dsa_user_ports(ds));
-                       if (ret)
-                               return ret;
-@@ -1193,16 +1201,14 @@ qca8k_setup(struct dsa_switch *ds)
-                       if (ret)
-                               return ret;
-               }
--      }
--      /* The port 5 of the qca8337 have some problem in flood condition. The
--       * original legacy driver had some specific buffer and priority settings
--       * for the different port suggested by the QCA switch team. Add this
--       * missing settings to improve switch stability under load condition.
--       * This problem is limited to qca8337 and other qca8k switch are not affected.
--       */
--      if (priv->switch_id == QCA8K_ID_QCA8337) {
--              for (i = 0; i < QCA8K_NUM_PORTS; i++) {
-+              /* The port 5 of the qca8337 have some problem in flood condition. The
-+               * original legacy driver had some specific buffer and priority settings
-+               * for the different port suggested by the QCA switch team. Add this
-+               * missing settings to improve switch stability under load condition.
-+               * This problem is limited to qca8337 and other qca8k switch are not affected.
-+               */
-+              if (priv->switch_id == QCA8K_ID_QCA8337) {
-                       switch (i) {
-                       /* The 2 CPU port and port 5 requires some different
-                        * priority than any other ports.
-@@ -1238,6 +1244,12 @@ qca8k_setup(struct dsa_switch *ds)
-                                 QCA8K_PORT_HOL_CTRL1_WRED_EN,
-                                 mask);
-               }
-+
-+              /* Set initial MTU for every port.
-+               * We have only have a general MTU setting. So track
-+               * every port and set the max across all port.
-+               */
-+              priv->port_mtu[i] = ETH_FRAME_LEN + ETH_FCS_LEN;
-       }
-       /* Special GLOBAL_FC_THRESH value are needed for ar8327 switch */
-@@ -1251,8 +1263,6 @@ qca8k_setup(struct dsa_switch *ds)
-       }
-       /* Setup our port MTUs to match power on defaults */
--      for (i = 0; i < QCA8K_NUM_PORTS; i++)
--              priv->port_mtu[i] = ETH_FRAME_LEN + ETH_FCS_LEN;
-       ret = qca8k_write(priv, QCA8K_MAX_FRAME_SIZE, ETH_FRAME_LEN + ETH_FCS_LEN);
-       if (ret)
-               dev_warn(priv->dev, "failed setting MTU settings");
-@@ -1728,7 +1738,9 @@ qca8k_port_bridge_join(struct dsa_switch
-       cpu_port = dsa_to_port(ds, port)->cpu_dp->index;
-       port_mask = BIT(cpu_port);
--      for (i = 1; i < QCA8K_NUM_PORTS; i++) {
-+      for (i = 0; i < QCA8K_NUM_PORTS; i++) {
-+              if (dsa_is_cpu_port(ds, i))
-+                      continue;
-               if (dsa_to_port(ds, i)->bridge_dev != br)
-                       continue;
-               /* Add this port to the portvlan mask of the other ports
-@@ -1758,7 +1770,9 @@ qca8k_port_bridge_leave(struct dsa_switc
-       cpu_port = dsa_to_port(ds, port)->cpu_dp->index;
--      for (i = 1; i < QCA8K_NUM_PORTS; i++) {
-+      for (i = 0; i < QCA8K_NUM_PORTS; i++) {
-+              if (dsa_is_cpu_port(ds, i))
-+                      continue;
-               if (dsa_to_port(ds, i)->bridge_dev != br)
-                       continue;
-               /* Remove this port to the portvlan mask of the other ports
diff --git a/target/linux/generic/backport-5.15/750-v5.16-net-dsa-qca8k-make-sure-pad0-mac06-exchange-is-disabled.patch b/target/linux/generic/backport-5.15/750-v5.16-net-dsa-qca8k-make-sure-pad0-mac06-exchange-is-disabled.patch
deleted file mode 100644 (file)
index 4a61703..0000000
+++ /dev/null
@@ -1,47 +0,0 @@
-From 5f15d392dcb4aa250a63d6f2c5adfc26c0aedc78 Mon Sep 17 00:00:00 2001
-From: Ansuel Smith <[email protected]>
-Date: Tue, 2 Nov 2021 19:30:41 +0100
-Subject: net: dsa: qca8k: make sure PAD0 MAC06 exchange is disabled
-
-Some device set MAC06 exchange in the bootloader. This cause some
-problem as we don't support this strange mode and we just set the port6
-as the primary CPU port. With MAC06 exchange, PAD0 reg configure port6
-instead of port0. Add an extra check and explicitly disable MAC06 exchange
-to correctly configure the port PAD config.
-
-Signed-off-by: Ansuel Smith <[email protected]>
-Fixes: 3fcf734aa482 ("net: dsa: qca8k: add support for cpu port 6")
-Reviewed-by: Vladimir Oltean <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/dsa/qca8k.c | 8 ++++++++
- drivers/net/dsa/qca8k.h | 1 +
- 2 files changed, 9 insertions(+)
-
---- a/drivers/net/dsa/qca8k.c
-+++ b/drivers/net/dsa/qca8k.c
-@@ -1109,6 +1109,14 @@ qca8k_setup(struct dsa_switch *ds)
-       if (ret)
-               return ret;
-+      /* Make sure MAC06 is disabled */
-+      ret = qca8k_reg_clear(priv, QCA8K_REG_PORT0_PAD_CTRL,
-+                            QCA8K_PORT0_PAD_MAC06_EXCHANGE_EN);
-+      if (ret) {
-+              dev_err(priv->dev, "failed disabling MAC06 exchange");
-+              return ret;
-+      }
-+
-       /* Enable CPU Port */
-       ret = qca8k_reg_set(priv, QCA8K_REG_GLOBAL_FW_CTRL0,
-                           QCA8K_GLOBAL_FW_CTRL0_CPU_PORT_EN);
---- a/drivers/net/dsa/qca8k.h
-+++ b/drivers/net/dsa/qca8k.h
-@@ -34,6 +34,7 @@
- #define   QCA8K_MASK_CTRL_DEVICE_ID_MASK              GENMASK(15, 8)
- #define   QCA8K_MASK_CTRL_DEVICE_ID(x)                        ((x) >> 8)
- #define QCA8K_REG_PORT0_PAD_CTRL                      0x004
-+#define   QCA8K_PORT0_PAD_MAC06_EXCHANGE_EN           BIT(31)
- #define   QCA8K_PORT0_PAD_SGMII_RXCLK_FALLING_EDGE    BIT(19)
- #define   QCA8K_PORT0_PAD_SGMII_TXCLK_FALLING_EDGE    BIT(18)
- #define QCA8K_REG_PORT5_PAD_CTRL                      0x008
diff --git a/target/linux/generic/backport-5.15/750-v6.5-01-net-ethernet-mtk_ppe-add-MTK_FOE_ENTRY_V-1-2-_SIZE-m.patch b/target/linux/generic/backport-5.15/750-v6.5-01-net-ethernet-mtk_ppe-add-MTK_FOE_ENTRY_V-1-2-_SIZE-m.patch
deleted file mode 100644 (file)
index 25ac8db..0000000
+++ /dev/null
@@ -1,78 +0,0 @@
-From 5ea0e1312bcfebc06b5f91d1bb82b823d6395125 Mon Sep 17 00:00:00 2001
-From: Lorenzo Bianconi <[email protected]>
-Date: Wed, 19 Jul 2023 12:29:49 +0200
-Subject: [PATCH 095/250] net: ethernet: mtk_ppe: add MTK_FOE_ENTRY_V{1,2}_SIZE
- macros
-
-Introduce MTK_FOE_ENTRY_V{1,2}_SIZE macros in order to make more
-explicit foe_entry size for different chipset revisions.
-
-Signed-off-by: Lorenzo Bianconi <[email protected]>
-Reviewed-by: Simon Horman <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/ethernet/mediatek/mtk_eth_soc.c | 10 +++++-----
- drivers/net/ethernet/mediatek/mtk_ppe.h     |  3 +++
- 2 files changed, 8 insertions(+), 5 deletions(-)
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-@@ -4713,7 +4713,7 @@ static const struct mtk_soc_data mt7621_
-       .required_pctl = false,
-       .offload_version = 1,
-       .hash_offset = 2,
--      .foe_entry_size = sizeof(struct mtk_foe_entry) - 16,
-+      .foe_entry_size = MTK_FOE_ENTRY_V1_SIZE,
-       .txrx = {
-               .txd_size = sizeof(struct mtk_tx_dma),
-               .rxd_size = sizeof(struct mtk_rx_dma),
-@@ -4734,7 +4734,7 @@ static const struct mtk_soc_data mt7622_
-       .offload_version = 2,
-       .hash_offset = 2,
-       .has_accounting = true,
--      .foe_entry_size = sizeof(struct mtk_foe_entry) - 16,
-+      .foe_entry_size = MTK_FOE_ENTRY_V1_SIZE,
-       .txrx = {
-               .txd_size = sizeof(struct mtk_tx_dma),
-               .rxd_size = sizeof(struct mtk_rx_dma),
-@@ -4753,7 +4753,7 @@ static const struct mtk_soc_data mt7623_
-       .required_pctl = true,
-       .offload_version = 1,
-       .hash_offset = 2,
--      .foe_entry_size = sizeof(struct mtk_foe_entry) - 16,
-+      .foe_entry_size = MTK_FOE_ENTRY_V1_SIZE,
-       .txrx = {
-               .txd_size = sizeof(struct mtk_tx_dma),
-               .rxd_size = sizeof(struct mtk_rx_dma),
-@@ -4791,8 +4791,8 @@ static const struct mtk_soc_data mt7981_
-       .required_pctl = false,
-       .offload_version = 2,
-       .hash_offset = 4,
--      .foe_entry_size = sizeof(struct mtk_foe_entry),
-       .has_accounting = true,
-+      .foe_entry_size = MTK_FOE_ENTRY_V2_SIZE,
-       .txrx = {
-               .txd_size = sizeof(struct mtk_tx_dma_v2),
-               .rxd_size = sizeof(struct mtk_rx_dma_v2),
-@@ -4812,8 +4812,8 @@ static const struct mtk_soc_data mt7986_
-       .required_pctl = false,
-       .offload_version = 2,
-       .hash_offset = 4,
--      .foe_entry_size = sizeof(struct mtk_foe_entry),
-       .has_accounting = true,
-+      .foe_entry_size = MTK_FOE_ENTRY_V2_SIZE,
-       .txrx = {
-               .txd_size = sizeof(struct mtk_tx_dma_v2),
-               .rxd_size = sizeof(struct mtk_rx_dma_v2),
---- a/drivers/net/ethernet/mediatek/mtk_ppe.h
-+++ b/drivers/net/ethernet/mediatek/mtk_ppe.h
-@@ -216,6 +216,9 @@ struct mtk_foe_ipv6_6rd {
-       struct mtk_foe_mac_info l2;
- };
-+#define MTK_FOE_ENTRY_V1_SIZE 80
-+#define MTK_FOE_ENTRY_V2_SIZE 96
-+
- struct mtk_foe_entry {
-       u32 ib1;
diff --git a/target/linux/generic/backport-5.15/750-v6.5-02-net-ethernet-mtk_eth_soc-remove-incorrect-PLL-config.patch b/target/linux/generic/backport-5.15/750-v6.5-02-net-ethernet-mtk_eth_soc-remove-incorrect-PLL-config.patch
deleted file mode 100644 (file)
index 9720995..0000000
+++ /dev/null
@@ -1,141 +0,0 @@
-From 8cfa2576d79f9379d167a8994f0fca935c07a8bc Mon Sep 17 00:00:00 2001
-From: "Russell King (Oracle)" <[email protected]>
-Date: Sat, 22 Jul 2023 21:32:49 +0100
-Subject: [PATCH 096/250] net: ethernet: mtk_eth_soc: remove incorrect PLL
- configuration
-
-MT7623 GMAC0 attempts to configure the system clocking according to the
-required speed in the .mac_config callback for non-SGMII, non-baseX and
-non-TRGMII modes.
-
-state->speed setting has never been reliable in the .mac_config
-callback - there are cases where this is not the link speed,
-particularly via ethtool paths, so this has always been unreliable (as
-detailed in phylink's documentation.)
-
-There is the additional issue that mtk_gmac0_rgmii_adjust() will only
-be called if state->interface changes, which means it only configures
-the system clocking on the very first .mac_config call, which will be
-made when the network device is first brought up before any link is
-established.
-
-Essentially, this code is incredibly buggy, and probably never worked.
-
-Moreover, checking the in-kernel DT files, it seems no platform makes
-use of this code path.
-
-Therefore, let's remove it, and disable interface modes for port 0 that
-are not SGMII, 1000base-X, 2500base-X or TRGMII on the MT7623.
-
-Reviewed-by: Daniel Golle <[email protected]>
-Tested-by: Daniel Golle <[email protected]>
-Tested-by: Frank Wunderlich <[email protected]>
-Signed-off-by: Russell King (Oracle) <[email protected]>
-Signed-off-by: Paolo Abeni <[email protected]>
----
- drivers/net/ethernet/mediatek/mtk_eth_soc.c | 54 ++++++---------------
- drivers/net/ethernet/mediatek/mtk_eth_soc.h |  1 +
- 2 files changed, 17 insertions(+), 38 deletions(-)
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-@@ -309,7 +309,7 @@ static int mt7621_gmac0_rgmii_adjust(str
- }
- static void mtk_gmac0_rgmii_adjust(struct mtk_eth *eth,
--                                 phy_interface_t interface, int speed)
-+                                 phy_interface_t interface)
- {
-       u32 val;
-       int ret;
-@@ -323,26 +323,7 @@ static void mtk_gmac0_rgmii_adjust(struc
-               return;
-       }
--      val = (speed == SPEED_1000) ?
--              INTF_MODE_RGMII_1000 : INTF_MODE_RGMII_10_100;
--      mtk_w32(eth, val, INTF_MODE);
--
--      regmap_update_bits(eth->ethsys, ETHSYS_CLKCFG0,
--                         ETHSYS_TRGMII_CLK_SEL362_5,
--                         ETHSYS_TRGMII_CLK_SEL362_5);
--
--      val = (speed == SPEED_1000) ? 250000000 : 500000000;
--      ret = clk_set_rate(eth->clks[MTK_CLK_TRGPLL], val);
--      if (ret)
--              dev_err(eth->dev, "Failed to set trgmii pll: %d\n", ret);
--
--      val = (speed == SPEED_1000) ?
--              RCK_CTRL_RGMII_1000 : RCK_CTRL_RGMII_10_100;
--      mtk_w32(eth, val, TRGMII_RCK_CTRL);
--
--      val = (speed == SPEED_1000) ?
--              TCK_CTRL_RGMII_1000 : TCK_CTRL_RGMII_10_100;
--      mtk_w32(eth, val, TRGMII_TCK_CTRL);
-+      dev_err(eth->dev, "Missing PLL configuration, ethernet may not work\n");
- }
- static struct phylink_pcs *mtk_mac_select_pcs(struct phylink_config *config,
-@@ -428,17 +409,8 @@ static void mtk_mac_config(struct phylin
-                                                             state->interface))
-                                       goto err_phy;
-                       } else {
--                              /* FIXME: this is incorrect. Not only does it
--                               * use state->speed (which is not guaranteed
--                               * to be correct) but it also makes use of it
--                               * in a code path that will only be reachable
--                               * when the PHY interface mode changes, not
--                               * when the speed changes. Consequently, RGMII
--                               * is probably broken.
--                               */
-                               mtk_gmac0_rgmii_adjust(mac->hw,
--                                                     state->interface,
--                                                     state->speed);
-+                                                     state->interface);
-                               /* mt7623_pad_clk_setup */
-                               for (i = 0 ; i < NUM_TRGMII_CTRL; i++)
-@@ -4288,13 +4260,19 @@ static int mtk_add_mac(struct mtk_eth *e
-       mac->phylink_config.mac_capabilities = MAC_ASYM_PAUSE | MAC_SYM_PAUSE |
-               MAC_10 | MAC_100 | MAC_1000 | MAC_2500FD;
--      __set_bit(PHY_INTERFACE_MODE_MII,
--                mac->phylink_config.supported_interfaces);
--      __set_bit(PHY_INTERFACE_MODE_GMII,
--                mac->phylink_config.supported_interfaces);
-+      /* MT7623 gmac0 is now missing its speed-specific PLL configuration
-+       * in its .mac_config method (since state->speed is not valid there.
-+       * Disable support for MII, GMII and RGMII.
-+       */
-+      if (!mac->hw->soc->disable_pll_modes || mac->id != 0) {
-+              __set_bit(PHY_INTERFACE_MODE_MII,
-+                        mac->phylink_config.supported_interfaces);
-+              __set_bit(PHY_INTERFACE_MODE_GMII,
-+                        mac->phylink_config.supported_interfaces);
--      if (MTK_HAS_CAPS(mac->hw->soc->caps, MTK_RGMII))
--              phy_interface_set_rgmii(mac->phylink_config.supported_interfaces);
-+              if (MTK_HAS_CAPS(mac->hw->soc->caps, MTK_RGMII))
-+                      phy_interface_set_rgmii(mac->phylink_config.supported_interfaces);
-+      }
-       if (MTK_HAS_CAPS(mac->hw->soc->caps, MTK_TRGMII) && !mac->id)
-               __set_bit(PHY_INTERFACE_MODE_TRGMII,
-@@ -4754,6 +4732,7 @@ static const struct mtk_soc_data mt7623_
-       .offload_version = 1,
-       .hash_offset = 2,
-       .foe_entry_size = MTK_FOE_ENTRY_V1_SIZE,
-+      .disable_pll_modes = true,
-       .txrx = {
-               .txd_size = sizeof(struct mtk_tx_dma),
-               .rxd_size = sizeof(struct mtk_rx_dma),
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-@@ -1027,6 +1027,7 @@ struct mtk_soc_data {
-       u16             foe_entry_size;
-       netdev_features_t hw_features;
-       bool            has_accounting;
-+      bool            disable_pll_modes;
-       struct {
-               u32     txd_size;
-               u32     rxd_size;
diff --git a/target/linux/generic/backport-5.15/750-v6.5-03-net-ethernet-mtk_eth_soc-remove-mac_pcs_get_state-an.patch b/target/linux/generic/backport-5.15/750-v6.5-03-net-ethernet-mtk_eth_soc-remove-mac_pcs_get_state-an.patch
deleted file mode 100644 (file)
index e1b1272..0000000
+++ /dev/null
@@ -1,81 +0,0 @@
-From a4c2233b1e4359b6c64b6f9ba98c8718a11fffee Mon Sep 17 00:00:00 2001
-From: "Russell King (Oracle)" <[email protected]>
-Date: Sat, 22 Jul 2023 21:32:54 +0100
-Subject: [PATCH 097/250] net: ethernet: mtk_eth_soc: remove mac_pcs_get_state
- and modernise
-
-Remove the .mac_pcs_get_state function, since as far as I can tell is
-never called - no DT appears to specify an in-band-status management
-nor SFP support for this driver.
-
-Removal of this, along with the previous patch to remove the incorrect
-clocking configuration, means that the driver becomes non-legacy, so
-we can remove the "legacy_pre_march2020" status from this driver.
-
-Reviewed-by: Daniel Golle <[email protected]>
-Tested-by: Daniel Golle <[email protected]>
-Tested-by: Frank Wunderlich <[email protected]>
-Signed-off-by: Russell King (Oracle) <[email protected]>
-Signed-off-by: Paolo Abeni <[email protected]>
----
- drivers/net/ethernet/mediatek/mtk_eth_soc.c | 35 ---------------------
- 1 file changed, 35 deletions(-)
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-@@ -511,38 +511,6 @@ static int mtk_mac_finish(struct phylink
-       return 0;
- }
--static void mtk_mac_pcs_get_state(struct phylink_config *config,
--                                struct phylink_link_state *state)
--{
--      struct mtk_mac *mac = container_of(config, struct mtk_mac,
--                                         phylink_config);
--      u32 pmsr = mtk_r32(mac->hw, MTK_MAC_MSR(mac->id));
--
--      state->link = (pmsr & MAC_MSR_LINK);
--      state->duplex = (pmsr & MAC_MSR_DPX) >> 1;
--
--      switch (pmsr & (MAC_MSR_SPEED_1000 | MAC_MSR_SPEED_100)) {
--      case 0:
--              state->speed = SPEED_10;
--              break;
--      case MAC_MSR_SPEED_100:
--              state->speed = SPEED_100;
--              break;
--      case MAC_MSR_SPEED_1000:
--              state->speed = SPEED_1000;
--              break;
--      default:
--              state->speed = SPEED_UNKNOWN;
--              break;
--      }
--
--      state->pause &= (MLO_PAUSE_RX | MLO_PAUSE_TX);
--      if (pmsr & MAC_MSR_RX_FC)
--              state->pause |= MLO_PAUSE_RX;
--      if (pmsr & MAC_MSR_TX_FC)
--              state->pause |= MLO_PAUSE_TX;
--}
--
- static void mtk_mac_link_down(struct phylink_config *config, unsigned int mode,
-                             phy_interface_t interface)
- {
-@@ -665,7 +633,6 @@ static void mtk_mac_link_up(struct phyli
- static const struct phylink_mac_ops mtk_phylink_ops = {
-       .validate = phylink_generic_validate,
-       .mac_select_pcs = mtk_mac_select_pcs,
--      .mac_pcs_get_state = mtk_mac_pcs_get_state,
-       .mac_config = mtk_mac_config,
-       .mac_finish = mtk_mac_finish,
-       .mac_link_down = mtk_mac_link_down,
-@@ -4255,8 +4222,6 @@ static int mtk_add_mac(struct mtk_eth *e
-       mac->phylink_config.dev = &eth->netdev[id]->dev;
-       mac->phylink_config.type = PHYLINK_NETDEV;
--      /* This driver makes use of state->speed in mac_config */
--      mac->phylink_config.legacy_pre_march2020 = true;
-       mac->phylink_config.mac_capabilities = MAC_ASYM_PAUSE | MAC_SYM_PAUSE |
-               MAC_10 | MAC_100 | MAC_1000 | MAC_2500FD;
diff --git a/target/linux/generic/backport-5.15/750-v6.5-05-net-ethernet-mtk_eth_soc-add-version-in-mtk_soc_data.patch b/target/linux/generic/backport-5.15/750-v6.5-05-net-ethernet-mtk_eth_soc-add-version-in-mtk_soc_data.patch
deleted file mode 100644 (file)
index e4be17c..0000000
+++ /dev/null
@@ -1,550 +0,0 @@
-From 5d8d05fbf804b4485646d39551ac27452e45afd3 Mon Sep 17 00:00:00 2001
-From: Lorenzo Bianconi <[email protected]>
-Date: Tue, 25 Jul 2023 01:52:02 +0100
-Subject: [PATCH 099/250] net: ethernet: mtk_eth_soc: add version in
- mtk_soc_data
-
-Introduce version field in mtk_soc_data data structure in order to
-make mtk_eth driver easier to maintain for chipset configuration
-codebase. Get rid of MTK_NETSYS_V2 bit in chip capabilities.
-This is a preliminary patch to introduce support for MT7988 SoC.
-
-Signed-off-by: Lorenzo Bianconi <[email protected]>
-Signed-off-by: Daniel Golle <[email protected]>
-Link: https://lore.kernel.org/r/e52fae302ca135436e5cdd26d38d87be2da63055.1690246066.git.daniel@makrotopia.org
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- drivers/net/ethernet/mediatek/mtk_eth_soc.c   | 55 +++++++++++--------
- drivers/net/ethernet/mediatek/mtk_eth_soc.h   | 36 +++++++-----
- drivers/net/ethernet/mediatek/mtk_ppe.c       | 18 +++---
- .../net/ethernet/mediatek/mtk_ppe_offload.c   |  2 +-
- drivers/net/ethernet/mediatek/mtk_wed.c       |  4 +-
- 5 files changed, 66 insertions(+), 49 deletions(-)
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-@@ -536,7 +536,7 @@ static void mtk_set_queue_speed(struct m
-             FIELD_PREP(MTK_QTX_SCH_MIN_RATE_MAN, 1) |
-             FIELD_PREP(MTK_QTX_SCH_MIN_RATE_EXP, 4) |
-             MTK_QTX_SCH_LEAKY_BUCKET_SIZE;
--      if (!MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2))
-+      if (mtk_is_netsys_v1(eth))
-               val |= MTK_QTX_SCH_LEAKY_BUCKET_EN;
-       if (IS_ENABLED(CONFIG_SOC_MT7621)) {
-@@ -911,7 +911,7 @@ static bool mtk_rx_get_desc(struct mtk_e
-       rxd->rxd1 = READ_ONCE(dma_rxd->rxd1);
-       rxd->rxd3 = READ_ONCE(dma_rxd->rxd3);
-       rxd->rxd4 = READ_ONCE(dma_rxd->rxd4);
--      if (MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2)) {
-+      if (mtk_is_netsys_v2_or_greater(eth)) {
-               rxd->rxd5 = READ_ONCE(dma_rxd->rxd5);
-               rxd->rxd6 = READ_ONCE(dma_rxd->rxd6);
-       }
-@@ -969,7 +969,7 @@ static int mtk_init_fq_dma(struct mtk_et
-               txd->txd3 = TX_DMA_PLEN0(MTK_QDMA_PAGE_SIZE);
-               txd->txd4 = 0;
--              if (MTK_HAS_CAPS(soc->caps, MTK_NETSYS_V2)) {
-+              if (mtk_is_netsys_v2_or_greater(eth)) {
-                       txd->txd5 = 0;
-                       txd->txd6 = 0;
-                       txd->txd7 = 0;
-@@ -1158,7 +1158,7 @@ static void mtk_tx_set_dma_desc(struct n
-       struct mtk_mac *mac = netdev_priv(dev);
-       struct mtk_eth *eth = mac->hw;
--      if (MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2))
-+      if (mtk_is_netsys_v2_or_greater(eth))
-               mtk_tx_set_dma_desc_v2(dev, txd, info);
-       else
-               mtk_tx_set_dma_desc_v1(dev, txd, info);
-@@ -1465,7 +1465,7 @@ static void mtk_update_rx_cpu_idx(struct
- static bool mtk_page_pool_enabled(struct mtk_eth *eth)
- {
--      return MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2);
-+      return eth->soc->version == 2;
- }
- static struct page_pool *mtk_create_page_pool(struct mtk_eth *eth,
-@@ -1805,7 +1805,7 @@ static int mtk_poll_rx(struct napi_struc
-                       break;
-               /* find out which mac the packet come from. values start at 1 */
--              if (MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2))
-+              if (mtk_is_netsys_v2_or_greater(eth))
-                       mac = RX_DMA_GET_SPORT_V2(trxd.rxd5) - 1;
-               else if (!MTK_HAS_CAPS(eth->soc->caps, MTK_SOC_MT7628) &&
-                        !(trxd.rxd4 & RX_DMA_SPECIAL_TAG))
-@@ -1901,7 +1901,7 @@ static int mtk_poll_rx(struct napi_struc
-               skb->dev = netdev;
-               bytes += skb->len;
--              if (MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2)) {
-+              if (mtk_is_netsys_v2_or_greater(eth)) {
-                       reason = FIELD_GET(MTK_RXD5_PPE_CPU_REASON, trxd.rxd5);
-                       hash = trxd.rxd5 & MTK_RXD5_FOE_ENTRY;
-                       if (hash != MTK_RXD5_FOE_ENTRY)
-@@ -1926,8 +1926,8 @@ static int mtk_poll_rx(struct napi_struc
-               /* When using VLAN untagging in combination with DSA, the
-                * hardware treats the MTK special tag as a VLAN and untags it.
-                */
--              if (!MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2) &&
--                  (trxd.rxd2 & RX_DMA_VTAG) && netdev_uses_dsa(netdev)) {
-+              if (mtk_is_netsys_v1(eth) && (trxd.rxd2 & RX_DMA_VTAG) &&
-+                  netdev_uses_dsa(netdev)) {
-                       unsigned int port = RX_DMA_VPID(trxd.rxd3) & GENMASK(2, 0);
-                       if (port < ARRAY_SIZE(eth->dsa_meta) &&
-@@ -2231,7 +2231,7 @@ static int mtk_tx_alloc(struct mtk_eth *
-               txd->txd2 = next_ptr;
-               txd->txd3 = TX_DMA_LS0 | TX_DMA_OWNER_CPU;
-               txd->txd4 = 0;
--              if (MTK_HAS_CAPS(soc->caps, MTK_NETSYS_V2)) {
-+              if (mtk_is_netsys_v2_or_greater(eth)) {
-                       txd->txd5 = 0;
-                       txd->txd6 = 0;
-                       txd->txd7 = 0;
-@@ -2284,14 +2284,14 @@ static int mtk_tx_alloc(struct mtk_eth *
-                             FIELD_PREP(MTK_QTX_SCH_MIN_RATE_MAN, 1) |
-                             FIELD_PREP(MTK_QTX_SCH_MIN_RATE_EXP, 4) |
-                             MTK_QTX_SCH_LEAKY_BUCKET_SIZE;
--                      if (!MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2))
-+                      if (mtk_is_netsys_v1(eth))
-                               val |= MTK_QTX_SCH_LEAKY_BUCKET_EN;
-                       mtk_w32(eth, val, soc->reg_map->qdma.qtx_sch + ofs);
-                       ofs += MTK_QTX_OFFSET;
-               }
-               val = MTK_QDMA_TX_SCH_MAX_WFQ | (MTK_QDMA_TX_SCH_MAX_WFQ << 16);
-               mtk_w32(eth, val, soc->reg_map->qdma.tx_sch_rate);
--              if (MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2))
-+              if (mtk_is_netsys_v2_or_greater(eth))
-                       mtk_w32(eth, val, soc->reg_map->qdma.tx_sch_rate + 4);
-       } else {
-               mtk_w32(eth, ring->phys_pdma, MT7628_TX_BASE_PTR0);
-@@ -2418,7 +2418,7 @@ static int mtk_rx_alloc(struct mtk_eth *
-               rxd->rxd3 = 0;
-               rxd->rxd4 = 0;
--              if (MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2)) {
-+              if (mtk_is_netsys_v2_or_greater(eth)) {
-                       rxd->rxd5 = 0;
-                       rxd->rxd6 = 0;
-                       rxd->rxd7 = 0;
-@@ -2969,7 +2969,7 @@ static int mtk_start_dma(struct mtk_eth
-                      MTK_TX_BT_32DWORDS | MTK_NDP_CO_PRO |
-                      MTK_RX_2B_OFFSET | MTK_TX_WB_DDONE;
--              if (MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2))
-+              if (mtk_is_netsys_v2_or_greater(eth))
-                       val |= MTK_MUTLI_CNT | MTK_RESV_BUF |
-                              MTK_WCOMP_EN | MTK_DMAD_WR_WDONE |
-                              MTK_CHK_DDONE_EN | MTK_LEAKY_BUCKET_EN;
-@@ -3113,7 +3113,7 @@ static int mtk_open(struct net_device *d
-       phylink_start(mac->phylink);
-       netif_tx_start_all_queues(dev);
--      if (MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2))
-+      if (mtk_is_netsys_v2_or_greater(eth))
-               return 0;
-       if (mtk_uses_dsa(dev) && !eth->prog) {
-@@ -3378,7 +3378,7 @@ static void mtk_hw_reset(struct mtk_eth
- {
-       u32 val;
--      if (MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2)) {
-+      if (mtk_is_netsys_v2_or_greater(eth)) {
-               regmap_write(eth->ethsys, ETHSYS_FE_RST_CHK_IDLE_EN, 0);
-               val = RSTCTRL_PPE0_V2;
-       } else {
-@@ -3390,7 +3390,7 @@ static void mtk_hw_reset(struct mtk_eth
-       ethsys_reset(eth, RSTCTRL_ETH | RSTCTRL_FE | val);
--      if (MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2))
-+      if (mtk_is_netsys_v2_or_greater(eth))
-               regmap_write(eth->ethsys, ETHSYS_FE_RST_CHK_IDLE_EN,
-                            0x3ffffff);
- }
-@@ -3416,7 +3416,7 @@ static void mtk_hw_warm_reset(struct mtk
-               return;
-       }
--      if (MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2))
-+      if (mtk_is_netsys_v2_or_greater(eth))
-               rst_mask = RSTCTRL_ETH | RSTCTRL_PPE0_V2;
-       else
-               rst_mask = RSTCTRL_ETH | RSTCTRL_PPE0;
-@@ -3586,7 +3586,7 @@ static int mtk_hw_init(struct mtk_eth *e
-       else
-               mtk_hw_reset(eth);
--      if (MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2)) {
-+      if (mtk_is_netsys_v2_or_greater(eth)) {
-               /* Set FE to PDMAv2 if necessary */
-               val = mtk_r32(eth, MTK_FE_GLO_MISC);
-               mtk_w32(eth,  val | BIT(4), MTK_FE_GLO_MISC);
-@@ -3623,7 +3623,7 @@ static int mtk_hw_init(struct mtk_eth *e
-        */
-       val = mtk_r32(eth, MTK_CDMQ_IG_CTRL);
-       mtk_w32(eth, val | MTK_CDMQ_STAG_EN, MTK_CDMQ_IG_CTRL);
--      if (!MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2)) {
-+      if (mtk_is_netsys_v1(eth)) {
-               val = mtk_r32(eth, MTK_CDMP_IG_CTRL);
-               mtk_w32(eth, val | MTK_CDMP_STAG_EN, MTK_CDMP_IG_CTRL);
-@@ -3645,7 +3645,7 @@ static int mtk_hw_init(struct mtk_eth *e
-       mtk_w32(eth, eth->soc->txrx.rx_irq_done_mask, reg_map->qdma.int_grp + 4);
-       mtk_w32(eth, 0x21021000, MTK_FE_INT_GRP);
--      if (MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2)) {
-+      if (mtk_is_netsys_v2_or_greater(eth)) {
-               /* PSE should not drop port8 and port9 packets from WDMA Tx */
-               mtk_w32(eth, 0x00000300, PSE_DROP_CFG);
-@@ -4434,7 +4434,7 @@ static int mtk_probe(struct platform_dev
-               }
-       }
--      if (MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2)) {
-+      if (mtk_is_netsys_v2_or_greater(eth)) {
-               res = platform_get_resource(pdev, IORESOURCE_MEM, 0);
-               if (!res) {
-                       err = -EINVAL;
-@@ -4542,9 +4542,8 @@ static int mtk_probe(struct platform_dev
-       }
-       if (eth->soc->offload_version) {
--              u32 num_ppe;
-+              u32 num_ppe = mtk_is_netsys_v2_or_greater(eth) ? 2 : 1;
--              num_ppe = MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2) ? 2 : 1;
-               num_ppe = min_t(u32, ARRAY_SIZE(eth->ppe), num_ppe);
-               for (i = 0; i < num_ppe; i++) {
-                       u32 ppe_addr = eth->soc->reg_map->ppe_base + i * 0x400;
-@@ -4638,6 +4637,7 @@ static const struct mtk_soc_data mt2701_
-       .hw_features = MTK_HW_FEATURES,
-       .required_clks = MT7623_CLKS_BITMAP,
-       .required_pctl = true,
-+      .version = 1,
-       .txrx = {
-               .txd_size = sizeof(struct mtk_tx_dma),
-               .rxd_size = sizeof(struct mtk_rx_dma),
-@@ -4654,6 +4654,7 @@ static const struct mtk_soc_data mt7621_
-       .hw_features = MTK_HW_FEATURES,
-       .required_clks = MT7621_CLKS_BITMAP,
-       .required_pctl = false,
-+      .version = 1,
-       .offload_version = 1,
-       .hash_offset = 2,
-       .foe_entry_size = MTK_FOE_ENTRY_V1_SIZE,
-@@ -4674,6 +4675,7 @@ static const struct mtk_soc_data mt7622_
-       .hw_features = MTK_HW_FEATURES,
-       .required_clks = MT7622_CLKS_BITMAP,
-       .required_pctl = false,
-+      .version = 1,
-       .offload_version = 2,
-       .hash_offset = 2,
-       .has_accounting = true,
-@@ -4694,6 +4696,7 @@ static const struct mtk_soc_data mt7623_
-       .hw_features = MTK_HW_FEATURES,
-       .required_clks = MT7623_CLKS_BITMAP,
-       .required_pctl = true,
-+      .version = 1,
-       .offload_version = 1,
-       .hash_offset = 2,
-       .foe_entry_size = MTK_FOE_ENTRY_V1_SIZE,
-@@ -4716,6 +4719,7 @@ static const struct mtk_soc_data mt7629_
-       .required_clks = MT7629_CLKS_BITMAP,
-       .required_pctl = false,
-       .has_accounting = true,
-+      .version = 1,
-       .txrx = {
-               .txd_size = sizeof(struct mtk_tx_dma),
-               .rxd_size = sizeof(struct mtk_rx_dma),
-@@ -4733,6 +4737,7 @@ static const struct mtk_soc_data mt7981_
-       .hw_features = MTK_HW_FEATURES,
-       .required_clks = MT7981_CLKS_BITMAP,
-       .required_pctl = false,
-+      .version = 2,
-       .offload_version = 2,
-       .hash_offset = 4,
-       .has_accounting = true,
-@@ -4754,6 +4759,7 @@ static const struct mtk_soc_data mt7986_
-       .hw_features = MTK_HW_FEATURES,
-       .required_clks = MT7986_CLKS_BITMAP,
-       .required_pctl = false,
-+      .version = 2,
-       .offload_version = 2,
-       .hash_offset = 4,
-       .has_accounting = true,
-@@ -4774,6 +4780,7 @@ static const struct mtk_soc_data rt5350_
-       .hw_features = MTK_HW_FEATURES_MT7628,
-       .required_clks = MT7628_CLKS_BITMAP,
-       .required_pctl = false,
-+      .version = 1,
-       .txrx = {
-               .txd_size = sizeof(struct mtk_tx_dma),
-               .rxd_size = sizeof(struct mtk_rx_dma),
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-@@ -817,7 +817,6 @@ enum mkt_eth_capabilities {
-       MTK_SHARED_INT_BIT,
-       MTK_TRGMII_MT7621_CLK_BIT,
-       MTK_QDMA_BIT,
--      MTK_NETSYS_V2_BIT,
-       MTK_SOC_MT7628_BIT,
-       MTK_RSTCTRL_PPE1_BIT,
-       MTK_U3_COPHY_V2_BIT,
-@@ -852,7 +851,6 @@ enum mkt_eth_capabilities {
- #define MTK_SHARED_INT                BIT(MTK_SHARED_INT_BIT)
- #define MTK_TRGMII_MT7621_CLK BIT(MTK_TRGMII_MT7621_CLK_BIT)
- #define MTK_QDMA              BIT(MTK_QDMA_BIT)
--#define MTK_NETSYS_V2         BIT(MTK_NETSYS_V2_BIT)
- #define MTK_SOC_MT7628                BIT(MTK_SOC_MT7628_BIT)
- #define MTK_RSTCTRL_PPE1      BIT(MTK_RSTCTRL_PPE1_BIT)
- #define MTK_U3_COPHY_V2               BIT(MTK_U3_COPHY_V2_BIT)
-@@ -931,11 +929,11 @@ enum mkt_eth_capabilities {
- #define MT7981_CAPS  (MTK_GMAC1_SGMII | MTK_GMAC2_SGMII | MTK_GMAC2_GEPHY | \
-                     MTK_MUX_GMAC12_TO_GEPHY_SGMII | MTK_QDMA | \
-                     MTK_MUX_U3_GMAC2_TO_QPHY | MTK_U3_COPHY_V2 | \
--                    MTK_NETSYS_V2 | MTK_RSTCTRL_PPE1)
-+                    MTK_RSTCTRL_PPE1)
- #define MT7986_CAPS  (MTK_GMAC1_SGMII | MTK_GMAC2_SGMII | \
-                     MTK_MUX_GMAC12_TO_GEPHY_SGMII | MTK_QDMA | \
--                    MTK_NETSYS_V2 | MTK_RSTCTRL_PPE1)
-+                    MTK_RSTCTRL_PPE1)
- struct mtk_tx_dma_desc_info {
-       dma_addr_t      addr;
-@@ -1006,6 +1004,7 @@ struct mtk_reg_map {
-  * @required_pctl             A bool value to show whether the SoC requires
-  *                            the extra setup for those pins used by GMAC.
-  * @hash_offset                       Flow table hash offset.
-+ * @version                   SoC version.
-  * @foe_entry_size            Foe table entry size.
-  * @has_accounting            Bool indicating support for accounting of
-  *                            offloaded flows.
-@@ -1024,6 +1023,7 @@ struct mtk_soc_data {
-       bool            required_pctl;
-       u8              offload_version;
-       u8              hash_offset;
-+      u8              version;
-       u16             foe_entry_size;
-       netdev_features_t hw_features;
-       bool            has_accounting;
-@@ -1180,6 +1180,16 @@ struct mtk_mac {
- /* the struct describing the SoC. these are declared in the soc_xyz.c files */
- extern const struct of_device_id of_mtk_match[];
-+static inline bool mtk_is_netsys_v1(struct mtk_eth *eth)
-+{
-+      return eth->soc->version == 1;
-+}
-+
-+static inline bool mtk_is_netsys_v2_or_greater(struct mtk_eth *eth)
-+{
-+      return eth->soc->version > 1;
-+}
-+
- static inline struct mtk_foe_entry *
- mtk_foe_get_entry(struct mtk_ppe *ppe, u16 hash)
- {
-@@ -1190,7 +1200,7 @@ mtk_foe_get_entry(struct mtk_ppe *ppe, u
- static inline u32 mtk_get_ib1_ts_mask(struct mtk_eth *eth)
- {
--      if (MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2))
-+      if (mtk_is_netsys_v2_or_greater(eth))
-               return MTK_FOE_IB1_BIND_TIMESTAMP_V2;
-       return MTK_FOE_IB1_BIND_TIMESTAMP;
-@@ -1198,7 +1208,7 @@ static inline u32 mtk_get_ib1_ts_mask(st
- static inline u32 mtk_get_ib1_ppoe_mask(struct mtk_eth *eth)
- {
--      if (MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2))
-+      if (mtk_is_netsys_v2_or_greater(eth))
-               return MTK_FOE_IB1_BIND_PPPOE_V2;
-       return MTK_FOE_IB1_BIND_PPPOE;
-@@ -1206,7 +1216,7 @@ static inline u32 mtk_get_ib1_ppoe_mask(
- static inline u32 mtk_get_ib1_vlan_tag_mask(struct mtk_eth *eth)
- {
--      if (MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2))
-+      if (mtk_is_netsys_v2_or_greater(eth))
-               return MTK_FOE_IB1_BIND_VLAN_TAG_V2;
-       return MTK_FOE_IB1_BIND_VLAN_TAG;
-@@ -1214,7 +1224,7 @@ static inline u32 mtk_get_ib1_vlan_tag_m
- static inline u32 mtk_get_ib1_vlan_layer_mask(struct mtk_eth *eth)
- {
--      if (MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2))
-+      if (mtk_is_netsys_v2_or_greater(eth))
-               return MTK_FOE_IB1_BIND_VLAN_LAYER_V2;
-       return MTK_FOE_IB1_BIND_VLAN_LAYER;
-@@ -1222,7 +1232,7 @@ static inline u32 mtk_get_ib1_vlan_layer
- static inline u32 mtk_prep_ib1_vlan_layer(struct mtk_eth *eth, u32 val)
- {
--      if (MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2))
-+      if (mtk_is_netsys_v2_or_greater(eth))
-               return FIELD_PREP(MTK_FOE_IB1_BIND_VLAN_LAYER_V2, val);
-       return FIELD_PREP(MTK_FOE_IB1_BIND_VLAN_LAYER, val);
-@@ -1230,7 +1240,7 @@ static inline u32 mtk_prep_ib1_vlan_laye
- static inline u32 mtk_get_ib1_vlan_layer(struct mtk_eth *eth, u32 val)
- {
--      if (MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2))
-+      if (mtk_is_netsys_v2_or_greater(eth))
-               return FIELD_GET(MTK_FOE_IB1_BIND_VLAN_LAYER_V2, val);
-       return FIELD_GET(MTK_FOE_IB1_BIND_VLAN_LAYER, val);
-@@ -1238,7 +1248,7 @@ static inline u32 mtk_get_ib1_vlan_layer
- static inline u32 mtk_get_ib1_pkt_type_mask(struct mtk_eth *eth)
- {
--      if (MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2))
-+      if (mtk_is_netsys_v2_or_greater(eth))
-               return MTK_FOE_IB1_PACKET_TYPE_V2;
-       return MTK_FOE_IB1_PACKET_TYPE;
-@@ -1246,7 +1256,7 @@ static inline u32 mtk_get_ib1_pkt_type_m
- static inline u32 mtk_get_ib1_pkt_type(struct mtk_eth *eth, u32 val)
- {
--      if (MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2))
-+      if (mtk_is_netsys_v2_or_greater(eth))
-               return FIELD_GET(MTK_FOE_IB1_PACKET_TYPE_V2, val);
-       return FIELD_GET(MTK_FOE_IB1_PACKET_TYPE, val);
-@@ -1254,7 +1264,7 @@ static inline u32 mtk_get_ib1_pkt_type(s
- static inline u32 mtk_get_ib2_multicast_mask(struct mtk_eth *eth)
- {
--      if (MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2))
-+      if (mtk_is_netsys_v2_or_greater(eth))
-               return MTK_FOE_IB2_MULTICAST_V2;
-       return MTK_FOE_IB2_MULTICAST;
---- a/drivers/net/ethernet/mediatek/mtk_ppe.c
-+++ b/drivers/net/ethernet/mediatek/mtk_ppe.c
-@@ -207,7 +207,7 @@ int mtk_foe_entry_prepare(struct mtk_eth
-       memset(entry, 0, sizeof(*entry));
--      if (MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2)) {
-+      if (mtk_is_netsys_v2_or_greater(eth)) {
-               val = FIELD_PREP(MTK_FOE_IB1_STATE, MTK_FOE_STATE_BIND) |
-                     FIELD_PREP(MTK_FOE_IB1_PACKET_TYPE_V2, type) |
-                     FIELD_PREP(MTK_FOE_IB1_UDP, l4proto == IPPROTO_UDP) |
-@@ -271,7 +271,7 @@ int mtk_foe_entry_set_pse_port(struct mt
-       u32 *ib2 = mtk_foe_entry_ib2(eth, entry);
-       u32 val = *ib2;
--      if (MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2)) {
-+      if (mtk_is_netsys_v2_or_greater(eth)) {
-               val &= ~MTK_FOE_IB2_DEST_PORT_V2;
-               val |= FIELD_PREP(MTK_FOE_IB2_DEST_PORT_V2, port);
-       } else {
-@@ -422,7 +422,7 @@ int mtk_foe_entry_set_wdma(struct mtk_et
-       struct mtk_foe_mac_info *l2 = mtk_foe_entry_l2(eth, entry);
-       u32 *ib2 = mtk_foe_entry_ib2(eth, entry);
--      if (MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2)) {
-+      if (mtk_is_netsys_v2_or_greater(eth)) {
-               *ib2 &= ~MTK_FOE_IB2_PORT_MG_V2;
-               *ib2 |=  FIELD_PREP(MTK_FOE_IB2_RX_IDX, txq) |
-                        MTK_FOE_IB2_WDMA_WINFO_V2;
-@@ -452,7 +452,7 @@ int mtk_foe_entry_set_queue(struct mtk_e
- {
-       u32 *ib2 = mtk_foe_entry_ib2(eth, entry);
--      if (MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2)) {
-+      if (mtk_is_netsys_v2_or_greater(eth)) {
-               *ib2 &= ~MTK_FOE_IB2_QID_V2;
-               *ib2 |= FIELD_PREP(MTK_FOE_IB2_QID_V2, queue);
-               *ib2 |= MTK_FOE_IB2_PSE_QOS_V2;
-@@ -607,7 +607,7 @@ __mtk_foe_entry_commit(struct mtk_ppe *p
-       struct mtk_foe_entry *hwe;
-       u32 val;
--      if (MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2)) {
-+      if (mtk_is_netsys_v2_or_greater(eth)) {
-               entry->ib1 &= ~MTK_FOE_IB1_BIND_TIMESTAMP_V2;
-               entry->ib1 |= FIELD_PREP(MTK_FOE_IB1_BIND_TIMESTAMP_V2,
-                                        timestamp);
-@@ -623,7 +623,7 @@ __mtk_foe_entry_commit(struct mtk_ppe *p
-       hwe->ib1 = entry->ib1;
-       if (ppe->accounting) {
--              if (MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2))
-+              if (mtk_is_netsys_v2_or_greater(eth))
-                       val = MTK_FOE_IB2_MIB_CNT_V2;
-               else
-                       val = MTK_FOE_IB2_MIB_CNT;
-@@ -971,7 +971,7 @@ void mtk_ppe_start(struct mtk_ppe *ppe)
-                        MTK_PPE_SCAN_MODE_CHECK_AGE) |
-             FIELD_PREP(MTK_PPE_TB_CFG_ENTRY_NUM,
-                        MTK_PPE_ENTRIES_SHIFT);
--      if (MTK_HAS_CAPS(ppe->eth->soc->caps, MTK_NETSYS_V2))
-+      if (mtk_is_netsys_v2_or_greater(ppe->eth))
-               val |= MTK_PPE_TB_CFG_INFO_SEL;
-       ppe_w32(ppe, MTK_PPE_TB_CFG, val);
-@@ -987,7 +987,7 @@ void mtk_ppe_start(struct mtk_ppe *ppe)
-             MTK_PPE_FLOW_CFG_IP4_NAPT |
-             MTK_PPE_FLOW_CFG_IP4_DSLITE |
-             MTK_PPE_FLOW_CFG_IP4_NAT_FRAG;
--      if (MTK_HAS_CAPS(ppe->eth->soc->caps, MTK_NETSYS_V2))
-+      if (mtk_is_netsys_v2_or_greater(ppe->eth))
-               val |= MTK_PPE_MD_TOAP_BYP_CRSN0 |
-                      MTK_PPE_MD_TOAP_BYP_CRSN1 |
-                      MTK_PPE_MD_TOAP_BYP_CRSN2 |
-@@ -1029,7 +1029,7 @@ void mtk_ppe_start(struct mtk_ppe *ppe)
-       ppe_w32(ppe, MTK_PPE_DEFAULT_CPU_PORT, 0);
--      if (MTK_HAS_CAPS(ppe->eth->soc->caps, MTK_NETSYS_V2)) {
-+      if (mtk_is_netsys_v2_or_greater(ppe->eth)) {
-               ppe_w32(ppe, MTK_PPE_DEFAULT_CPU_PORT1, 0xcb777);
-               ppe_w32(ppe, MTK_PPE_SBW_CTRL, 0x7f);
-       }
---- a/drivers/net/ethernet/mediatek/mtk_ppe_offload.c
-+++ b/drivers/net/ethernet/mediatek/mtk_ppe_offload.c
-@@ -193,7 +193,7 @@ mtk_flow_set_output_device(struct mtk_et
-       if (mtk_flow_get_wdma_info(dev, dest_mac, &info) == 0) {
-               mtk_foe_entry_set_wdma(eth, foe, info.wdma_idx, info.queue,
-                                      info.bss, info.wcid);
--              if (MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2)) {
-+              if (mtk_is_netsys_v2_or_greater(eth)) {
-                       switch (info.wdma_idx) {
-                       case 0:
-                               pse_port = 8;
---- a/drivers/net/ethernet/mediatek/mtk_wed.c
-+++ b/drivers/net/ethernet/mediatek/mtk_wed.c
-@@ -1084,7 +1084,7 @@ mtk_wed_rx_reset(struct mtk_wed_device *
-       } else {
-               struct mtk_eth *eth = dev->hw->eth;
--              if (MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2))
-+              if (mtk_is_netsys_v2_or_greater(eth))
-                       wed_set(dev, MTK_WED_RESET_IDX,
-                               MTK_WED_RESET_IDX_RX_V2);
-               else
-@@ -1806,7 +1806,7 @@ void mtk_wed_add_hw(struct device_node *
-       hw->wdma = wdma;
-       hw->index = index;
-       hw->irq = irq;
--      hw->version = MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2) ? 2 : 1;
-+      hw->version = mtk_is_netsys_v1(eth) ? 1 : 2;
-       if (hw->version == 1) {
-               hw->mirror = syscon_regmap_lookup_by_phandle(eth_np,
diff --git a/target/linux/generic/backport-5.15/750-v6.5-06-net-ethernet-mtk_eth_soc-increase-MAX_DEVS-to-3.patch b/target/linux/generic/backport-5.15/750-v6.5-06-net-ethernet-mtk_eth_soc-increase-MAX_DEVS-to-3.patch
deleted file mode 100644 (file)
index 5a08b9d..0000000
+++ /dev/null
@@ -1,29 +0,0 @@
-From f8fb8dbd158c585be7574faf92db7d614b6722ff Mon Sep 17 00:00:00 2001
-From: Lorenzo Bianconi <[email protected]>
-Date: Tue, 25 Jul 2023 01:52:27 +0100
-Subject: [PATCH 100/250] net: ethernet: mtk_eth_soc: increase MAX_DEVS to 3
-
-This is a preliminary patch to add MT7988 SoC support since it runs 3
-macs instead of 2.
-
-Signed-off-by: Lorenzo Bianconi <[email protected]>
-Signed-off-by: Daniel Golle <[email protected]>
-Link: https://lore.kernel.org/r/3563e5fab367e7d79a7f1296fabaa5c20f202d7a.1690246066.git.daniel@makrotopia.org
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- drivers/net/ethernet/mediatek/mtk_eth_soc.h | 4 ++--
- 1 file changed, 2 insertions(+), 2 deletions(-)
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-@@ -1040,8 +1040,8 @@ struct mtk_soc_data {
- #define MTK_DMA_MONITOR_TIMEOUT               msecs_to_jiffies(1000)
--/* currently no SoC has more than 2 macs */
--#define MTK_MAX_DEVS                  2
-+/* currently no SoC has more than 3 macs */
-+#define MTK_MAX_DEVS  3
- /* struct mtk_eth -   This is the main datasructure for holding the state
-  *                    of the driver
diff --git a/target/linux/generic/backport-5.15/750-v6.5-07-net-ethernet-mtk_eth_soc-rely-on-MTK_MAX_DEVS-and-re.patch b/target/linux/generic/backport-5.15/750-v6.5-07-net-ethernet-mtk_eth_soc-rely-on-MTK_MAX_DEVS-and-re.patch
deleted file mode 100644 (file)
index faa8734..0000000
+++ /dev/null
@@ -1,186 +0,0 @@
-From 856be974290f28d7943be2ac5a382c4139486196 Mon Sep 17 00:00:00 2001
-From: Lorenzo Bianconi <[email protected]>
-Date: Tue, 25 Jul 2023 01:52:44 +0100
-Subject: [PATCH 101/250] net: ethernet: mtk_eth_soc: rely on MTK_MAX_DEVS and
- remove MTK_MAC_COUNT
-
-Get rid of MTK_MAC_COUNT since it is a duplicated of MTK_MAX_DEVS.
-
-Signed-off-by: Lorenzo Bianconi <[email protected]>
-Signed-off-by: Daniel Golle <[email protected]>
-Link: https://lore.kernel.org/r/1856f4266f2fc80677807b1bad867659e7b00c65.1690246066.git.daniel@makrotopia.org
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- drivers/net/ethernet/mediatek/mtk_eth_soc.c | 49 ++++++++++++---------
- drivers/net/ethernet/mediatek/mtk_eth_soc.h |  1 -
- 2 files changed, 27 insertions(+), 23 deletions(-)
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-@@ -837,7 +837,7 @@ static void mtk_stats_update(struct mtk_
- {
-       int i;
--      for (i = 0; i < MTK_MAC_COUNT; i++) {
-+      for (i = 0; i < MTK_MAX_DEVS; i++) {
-               if (!eth->mac[i] || !eth->mac[i]->hw_stats)
-                       continue;
-               if (spin_trylock(&eth->mac[i]->hw_stats->stats_lock)) {
-@@ -1340,7 +1340,7 @@ static int mtk_queue_stopped(struct mtk_
- {
-       int i;
--      for (i = 0; i < MTK_MAC_COUNT; i++) {
-+      for (i = 0; i < MTK_MAX_DEVS; i++) {
-               if (!eth->netdev[i])
-                       continue;
-               if (netif_queue_stopped(eth->netdev[i]))
-@@ -1354,7 +1354,7 @@ static void mtk_wake_queue(struct mtk_et
- {
-       int i;
--      for (i = 0; i < MTK_MAC_COUNT; i++) {
-+      for (i = 0; i < MTK_MAX_DEVS; i++) {
-               if (!eth->netdev[i])
-                       continue;
-               netif_tx_wake_all_queues(eth->netdev[i]);
-@@ -1811,7 +1811,7 @@ static int mtk_poll_rx(struct napi_struc
-                        !(trxd.rxd4 & RX_DMA_SPECIAL_TAG))
-                       mac = RX_DMA_GET_SPORT(trxd.rxd4) - 1;
--              if (unlikely(mac < 0 || mac >= MTK_MAC_COUNT ||
-+              if (unlikely(mac < 0 || mac >= MTK_MAX_DEVS ||
-                            !eth->netdev[mac]))
-                       goto release_desc;
-@@ -2843,7 +2843,7 @@ static void mtk_dma_free(struct mtk_eth
-       const struct mtk_soc_data *soc = eth->soc;
-       int i;
--      for (i = 0; i < MTK_MAC_COUNT; i++)
-+      for (i = 0; i < MTK_MAX_DEVS; i++)
-               if (eth->netdev[i])
-                       netdev_reset_queue(eth->netdev[i]);
-       if (eth->scratch_ring) {
-@@ -2997,8 +2997,13 @@ static void mtk_gdm_config(struct mtk_et
-       if (MTK_HAS_CAPS(eth->soc->caps, MTK_SOC_MT7628))
-               return;
--      for (i = 0; i < MTK_MAC_COUNT; i++) {
--              u32 val = mtk_r32(eth, MTK_GDMA_FWD_CFG(i));
-+      for (i = 0; i < MTK_MAX_DEVS; i++) {
-+              u32 val;
-+
-+              if (!eth->netdev[i])
-+                      continue;
-+
-+              val = mtk_r32(eth, MTK_GDMA_FWD_CFG(i));
-               /* default setup the forward port to send frame to PDMA */
-               val &= ~0xffff;
-@@ -3008,7 +3013,7 @@ static void mtk_gdm_config(struct mtk_et
-               val |= config;
--              if (eth->netdev[i] && netdev_uses_dsa(eth->netdev[i]))
-+              if (netdev_uses_dsa(eth->netdev[i]))
-                       val |= MTK_GDMA_SPECIAL_TAG;
-               mtk_w32(eth, val, MTK_GDMA_FWD_CFG(i));
-@@ -3607,15 +3612,15 @@ static int mtk_hw_init(struct mtk_eth *e
-        * up with the more appropriate value when mtk_mac_config call is being
-        * invoked.
-        */
--      for (i = 0; i < MTK_MAC_COUNT; i++) {
-+      for (i = 0; i < MTK_MAX_DEVS; i++) {
-               struct net_device *dev = eth->netdev[i];
--              mtk_w32(eth, MAC_MCR_FORCE_LINK_DOWN, MTK_MAC_MCR(i));
--              if (dev) {
--                      struct mtk_mac *mac = netdev_priv(dev);
-+              if (!dev)
-+                      continue;
--                      mtk_set_mcr_max_rx(mac, dev->mtu + MTK_RX_ETH_HLEN);
--              }
-+              mtk_w32(eth, MAC_MCR_FORCE_LINK_DOWN, MTK_MAC_MCR(i));
-+              mtk_set_mcr_max_rx(netdev_priv(dev),
-+                                 dev->mtu + MTK_RX_ETH_HLEN);
-       }
-       /* Indicates CDM to parse the MTK special tag from CPU
-@@ -3795,7 +3800,7 @@ static void mtk_pending_work(struct work
-       mtk_prepare_for_reset(eth);
-       /* stop all devices to make sure that dma is properly shut down */
--      for (i = 0; i < MTK_MAC_COUNT; i++) {
-+      for (i = 0; i < MTK_MAX_DEVS; i++) {
-               if (!eth->netdev[i] || !netif_running(eth->netdev[i]))
-                       continue;
-@@ -3811,8 +3816,8 @@ static void mtk_pending_work(struct work
-       mtk_hw_init(eth, true);
-       /* restart DMA and enable IRQs */
--      for (i = 0; i < MTK_MAC_COUNT; i++) {
--              if (!test_bit(i, &restart))
-+      for (i = 0; i < MTK_MAX_DEVS; i++) {
-+              if (!eth->netdev[i] || !test_bit(i, &restart))
-                       continue;
-               if (mtk_open(eth->netdev[i])) {
-@@ -3839,7 +3844,7 @@ static int mtk_free_dev(struct mtk_eth *
- {
-       int i;
--      for (i = 0; i < MTK_MAC_COUNT; i++) {
-+      for (i = 0; i < MTK_MAX_DEVS; i++) {
-               if (!eth->netdev[i])
-                       continue;
-               free_netdev(eth->netdev[i]);
-@@ -3858,7 +3863,7 @@ static int mtk_unreg_dev(struct mtk_eth
- {
-       int i;
--      for (i = 0; i < MTK_MAC_COUNT; i++) {
-+      for (i = 0; i < MTK_MAX_DEVS; i++) {
-               struct mtk_mac *mac;
-               if (!eth->netdev[i])
-                       continue;
-@@ -4159,7 +4164,7 @@ static int mtk_add_mac(struct mtk_eth *e
-       }
-       id = be32_to_cpup(_id);
--      if (id >= MTK_MAC_COUNT) {
-+      if (id >= MTK_MAX_DEVS) {
-               dev_err(eth->dev, "%d is not a valid mac id\n", id);
-               return -EINVAL;
-       }
-@@ -4304,7 +4309,7 @@ void mtk_eth_set_dma_device(struct mtk_e
-       rtnl_lock();
--      for (i = 0; i < MTK_MAC_COUNT; i++) {
-+      for (i = 0; i < MTK_MAX_DEVS; i++) {
-               dev = eth->netdev[i];
-               if (!dev || !(dev->flags & IFF_UP))
-@@ -4612,7 +4617,7 @@ static int mtk_remove(struct platform_de
-       int i;
-       /* stop all devices to make sure that dma is properly shut down */
--      for (i = 0; i < MTK_MAC_COUNT; i++) {
-+      for (i = 0; i < MTK_MAX_DEVS; i++) {
-               if (!eth->netdev[i])
-                       continue;
-               mtk_stop(eth->netdev[i]);
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-@@ -33,7 +33,6 @@
- #define MTK_TX_DMA_BUF_LEN_V2 0xffff
- #define MTK_QDMA_RING_SIZE    2048
- #define MTK_DMA_SIZE          512
--#define MTK_MAC_COUNT         2
- #define MTK_RX_ETH_HLEN               (VLAN_ETH_HLEN + ETH_FCS_LEN)
- #define MTK_RX_HLEN           (NET_SKB_PAD + MTK_RX_ETH_HLEN + NET_IP_ALIGN)
- #define MTK_DMA_DUMMY_DESC    0xffffffff
diff --git a/target/linux/generic/backport-5.15/750-v6.5-08-net-ethernet-mtk_eth_soc-add-NETSYS_V3-version-suppo.patch b/target/linux/generic/backport-5.15/750-v6.5-08-net-ethernet-mtk_eth_soc-add-NETSYS_V3-version-suppo.patch
deleted file mode 100644 (file)
index c22b55c..0000000
+++ /dev/null
@@ -1,307 +0,0 @@
-From a41d535855976838d246c079143c948dcf0f7931 Mon Sep 17 00:00:00 2001
-From: Lorenzo Bianconi <[email protected]>
-Date: Tue, 25 Jul 2023 01:52:59 +0100
-Subject: [PATCH 102/250] net: ethernet: mtk_eth_soc: add NETSYS_V3 version
- support
-
-Introduce NETSYS_V3 chipset version support.
-This is a preliminary patch to introduce support for MT7988 SoC.
-
-Signed-off-by: Lorenzo Bianconi <[email protected]>
-Signed-off-by: Daniel Golle <[email protected]>
-Link: https://lore.kernel.org/r/0db2260910755d76fa48e303b9f9bdf4e5a82340.1690246066.git.daniel@makrotopia.org
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- drivers/net/ethernet/mediatek/mtk_eth_soc.c | 105 ++++++++++++++------
- drivers/net/ethernet/mediatek/mtk_eth_soc.h |  48 +++++++--
- 2 files changed, 116 insertions(+), 37 deletions(-)
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-@@ -817,17 +817,32 @@ void mtk_stats_update_mac(struct mtk_mac
-                       mtk_r32(mac->hw, reg_map->gdm1_cnt + 0x20 + offs);
-               hw_stats->rx_flow_control_packets +=
-                       mtk_r32(mac->hw, reg_map->gdm1_cnt + 0x24 + offs);
--              hw_stats->tx_skip +=
--                      mtk_r32(mac->hw, reg_map->gdm1_cnt + 0x28 + offs);
--              hw_stats->tx_collisions +=
--                      mtk_r32(mac->hw, reg_map->gdm1_cnt + 0x2c + offs);
--              hw_stats->tx_bytes +=
--                      mtk_r32(mac->hw, reg_map->gdm1_cnt + 0x30 + offs);
--              stats =  mtk_r32(mac->hw, reg_map->gdm1_cnt + 0x34 + offs);
--              if (stats)
--                      hw_stats->tx_bytes += (stats << 32);
--              hw_stats->tx_packets +=
--                      mtk_r32(mac->hw, reg_map->gdm1_cnt + 0x38 + offs);
-+
-+              if (mtk_is_netsys_v3_or_greater(eth)) {
-+                      hw_stats->tx_skip +=
-+                              mtk_r32(mac->hw, reg_map->gdm1_cnt + 0x50 + offs);
-+                      hw_stats->tx_collisions +=
-+                              mtk_r32(mac->hw, reg_map->gdm1_cnt + 0x54 + offs);
-+                      hw_stats->tx_bytes +=
-+                              mtk_r32(mac->hw, reg_map->gdm1_cnt + 0x40 + offs);
-+                      stats =  mtk_r32(mac->hw, reg_map->gdm1_cnt + 0x44 + offs);
-+                      if (stats)
-+                              hw_stats->tx_bytes += (stats << 32);
-+                      hw_stats->tx_packets +=
-+                              mtk_r32(mac->hw, reg_map->gdm1_cnt + 0x48 + offs);
-+              } else {
-+                      hw_stats->tx_skip +=
-+                              mtk_r32(mac->hw, reg_map->gdm1_cnt + 0x28 + offs);
-+                      hw_stats->tx_collisions +=
-+                              mtk_r32(mac->hw, reg_map->gdm1_cnt + 0x2c + offs);
-+                      hw_stats->tx_bytes +=
-+                              mtk_r32(mac->hw, reg_map->gdm1_cnt + 0x30 + offs);
-+                      stats =  mtk_r32(mac->hw, reg_map->gdm1_cnt + 0x34 + offs);
-+                      if (stats)
-+                              hw_stats->tx_bytes += (stats << 32);
-+                      hw_stats->tx_packets +=
-+                              mtk_r32(mac->hw, reg_map->gdm1_cnt + 0x38 + offs);
-+              }
-       }
-       u64_stats_update_end(&hw_stats->syncp);
-@@ -1129,7 +1144,10 @@ static void mtk_tx_set_dma_desc_v2(struc
-               data |= TX_DMA_LS0;
-       WRITE_ONCE(desc->txd3, data);
--      data = (mac->id + 1) << TX_DMA_FPORT_SHIFT_V2; /* forward port */
-+      if (mac->id == MTK_GMAC3_ID)
-+              data = PSE_GDM3_PORT;
-+      else
-+              data = (mac->id + 1) << TX_DMA_FPORT_SHIFT_V2; /* forward port */
-       data |= TX_DMA_SWC_V2 | QID_BITS_V2(info->qid);
-       WRITE_ONCE(desc->txd4, data);
-@@ -1140,6 +1158,8 @@ static void mtk_tx_set_dma_desc_v2(struc
-               /* tx checksum offload */
-               if (info->csum)
-                       data |= TX_DMA_CHKSUM_V2;
-+              if (mtk_is_netsys_v3_or_greater(eth) && netdev_uses_dsa(dev))
-+                      data |= TX_DMA_SPTAG_V3;
-       }
-       WRITE_ONCE(desc->txd5, data);
-@@ -1205,8 +1225,7 @@ static int mtk_tx_map(struct sk_buff *sk
-       mtk_tx_set_dma_desc(dev, itxd, &txd_info);
-       itx_buf->flags |= MTK_TX_FLAGS_SINGLE0;
--      itx_buf->flags |= (!mac->id) ? MTK_TX_FLAGS_FPORT0 :
--                        MTK_TX_FLAGS_FPORT1;
-+      itx_buf->mac_id = mac->id;
-       setup_tx_buf(eth, itx_buf, itxd_pdma, txd_info.addr, txd_info.size,
-                    k++);
-@@ -1254,8 +1273,7 @@ static int mtk_tx_map(struct sk_buff *sk
-                               memset(tx_buf, 0, sizeof(*tx_buf));
-                       tx_buf->data = (void *)MTK_DMA_DUMMY_DESC;
-                       tx_buf->flags |= MTK_TX_FLAGS_PAGE0;
--                      tx_buf->flags |= (!mac->id) ? MTK_TX_FLAGS_FPORT0 :
--                                       MTK_TX_FLAGS_FPORT1;
-+                      tx_buf->mac_id = mac->id;
-                       setup_tx_buf(eth, tx_buf, txd_pdma, txd_info.addr,
-                                    txd_info.size, k++);
-@@ -1557,7 +1575,7 @@ static int mtk_xdp_frame_map(struct mtk_
-       }
-       mtk_tx_set_dma_desc(dev, txd, txd_info);
--      tx_buf->flags |= !mac->id ? MTK_TX_FLAGS_FPORT0 : MTK_TX_FLAGS_FPORT1;
-+      tx_buf->mac_id = mac->id;
-       tx_buf->type = dma_map ? MTK_TYPE_XDP_NDO : MTK_TYPE_XDP_TX;
-       tx_buf->data = (void *)MTK_DMA_DUMMY_DESC;
-@@ -1805,11 +1823,24 @@ static int mtk_poll_rx(struct napi_struc
-                       break;
-               /* find out which mac the packet come from. values start at 1 */
--              if (mtk_is_netsys_v2_or_greater(eth))
--                      mac = RX_DMA_GET_SPORT_V2(trxd.rxd5) - 1;
--              else if (!MTK_HAS_CAPS(eth->soc->caps, MTK_SOC_MT7628) &&
--                       !(trxd.rxd4 & RX_DMA_SPECIAL_TAG))
-+              if (mtk_is_netsys_v2_or_greater(eth)) {
-+                      u32 val = RX_DMA_GET_SPORT_V2(trxd.rxd5);
-+
-+                      switch (val) {
-+                      case PSE_GDM1_PORT:
-+                      case PSE_GDM2_PORT:
-+                              mac = val - 1;
-+                              break;
-+                      case PSE_GDM3_PORT:
-+                              mac = MTK_GMAC3_ID;
-+                              break;
-+                      default:
-+                              break;
-+                      }
-+              } else if (!MTK_HAS_CAPS(eth->soc->caps, MTK_SOC_MT7628) &&
-+                         !(trxd.rxd4 & RX_DMA_SPECIAL_TAG)) {
-                       mac = RX_DMA_GET_SPORT(trxd.rxd4) - 1;
-+              }
-               if (unlikely(mac < 0 || mac >= MTK_MAX_DEVS ||
-                            !eth->netdev[mac]))
-@@ -2029,7 +2060,6 @@ static int mtk_poll_tx_qdma(struct mtk_e
-       while ((cpu != dma) && budget) {
-               u32 next_cpu = desc->txd2;
--              int mac = 0;
-               desc = mtk_qdma_phys_to_virt(ring, desc->txd2);
-               if ((desc->txd3 & TX_DMA_OWNER_CPU) == 0)
-@@ -2037,15 +2067,13 @@ static int mtk_poll_tx_qdma(struct mtk_e
-               tx_buf = mtk_desc_to_tx_buf(ring, desc,
-                                           eth->soc->txrx.txd_size);
--              if (tx_buf->flags & MTK_TX_FLAGS_FPORT1)
--                      mac = 1;
--
-               if (!tx_buf->data)
-                       break;
-               if (tx_buf->data != (void *)MTK_DMA_DUMMY_DESC) {
-                       if (tx_buf->type == MTK_TYPE_SKB)
--                              mtk_poll_tx_done(eth, state, mac, tx_buf->data);
-+                              mtk_poll_tx_done(eth, state, tx_buf->mac_id,
-+                                               tx_buf->data);
-                       budget--;
-               }
-@@ -3650,7 +3678,24 @@ static int mtk_hw_init(struct mtk_eth *e
-       mtk_w32(eth, eth->soc->txrx.rx_irq_done_mask, reg_map->qdma.int_grp + 4);
-       mtk_w32(eth, 0x21021000, MTK_FE_INT_GRP);
--      if (mtk_is_netsys_v2_or_greater(eth)) {
-+      if (mtk_is_netsys_v3_or_greater(eth)) {
-+              /* PSE should not drop port1, port8 and port9 packets */
-+              mtk_w32(eth, 0x00000302, PSE_DROP_CFG);
-+
-+              /* GDM and CDM Threshold */
-+              mtk_w32(eth, 0x00000707, MTK_CDMW0_THRES);
-+              mtk_w32(eth, 0x00000077, MTK_CDMW1_THRES);
-+
-+              /* Disable GDM1 RX CRC stripping */
-+              mtk_m32(eth, MTK_GDMA_STRP_CRC, 0, MTK_GDMA_FWD_CFG(0));
-+
-+              /* PSE GDM3 MIB counter has incorrect hw default values,
-+               * so the driver ought to read clear the values beforehand
-+               * in case ethtool retrieve wrong mib values.
-+               */
-+              for (i = 0; i < 0x80; i += 0x4)
-+                      mtk_r32(eth, reg_map->gdm1_cnt + 0x100 + i);
-+      } else if (!mtk_is_netsys_v1(eth)) {
-               /* PSE should not drop port8 and port9 packets from WDMA Tx */
-               mtk_w32(eth, 0x00000300, PSE_DROP_CFG);
-@@ -4212,7 +4257,11 @@ static int mtk_add_mac(struct mtk_eth *e
-       }
-       spin_lock_init(&mac->hw_stats->stats_lock);
-       u64_stats_init(&mac->hw_stats->syncp);
--      mac->hw_stats->reg_offset = id * MTK_STAT_OFFSET;
-+
-+      if (mtk_is_netsys_v3_or_greater(eth))
-+              mac->hw_stats->reg_offset = id * 0x80;
-+      else
-+              mac->hw_stats->reg_offset = id * 0x40;
-       /* phylink create */
-       err = of_get_phy_mode(np, &phy_mode);
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-@@ -122,6 +122,7 @@
- #define MTK_GDMA_ICS_EN               BIT(22)
- #define MTK_GDMA_TCS_EN               BIT(21)
- #define MTK_GDMA_UCS_EN               BIT(20)
-+#define MTK_GDMA_STRP_CRC     BIT(16)
- #define MTK_GDMA_TO_PDMA      0x0
- #define MTK_GDMA_DROP_ALL       0x7777
-@@ -287,8 +288,6 @@
- /* QDMA Interrupt grouping registers */
- #define MTK_RLS_DONE_INT      BIT(0)
--#define MTK_STAT_OFFSET               0x40
--
- /* QDMA TX NUM */
- #define QID_BITS_V2(x)                (((x) & 0x3f) << 16)
- #define MTK_QDMA_GMAC2_QID    8
-@@ -301,6 +300,8 @@
- #define TX_DMA_CHKSUM_V2      (0x7 << 28)
- #define TX_DMA_TSO_V2         BIT(31)
-+#define TX_DMA_SPTAG_V3         BIT(27)
-+
- /* QDMA V2 descriptor txd4 */
- #define TX_DMA_FPORT_SHIFT_V2 8
- #define TX_DMA_FPORT_MASK_V2  0xf
-@@ -631,12 +632,6 @@ enum mtk_tx_flags {
-        */
-       MTK_TX_FLAGS_SINGLE0    = 0x01,
-       MTK_TX_FLAGS_PAGE0      = 0x02,
--
--      /* MTK_TX_FLAGS_FPORTx allows tracking which port the transmitted
--       * SKB out instead of looking up through hardware TX descriptor.
--       */
--      MTK_TX_FLAGS_FPORT0     = 0x04,
--      MTK_TX_FLAGS_FPORT1     = 0x08,
- };
- /* This enum allows us to identify how the clock is defined on the array of the
-@@ -722,6 +717,35 @@ enum mtk_dev_state {
-       MTK_RESETTING
- };
-+/* PSE Port Definition */
-+enum mtk_pse_port {
-+      PSE_ADMA_PORT = 0,
-+      PSE_GDM1_PORT,
-+      PSE_GDM2_PORT,
-+      PSE_PPE0_PORT,
-+      PSE_PPE1_PORT,
-+      PSE_QDMA_TX_PORT,
-+      PSE_QDMA_RX_PORT,
-+      PSE_DROP_PORT,
-+      PSE_WDMA0_PORT,
-+      PSE_WDMA1_PORT,
-+      PSE_TDMA_PORT,
-+      PSE_NONE_PORT,
-+      PSE_PPE2_PORT,
-+      PSE_WDMA2_PORT,
-+      PSE_EIP197_PORT,
-+      PSE_GDM3_PORT,
-+      PSE_PORT_MAX
-+};
-+
-+/* GMAC Identifier */
-+enum mtk_gmac_id {
-+      MTK_GMAC1_ID = 0,
-+      MTK_GMAC2_ID,
-+      MTK_GMAC3_ID,
-+      MTK_GMAC_ID_MAX
-+};
-+
- enum mtk_tx_buf_type {
-       MTK_TYPE_SKB,
-       MTK_TYPE_XDP_TX,
-@@ -740,7 +764,8 @@ struct mtk_tx_buf {
-       enum mtk_tx_buf_type type;
-       void *data;
--      u32 flags;
-+      u16 mac_id;
-+      u16 flags;
-       DEFINE_DMA_UNMAP_ADDR(dma_addr0);
-       DEFINE_DMA_UNMAP_LEN(dma_len0);
-       DEFINE_DMA_UNMAP_ADDR(dma_addr1);
-@@ -1189,6 +1214,11 @@ static inline bool mtk_is_netsys_v2_or_g
-       return eth->soc->version > 1;
- }
-+static inline bool mtk_is_netsys_v3_or_greater(struct mtk_eth *eth)
-+{
-+      return eth->soc->version > 2;
-+}
-+
- static inline struct mtk_foe_entry *
- mtk_foe_get_entry(struct mtk_ppe *ppe, u16 hash)
- {
diff --git a/target/linux/generic/backport-5.15/750-v6.5-09-net-ethernet-mtk_eth_soc-convert-caps-in-mtk_soc_dat.patch b/target/linux/generic/backport-5.15/750-v6.5-09-net-ethernet-mtk_eth_soc-convert-caps-in-mtk_soc_dat.patch
deleted file mode 100644 (file)
index 0a72eec..0000000
+++ /dev/null
@@ -1,193 +0,0 @@
-From db797ae0542220a98658229397da464c383c991c Mon Sep 17 00:00:00 2001
-From: Lorenzo Bianconi <[email protected]>
-Date: Tue, 25 Jul 2023 01:53:13 +0100
-Subject: [PATCH 103/250] net: ethernet: mtk_eth_soc: convert caps in
- mtk_soc_data struct to u64
-
-This is a preliminary patch to introduce support for MT7988 SoC.
-
-Signed-off-by: Lorenzo Bianconi <[email protected]>
-Signed-off-by: Daniel Golle <[email protected]>
-Link: https://lore.kernel.org/r/9499ac3670b2fc5b444404b84e8a4a169beabbf2.1690246066.git.daniel@makrotopia.org
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- drivers/net/ethernet/mediatek/mtk_eth_path.c | 22 ++++----
- drivers/net/ethernet/mediatek/mtk_eth_soc.h  | 56 ++++++++++----------
- 2 files changed, 39 insertions(+), 39 deletions(-)
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_path.c
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_path.c
-@@ -15,10 +15,10 @@
- struct mtk_eth_muxc {
-       const char      *name;
-       int             cap_bit;
--      int             (*set_path)(struct mtk_eth *eth, int path);
-+      int             (*set_path)(struct mtk_eth *eth, u64 path);
- };
--static const char *mtk_eth_path_name(int path)
-+static const char *mtk_eth_path_name(u64 path)
- {
-       switch (path) {
-       case MTK_ETH_PATH_GMAC1_RGMII:
-@@ -40,7 +40,7 @@ static const char *mtk_eth_path_name(int
-       }
- }
--static int set_mux_gdm1_to_gmac1_esw(struct mtk_eth *eth, int path)
-+static int set_mux_gdm1_to_gmac1_esw(struct mtk_eth *eth, u64 path)
- {
-       bool updated = true;
-       u32 val, mask, set;
-@@ -71,7 +71,7 @@ static int set_mux_gdm1_to_gmac1_esw(str
-       return 0;
- }
--static int set_mux_gmac2_gmac0_to_gephy(struct mtk_eth *eth, int path)
-+static int set_mux_gmac2_gmac0_to_gephy(struct mtk_eth *eth, u64 path)
- {
-       unsigned int val = 0;
-       bool updated = true;
-@@ -94,7 +94,7 @@ static int set_mux_gmac2_gmac0_to_gephy(
-       return 0;
- }
--static int set_mux_u3_gmac2_to_qphy(struct mtk_eth *eth, int path)
-+static int set_mux_u3_gmac2_to_qphy(struct mtk_eth *eth, u64 path)
- {
-       unsigned int val = 0, mask = 0, reg = 0;
-       bool updated = true;
-@@ -125,7 +125,7 @@ static int set_mux_u3_gmac2_to_qphy(stru
-       return 0;
- }
--static int set_mux_gmac1_gmac2_to_sgmii_rgmii(struct mtk_eth *eth, int path)
-+static int set_mux_gmac1_gmac2_to_sgmii_rgmii(struct mtk_eth *eth, u64 path)
- {
-       unsigned int val = 0;
-       bool updated = true;
-@@ -163,7 +163,7 @@ static int set_mux_gmac1_gmac2_to_sgmii_
-       return 0;
- }
--static int set_mux_gmac12_to_gephy_sgmii(struct mtk_eth *eth, int path)
-+static int set_mux_gmac12_to_gephy_sgmii(struct mtk_eth *eth, u64 path)
- {
-       unsigned int val = 0;
-       bool updated = true;
-@@ -218,7 +218,7 @@ static const struct mtk_eth_muxc mtk_eth
-       },
- };
--static int mtk_eth_mux_setup(struct mtk_eth *eth, int path)
-+static int mtk_eth_mux_setup(struct mtk_eth *eth, u64 path)
- {
-       int i, err = 0;
-@@ -249,7 +249,7 @@ out:
- int mtk_gmac_sgmii_path_setup(struct mtk_eth *eth, int mac_id)
- {
--      int path;
-+      u64 path;
-       path = (mac_id == 0) ?  MTK_ETH_PATH_GMAC1_SGMII :
-                               MTK_ETH_PATH_GMAC2_SGMII;
-@@ -260,7 +260,7 @@ int mtk_gmac_sgmii_path_setup(struct mtk
- int mtk_gmac_gephy_path_setup(struct mtk_eth *eth, int mac_id)
- {
--      int path = 0;
-+      u64 path = 0;
-       if (mac_id == 1)
-               path = MTK_ETH_PATH_GMAC2_GEPHY;
-@@ -274,7 +274,7 @@ int mtk_gmac_gephy_path_setup(struct mtk
- int mtk_gmac_rgmii_path_setup(struct mtk_eth *eth, int mac_id)
- {
--      int path;
-+      u64 path;
-       path = (mac_id == 0) ?  MTK_ETH_PATH_GMAC1_RGMII :
-                               MTK_ETH_PATH_GMAC2_RGMII;
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-@@ -863,41 +863,41 @@ enum mkt_eth_capabilities {
- };
- /* Supported hardware group on SoCs */
--#define MTK_RGMII             BIT(MTK_RGMII_BIT)
--#define MTK_TRGMII            BIT(MTK_TRGMII_BIT)
--#define MTK_SGMII             BIT(MTK_SGMII_BIT)
--#define MTK_ESW                       BIT(MTK_ESW_BIT)
--#define MTK_GEPHY             BIT(MTK_GEPHY_BIT)
--#define MTK_MUX                       BIT(MTK_MUX_BIT)
--#define MTK_INFRA             BIT(MTK_INFRA_BIT)
--#define MTK_SHARED_SGMII      BIT(MTK_SHARED_SGMII_BIT)
--#define MTK_HWLRO             BIT(MTK_HWLRO_BIT)
--#define MTK_SHARED_INT                BIT(MTK_SHARED_INT_BIT)
--#define MTK_TRGMII_MT7621_CLK BIT(MTK_TRGMII_MT7621_CLK_BIT)
--#define MTK_QDMA              BIT(MTK_QDMA_BIT)
--#define MTK_SOC_MT7628                BIT(MTK_SOC_MT7628_BIT)
--#define MTK_RSTCTRL_PPE1      BIT(MTK_RSTCTRL_PPE1_BIT)
--#define MTK_U3_COPHY_V2               BIT(MTK_U3_COPHY_V2_BIT)
-+#define MTK_RGMII             BIT_ULL(MTK_RGMII_BIT)
-+#define MTK_TRGMII            BIT_ULL(MTK_TRGMII_BIT)
-+#define MTK_SGMII             BIT_ULL(MTK_SGMII_BIT)
-+#define MTK_ESW                       BIT_ULL(MTK_ESW_BIT)
-+#define MTK_GEPHY             BIT_ULL(MTK_GEPHY_BIT)
-+#define MTK_MUX                       BIT_ULL(MTK_MUX_BIT)
-+#define MTK_INFRA             BIT_ULL(MTK_INFRA_BIT)
-+#define MTK_SHARED_SGMII      BIT_ULL(MTK_SHARED_SGMII_BIT)
-+#define MTK_HWLRO             BIT_ULL(MTK_HWLRO_BIT)
-+#define MTK_SHARED_INT                BIT_ULL(MTK_SHARED_INT_BIT)
-+#define MTK_TRGMII_MT7621_CLK BIT_ULL(MTK_TRGMII_MT7621_CLK_BIT)
-+#define MTK_QDMA              BIT_ULL(MTK_QDMA_BIT)
-+#define MTK_SOC_MT7628                BIT_ULL(MTK_SOC_MT7628_BIT)
-+#define MTK_RSTCTRL_PPE1      BIT_ULL(MTK_RSTCTRL_PPE1_BIT)
-+#define MTK_U3_COPHY_V2               BIT_ULL(MTK_U3_COPHY_V2_BIT)
- #define MTK_ETH_MUX_GDM1_TO_GMAC1_ESW         \
--      BIT(MTK_ETH_MUX_GDM1_TO_GMAC1_ESW_BIT)
-+      BIT_ULL(MTK_ETH_MUX_GDM1_TO_GMAC1_ESW_BIT)
- #define MTK_ETH_MUX_GMAC2_GMAC0_TO_GEPHY      \
--      BIT(MTK_ETH_MUX_GMAC2_GMAC0_TO_GEPHY_BIT)
-+      BIT_ULL(MTK_ETH_MUX_GMAC2_GMAC0_TO_GEPHY_BIT)
- #define MTK_ETH_MUX_U3_GMAC2_TO_QPHY          \
--      BIT(MTK_ETH_MUX_U3_GMAC2_TO_QPHY_BIT)
-+      BIT_ULL(MTK_ETH_MUX_U3_GMAC2_TO_QPHY_BIT)
- #define MTK_ETH_MUX_GMAC1_GMAC2_TO_SGMII_RGMII        \
--      BIT(MTK_ETH_MUX_GMAC1_GMAC2_TO_SGMII_RGMII_BIT)
-+      BIT_ULL(MTK_ETH_MUX_GMAC1_GMAC2_TO_SGMII_RGMII_BIT)
- #define MTK_ETH_MUX_GMAC12_TO_GEPHY_SGMII     \
--      BIT(MTK_ETH_MUX_GMAC12_TO_GEPHY_SGMII_BIT)
-+      BIT_ULL(MTK_ETH_MUX_GMAC12_TO_GEPHY_SGMII_BIT)
- /* Supported path present on SoCs */
--#define MTK_ETH_PATH_GMAC1_RGMII      BIT(MTK_ETH_PATH_GMAC1_RGMII_BIT)
--#define MTK_ETH_PATH_GMAC1_TRGMII     BIT(MTK_ETH_PATH_GMAC1_TRGMII_BIT)
--#define MTK_ETH_PATH_GMAC1_SGMII      BIT(MTK_ETH_PATH_GMAC1_SGMII_BIT)
--#define MTK_ETH_PATH_GMAC2_RGMII      BIT(MTK_ETH_PATH_GMAC2_RGMII_BIT)
--#define MTK_ETH_PATH_GMAC2_SGMII      BIT(MTK_ETH_PATH_GMAC2_SGMII_BIT)
--#define MTK_ETH_PATH_GMAC2_GEPHY      BIT(MTK_ETH_PATH_GMAC2_GEPHY_BIT)
--#define MTK_ETH_PATH_GDM1_ESW         BIT(MTK_ETH_PATH_GDM1_ESW_BIT)
-+#define MTK_ETH_PATH_GMAC1_RGMII      BIT_ULL(MTK_ETH_PATH_GMAC1_RGMII_BIT)
-+#define MTK_ETH_PATH_GMAC1_TRGMII     BIT_ULL(MTK_ETH_PATH_GMAC1_TRGMII_BIT)
-+#define MTK_ETH_PATH_GMAC1_SGMII      BIT_ULL(MTK_ETH_PATH_GMAC1_SGMII_BIT)
-+#define MTK_ETH_PATH_GMAC2_RGMII      BIT_ULL(MTK_ETH_PATH_GMAC2_RGMII_BIT)
-+#define MTK_ETH_PATH_GMAC2_SGMII      BIT_ULL(MTK_ETH_PATH_GMAC2_SGMII_BIT)
-+#define MTK_ETH_PATH_GMAC2_GEPHY      BIT_ULL(MTK_ETH_PATH_GMAC2_GEPHY_BIT)
-+#define MTK_ETH_PATH_GDM1_ESW         BIT_ULL(MTK_ETH_PATH_GDM1_ESW_BIT)
- #define MTK_GMAC1_RGMII               (MTK_ETH_PATH_GMAC1_RGMII | MTK_RGMII)
- #define MTK_GMAC1_TRGMII      (MTK_ETH_PATH_GMAC1_TRGMII | MTK_TRGMII)
-@@ -1042,7 +1042,7 @@ struct mtk_reg_map {
- struct mtk_soc_data {
-       const struct mtk_reg_map *reg_map;
-       u32             ana_rgc3;
--      u32             caps;
-+      u64             caps;
-       u32             required_clks;
-       bool            required_pctl;
-       u8              offload_version;
diff --git a/target/linux/generic/backport-5.15/750-v6.5-10-net-ethernet-mtk_eth_soc-convert-clock-bitmap-to-u64.patch b/target/linux/generic/backport-5.15/750-v6.5-10-net-ethernet-mtk_eth_soc-convert-clock-bitmap-to-u64.patch
deleted file mode 100644 (file)
index 4e5b857..0000000
+++ /dev/null
@@ -1,132 +0,0 @@
-From a1c9f7d1d24e90294f6a6755b137fcf306851e93 Mon Sep 17 00:00:00 2001
-From: Daniel Golle <[email protected]>
-Date: Tue, 25 Jul 2023 01:53:28 +0100
-Subject: [PATCH 104/250] net: ethernet: mtk_eth_soc: convert clock bitmap to
- u64
-
-The to-be-added MT7988 SoC adds many new clocks which need to be
-controlled by the Ethernet driver, which will result in their total
-number exceeding 32.
-Prepare by converting clock bitmaps into 64-bit types.
-
-Signed-off-by: Daniel Golle <[email protected]>
-Link: https://lore.kernel.org/r/6960a39bb0078cf84d7642a9558e6a91c6cc9df3.1690246066.git.daniel@makrotopia.org
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- drivers/net/ethernet/mediatek/mtk_eth_soc.h | 96 +++++++++++----------
- 1 file changed, 49 insertions(+), 47 deletions(-)
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-@@ -663,54 +663,56 @@ enum mtk_clks_map {
-       MTK_CLK_MAX
- };
--#define MT7623_CLKS_BITMAP    (BIT(MTK_CLK_ETHIF) | BIT(MTK_CLK_ESW) |  \
--                               BIT(MTK_CLK_GP1) | BIT(MTK_CLK_GP2) | \
--                               BIT(MTK_CLK_TRGPLL))
--#define MT7622_CLKS_BITMAP    (BIT(MTK_CLK_ETHIF) | BIT(MTK_CLK_ESW) |  \
--                               BIT(MTK_CLK_GP0) | BIT(MTK_CLK_GP1) | \
--                               BIT(MTK_CLK_GP2) | \
--                               BIT(MTK_CLK_SGMII_TX_250M) | \
--                               BIT(MTK_CLK_SGMII_RX_250M) | \
--                               BIT(MTK_CLK_SGMII_CDR_REF) | \
--                               BIT(MTK_CLK_SGMII_CDR_FB) | \
--                               BIT(MTK_CLK_SGMII_CK) | \
--                               BIT(MTK_CLK_ETH2PLL))
-+#define MT7623_CLKS_BITMAP    (BIT_ULL(MTK_CLK_ETHIF) | BIT_ULL(MTK_CLK_ESW) |  \
-+                               BIT_ULL(MTK_CLK_GP1) | BIT_ULL(MTK_CLK_GP2) | \
-+                               BIT_ULL(MTK_CLK_TRGPLL))
-+#define MT7622_CLKS_BITMAP    (BIT_ULL(MTK_CLK_ETHIF) | BIT_ULL(MTK_CLK_ESW) |  \
-+                               BIT_ULL(MTK_CLK_GP0) | BIT_ULL(MTK_CLK_GP1) | \
-+                               BIT_ULL(MTK_CLK_GP2) | \
-+                               BIT_ULL(MTK_CLK_SGMII_TX_250M) | \
-+                               BIT_ULL(MTK_CLK_SGMII_RX_250M) | \
-+                               BIT_ULL(MTK_CLK_SGMII_CDR_REF) | \
-+                               BIT_ULL(MTK_CLK_SGMII_CDR_FB) | \
-+                               BIT_ULL(MTK_CLK_SGMII_CK) | \
-+                               BIT_ULL(MTK_CLK_ETH2PLL))
- #define MT7621_CLKS_BITMAP    (0)
- #define MT7628_CLKS_BITMAP    (0)
--#define MT7629_CLKS_BITMAP    (BIT(MTK_CLK_ETHIF) | BIT(MTK_CLK_ESW) |  \
--                               BIT(MTK_CLK_GP0) | BIT(MTK_CLK_GP1) | \
--                               BIT(MTK_CLK_GP2) | BIT(MTK_CLK_FE) | \
--                               BIT(MTK_CLK_SGMII_TX_250M) | \
--                               BIT(MTK_CLK_SGMII_RX_250M) | \
--                               BIT(MTK_CLK_SGMII_CDR_REF) | \
--                               BIT(MTK_CLK_SGMII_CDR_FB) | \
--                               BIT(MTK_CLK_SGMII2_TX_250M) | \
--                               BIT(MTK_CLK_SGMII2_RX_250M) | \
--                               BIT(MTK_CLK_SGMII2_CDR_REF) | \
--                               BIT(MTK_CLK_SGMII2_CDR_FB) | \
--                               BIT(MTK_CLK_SGMII_CK) | \
--                               BIT(MTK_CLK_ETH2PLL) | BIT(MTK_CLK_SGMIITOP))
--#define MT7981_CLKS_BITMAP    (BIT(MTK_CLK_FE) | BIT(MTK_CLK_GP2) | BIT(MTK_CLK_GP1) | \
--                               BIT(MTK_CLK_WOCPU0) | \
--                               BIT(MTK_CLK_SGMII_TX_250M) | \
--                               BIT(MTK_CLK_SGMII_RX_250M) | \
--                               BIT(MTK_CLK_SGMII_CDR_REF) | \
--                               BIT(MTK_CLK_SGMII_CDR_FB) | \
--                               BIT(MTK_CLK_SGMII2_TX_250M) | \
--                               BIT(MTK_CLK_SGMII2_RX_250M) | \
--                               BIT(MTK_CLK_SGMII2_CDR_REF) | \
--                               BIT(MTK_CLK_SGMII2_CDR_FB) | \
--                               BIT(MTK_CLK_SGMII_CK))
--#define MT7986_CLKS_BITMAP    (BIT(MTK_CLK_FE) | BIT(MTK_CLK_GP2) | BIT(MTK_CLK_GP1) | \
--                               BIT(MTK_CLK_WOCPU1) | BIT(MTK_CLK_WOCPU0) | \
--                               BIT(MTK_CLK_SGMII_TX_250M) | \
--                               BIT(MTK_CLK_SGMII_RX_250M) | \
--                               BIT(MTK_CLK_SGMII_CDR_REF) | \
--                               BIT(MTK_CLK_SGMII_CDR_FB) | \
--                               BIT(MTK_CLK_SGMII2_TX_250M) | \
--                               BIT(MTK_CLK_SGMII2_RX_250M) | \
--                               BIT(MTK_CLK_SGMII2_CDR_REF) | \
--                               BIT(MTK_CLK_SGMII2_CDR_FB))
-+#define MT7629_CLKS_BITMAP    (BIT_ULL(MTK_CLK_ETHIF) | BIT_ULL(MTK_CLK_ESW) |  \
-+                               BIT_ULL(MTK_CLK_GP0) | BIT_ULL(MTK_CLK_GP1) | \
-+                               BIT_ULL(MTK_CLK_GP2) | BIT_ULL(MTK_CLK_FE) | \
-+                               BIT_ULL(MTK_CLK_SGMII_TX_250M) | \
-+                               BIT_ULL(MTK_CLK_SGMII_RX_250M) | \
-+                               BIT_ULL(MTK_CLK_SGMII_CDR_REF) | \
-+                               BIT_ULL(MTK_CLK_SGMII_CDR_FB) | \
-+                               BIT_ULL(MTK_CLK_SGMII2_TX_250M) | \
-+                               BIT_ULL(MTK_CLK_SGMII2_RX_250M) | \
-+                               BIT_ULL(MTK_CLK_SGMII2_CDR_REF) | \
-+                               BIT_ULL(MTK_CLK_SGMII2_CDR_FB) | \
-+                               BIT_ULL(MTK_CLK_SGMII_CK) | \
-+                               BIT_ULL(MTK_CLK_ETH2PLL) | BIT_ULL(MTK_CLK_SGMIITOP))
-+#define MT7981_CLKS_BITMAP    (BIT_ULL(MTK_CLK_FE) | BIT_ULL(MTK_CLK_GP2) | \
-+                               BIT_ULL(MTK_CLK_GP1) | \
-+                               BIT_ULL(MTK_CLK_WOCPU0) | \
-+                               BIT_ULL(MTK_CLK_SGMII_TX_250M) | \
-+                               BIT_ULL(MTK_CLK_SGMII_RX_250M) | \
-+                               BIT_ULL(MTK_CLK_SGMII_CDR_REF) | \
-+                               BIT_ULL(MTK_CLK_SGMII_CDR_FB) | \
-+                               BIT_ULL(MTK_CLK_SGMII2_TX_250M) | \
-+                               BIT_ULL(MTK_CLK_SGMII2_RX_250M) | \
-+                               BIT_ULL(MTK_CLK_SGMII2_CDR_REF) | \
-+                               BIT_ULL(MTK_CLK_SGMII2_CDR_FB) | \
-+                               BIT_ULL(MTK_CLK_SGMII_CK))
-+#define MT7986_CLKS_BITMAP    (BIT_ULL(MTK_CLK_FE) | BIT_ULL(MTK_CLK_GP2) | \
-+                               BIT_ULL(MTK_CLK_GP1) | \
-+                               BIT_ULL(MTK_CLK_WOCPU1) | BIT_ULL(MTK_CLK_WOCPU0) | \
-+                               BIT_ULL(MTK_CLK_SGMII_TX_250M) | \
-+                               BIT_ULL(MTK_CLK_SGMII_RX_250M) | \
-+                               BIT_ULL(MTK_CLK_SGMII_CDR_REF) | \
-+                               BIT_ULL(MTK_CLK_SGMII_CDR_FB) | \
-+                               BIT_ULL(MTK_CLK_SGMII2_TX_250M) | \
-+                               BIT_ULL(MTK_CLK_SGMII2_RX_250M) | \
-+                               BIT_ULL(MTK_CLK_SGMII2_CDR_REF) | \
-+                               BIT_ULL(MTK_CLK_SGMII2_CDR_FB))
- enum mtk_dev_state {
-       MTK_HW_INIT,
-@@ -1043,7 +1045,7 @@ struct mtk_soc_data {
-       const struct mtk_reg_map *reg_map;
-       u32             ana_rgc3;
-       u64             caps;
--      u32             required_clks;
-+      u64             required_clks;
-       bool            required_pctl;
-       u8              offload_version;
-       u8              hash_offset;
diff --git a/target/linux/generic/backport-5.15/750-v6.5-11-net-ethernet-mtk_eth_soc-add-basic-support-for-MT798.patch b/target/linux/generic/backport-5.15/750-v6.5-11-net-ethernet-mtk_eth_soc-add-basic-support-for-MT798.patch
deleted file mode 100644 (file)
index 58b9cec..0000000
+++ /dev/null
@@ -1,477 +0,0 @@
-From 94f825a7eadfc8b4c8828efdb7705d9703f9c73e Mon Sep 17 00:00:00 2001
-From: Lorenzo Bianconi <[email protected]>
-Date: Tue, 25 Jul 2023 01:57:42 +0100
-Subject: [PATCH 105/250] net: ethernet: mtk_eth_soc: add basic support for
- MT7988 SoC
-
-Introduce support for ethernet chip available in MT7988 SoC to
-mtk_eth_soc driver. As a first step support only the first GMAC which
-is hard-wired to the internal DSA switch having 4 built-in gigabit
-Ethernet PHYs.
-
-Signed-off-by: Lorenzo Bianconi <[email protected]>
-Signed-off-by: Daniel Golle <[email protected]>
-Link: https://lore.kernel.org/r/25c8377095b95d186872eeda7aa055da83e8f0ca.1690246605.git.daniel@makrotopia.org
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- drivers/net/ethernet/mediatek/mtk_eth_path.c |  14 +-
- drivers/net/ethernet/mediatek/mtk_eth_soc.c  | 201 +++++++++++++++++--
- drivers/net/ethernet/mediatek/mtk_eth_soc.h  |  86 +++++++-
- 3 files changed, 273 insertions(+), 28 deletions(-)
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_path.c
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_path.c
-@@ -43,7 +43,7 @@ static const char *mtk_eth_path_name(u64
- static int set_mux_gdm1_to_gmac1_esw(struct mtk_eth *eth, u64 path)
- {
-       bool updated = true;
--      u32 val, mask, set;
-+      u32 mask, set, reg;
-       switch (path) {
-       case MTK_ETH_PATH_GMAC1_SGMII:
-@@ -59,11 +59,13 @@ static int set_mux_gdm1_to_gmac1_esw(str
-               break;
-       }
--      if (updated) {
--              val = mtk_r32(eth, MTK_MAC_MISC);
--              val = (val & mask) | set;
--              mtk_w32(eth, val, MTK_MAC_MISC);
--      }
-+      if (mtk_is_netsys_v3_or_greater(eth))
-+              reg = MTK_MAC_MISC_V3;
-+      else
-+              reg = MTK_MAC_MISC;
-+
-+      if (updated)
-+              mtk_m32(eth, mask, set, reg);
-       dev_dbg(eth->dev, "path %s in %s updated = %d\n",
-               mtk_eth_path_name(path), __func__, updated);
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-@@ -152,6 +152,54 @@ static const struct mtk_reg_map mt7986_r
-       .pse_oq_sta             = 0x01a0,
- };
-+static const struct mtk_reg_map mt7988_reg_map = {
-+      .tx_irq_mask            = 0x461c,
-+      .tx_irq_status          = 0x4618,
-+      .pdma = {
-+              .rx_ptr         = 0x6900,
-+              .rx_cnt_cfg     = 0x6904,
-+              .pcrx_ptr       = 0x6908,
-+              .glo_cfg        = 0x6a04,
-+              .rst_idx        = 0x6a08,
-+              .delay_irq      = 0x6a0c,
-+              .irq_status     = 0x6a20,
-+              .irq_mask       = 0x6a28,
-+              .adma_rx_dbg0   = 0x6a38,
-+              .int_grp        = 0x6a50,
-+      },
-+      .qdma = {
-+              .qtx_cfg        = 0x4400,
-+              .qtx_sch        = 0x4404,
-+              .rx_ptr         = 0x4500,
-+              .rx_cnt_cfg     = 0x4504,
-+              .qcrx_ptr       = 0x4508,
-+              .glo_cfg        = 0x4604,
-+              .rst_idx        = 0x4608,
-+              .delay_irq      = 0x460c,
-+              .fc_th          = 0x4610,
-+              .int_grp        = 0x4620,
-+              .hred           = 0x4644,
-+              .ctx_ptr        = 0x4700,
-+              .dtx_ptr        = 0x4704,
-+              .crx_ptr        = 0x4710,
-+              .drx_ptr        = 0x4714,
-+              .fq_head        = 0x4720,
-+              .fq_tail        = 0x4724,
-+              .fq_count       = 0x4728,
-+              .fq_blen        = 0x472c,
-+              .tx_sch_rate    = 0x4798,
-+      },
-+      .gdm1_cnt               = 0x1c00,
-+      .gdma_to_ppe0           = 0x3333,
-+      .ppe_base               = 0x2000,
-+      .wdma_base = {
-+              [0]             = 0x4800,
-+              [1]             = 0x4c00,
-+      },
-+      .pse_iq_sta             = 0x0180,
-+      .pse_oq_sta             = 0x01a0,
-+};
-+
- /* strings used by ethtool */
- static const struct mtk_ethtool_stats {
-       char str[ETH_GSTRING_LEN];
-@@ -179,10 +227,54 @@ static const struct mtk_ethtool_stats {
- };
- static const char * const mtk_clks_source_name[] = {
--      "ethif", "sgmiitop", "esw", "gp0", "gp1", "gp2", "fe", "trgpll",
--      "sgmii_tx250m", "sgmii_rx250m", "sgmii_cdr_ref", "sgmii_cdr_fb",
--      "sgmii2_tx250m", "sgmii2_rx250m", "sgmii2_cdr_ref", "sgmii2_cdr_fb",
--      "sgmii_ck", "eth2pll", "wocpu0", "wocpu1", "netsys0", "netsys1"
-+      "ethif",
-+      "sgmiitop",
-+      "esw",
-+      "gp0",
-+      "gp1",
-+      "gp2",
-+      "gp3",
-+      "xgp1",
-+      "xgp2",
-+      "xgp3",
-+      "crypto",
-+      "fe",
-+      "trgpll",
-+      "sgmii_tx250m",
-+      "sgmii_rx250m",
-+      "sgmii_cdr_ref",
-+      "sgmii_cdr_fb",
-+      "sgmii2_tx250m",
-+      "sgmii2_rx250m",
-+      "sgmii2_cdr_ref",
-+      "sgmii2_cdr_fb",
-+      "sgmii_ck",
-+      "eth2pll",
-+      "wocpu0",
-+      "wocpu1",
-+      "netsys0",
-+      "netsys1",
-+      "ethwarp_wocpu2",
-+      "ethwarp_wocpu1",
-+      "ethwarp_wocpu0",
-+      "top_usxgmii0_sel",
-+      "top_usxgmii1_sel",
-+      "top_sgm0_sel",
-+      "top_sgm1_sel",
-+      "top_xfi_phy0_xtal_sel",
-+      "top_xfi_phy1_xtal_sel",
-+      "top_eth_gmii_sel",
-+      "top_eth_refck_50m_sel",
-+      "top_eth_sys_200m_sel",
-+      "top_eth_sys_sel",
-+      "top_eth_xgmii_sel",
-+      "top_eth_mii_sel",
-+      "top_netsys_sel",
-+      "top_netsys_500m_sel",
-+      "top_netsys_pao_2x_sel",
-+      "top_netsys_sync_250m_sel",
-+      "top_netsys_ppefb_250m_sel",
-+      "top_netsys_warp_sel",
- };
- void mtk_w32(struct mtk_eth *eth, u32 val, unsigned reg)
-@@ -195,7 +287,7 @@ u32 mtk_r32(struct mtk_eth *eth, unsigne
-       return __raw_readl(eth->base + reg);
- }
--static u32 mtk_m32(struct mtk_eth *eth, u32 mask, u32 set, unsigned reg)
-+u32 mtk_m32(struct mtk_eth *eth, u32 mask, u32 set, unsigned int reg)
- {
-       u32 val;
-@@ -326,6 +418,19 @@ static void mtk_gmac0_rgmii_adjust(struc
-       dev_err(eth->dev, "Missing PLL configuration, ethernet may not work\n");
- }
-+static void mtk_setup_bridge_switch(struct mtk_eth *eth)
-+{
-+      /* Force Port1 XGMAC Link Up */
-+      mtk_m32(eth, 0, MTK_XGMAC_FORCE_LINK(MTK_GMAC1_ID),
-+              MTK_XGMAC_STS(MTK_GMAC1_ID));
-+
-+      /* Adjust GSW bridge IPG to 11 */
-+      mtk_m32(eth, GSWTX_IPG_MASK | GSWRX_IPG_MASK,
-+              (GSW_IPG_11 << GSWTX_IPG_SHIFT) |
-+              (GSW_IPG_11 << GSWRX_IPG_SHIFT),
-+              MTK_GSW_CFG);
-+}
-+
- static struct phylink_pcs *mtk_mac_select_pcs(struct phylink_config *config,
-                                             phy_interface_t interface)
- {
-@@ -395,6 +500,8 @@ static void mtk_mac_config(struct phylin
-                                       goto init_err;
-                       }
-                       break;
-+              case PHY_INTERFACE_MODE_INTERNAL:
-+                      break;
-               default:
-                       goto err_phy;
-               }
-@@ -472,6 +579,15 @@ static void mtk_mac_config(struct phylin
-               return;
-       }
-+      /* Setup gmac */
-+      if (mtk_is_netsys_v3_or_greater(eth) &&
-+          mac->interface == PHY_INTERFACE_MODE_INTERNAL) {
-+              mtk_w32(mac->hw, MTK_GDMA_XGDM_SEL, MTK_GDMA_EG_CTRL(mac->id));
-+              mtk_w32(mac->hw, MAC_MCR_FORCE_LINK_DOWN, MTK_MAC_MCR(mac->id));
-+
-+              mtk_setup_bridge_switch(eth);
-+      }
-+
-       return;
- err_phy:
-@@ -681,11 +797,15 @@ static int mtk_mdio_init(struct mtk_eth
-       }
-       divider = min_t(unsigned int, DIV_ROUND_UP(MDC_MAX_FREQ, max_clk), 63);
-+      /* Configure MDC Turbo Mode */
-+      if (mtk_is_netsys_v3_or_greater(eth))
-+              mtk_m32(eth, 0, MISC_MDC_TURBO, MTK_MAC_MISC_V3);
-+
-       /* Configure MDC Divider */
--      val = mtk_r32(eth, MTK_PPSC);
--      val &= ~PPSC_MDC_CFG;
--      val |= FIELD_PREP(PPSC_MDC_CFG, divider) | PPSC_MDC_TURBO;
--      mtk_w32(eth, val, MTK_PPSC);
-+      val = FIELD_PREP(PPSC_MDC_CFG, divider);
-+      if (!mtk_is_netsys_v3_or_greater(eth))
-+              val |= PPSC_MDC_TURBO;
-+      mtk_m32(eth, PPSC_MDC_CFG, val, MTK_PPSC);
-       dev_dbg(eth->dev, "MDC is running on %d Hz\n", MDC_MAX_FREQ / divider);
-@@ -1144,10 +1264,19 @@ static void mtk_tx_set_dma_desc_v2(struc
-               data |= TX_DMA_LS0;
-       WRITE_ONCE(desc->txd3, data);
--      if (mac->id == MTK_GMAC3_ID)
--              data = PSE_GDM3_PORT;
--      else
--              data = (mac->id + 1) << TX_DMA_FPORT_SHIFT_V2; /* forward port */
-+       /* set forward port */
-+      switch (mac->id) {
-+      case MTK_GMAC1_ID:
-+              data = PSE_GDM1_PORT << TX_DMA_FPORT_SHIFT_V2;
-+              break;
-+      case MTK_GMAC2_ID:
-+              data = PSE_GDM2_PORT << TX_DMA_FPORT_SHIFT_V2;
-+              break;
-+      case MTK_GMAC3_ID:
-+              data = PSE_GDM3_PORT << TX_DMA_FPORT_SHIFT_V2;
-+              break;
-+      }
-+
-       data |= TX_DMA_SWC_V2 | QID_BITS_V2(info->qid);
-       WRITE_ONCE(desc->txd4, data);
-@@ -4306,6 +4435,17 @@ static int mtk_add_mac(struct mtk_eth *e
-                         mac->phylink_config.supported_interfaces);
-       }
-+      if (mtk_is_netsys_v3_or_greater(mac->hw) &&
-+          MTK_HAS_CAPS(mac->hw->soc->caps, MTK_ESW_BIT) &&
-+          id == MTK_GMAC1_ID) {
-+              mac->phylink_config.mac_capabilities = MAC_ASYM_PAUSE |
-+                                                     MAC_SYM_PAUSE |
-+                                                     MAC_10000FD;
-+              phy_interface_zero(mac->phylink_config.supported_interfaces);
-+              __set_bit(PHY_INTERFACE_MODE_INTERNAL,
-+                        mac->phylink_config.supported_interfaces);
-+      }
-+
-       phylink = phylink_create(&mac->phylink_config,
-                                of_fwnode_handle(mac->of_node),
-                                phy_mode, &mtk_phylink_ops);
-@@ -4828,6 +4968,24 @@ static const struct mtk_soc_data mt7986_
-       },
- };
-+static const struct mtk_soc_data mt7988_data = {
-+      .reg_map = &mt7988_reg_map,
-+      .ana_rgc3 = 0x128,
-+      .caps = MT7988_CAPS,
-+      .hw_features = MTK_HW_FEATURES,
-+      .required_clks = MT7988_CLKS_BITMAP,
-+      .required_pctl = false,
-+      .version = 3,
-+      .txrx = {
-+              .txd_size = sizeof(struct mtk_tx_dma_v2),
-+              .rxd_size = sizeof(struct mtk_rx_dma_v2),
-+              .rx_irq_done_mask = MTK_RX_DONE_INT_V2,
-+              .rx_dma_l4_valid = RX_DMA_L4_VALID_V2,
-+              .dma_max_len = MTK_TX_DMA_BUF_LEN_V2,
-+              .dma_len_offset = 8,
-+      },
-+};
-+
- static const struct mtk_soc_data rt5350_data = {
-       .reg_map = &mt7628_reg_map,
-       .caps = MT7628_CAPS,
-@@ -4846,14 +5004,15 @@ static const struct mtk_soc_data rt5350_
- };
- const struct of_device_id of_mtk_match[] = {
--      { .compatible = "mediatek,mt2701-eth", .data = &mt2701_data},
--      { .compatible = "mediatek,mt7621-eth", .data = &mt7621_data},
--      { .compatible = "mediatek,mt7622-eth", .data = &mt7622_data},
--      { .compatible = "mediatek,mt7623-eth", .data = &mt7623_data},
--      { .compatible = "mediatek,mt7629-eth", .data = &mt7629_data},
--      { .compatible = "mediatek,mt7981-eth", .data = &mt7981_data},
--      { .compatible = "mediatek,mt7986-eth", .data = &mt7986_data},
--      { .compatible = "ralink,rt5350-eth", .data = &rt5350_data},
-+      { .compatible = "mediatek,mt2701-eth", .data = &mt2701_data },
-+      { .compatible = "mediatek,mt7621-eth", .data = &mt7621_data },
-+      { .compatible = "mediatek,mt7622-eth", .data = &mt7622_data },
-+      { .compatible = "mediatek,mt7623-eth", .data = &mt7623_data },
-+      { .compatible = "mediatek,mt7629-eth", .data = &mt7629_data },
-+      { .compatible = "mediatek,mt7981-eth", .data = &mt7981_data },
-+      { .compatible = "mediatek,mt7986-eth", .data = &mt7986_data },
-+      { .compatible = "mediatek,mt7988-eth", .data = &mt7988_data },
-+      { .compatible = "ralink,rt5350-eth", .data = &rt5350_data },
-       {},
- };
- MODULE_DEVICE_TABLE(of, of_mtk_match);
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-@@ -117,7 +117,8 @@
- #define MTK_CDMP_EG_CTRL      0x404
- /* GDM Exgress Control Register */
--#define MTK_GDMA_FWD_CFG(x)   (0x500 + (x * 0x1000))
-+#define MTK_GDMA_FWD_CFG(x)   ({ typeof(x) _x = (x); (_x == MTK_GMAC3_ID) ?   \
-+                                 0x540 : 0x500 + (_x * 0x1000); })
- #define MTK_GDMA_SPECIAL_TAG  BIT(24)
- #define MTK_GDMA_ICS_EN               BIT(22)
- #define MTK_GDMA_TCS_EN               BIT(21)
-@@ -126,6 +127,11 @@
- #define MTK_GDMA_TO_PDMA      0x0
- #define MTK_GDMA_DROP_ALL       0x7777
-+/* GDM Egress Control Register */
-+#define MTK_GDMA_EG_CTRL(x)   ({ typeof(x) _x = (x); (_x == MTK_GMAC3_ID) ?   \
-+                                 0x544 : 0x504 + (_x * 0x1000); })
-+#define MTK_GDMA_XGDM_SEL     BIT(31)
-+
- /* Unicast Filter MAC Address Register - Low */
- #define MTK_GDMA_MAC_ADRL(x)  (0x508 + (x * 0x1000))
-@@ -386,7 +392,26 @@
- #define PHY_IAC_TIMEOUT               HZ
- #define MTK_MAC_MISC          0x1000c
-+#define MTK_MAC_MISC_V3               0x10010
- #define MTK_MUX_TO_ESW                BIT(0)
-+#define MISC_MDC_TURBO                BIT(4)
-+
-+/* XMAC status registers */
-+#define MTK_XGMAC_STS(x)      (((x) == MTK_GMAC3_ID) ? 0x1001C : 0x1000C)
-+#define MTK_XGMAC_FORCE_LINK(x)       (((x) == MTK_GMAC2_ID) ? BIT(31) : BIT(15))
-+#define MTK_USXGMII_PCS_LINK  BIT(8)
-+#define MTK_XGMAC_RX_FC               BIT(5)
-+#define MTK_XGMAC_TX_FC               BIT(4)
-+#define MTK_USXGMII_PCS_MODE  GENMASK(3, 1)
-+#define MTK_XGMAC_LINK_STS    BIT(0)
-+
-+/* GSW bridge registers */
-+#define MTK_GSW_CFG           (0x10080)
-+#define GSWTX_IPG_MASK                GENMASK(19, 16)
-+#define GSWTX_IPG_SHIFT               16
-+#define GSWRX_IPG_MASK                GENMASK(3, 0)
-+#define GSWRX_IPG_SHIFT               0
-+#define GSW_IPG_11            11
- /* Mac control registers */
- #define MTK_MAC_MCR(x)                (0x10100 + (x * 0x100))
-@@ -644,6 +669,11 @@ enum mtk_clks_map {
-       MTK_CLK_GP0,
-       MTK_CLK_GP1,
-       MTK_CLK_GP2,
-+      MTK_CLK_GP3,
-+      MTK_CLK_XGP1,
-+      MTK_CLK_XGP2,
-+      MTK_CLK_XGP3,
-+      MTK_CLK_CRYPTO,
-       MTK_CLK_FE,
-       MTK_CLK_TRGPLL,
-       MTK_CLK_SGMII_TX_250M,
-@@ -660,6 +690,27 @@ enum mtk_clks_map {
-       MTK_CLK_WOCPU1,
-       MTK_CLK_NETSYS0,
-       MTK_CLK_NETSYS1,
-+      MTK_CLK_ETHWARP_WOCPU2,
-+      MTK_CLK_ETHWARP_WOCPU1,
-+      MTK_CLK_ETHWARP_WOCPU0,
-+      MTK_CLK_TOP_USXGMII_SBUS_0_SEL,
-+      MTK_CLK_TOP_USXGMII_SBUS_1_SEL,
-+      MTK_CLK_TOP_SGM_0_SEL,
-+      MTK_CLK_TOP_SGM_1_SEL,
-+      MTK_CLK_TOP_XFI_PHY_0_XTAL_SEL,
-+      MTK_CLK_TOP_XFI_PHY_1_XTAL_SEL,
-+      MTK_CLK_TOP_ETH_GMII_SEL,
-+      MTK_CLK_TOP_ETH_REFCK_50M_SEL,
-+      MTK_CLK_TOP_ETH_SYS_200M_SEL,
-+      MTK_CLK_TOP_ETH_SYS_SEL,
-+      MTK_CLK_TOP_ETH_XGMII_SEL,
-+      MTK_CLK_TOP_ETH_MII_SEL,
-+      MTK_CLK_TOP_NETSYS_SEL,
-+      MTK_CLK_TOP_NETSYS_500M_SEL,
-+      MTK_CLK_TOP_NETSYS_PAO_2X_SEL,
-+      MTK_CLK_TOP_NETSYS_SYNC_250M_SEL,
-+      MTK_CLK_TOP_NETSYS_PPEFB_250M_SEL,
-+      MTK_CLK_TOP_NETSYS_WARP_SEL,
-       MTK_CLK_MAX
- };
-@@ -713,6 +764,36 @@ enum mtk_clks_map {
-                                BIT_ULL(MTK_CLK_SGMII2_RX_250M) | \
-                                BIT_ULL(MTK_CLK_SGMII2_CDR_REF) | \
-                                BIT_ULL(MTK_CLK_SGMII2_CDR_FB))
-+#define MT7988_CLKS_BITMAP    (BIT_ULL(MTK_CLK_FE) | BIT_ULL(MTK_CLK_ESW) | \
-+                               BIT_ULL(MTK_CLK_GP1) | BIT_ULL(MTK_CLK_GP2) | \
-+                               BIT_ULL(MTK_CLK_GP3) | BIT_ULL(MTK_CLK_XGP1) | \
-+                               BIT_ULL(MTK_CLK_XGP2) | BIT_ULL(MTK_CLK_XGP3) | \
-+                               BIT_ULL(MTK_CLK_CRYPTO) | \
-+                               BIT_ULL(MTK_CLK_SGMII_TX_250M) | \
-+                               BIT_ULL(MTK_CLK_SGMII_RX_250M) | \
-+                               BIT_ULL(MTK_CLK_SGMII2_TX_250M) | \
-+                               BIT_ULL(MTK_CLK_SGMII2_RX_250M) | \
-+                               BIT_ULL(MTK_CLK_ETHWARP_WOCPU2) | \
-+                               BIT_ULL(MTK_CLK_ETHWARP_WOCPU1) | \
-+                               BIT_ULL(MTK_CLK_ETHWARP_WOCPU0) | \
-+                               BIT_ULL(MTK_CLK_TOP_USXGMII_SBUS_0_SEL) | \
-+                               BIT_ULL(MTK_CLK_TOP_USXGMII_SBUS_1_SEL) | \
-+                               BIT_ULL(MTK_CLK_TOP_SGM_0_SEL) | \
-+                               BIT_ULL(MTK_CLK_TOP_SGM_1_SEL) | \
-+                               BIT_ULL(MTK_CLK_TOP_XFI_PHY_0_XTAL_SEL) | \
-+                               BIT_ULL(MTK_CLK_TOP_XFI_PHY_1_XTAL_SEL) | \
-+                               BIT_ULL(MTK_CLK_TOP_ETH_GMII_SEL) | \
-+                               BIT_ULL(MTK_CLK_TOP_ETH_REFCK_50M_SEL) | \
-+                               BIT_ULL(MTK_CLK_TOP_ETH_SYS_200M_SEL) | \
-+                               BIT_ULL(MTK_CLK_TOP_ETH_SYS_SEL) | \
-+                               BIT_ULL(MTK_CLK_TOP_ETH_XGMII_SEL) | \
-+                               BIT_ULL(MTK_CLK_TOP_ETH_MII_SEL) | \
-+                               BIT_ULL(MTK_CLK_TOP_NETSYS_SEL) | \
-+                               BIT_ULL(MTK_CLK_TOP_NETSYS_500M_SEL) | \
-+                               BIT_ULL(MTK_CLK_TOP_NETSYS_PAO_2X_SEL) | \
-+                               BIT_ULL(MTK_CLK_TOP_NETSYS_SYNC_250M_SEL) | \
-+                               BIT_ULL(MTK_CLK_TOP_NETSYS_PPEFB_250M_SEL) | \
-+                               BIT_ULL(MTK_CLK_TOP_NETSYS_WARP_SEL))
- enum mtk_dev_state {
-       MTK_HW_INIT,
-@@ -961,6 +1042,8 @@ enum mkt_eth_capabilities {
-                     MTK_MUX_GMAC12_TO_GEPHY_SGMII | MTK_QDMA | \
-                     MTK_RSTCTRL_PPE1)
-+#define MT7988_CAPS  (MTK_GDM1_ESW | MTK_QDMA | MTK_RSTCTRL_PPE1)
-+
- struct mtk_tx_dma_desc_info {
-       dma_addr_t      addr;
-       u32             size;
-@@ -1306,6 +1389,7 @@ void mtk_stats_update_mac(struct mtk_mac
- void mtk_w32(struct mtk_eth *eth, u32 val, unsigned reg);
- u32 mtk_r32(struct mtk_eth *eth, unsigned reg);
-+u32 mtk_m32(struct mtk_eth *eth, u32 mask, u32 set, unsigned int reg);
- int mtk_gmac_sgmii_path_setup(struct mtk_eth *eth, int mac_id);
- int mtk_gmac_gephy_path_setup(struct mtk_eth *eth, int mac_id);
diff --git a/target/linux/generic/backport-5.15/750-v6.5-12-net-ethernet-mtk_eth_soc-enable-page_pool-support-fo.patch b/target/linux/generic/backport-5.15/750-v6.5-12-net-ethernet-mtk_eth_soc-enable-page_pool-support-fo.patch
deleted file mode 100644 (file)
index 95bf60d..0000000
+++ /dev/null
@@ -1,27 +0,0 @@
-From 38a7eb76220731eff40602cf433f24880be0a6c2 Mon Sep 17 00:00:00 2001
-From: Lorenzo Bianconi <[email protected]>
-Date: Thu, 27 Jul 2023 09:02:26 +0200
-Subject: [PATCH 106/250] net: ethernet: mtk_eth_soc: enable page_pool support
- for MT7988 SoC
-
-In order to recycle pages, enable page_pool allocator for MT7988 SoC.
-
-Tested-by: Daniel Golle <[email protected]>
-Signed-off-by: Lorenzo Bianconi <[email protected]>
-Link: https://lore.kernel.org/r/fd4e8693980e47385a543e7b002eec0b88bd09df.1690440675.git.lorenzo@kernel.org
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- drivers/net/ethernet/mediatek/mtk_eth_soc.c | 2 +-
- 1 file changed, 1 insertion(+), 1 deletion(-)
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-@@ -1612,7 +1612,7 @@ static void mtk_update_rx_cpu_idx(struct
- static bool mtk_page_pool_enabled(struct mtk_eth *eth)
- {
--      return eth->soc->version == 2;
-+      return mtk_is_netsys_v2_or_greater(eth);
- }
- static struct page_pool *mtk_create_page_pool(struct mtk_eth *eth,
diff --git a/target/linux/generic/backport-5.15/750-v6.5-13-net-ethernet-mtk_eth_soc-enable-nft-hw-flowtable_off.patch b/target/linux/generic/backport-5.15/750-v6.5-13-net-ethernet-mtk_eth_soc-enable-nft-hw-flowtable_off.patch
deleted file mode 100644 (file)
index 5205914..0000000
+++ /dev/null
@@ -1,135 +0,0 @@
-From 199e7d5a7f03dd377f3a7a458360dbedd71d50ba Mon Sep 17 00:00:00 2001
-From: Lorenzo Bianconi <[email protected]>
-Date: Thu, 27 Jul 2023 09:07:28 +0200
-Subject: [PATCH 107/250] net: ethernet: mtk_eth_soc: enable nft hw
- flowtable_offload for MT7988 SoC
-
-Enable hw Packet Process Engine (PPE) for MT7988 SoC.
-
-Tested-by: Daniel Golle <[email protected]>
-Signed-off-by: Lorenzo Bianconi <[email protected]>
-Link: https://lore.kernel.org/r/5e86341b0220a49620dadc02d77970de5ded9efc.1690441576.git.lorenzo@kernel.org
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- drivers/net/ethernet/mediatek/mtk_eth_soc.c |  3 +++
- drivers/net/ethernet/mediatek/mtk_ppe.c     | 19 +++++++++++++++----
- drivers/net/ethernet/mediatek/mtk_ppe.h     | 19 ++++++++++++++++++-
- 3 files changed, 36 insertions(+), 5 deletions(-)
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-@@ -4976,6 +4976,9 @@ static const struct mtk_soc_data mt7988_
-       .required_clks = MT7988_CLKS_BITMAP,
-       .required_pctl = false,
-       .version = 3,
-+      .offload_version = 2,
-+      .hash_offset = 4,
-+      .foe_entry_size = MTK_FOE_ENTRY_V3_SIZE,
-       .txrx = {
-               .txd_size = sizeof(struct mtk_tx_dma_v2),
-               .rxd_size = sizeof(struct mtk_rx_dma_v2),
---- a/drivers/net/ethernet/mediatek/mtk_ppe.c
-+++ b/drivers/net/ethernet/mediatek/mtk_ppe.c
-@@ -422,13 +422,22 @@ int mtk_foe_entry_set_wdma(struct mtk_et
-       struct mtk_foe_mac_info *l2 = mtk_foe_entry_l2(eth, entry);
-       u32 *ib2 = mtk_foe_entry_ib2(eth, entry);
--      if (mtk_is_netsys_v2_or_greater(eth)) {
-+      switch (eth->soc->version) {
-+      case 3:
-+              *ib2 &= ~MTK_FOE_IB2_PORT_MG_V2;
-+              *ib2 |=  FIELD_PREP(MTK_FOE_IB2_RX_IDX, txq) |
-+                       MTK_FOE_IB2_WDMA_WINFO_V2;
-+              l2->w3info = FIELD_PREP(MTK_FOE_WINFO_WCID_V3, wcid) |
-+                           FIELD_PREP(MTK_FOE_WINFO_BSS_V3, bss);
-+              break;
-+      case 2:
-               *ib2 &= ~MTK_FOE_IB2_PORT_MG_V2;
-               *ib2 |=  FIELD_PREP(MTK_FOE_IB2_RX_IDX, txq) |
-                        MTK_FOE_IB2_WDMA_WINFO_V2;
-               l2->winfo = FIELD_PREP(MTK_FOE_WINFO_WCID, wcid) |
-                           FIELD_PREP(MTK_FOE_WINFO_BSS, bss);
--      } else {
-+              break;
-+      default:
-               *ib2 &= ~MTK_FOE_IB2_PORT_MG;
-               *ib2 |= MTK_FOE_IB2_WDMA_WINFO;
-               if (wdma_idx)
-@@ -436,6 +445,7 @@ int mtk_foe_entry_set_wdma(struct mtk_et
-               l2->vlan2 = FIELD_PREP(MTK_FOE_VLAN2_WINFO_BSS, bss) |
-                           FIELD_PREP(MTK_FOE_VLAN2_WINFO_WCID, wcid) |
-                           FIELD_PREP(MTK_FOE_VLAN2_WINFO_RING, txq);
-+              break;
-       }
-       return 0;
-@@ -956,8 +966,7 @@ void mtk_ppe_start(struct mtk_ppe *ppe)
-       mtk_ppe_init_foe_table(ppe);
-       ppe_w32(ppe, MTK_PPE_TB_BASE, ppe->foe_phys);
--      val = MTK_PPE_TB_CFG_ENTRY_80B |
--            MTK_PPE_TB_CFG_AGE_NON_L4 |
-+      val = MTK_PPE_TB_CFG_AGE_NON_L4 |
-             MTK_PPE_TB_CFG_AGE_UNBIND |
-             MTK_PPE_TB_CFG_AGE_TCP |
-             MTK_PPE_TB_CFG_AGE_UDP |
-@@ -973,6 +982,8 @@ void mtk_ppe_start(struct mtk_ppe *ppe)
-                        MTK_PPE_ENTRIES_SHIFT);
-       if (mtk_is_netsys_v2_or_greater(ppe->eth))
-               val |= MTK_PPE_TB_CFG_INFO_SEL;
-+      if (!mtk_is_netsys_v3_or_greater(ppe->eth))
-+              val |= MTK_PPE_TB_CFG_ENTRY_80B;
-       ppe_w32(ppe, MTK_PPE_TB_CFG, val);
-       ppe_w32(ppe, MTK_PPE_IP_PROTO_CHK,
---- a/drivers/net/ethernet/mediatek/mtk_ppe.h
-+++ b/drivers/net/ethernet/mediatek/mtk_ppe.h
-@@ -85,6 +85,17 @@ enum {
- #define MTK_FOE_WINFO_BSS             GENMASK(5, 0)
- #define MTK_FOE_WINFO_WCID            GENMASK(15, 6)
-+#define MTK_FOE_WINFO_BSS_V3          GENMASK(23, 16)
-+#define MTK_FOE_WINFO_WCID_V3         GENMASK(15, 0)
-+
-+#define MTK_FOE_WINFO_PAO_USR_INFO    GENMASK(15, 0)
-+#define MTK_FOE_WINFO_PAO_TID         GENMASK(19, 16)
-+#define MTK_FOE_WINFO_PAO_IS_FIXEDRATE        BIT(20)
-+#define MTK_FOE_WINFO_PAO_IS_PRIOR    BIT(21)
-+#define MTK_FOE_WINFO_PAO_IS_SP               BIT(22)
-+#define MTK_FOE_WINFO_PAO_HF          BIT(23)
-+#define MTK_FOE_WINFO_PAO_AMSDU_EN    BIT(24)
-+
- enum {
-       MTK_FOE_STATE_INVALID,
-       MTK_FOE_STATE_UNBIND,
-@@ -106,8 +117,13 @@ struct mtk_foe_mac_info {
-       u16 pppoe_id;
-       u16 src_mac_lo;
-+      /* netsys_v2 */
-       u16 minfo;
-       u16 winfo;
-+
-+      /* netsys_v3 */
-+      u32 w3info;
-+      u32 wpao;
- };
- /* software-only entry type */
-@@ -218,6 +234,7 @@ struct mtk_foe_ipv6_6rd {
- #define MTK_FOE_ENTRY_V1_SIZE 80
- #define MTK_FOE_ENTRY_V2_SIZE 96
-+#define MTK_FOE_ENTRY_V3_SIZE 128
- struct mtk_foe_entry {
-       u32 ib1;
-@@ -228,7 +245,7 @@ struct mtk_foe_entry {
-               struct mtk_foe_ipv4_dslite dslite;
-               struct mtk_foe_ipv6 ipv6;
-               struct mtk_foe_ipv6_6rd ipv6_6rd;
--              u32 data[23];
-+              u32 data[31];
-       };
- };
diff --git a/target/linux/generic/backport-5.15/750-v6.5-14-net-ethernet-mtk_eth_soc-support-per-flow-accounting.patch b/target/linux/generic/backport-5.15/750-v6.5-14-net-ethernet-mtk_eth_soc-support-per-flow-accounting.patch
deleted file mode 100644 (file)
index 8a48976..0000000
+++ /dev/null
@@ -1,78 +0,0 @@
-From 0c024632c1e7ff69914329bfd87bec749b9c0aed Mon Sep 17 00:00:00 2001
-From: Daniel Golle <[email protected]>
-Date: Wed, 2 Aug 2023 04:31:09 +0100
-Subject: [PATCH 108/250] net: ethernet: mtk_eth_soc: support per-flow
- accounting on MT7988
-
-NETSYS_V3 uses 64 bits for each counters while older SoCs are using
-48/40 bits for each counter.
-Support reading per-flow byte and package counters on NETSYS_V3.
-
-Signed-off-by: Daniel Golle <[email protected]>
-Reviewed-by: Simon Horman <[email protected]>
-Link: https://lore.kernel.org/r/37a0928fa8c1253b197884c68ce1f54239421ac5.1690946442.git.daniel@makrotopia.org
-Signed-off-by: Paolo Abeni <[email protected]>
----
- drivers/net/ethernet/mediatek/mtk_eth_soc.c  |  1 +
- drivers/net/ethernet/mediatek/mtk_ppe.c      | 21 +++++++++++++-------
- drivers/net/ethernet/mediatek/mtk_ppe_regs.h |  2 ++
- 3 files changed, 17 insertions(+), 7 deletions(-)
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-@@ -4978,6 +4978,7 @@ static const struct mtk_soc_data mt7988_
-       .version = 3,
-       .offload_version = 2,
-       .hash_offset = 4,
-+      .has_accounting = true,
-       .foe_entry_size = MTK_FOE_ENTRY_V3_SIZE,
-       .txrx = {
-               .txd_size = sizeof(struct mtk_tx_dma_v2),
---- a/drivers/net/ethernet/mediatek/mtk_ppe.c
-+++ b/drivers/net/ethernet/mediatek/mtk_ppe.c
-@@ -91,7 +91,6 @@ static int mtk_ppe_mib_wait_busy(struct
- static int mtk_mib_entry_read(struct mtk_ppe *ppe, u16 index, u64 *bytes, u64 *packets)
- {
--      u32 byte_cnt_low, byte_cnt_high, pkt_cnt_low, pkt_cnt_high;
-       u32 val, cnt_r0, cnt_r1, cnt_r2;
-       int ret;
-@@ -106,12 +105,20 @@ static int mtk_mib_entry_read(struct mtk
-       cnt_r1 = readl(ppe->base + MTK_PPE_MIB_SER_R1);
-       cnt_r2 = readl(ppe->base + MTK_PPE_MIB_SER_R2);
--      byte_cnt_low = FIELD_GET(MTK_PPE_MIB_SER_R0_BYTE_CNT_LOW, cnt_r0);
--      byte_cnt_high = FIELD_GET(MTK_PPE_MIB_SER_R1_BYTE_CNT_HIGH, cnt_r1);
--      pkt_cnt_low = FIELD_GET(MTK_PPE_MIB_SER_R1_PKT_CNT_LOW, cnt_r1);
--      pkt_cnt_high = FIELD_GET(MTK_PPE_MIB_SER_R2_PKT_CNT_HIGH, cnt_r2);
--      *bytes = ((u64)byte_cnt_high << 32) | byte_cnt_low;
--      *packets = (pkt_cnt_high << 16) | pkt_cnt_low;
-+      if (mtk_is_netsys_v3_or_greater(ppe->eth)) {
-+              /* 64 bit for each counter */
-+              u32 cnt_r3 = readl(ppe->base + MTK_PPE_MIB_SER_R3);
-+              *bytes = ((u64)cnt_r1 << 32) | cnt_r0;
-+              *packets = ((u64)cnt_r3 << 32) | cnt_r2;
-+      } else {
-+              /* 48 bit byte counter, 40 bit packet counter */
-+              u32 byte_cnt_low = FIELD_GET(MTK_PPE_MIB_SER_R0_BYTE_CNT_LOW, cnt_r0);
-+              u32 byte_cnt_high = FIELD_GET(MTK_PPE_MIB_SER_R1_BYTE_CNT_HIGH, cnt_r1);
-+              u32 pkt_cnt_low = FIELD_GET(MTK_PPE_MIB_SER_R1_PKT_CNT_LOW, cnt_r1);
-+              u32 pkt_cnt_high = FIELD_GET(MTK_PPE_MIB_SER_R2_PKT_CNT_HIGH, cnt_r2);
-+              *bytes = ((u64)byte_cnt_high << 32) | byte_cnt_low;
-+              *packets = (pkt_cnt_high << 16) | pkt_cnt_low;
-+      }
-       return 0;
- }
---- a/drivers/net/ethernet/mediatek/mtk_ppe_regs.h
-+++ b/drivers/net/ethernet/mediatek/mtk_ppe_regs.h
-@@ -163,6 +163,8 @@ enum {
- #define MTK_PPE_MIB_SER_R2                    0x348
- #define MTK_PPE_MIB_SER_R2_PKT_CNT_HIGH               GENMASK(23, 0)
-+#define MTK_PPE_MIB_SER_R3                    0x34c
-+
- #define MTK_PPE_MIB_CACHE_CTL                 0x350
- #define MTK_PPE_MIB_CACHE_CTL_EN              BIT(0)
- #define MTK_PPE_MIB_CACHE_CTL_FLUSH           BIT(2)
diff --git a/target/linux/generic/backport-5.15/750-v6.5-15-net-ethernet-mtk_eth_soc-fix-NULL-pointer-on-hw-rese.patch b/target/linux/generic/backport-5.15/750-v6.5-15-net-ethernet-mtk_eth_soc-fix-NULL-pointer-on-hw-rese.patch
deleted file mode 100644 (file)
index 6f1639a..0000000
+++ /dev/null
@@ -1,52 +0,0 @@
-From 3b12f42772c26869d60398c1710aa27b27cd945c Mon Sep 17 00:00:00 2001
-From: Daniel Golle <[email protected]>
-Date: Mon, 21 Aug 2023 17:12:44 +0100
-Subject: [PATCH 109/250] net: ethernet: mtk_eth_soc: fix NULL pointer on hw
- reset
-
-When a hardware reset is triggered on devices not initializing WED the
-calls to mtk_wed_fe_reset and mtk_wed_fe_reset_complete dereference a
-pointer on uninitialized stack memory.
-Break out of both functions in case a hw_list entry is 0.
-
-Fixes: 08a764a7c51b ("net: ethernet: mtk_wed: add reset/reset_complete callbacks")
-Signed-off-by: Daniel Golle <[email protected]>
-Reviewed-by: Simon Horman <[email protected]>
-Acked-by: Lorenzo Bianconi <[email protected]>
-Link: https://lore.kernel.org/r/5465c1609b464cc7407ae1530c40821dcdf9d3e6.1692634266.git.daniel@makrotopia.org
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- drivers/net/ethernet/mediatek/mtk_wed.c | 12 ++++++++++--
- 1 file changed, 10 insertions(+), 2 deletions(-)
-
---- a/drivers/net/ethernet/mediatek/mtk_wed.c
-+++ b/drivers/net/ethernet/mediatek/mtk_wed.c
-@@ -214,9 +214,13 @@ void mtk_wed_fe_reset(void)
-       for (i = 0; i < ARRAY_SIZE(hw_list); i++) {
-               struct mtk_wed_hw *hw = hw_list[i];
--              struct mtk_wed_device *dev = hw->wed_dev;
-+              struct mtk_wed_device *dev;
-               int err;
-+              if (!hw)
-+                      break;
-+
-+              dev = hw->wed_dev;
-               if (!dev || !dev->wlan.reset)
-                       continue;
-@@ -237,8 +241,12 @@ void mtk_wed_fe_reset_complete(void)
-       for (i = 0; i < ARRAY_SIZE(hw_list); i++) {
-               struct mtk_wed_hw *hw = hw_list[i];
--              struct mtk_wed_device *dev = hw->wed_dev;
-+              struct mtk_wed_device *dev;
-+
-+              if (!hw)
-+                      break;
-+              dev = hw->wed_dev;
-               if (!dev || !dev->wlan.reset_complete)
-                       continue;
diff --git a/target/linux/generic/backport-5.15/750-v6.5-16-net-ethernet-mtk_eth_soc-fix-register-definitions-fo.patch b/target/linux/generic/backport-5.15/750-v6.5-16-net-ethernet-mtk_eth_soc-fix-register-definitions-fo.patch
deleted file mode 100644 (file)
index 3597794..0000000
+++ /dev/null
@@ -1,44 +0,0 @@
-From 489aea123d74a846ce746bfdb3efe1e7ad512e0d Mon Sep 17 00:00:00 2001
-From: Daniel Golle <[email protected]>
-Date: Tue, 22 Aug 2023 17:31:24 +0100
-Subject: [PATCH 110/250] net: ethernet: mtk_eth_soc: fix register definitions
- for MT7988
-
-More register macros need to be adjusted for the 3rd GMAC on MT7988.
-Account for added bit in SYSCFG0_SGMII_MASK.
-
-Fixes: 445eb6448ed3 ("net: ethernet: mtk_eth_soc: add basic support for MT7988 SoC")
-Signed-off-by: Daniel Golle <[email protected]>
-Reviewed-by: Simon Horman <[email protected]>
-Link: https://lore.kernel.org/r/1c8da012e2ca80939906d85f314138c552139f0f.1692721443.git.daniel@makrotopia.org
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- drivers/net/ethernet/mediatek/mtk_eth_soc.h | 8 +++++---
- 1 file changed, 5 insertions(+), 3 deletions(-)
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-@@ -133,10 +133,12 @@
- #define MTK_GDMA_XGDM_SEL     BIT(31)
- /* Unicast Filter MAC Address Register - Low */
--#define MTK_GDMA_MAC_ADRL(x)  (0x508 + (x * 0x1000))
-+#define MTK_GDMA_MAC_ADRL(x)  ({ typeof(x) _x = (x); (_x == MTK_GMAC3_ID) ?   \
-+                                 0x548 : 0x508 + (_x * 0x1000); })
- /* Unicast Filter MAC Address Register - High */
--#define MTK_GDMA_MAC_ADRH(x)  (0x50C + (x * 0x1000))
-+#define MTK_GDMA_MAC_ADRH(x)  ({ typeof(x) _x = (x); (_x == MTK_GMAC3_ID) ?   \
-+                                 0x54C : 0x50C + (_x * 0x1000); })
- /* FE global misc reg*/
- #define MTK_FE_GLO_MISC         0x124
-@@ -500,7 +502,7 @@
- #define ETHSYS_SYSCFG0                0x14
- #define SYSCFG0_GE_MASK               0x3
- #define SYSCFG0_GE_MODE(x, y) (x << (12 + (y * 2)))
--#define SYSCFG0_SGMII_MASK     GENMASK(9, 8)
-+#define SYSCFG0_SGMII_MASK     GENMASK(9, 7)
- #define SYSCFG0_SGMII_GMAC1    ((2 << 8) & SYSCFG0_SGMII_MASK)
- #define SYSCFG0_SGMII_GMAC2    ((3 << 8) & SYSCFG0_SGMII_MASK)
- #define SYSCFG0_SGMII_GMAC1_V2 BIT(9)
diff --git a/target/linux/generic/backport-5.15/750-v6.5-17-net-ethernet-mtk_eth_soc-add-reset-bits-for-MT7988.patch b/target/linux/generic/backport-5.15/750-v6.5-17-net-ethernet-mtk_eth_soc-add-reset-bits-for-MT7988.patch
deleted file mode 100644 (file)
index 963807a..0000000
+++ /dev/null
@@ -1,188 +0,0 @@
-From 15a84d1c44ae8c1451c265ee60500588a24e8cd6 Mon Sep 17 00:00:00 2001
-From: Daniel Golle <[email protected]>
-Date: Tue, 22 Aug 2023 17:32:03 +0100
-Subject: [PATCH 111/250] net: ethernet: mtk_eth_soc: add reset bits for MT7988
-
-Add bits needed to reset the frame engine on MT7988.
-
-Fixes: 445eb6448ed3 ("net: ethernet: mtk_eth_soc: add basic support for MT7988 SoC")
-Signed-off-by: Daniel Golle <[email protected]>
-Link: https://lore.kernel.org/r/89b6c38380e7a3800c1362aa7575600717bc7543.1692721443.git.daniel@makrotopia.org
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- drivers/net/ethernet/mediatek/mtk_eth_soc.c | 76 +++++++++++++++------
- drivers/net/ethernet/mediatek/mtk_eth_soc.h | 16 +++--
- 2 files changed, 68 insertions(+), 24 deletions(-)
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-@@ -3540,19 +3540,34 @@ static void mtk_hw_reset(struct mtk_eth
- {
-       u32 val;
--      if (mtk_is_netsys_v2_or_greater(eth)) {
-+      if (mtk_is_netsys_v2_or_greater(eth))
-               regmap_write(eth->ethsys, ETHSYS_FE_RST_CHK_IDLE_EN, 0);
-+
-+      if (mtk_is_netsys_v3_or_greater(eth)) {
-+              val = RSTCTRL_PPE0_V3;
-+
-+              if (MTK_HAS_CAPS(eth->soc->caps, MTK_RSTCTRL_PPE1))
-+                      val |= RSTCTRL_PPE1_V3;
-+
-+              if (MTK_HAS_CAPS(eth->soc->caps, MTK_RSTCTRL_PPE2))
-+                      val |= RSTCTRL_PPE2;
-+
-+              val |= RSTCTRL_WDMA0 | RSTCTRL_WDMA1 | RSTCTRL_WDMA2;
-+      } else if (mtk_is_netsys_v2_or_greater(eth)) {
-               val = RSTCTRL_PPE0_V2;
-+
-+              if (MTK_HAS_CAPS(eth->soc->caps, MTK_RSTCTRL_PPE1))
-+                      val |= RSTCTRL_PPE1;
-       } else {
-               val = RSTCTRL_PPE0;
-       }
--      if (MTK_HAS_CAPS(eth->soc->caps, MTK_RSTCTRL_PPE1))
--              val |= RSTCTRL_PPE1;
--
-       ethsys_reset(eth, RSTCTRL_ETH | RSTCTRL_FE | val);
--      if (mtk_is_netsys_v2_or_greater(eth))
-+      if (mtk_is_netsys_v3_or_greater(eth))
-+              regmap_write(eth->ethsys, ETHSYS_FE_RST_CHK_IDLE_EN,
-+                           0x6f8ff);
-+      else if (mtk_is_netsys_v2_or_greater(eth))
-               regmap_write(eth->ethsys, ETHSYS_FE_RST_CHK_IDLE_EN,
-                            0x3ffffff);
- }
-@@ -3578,13 +3593,21 @@ static void mtk_hw_warm_reset(struct mtk
-               return;
-       }
--      if (mtk_is_netsys_v2_or_greater(eth))
-+      if (mtk_is_netsys_v3_or_greater(eth)) {
-+              rst_mask = RSTCTRL_ETH | RSTCTRL_PPE0_V3;
-+              if (MTK_HAS_CAPS(eth->soc->caps, MTK_RSTCTRL_PPE1))
-+                      rst_mask |= RSTCTRL_PPE1_V3;
-+              if (MTK_HAS_CAPS(eth->soc->caps, MTK_RSTCTRL_PPE2))
-+                      rst_mask |= RSTCTRL_PPE2;
-+
-+              rst_mask |= RSTCTRL_WDMA0 | RSTCTRL_WDMA1 | RSTCTRL_WDMA2;
-+      } else if (mtk_is_netsys_v2_or_greater(eth)) {
-               rst_mask = RSTCTRL_ETH | RSTCTRL_PPE0_V2;
--      else
-+              if (MTK_HAS_CAPS(eth->soc->caps, MTK_RSTCTRL_PPE1))
-+                      rst_mask |= RSTCTRL_PPE1;
-+      } else {
-               rst_mask = RSTCTRL_ETH | RSTCTRL_PPE0;
--
--      if (MTK_HAS_CAPS(eth->soc->caps, MTK_RSTCTRL_PPE1))
--              rst_mask |= RSTCTRL_PPE1;
-+      }
-       regmap_update_bits(eth->ethsys, ETHSYS_RSTCTRL, rst_mask, rst_mask);
-@@ -3936,11 +3959,17 @@ static void mtk_prepare_for_reset(struct
-       u32 val;
-       int i;
--      /* disabe FE P3 and P4 */
--      val = mtk_r32(eth, MTK_FE_GLO_CFG) | MTK_FE_LINK_DOWN_P3;
--      if (MTK_HAS_CAPS(eth->soc->caps, MTK_RSTCTRL_PPE1))
--              val |= MTK_FE_LINK_DOWN_P4;
--      mtk_w32(eth, val, MTK_FE_GLO_CFG);
-+      /* set FE PPE ports link down */
-+      for (i = MTK_GMAC1_ID;
-+           i <= (mtk_is_netsys_v3_or_greater(eth) ? MTK_GMAC3_ID : MTK_GMAC2_ID);
-+           i += 2) {
-+              val = mtk_r32(eth, MTK_FE_GLO_CFG(i)) | MTK_FE_LINK_DOWN_P(PSE_PPE0_PORT);
-+              if (MTK_HAS_CAPS(eth->soc->caps, MTK_RSTCTRL_PPE1))
-+                      val |= MTK_FE_LINK_DOWN_P(PSE_PPE1_PORT);
-+              if (MTK_HAS_CAPS(eth->soc->caps, MTK_RSTCTRL_PPE2))
-+                      val |= MTK_FE_LINK_DOWN_P(PSE_PPE2_PORT);
-+              mtk_w32(eth, val, MTK_FE_GLO_CFG(i));
-+      }
-       /* adjust PPE configurations to prepare for reset */
-       for (i = 0; i < ARRAY_SIZE(eth->ppe); i++)
-@@ -4001,11 +4030,18 @@ static void mtk_pending_work(struct work
-               }
-       }
--      /* enabe FE P3 and P4 */
--      val = mtk_r32(eth, MTK_FE_GLO_CFG) & ~MTK_FE_LINK_DOWN_P3;
--      if (MTK_HAS_CAPS(eth->soc->caps, MTK_RSTCTRL_PPE1))
--              val &= ~MTK_FE_LINK_DOWN_P4;
--      mtk_w32(eth, val, MTK_FE_GLO_CFG);
-+      /* set FE PPE ports link up */
-+      for (i = MTK_GMAC1_ID;
-+           i <= (mtk_is_netsys_v3_or_greater(eth) ? MTK_GMAC3_ID : MTK_GMAC2_ID);
-+           i += 2) {
-+              val = mtk_r32(eth, MTK_FE_GLO_CFG(i)) & ~MTK_FE_LINK_DOWN_P(PSE_PPE0_PORT);
-+              if (MTK_HAS_CAPS(eth->soc->caps, MTK_RSTCTRL_PPE1))
-+                      val &= ~MTK_FE_LINK_DOWN_P(PSE_PPE1_PORT);
-+              if (MTK_HAS_CAPS(eth->soc->caps, MTK_RSTCTRL_PPE2))
-+                      val &= ~MTK_FE_LINK_DOWN_P(PSE_PPE2_PORT);
-+
-+              mtk_w32(eth, val, MTK_FE_GLO_CFG(i));
-+      }
-       clear_bit(MTK_RESETTING, &eth->state);
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-@@ -76,9 +76,8 @@
- #define       MTK_HW_LRO_SDL_REMAIN_ROOM      1522
- /* Frame Engine Global Configuration */
--#define MTK_FE_GLO_CFG                0x00
--#define MTK_FE_LINK_DOWN_P3   BIT(11)
--#define MTK_FE_LINK_DOWN_P4   BIT(12)
-+#define MTK_FE_GLO_CFG(x)     (((x) == MTK_GMAC3_ID) ? 0x24 : 0x00)
-+#define MTK_FE_LINK_DOWN_P(x) BIT(((x) + 8) % 16)
- /* Frame Engine Global Reset Register */
- #define MTK_RST_GL            0x04
-@@ -519,9 +518,15 @@
- /* ethernet reset control register */
- #define ETHSYS_RSTCTRL                        0x34
- #define RSTCTRL_FE                    BIT(6)
-+#define RSTCTRL_WDMA0                 BIT(24)
-+#define RSTCTRL_WDMA1                 BIT(25)
-+#define RSTCTRL_WDMA2                 BIT(26)
- #define RSTCTRL_PPE0                  BIT(31)
- #define RSTCTRL_PPE0_V2                       BIT(30)
- #define RSTCTRL_PPE1                  BIT(31)
-+#define RSTCTRL_PPE0_V3                       BIT(29)
-+#define RSTCTRL_PPE1_V3                       BIT(30)
-+#define RSTCTRL_PPE2                  BIT(31)
- #define RSTCTRL_ETH                   BIT(23)
- /* ethernet reset check idle register */
-@@ -928,6 +933,7 @@ enum mkt_eth_capabilities {
-       MTK_QDMA_BIT,
-       MTK_SOC_MT7628_BIT,
-       MTK_RSTCTRL_PPE1_BIT,
-+      MTK_RSTCTRL_PPE2_BIT,
-       MTK_U3_COPHY_V2_BIT,
-       /* MUX BITS*/
-@@ -962,6 +968,7 @@ enum mkt_eth_capabilities {
- #define MTK_QDMA              BIT_ULL(MTK_QDMA_BIT)
- #define MTK_SOC_MT7628                BIT_ULL(MTK_SOC_MT7628_BIT)
- #define MTK_RSTCTRL_PPE1      BIT_ULL(MTK_RSTCTRL_PPE1_BIT)
-+#define MTK_RSTCTRL_PPE2      BIT_ULL(MTK_RSTCTRL_PPE2_BIT)
- #define MTK_U3_COPHY_V2               BIT_ULL(MTK_U3_COPHY_V2_BIT)
- #define MTK_ETH_MUX_GDM1_TO_GMAC1_ESW         \
-@@ -1044,7 +1051,8 @@ enum mkt_eth_capabilities {
-                     MTK_MUX_GMAC12_TO_GEPHY_SGMII | MTK_QDMA | \
-                     MTK_RSTCTRL_PPE1)
--#define MT7988_CAPS  (MTK_GDM1_ESW | MTK_QDMA | MTK_RSTCTRL_PPE1)
-+#define MT7988_CAPS  (MTK_GDM1_ESW | MTK_QDMA | MTK_RSTCTRL_PPE1 | \
-+                    MTK_RSTCTRL_PPE2)
- struct mtk_tx_dma_desc_info {
-       dma_addr_t      addr;
diff --git a/target/linux/generic/backport-5.15/750-v6.5-18-net-ethernet-mtk_eth_soc-add-support-for-in-SoC-SRAM.patch b/target/linux/generic/backport-5.15/750-v6.5-18-net-ethernet-mtk_eth_soc-add-support-for-in-SoC-SRAM.patch
deleted file mode 100644 (file)
index e224443..0000000
+++ /dev/null
@@ -1,254 +0,0 @@
-From 25ce45fe40b574e5d7ffa407f7f2db03e7d5a910 Mon Sep 17 00:00:00 2001
-From: Daniel Golle <[email protected]>
-Date: Tue, 22 Aug 2023 17:32:54 +0100
-Subject: [PATCH 112/250] net: ethernet: mtk_eth_soc: add support for in-SoC
- SRAM
-
-MT7981, MT7986 and MT7988 come with in-SoC SRAM dedicated for Ethernet
-DMA rings. Support using the SRAM without breaking existing device tree
-bindings, ie. only new SoC starting from MT7988 will have the SRAM
-declared as additional resource in device tree. For MT7981 and MT7986
-an offset on top of the main I/O base is used.
-
-Signed-off-by: Daniel Golle <[email protected]>
-Link: https://lore.kernel.org/r/e45e0f230c63ad58869e8fe35b95a2fb8925b625.1692721443.git.daniel@makrotopia.org
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- drivers/net/ethernet/mediatek/mtk_eth_soc.c | 88 ++++++++++++++++-----
- drivers/net/ethernet/mediatek/mtk_eth_soc.h | 12 ++-
- 2 files changed, 78 insertions(+), 22 deletions(-)
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-@@ -1074,10 +1074,13 @@ static int mtk_init_fq_dma(struct mtk_et
-       dma_addr_t dma_addr;
-       int i;
--      eth->scratch_ring = dma_alloc_coherent(eth->dma_dev,
--                                             cnt * soc->txrx.txd_size,
--                                             &eth->phy_scratch_ring,
--                                             GFP_KERNEL);
-+      if (MTK_HAS_CAPS(eth->soc->caps, MTK_SRAM))
-+              eth->scratch_ring = eth->sram_base;
-+      else
-+              eth->scratch_ring = dma_alloc_coherent(eth->dma_dev,
-+                                                     cnt * soc->txrx.txd_size,
-+                                                     &eth->phy_scratch_ring,
-+                                                     GFP_KERNEL);
-       if (unlikely(!eth->scratch_ring))
-               return -ENOMEM;
-@@ -2375,8 +2378,14 @@ static int mtk_tx_alloc(struct mtk_eth *
-       if (!ring->buf)
-               goto no_tx_mem;
--      ring->dma = dma_alloc_coherent(eth->dma_dev, ring_size * sz,
--                                     &ring->phys, GFP_KERNEL);
-+      if (MTK_HAS_CAPS(soc->caps, MTK_SRAM)) {
-+              ring->dma = eth->sram_base + ring_size * sz;
-+              ring->phys = eth->phy_scratch_ring + ring_size * (dma_addr_t)sz;
-+      } else {
-+              ring->dma = dma_alloc_coherent(eth->dma_dev, ring_size * sz,
-+                                             &ring->phys, GFP_KERNEL);
-+      }
-+
-       if (!ring->dma)
-               goto no_tx_mem;
-@@ -2475,8 +2484,7 @@ static void mtk_tx_clean(struct mtk_eth
-               kfree(ring->buf);
-               ring->buf = NULL;
-       }
--
--      if (ring->dma) {
-+      if (!MTK_HAS_CAPS(soc->caps, MTK_SRAM) && ring->dma) {
-               dma_free_coherent(eth->dma_dev,
-                                 ring->dma_size * soc->txrx.txd_size,
-                                 ring->dma, ring->phys);
-@@ -2495,9 +2503,14 @@ static int mtk_rx_alloc(struct mtk_eth *
- {
-       const struct mtk_reg_map *reg_map = eth->soc->reg_map;
-       struct mtk_rx_ring *ring;
--      int rx_data_len, rx_dma_size;
-+      int rx_data_len, rx_dma_size, tx_ring_size;
-       int i;
-+      if (MTK_HAS_CAPS(eth->soc->caps, MTK_QDMA))
-+              tx_ring_size = MTK_QDMA_RING_SIZE;
-+      else
-+              tx_ring_size = MTK_DMA_SIZE;
-+
-       if (rx_flag == MTK_RX_FLAGS_QDMA) {
-               if (ring_no)
-                       return -EINVAL;
-@@ -2532,9 +2545,20 @@ static int mtk_rx_alloc(struct mtk_eth *
-               ring->page_pool = pp;
-       }
--      ring->dma = dma_alloc_coherent(eth->dma_dev,
--                                     rx_dma_size * eth->soc->txrx.rxd_size,
--                                     &ring->phys, GFP_KERNEL);
-+      if (!MTK_HAS_CAPS(eth->soc->caps, MTK_SRAM) ||
-+          rx_flag != MTK_RX_FLAGS_NORMAL) {
-+              ring->dma = dma_alloc_coherent(eth->dma_dev,
-+                                             rx_dma_size * eth->soc->txrx.rxd_size,
-+                                             &ring->phys, GFP_KERNEL);
-+      } else {
-+              struct mtk_tx_ring *tx_ring = &eth->tx_ring;
-+
-+              ring->dma = tx_ring->dma + tx_ring_size *
-+                          eth->soc->txrx.txd_size * (ring_no + 1);
-+              ring->phys = tx_ring->phys + tx_ring_size *
-+                           eth->soc->txrx.txd_size * (ring_no + 1);
-+      }
-+
-       if (!ring->dma)
-               return -ENOMEM;
-@@ -2617,7 +2641,7 @@ static int mtk_rx_alloc(struct mtk_eth *
-       return 0;
- }
--static void mtk_rx_clean(struct mtk_eth *eth, struct mtk_rx_ring *ring)
-+static void mtk_rx_clean(struct mtk_eth *eth, struct mtk_rx_ring *ring, bool in_sram)
- {
-       int i;
-@@ -2640,7 +2664,7 @@ static void mtk_rx_clean(struct mtk_eth
-               ring->data = NULL;
-       }
--      if (ring->dma) {
-+      if (!in_sram && ring->dma) {
-               dma_free_coherent(eth->dma_dev,
-                                 ring->dma_size * eth->soc->txrx.rxd_size,
-                                 ring->dma, ring->phys);
-@@ -3003,7 +3027,7 @@ static void mtk_dma_free(struct mtk_eth
-       for (i = 0; i < MTK_MAX_DEVS; i++)
-               if (eth->netdev[i])
-                       netdev_reset_queue(eth->netdev[i]);
--      if (eth->scratch_ring) {
-+      if (!MTK_HAS_CAPS(soc->caps, MTK_SRAM) && eth->scratch_ring) {
-               dma_free_coherent(eth->dma_dev,
-                                 MTK_QDMA_RING_SIZE * soc->txrx.txd_size,
-                                 eth->scratch_ring, eth->phy_scratch_ring);
-@@ -3011,13 +3035,13 @@ static void mtk_dma_free(struct mtk_eth
-               eth->phy_scratch_ring = 0;
-       }
-       mtk_tx_clean(eth);
--      mtk_rx_clean(eth, &eth->rx_ring[0]);
--      mtk_rx_clean(eth, &eth->rx_ring_qdma);
-+      mtk_rx_clean(eth, &eth->rx_ring[0], MTK_HAS_CAPS(soc->caps, MTK_SRAM));
-+      mtk_rx_clean(eth, &eth->rx_ring_qdma, false);
-       if (eth->hwlro) {
-               mtk_hwlro_rx_uninit(eth);
-               for (i = 1; i < MTK_MAX_RX_RING_NUM; i++)
--                      mtk_rx_clean(eth, &eth->rx_ring[i]);
-+                      mtk_rx_clean(eth, &eth->rx_ring[i], false);
-       }
-       kfree(eth->scratch_head);
-@@ -4587,7 +4611,7 @@ static int mtk_sgmii_init(struct mtk_eth
- static int mtk_probe(struct platform_device *pdev)
- {
--      struct resource *res = NULL;
-+      struct resource *res = NULL, *res_sram;
-       struct device_node *mac_np;
-       struct mtk_eth *eth;
-       int err, i;
-@@ -4607,6 +4631,20 @@ static int mtk_probe(struct platform_dev
-       if (MTK_HAS_CAPS(eth->soc->caps, MTK_SOC_MT7628))
-               eth->ip_align = NET_IP_ALIGN;
-+      if (MTK_HAS_CAPS(eth->soc->caps, MTK_SRAM)) {
-+              /* SRAM is actual memory and supports transparent access just like DRAM.
-+               * Hence we don't require __iomem being set and don't need to use accessor
-+               * functions to read from or write to SRAM.
-+               */
-+              if (mtk_is_netsys_v3_or_greater(eth)) {
-+                      eth->sram_base = (void __force *)devm_platform_ioremap_resource(pdev, 1);
-+                      if (IS_ERR(eth->sram_base))
-+                              return PTR_ERR(eth->sram_base);
-+              } else {
-+                      eth->sram_base = (void __force *)eth->base + MTK_ETH_SRAM_OFFSET;
-+              }
-+      }
-+
-       spin_lock_init(&eth->page_lock);
-       spin_lock_init(&eth->tx_irq_lock);
-       spin_lock_init(&eth->rx_irq_lock);
-@@ -4670,6 +4708,18 @@ static int mtk_probe(struct platform_dev
-                       err = -EINVAL;
-                       goto err_destroy_sgmii;
-               }
-+              if (MTK_HAS_CAPS(eth->soc->caps, MTK_SRAM)) {
-+                      if (mtk_is_netsys_v3_or_greater(eth)) {
-+                              res_sram = platform_get_resource(pdev, IORESOURCE_MEM, 1);
-+                              if (!res_sram) {
-+                                      err = -EINVAL;
-+                                      goto err_destroy_sgmii;
-+                              }
-+                              eth->phy_scratch_ring = res_sram->start;
-+                      } else {
-+                              eth->phy_scratch_ring = res->start + MTK_ETH_SRAM_OFFSET;
-+                      }
-+              }
-       }
-       if (eth->soc->offload_version) {
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-@@ -139,6 +139,9 @@
- #define MTK_GDMA_MAC_ADRH(x)  ({ typeof(x) _x = (x); (_x == MTK_GMAC3_ID) ?   \
-                                  0x54C : 0x50C + (_x * 0x1000); })
-+/* Internal SRAM offset */
-+#define MTK_ETH_SRAM_OFFSET   0x40000
-+
- /* FE global misc reg*/
- #define MTK_FE_GLO_MISC         0x124
-@@ -935,6 +938,7 @@ enum mkt_eth_capabilities {
-       MTK_RSTCTRL_PPE1_BIT,
-       MTK_RSTCTRL_PPE2_BIT,
-       MTK_U3_COPHY_V2_BIT,
-+      MTK_SRAM_BIT,
-       /* MUX BITS*/
-       MTK_ETH_MUX_GDM1_TO_GMAC1_ESW_BIT,
-@@ -970,6 +974,7 @@ enum mkt_eth_capabilities {
- #define MTK_RSTCTRL_PPE1      BIT_ULL(MTK_RSTCTRL_PPE1_BIT)
- #define MTK_RSTCTRL_PPE2      BIT_ULL(MTK_RSTCTRL_PPE2_BIT)
- #define MTK_U3_COPHY_V2               BIT_ULL(MTK_U3_COPHY_V2_BIT)
-+#define MTK_SRAM              BIT_ULL(MTK_SRAM_BIT)
- #define MTK_ETH_MUX_GDM1_TO_GMAC1_ESW         \
-       BIT_ULL(MTK_ETH_MUX_GDM1_TO_GMAC1_ESW_BIT)
-@@ -1045,14 +1050,14 @@ enum mkt_eth_capabilities {
- #define MT7981_CAPS  (MTK_GMAC1_SGMII | MTK_GMAC2_SGMII | MTK_GMAC2_GEPHY | \
-                     MTK_MUX_GMAC12_TO_GEPHY_SGMII | MTK_QDMA | \
-                     MTK_MUX_U3_GMAC2_TO_QPHY | MTK_U3_COPHY_V2 | \
--                    MTK_RSTCTRL_PPE1)
-+                    MTK_RSTCTRL_PPE1 | MTK_SRAM)
- #define MT7986_CAPS  (MTK_GMAC1_SGMII | MTK_GMAC2_SGMII | \
-                     MTK_MUX_GMAC12_TO_GEPHY_SGMII | MTK_QDMA | \
--                    MTK_RSTCTRL_PPE1)
-+                    MTK_RSTCTRL_PPE1 | MTK_SRAM)
- #define MT7988_CAPS  (MTK_GDM1_ESW | MTK_QDMA | MTK_RSTCTRL_PPE1 | \
--                    MTK_RSTCTRL_PPE2)
-+                    MTK_RSTCTRL_PPE2 | MTK_SRAM)
- struct mtk_tx_dma_desc_info {
-       dma_addr_t      addr;
-@@ -1212,6 +1217,7 @@ struct mtk_eth {
-       struct device                   *dev;
-       struct device                   *dma_dev;
-       void __iomem                    *base;
-+      void                            *sram_base;
-       spinlock_t                      page_lock;
-       spinlock_t                      tx_irq_lock;
-       spinlock_t                      rx_irq_lock;
diff --git a/target/linux/generic/backport-5.15/750-v6.5-19-net-ethernet-mtk_eth_soc-support-36-bit-DMA-addressi.patch b/target/linux/generic/backport-5.15/750-v6.5-19-net-ethernet-mtk_eth_soc-support-36-bit-DMA-addressi.patch
deleted file mode 100644 (file)
index 528f9a3..0000000
+++ /dev/null
@@ -1,166 +0,0 @@
-From 0b0d606eb9650fa01dd5621e072aa29a10544399 Mon Sep 17 00:00:00 2001
-From: Daniel Golle <[email protected]>
-Date: Tue, 22 Aug 2023 17:33:12 +0100
-Subject: [PATCH 113/250] net: ethernet: mtk_eth_soc: support 36-bit DMA
- addressing on MT7988
-
-Systems having 4 GiB of RAM and more require DMA addressing beyond the
-current 32-bit limit. Starting from MT7988 the hardware now supports
-36-bit DMA addressing, let's use that new capability in the driver to
-avoid running into swiotlb on systems with 4 GiB of RAM or more.
-
-Signed-off-by: Daniel Golle <[email protected]>
-Link: https://lore.kernel.org/r/95b919c98876c9e49761e44662e7c937479eecb8.1692721443.git.daniel@makrotopia.org
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- drivers/net/ethernet/mediatek/mtk_eth_soc.c | 30 +++++++++++++++++++--
- drivers/net/ethernet/mediatek/mtk_eth_soc.h | 22 +++++++++++++--
- 2 files changed, 48 insertions(+), 4 deletions(-)
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-@@ -1265,6 +1265,10 @@ static void mtk_tx_set_dma_desc_v2(struc
-       data = TX_DMA_PLEN0(info->size);
-       if (info->last)
-               data |= TX_DMA_LS0;
-+
-+      if (MTK_HAS_CAPS(eth->soc->caps, MTK_36BIT_DMA))
-+              data |= TX_DMA_PREP_ADDR64(info->addr);
-+
-       WRITE_ONCE(desc->txd3, data);
-        /* set forward port */
-@@ -1932,6 +1936,7 @@ static int mtk_poll_rx(struct napi_struc
-       bool xdp_flush = false;
-       int idx;
-       struct sk_buff *skb;
-+      u64 addr64 = 0;
-       u8 *data, *new_data;
-       struct mtk_rx_dma_v2 *rxd, trxd;
-       int done = 0, bytes = 0;
-@@ -2047,7 +2052,10 @@ static int mtk_poll_rx(struct napi_struc
-                               goto release_desc;
-                       }
--                      dma_unmap_single(eth->dma_dev, trxd.rxd1,
-+                      if (MTK_HAS_CAPS(eth->soc->caps, MTK_36BIT_DMA))
-+                              addr64 = RX_DMA_GET_ADDR64(trxd.rxd2);
-+
-+                      dma_unmap_single(eth->dma_dev, ((u64)trxd.rxd1 | addr64),
-                                        ring->buf_size, DMA_FROM_DEVICE);
-                       skb = build_skb(data, ring->frag_size);
-@@ -2113,6 +2121,9 @@ release_desc:
-               else
-                       rxd->rxd2 = RX_DMA_PREP_PLEN0(ring->buf_size);
-+              if (MTK_HAS_CAPS(eth->soc->caps, MTK_36BIT_DMA))
-+                      rxd->rxd2 |= RX_DMA_PREP_ADDR64(dma_addr);
-+
-               ring->calc_idx = idx;
-               done++;
-       }
-@@ -2597,6 +2608,9 @@ static int mtk_rx_alloc(struct mtk_eth *
-               else
-                       rxd->rxd2 = RX_DMA_PREP_PLEN0(ring->buf_size);
-+              if (MTK_HAS_CAPS(eth->soc->caps, MTK_36BIT_DMA))
-+                      rxd->rxd2 |= RX_DMA_PREP_ADDR64(dma_addr);
-+
-               rxd->rxd3 = 0;
-               rxd->rxd4 = 0;
-               if (mtk_is_netsys_v2_or_greater(eth)) {
-@@ -2643,6 +2657,7 @@ static int mtk_rx_alloc(struct mtk_eth *
- static void mtk_rx_clean(struct mtk_eth *eth, struct mtk_rx_ring *ring, bool in_sram)
- {
-+      u64 addr64 = 0;
-       int i;
-       if (ring->data && ring->dma) {
-@@ -2656,7 +2671,10 @@ static void mtk_rx_clean(struct mtk_eth
-                       if (!rxd->rxd1)
-                               continue;
--                      dma_unmap_single(eth->dma_dev, rxd->rxd1,
-+                      if (MTK_HAS_CAPS(eth->soc->caps, MTK_36BIT_DMA))
-+                              addr64 = RX_DMA_GET_ADDR64(rxd->rxd2);
-+
-+                      dma_unmap_single(eth->dma_dev, ((u64)rxd->rxd1 | addr64),
-                                        ring->buf_size, DMA_FROM_DEVICE);
-                       mtk_rx_put_buff(ring, ring->data[i], false);
-               }
-@@ -4645,6 +4663,14 @@ static int mtk_probe(struct platform_dev
-               }
-       }
-+      if (MTK_HAS_CAPS(eth->soc->caps, MTK_36BIT_DMA)) {
-+              err = dma_set_mask_and_coherent(&pdev->dev, DMA_BIT_MASK(36));
-+              if (err) {
-+                      dev_err(&pdev->dev, "Wrong DMA config\n");
-+                      return -EINVAL;
-+              }
-+      }
-+
-       spin_lock_init(&eth->page_lock);
-       spin_lock_init(&eth->tx_irq_lock);
-       spin_lock_init(&eth->rx_irq_lock);
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-@@ -331,6 +331,14 @@
- #define TX_DMA_PLEN1(x)               ((x) & eth->soc->txrx.dma_max_len)
- #define TX_DMA_SWC            BIT(14)
- #define TX_DMA_PQID           GENMASK(3, 0)
-+#define TX_DMA_ADDR64_MASK    GENMASK(3, 0)
-+#if IS_ENABLED(CONFIG_64BIT)
-+# define TX_DMA_GET_ADDR64(x) (((u64)FIELD_GET(TX_DMA_ADDR64_MASK, (x))) << 32)
-+# define TX_DMA_PREP_ADDR64(x)        FIELD_PREP(TX_DMA_ADDR64_MASK, ((x) >> 32))
-+#else
-+# define TX_DMA_GET_ADDR64(x) (0)
-+# define TX_DMA_PREP_ADDR64(x)        (0)
-+#endif
- /* PDMA on MT7628 */
- #define TX_DMA_DONE           BIT(31)
-@@ -343,6 +351,14 @@
- #define RX_DMA_PREP_PLEN0(x)  (((x) & eth->soc->txrx.dma_max_len) << eth->soc->txrx.dma_len_offset)
- #define RX_DMA_GET_PLEN0(x)   (((x) >> eth->soc->txrx.dma_len_offset) & eth->soc->txrx.dma_max_len)
- #define RX_DMA_VTAG           BIT(15)
-+#define RX_DMA_ADDR64_MASK    GENMASK(3, 0)
-+#if IS_ENABLED(CONFIG_64BIT)
-+# define RX_DMA_GET_ADDR64(x) (((u64)FIELD_GET(RX_DMA_ADDR64_MASK, (x))) << 32)
-+# define RX_DMA_PREP_ADDR64(x)        FIELD_PREP(RX_DMA_ADDR64_MASK, ((x) >> 32))
-+#else
-+# define RX_DMA_GET_ADDR64(x) (0)
-+# define RX_DMA_PREP_ADDR64(x)        (0)
-+#endif
- /* QDMA descriptor rxd3 */
- #define RX_DMA_VID(x)         ((x) & VLAN_VID_MASK)
-@@ -939,6 +955,7 @@ enum mkt_eth_capabilities {
-       MTK_RSTCTRL_PPE2_BIT,
-       MTK_U3_COPHY_V2_BIT,
-       MTK_SRAM_BIT,
-+      MTK_36BIT_DMA_BIT,
-       /* MUX BITS*/
-       MTK_ETH_MUX_GDM1_TO_GMAC1_ESW_BIT,
-@@ -975,6 +992,7 @@ enum mkt_eth_capabilities {
- #define MTK_RSTCTRL_PPE2      BIT_ULL(MTK_RSTCTRL_PPE2_BIT)
- #define MTK_U3_COPHY_V2               BIT_ULL(MTK_U3_COPHY_V2_BIT)
- #define MTK_SRAM              BIT_ULL(MTK_SRAM_BIT)
-+#define MTK_36BIT_DMA BIT_ULL(MTK_36BIT_DMA_BIT)
- #define MTK_ETH_MUX_GDM1_TO_GMAC1_ESW         \
-       BIT_ULL(MTK_ETH_MUX_GDM1_TO_GMAC1_ESW_BIT)
-@@ -1056,8 +1074,8 @@ enum mkt_eth_capabilities {
-                     MTK_MUX_GMAC12_TO_GEPHY_SGMII | MTK_QDMA | \
-                     MTK_RSTCTRL_PPE1 | MTK_SRAM)
--#define MT7988_CAPS  (MTK_GDM1_ESW | MTK_QDMA | MTK_RSTCTRL_PPE1 | \
--                    MTK_RSTCTRL_PPE2 | MTK_SRAM)
-+#define MT7988_CAPS  (MTK_36BIT_DMA | MTK_GDM1_ESW | MTK_QDMA | \
-+                    MTK_RSTCTRL_PPE1 | MTK_RSTCTRL_PPE2 | MTK_SRAM)
- struct mtk_tx_dma_desc_info {
-       dma_addr_t      addr;
diff --git a/target/linux/generic/backport-5.15/750-v6.5-20-net-ethernet-mtk_eth_soc-fix-uninitialized-variable.patch b/target/linux/generic/backport-5.15/750-v6.5-20-net-ethernet-mtk_eth_soc-fix-uninitialized-variable.patch
deleted file mode 100644 (file)
index 959add1..0000000
+++ /dev/null
@@ -1,44 +0,0 @@
-From e10a35abb3da12b812cfb6fc6137926a0c81e39a Mon Sep 17 00:00:00 2001
-From: Daniel Golle <[email protected]>
-Date: Sun, 10 Sep 2023 22:40:30 +0100
-Subject: [PATCH] net: ethernet: mtk_eth_soc: fix uninitialized variable
-
-Variable dma_addr in function mtk_poll_rx can be uninitialized on
-some of the error paths. In practise this doesn't matter, even random
-data present in uninitialized stack memory can safely be used in the
-way it happens in the error path.
-
-However, in order to make Smatch happy make sure the variable is
-always initialized.
-
-Signed-off-by: Daniel Golle <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/ethernet/mediatek/mtk_eth_soc.c | 5 +++--
- 1 file changed, 3 insertions(+), 2 deletions(-)
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-@@ -1940,11 +1940,11 @@ static int mtk_poll_rx(struct napi_struc
-       u8 *data, *new_data;
-       struct mtk_rx_dma_v2 *rxd, trxd;
-       int done = 0, bytes = 0;
-+      dma_addr_t dma_addr = DMA_MAPPING_ERROR;
-       while (done < budget) {
-               unsigned int pktlen, *rxdcsum;
-               struct net_device *netdev;
--              dma_addr_t dma_addr;
-               u32 hash, reason;
-               int mac = 0;
-@@ -2121,7 +2121,8 @@ release_desc:
-               else
-                       rxd->rxd2 = RX_DMA_PREP_PLEN0(ring->buf_size);
--              if (MTK_HAS_CAPS(eth->soc->caps, MTK_36BIT_DMA))
-+              if (MTK_HAS_CAPS(eth->soc->caps, MTK_36BIT_DMA) &&
-+                  likely(dma_addr != DMA_MAPPING_ERROR))
-                       rxd->rxd2 |= RX_DMA_PREP_ADDR64(dma_addr);
-               ring->calc_idx = idx;
diff --git a/target/linux/generic/backport-5.15/750-v6.5-21-net-ethernet-mtk_eth_soc-fix-pse_port-configuration-.patch b/target/linux/generic/backport-5.15/750-v6.5-21-net-ethernet-mtk_eth_soc-fix-pse_port-configuration-.patch
deleted file mode 100644 (file)
index ac3e3a3..0000000
+++ /dev/null
@@ -1,33 +0,0 @@
-From 5a124b1fd3e6cb15a943f0cdfe96aa8f6d3d2f39 Mon Sep 17 00:00:00 2001
-From: Lorenzo Bianconi <[email protected]>
-Date: Sat, 9 Sep 2023 20:41:56 +0200
-Subject: [PATCH] net: ethernet: mtk_eth_soc: fix pse_port configuration for
- MT7988
-
-MT7988 SoC support 3 NICs. Fix pse_port configuration in
-mtk_flow_set_output_device routine if the traffic is offloaded to eth2.
-Rely on mtk_pse_port definitions.
-
-Fixes: 88efedf517e6 ("net: ethernet: mtk_eth_soc: enable nft hw flowtable_offload for MT7988 SoC")
-Signed-off-by: Lorenzo Bianconi <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/ethernet/mediatek/mtk_ppe_offload.c | 6 ++++--
- 1 file changed, 4 insertions(+), 2 deletions(-)
-
---- a/drivers/net/ethernet/mediatek/mtk_ppe_offload.c
-+++ b/drivers/net/ethernet/mediatek/mtk_ppe_offload.c
-@@ -214,9 +214,11 @@ mtk_flow_set_output_device(struct mtk_et
-       dsa_port = mtk_flow_get_dsa_port(&dev);
-       if (dev == eth->netdev[0])
--              pse_port = 1;
-+              pse_port = PSE_GDM1_PORT;
-       else if (dev == eth->netdev[1])
--              pse_port = 2;
-+              pse_port = PSE_GDM2_PORT;
-+      else if (dev == eth->netdev[2])
-+              pse_port = PSE_GDM3_PORT;
-       else
-               return -EOPNOTSUPP;
diff --git a/target/linux/generic/backport-5.15/751-01-v6.4-net-ethernet-mtk_eth_soc-add-code-for-offloading-flo.patch b/target/linux/generic/backport-5.15/751-01-v6.4-net-ethernet-mtk_eth_soc-add-code-for-offloading-flo.patch
deleted file mode 100644 (file)
index 21d0f04..0000000
+++ /dev/null
@@ -1,271 +0,0 @@
-From: Felix Fietkau <[email protected]>
-Date: Mon, 20 Mar 2023 11:44:30 +0100
-Subject: [PATCH] net: ethernet: mtk_eth_soc: add code for offloading flows
- from wlan devices
-
-WED version 2 (on MT7986 and later) can offload flows originating from wireless
-devices. In order to make that work, ndo_setup_tc needs to be implemented on
-the netdevs. This adds the required code to offload flows coming in from WED,
-while keeping track of the incoming wed index used for selecting the correct
-PPE device.
-
-Signed-off-by: Felix Fietkau <[email protected]>
----
- drivers/net/ethernet/mediatek/mtk_eth_soc.h   |   3 +
- .../net/ethernet/mediatek/mtk_ppe_offload.c   |  37 ++++---
- drivers/net/ethernet/mediatek/mtk_wed.c       | 101 ++++++++++++++++++
- include/linux/soc/mediatek/mtk_wed.h          |   6 ++
- 4 files changed, 133 insertions(+), 14 deletions(-)
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-@@ -1432,6 +1432,9 @@ int mtk_gmac_rgmii_path_setup(struct mtk
- int mtk_eth_offload_init(struct mtk_eth *eth);
- int mtk_eth_setup_tc(struct net_device *dev, enum tc_setup_type type,
-                    void *type_data);
-+int mtk_flow_offload_cmd(struct mtk_eth *eth, struct flow_cls_offload *cls,
-+                       int ppe_index);
-+void mtk_flow_offload_cleanup(struct mtk_eth *eth, struct list_head *list);
- void mtk_eth_set_dma_device(struct mtk_eth *eth, struct device *dma_dev);
---- a/drivers/net/ethernet/mediatek/mtk_ppe_offload.c
-+++ b/drivers/net/ethernet/mediatek/mtk_ppe_offload.c
-@@ -237,7 +237,8 @@ out:
- }
- static int
--mtk_flow_offload_replace(struct mtk_eth *eth, struct flow_cls_offload *f)
-+mtk_flow_offload_replace(struct mtk_eth *eth, struct flow_cls_offload *f,
-+                       int ppe_index)
- {
-       struct flow_rule *rule = flow_cls_offload_flow_rule(f);
-       struct flow_action_entry *act;
-@@ -454,6 +455,7 @@ mtk_flow_offload_replace(struct mtk_eth
-       entry->cookie = f->cookie;
-       memcpy(&entry->data, &foe, sizeof(entry->data));
-       entry->wed_index = wed_index;
-+      entry->ppe_index = ppe_index;
-       err = mtk_foe_entry_commit(eth->ppe[entry->ppe_index], entry);
-       if (err < 0)
-@@ -522,25 +524,15 @@ mtk_flow_offload_stats(struct mtk_eth *e
- static DEFINE_MUTEX(mtk_flow_offload_mutex);
--static int
--mtk_eth_setup_tc_block_cb(enum tc_setup_type type, void *type_data, void *cb_priv)
-+int mtk_flow_offload_cmd(struct mtk_eth *eth, struct flow_cls_offload *cls,
-+                       int ppe_index)
- {
--      struct flow_cls_offload *cls = type_data;
--      struct net_device *dev = cb_priv;
--      struct mtk_mac *mac = netdev_priv(dev);
--      struct mtk_eth *eth = mac->hw;
-       int err;
--      if (!tc_can_offload(dev))
--              return -EOPNOTSUPP;
--
--      if (type != TC_SETUP_CLSFLOWER)
--              return -EOPNOTSUPP;
--
-       mutex_lock(&mtk_flow_offload_mutex);
-       switch (cls->command) {
-       case FLOW_CLS_REPLACE:
--              err = mtk_flow_offload_replace(eth, cls);
-+              err = mtk_flow_offload_replace(eth, cls, ppe_index);
-               break;
-       case FLOW_CLS_DESTROY:
-               err = mtk_flow_offload_destroy(eth, cls);
-@@ -558,6 +550,23 @@ mtk_eth_setup_tc_block_cb(enum tc_setup_
- }
- static int
-+mtk_eth_setup_tc_block_cb(enum tc_setup_type type, void *type_data, void *cb_priv)
-+{
-+      struct flow_cls_offload *cls = type_data;
-+      struct net_device *dev = cb_priv;
-+      struct mtk_mac *mac = netdev_priv(dev);
-+      struct mtk_eth *eth = mac->hw;
-+
-+      if (!tc_can_offload(dev))
-+              return -EOPNOTSUPP;
-+
-+      if (type != TC_SETUP_CLSFLOWER)
-+              return -EOPNOTSUPP;
-+
-+      return mtk_flow_offload_cmd(eth, cls, 0);
-+}
-+
-+static int
- mtk_eth_setup_tc_block(struct net_device *dev, struct flow_block_offload *f)
- {
-       struct mtk_mac *mac = netdev_priv(dev);
---- a/drivers/net/ethernet/mediatek/mtk_wed.c
-+++ b/drivers/net/ethernet/mediatek/mtk_wed.c
-@@ -13,6 +13,8 @@
- #include <linux/mfd/syscon.h>
- #include <linux/debugfs.h>
- #include <linux/soc/mediatek/mtk_wed.h>
-+#include <net/flow_offload.h>
-+#include <net/pkt_cls.h>
- #include "mtk_eth_soc.h"
- #include "mtk_wed_regs.h"
- #include "mtk_wed.h"
-@@ -41,6 +43,11 @@
- static struct mtk_wed_hw *hw_list[2];
- static DEFINE_MUTEX(hw_lock);
-+struct mtk_wed_flow_block_priv {
-+      struct mtk_wed_hw *hw;
-+      struct net_device *dev;
-+};
-+
- static void
- wed_m32(struct mtk_wed_device *dev, u32 reg, u32 mask, u32 val)
- {
-@@ -1753,6 +1760,99 @@ out:
-       mutex_unlock(&hw_lock);
- }
-+static int
-+mtk_wed_setup_tc_block_cb(enum tc_setup_type type, void *type_data, void *cb_priv)
-+{
-+      struct mtk_wed_flow_block_priv *priv = cb_priv;
-+      struct flow_cls_offload *cls = type_data;
-+      struct mtk_wed_hw *hw = priv->hw;
-+
-+      if (!tc_can_offload(priv->dev))
-+              return -EOPNOTSUPP;
-+
-+      if (type != TC_SETUP_CLSFLOWER)
-+              return -EOPNOTSUPP;
-+
-+      return mtk_flow_offload_cmd(hw->eth, cls, hw->index);
-+}
-+
-+static int
-+mtk_wed_setup_tc_block(struct mtk_wed_hw *hw, struct net_device *dev,
-+                     struct flow_block_offload *f)
-+{
-+      struct mtk_wed_flow_block_priv *priv;
-+      static LIST_HEAD(block_cb_list);
-+      struct flow_block_cb *block_cb;
-+      struct mtk_eth *eth = hw->eth;
-+      flow_setup_cb_t *cb;
-+
-+      if (!eth->soc->offload_version)
-+              return -EOPNOTSUPP;
-+
-+      if (f->binder_type != FLOW_BLOCK_BINDER_TYPE_CLSACT_INGRESS)
-+              return -EOPNOTSUPP;
-+
-+      cb = mtk_wed_setup_tc_block_cb;
-+      f->driver_block_list = &block_cb_list;
-+
-+      switch (f->command) {
-+      case FLOW_BLOCK_BIND:
-+              block_cb = flow_block_cb_lookup(f->block, cb, dev);
-+              if (block_cb) {
-+                      flow_block_cb_incref(block_cb);
-+                      return 0;
-+              }
-+
-+              priv = kzalloc(sizeof(*priv), GFP_KERNEL);
-+              if (!priv)
-+                      return -ENOMEM;
-+
-+              priv->hw = hw;
-+              priv->dev = dev;
-+              block_cb = flow_block_cb_alloc(cb, dev, priv, NULL);
-+              if (IS_ERR(block_cb)) {
-+                      kfree(priv);
-+                      return PTR_ERR(block_cb);
-+              }
-+
-+              flow_block_cb_incref(block_cb);
-+              flow_block_cb_add(block_cb, f);
-+              list_add_tail(&block_cb->driver_list, &block_cb_list);
-+              return 0;
-+      case FLOW_BLOCK_UNBIND:
-+              block_cb = flow_block_cb_lookup(f->block, cb, dev);
-+              if (!block_cb)
-+                      return -ENOENT;
-+
-+              if (!flow_block_cb_decref(block_cb)) {
-+                      flow_block_cb_remove(block_cb, f);
-+                      list_del(&block_cb->driver_list);
-+                      kfree(block_cb->cb_priv);
-+              }
-+              return 0;
-+      default:
-+              return -EOPNOTSUPP;
-+      }
-+}
-+
-+static int
-+mtk_wed_setup_tc(struct mtk_wed_device *wed, struct net_device *dev,
-+               enum tc_setup_type type, void *type_data)
-+{
-+      struct mtk_wed_hw *hw = wed->hw;
-+
-+      if (hw->version < 2)
-+              return -EOPNOTSUPP;
-+
-+      switch (type) {
-+      case TC_SETUP_BLOCK:
-+      case TC_SETUP_FT:
-+              return mtk_wed_setup_tc_block(hw, dev, type_data);
-+      default:
-+              return -EOPNOTSUPP;
-+      }
-+}
-+
- void mtk_wed_add_hw(struct device_node *np, struct mtk_eth *eth,
-                   void __iomem *wdma, phys_addr_t wdma_phy,
-                   int index)
-@@ -1772,6 +1872,7 @@ void mtk_wed_add_hw(struct device_node *
-               .irq_set_mask = mtk_wed_irq_set_mask,
-               .detach = mtk_wed_detach,
-               .ppe_check = mtk_wed_ppe_check,
-+              .setup_tc = mtk_wed_setup_tc,
-       };
-       struct device_node *eth_np = eth->dev->of_node;
-       struct platform_device *pdev;
---- a/include/linux/soc/mediatek/mtk_wed.h
-+++ b/include/linux/soc/mediatek/mtk_wed.h
-@@ -6,6 +6,7 @@
- #include <linux/regmap.h>
- #include <linux/pci.h>
- #include <linux/skbuff.h>
-+#include <linux/netdevice.h>
- #define MTK_WED_TX_QUEUES             2
- #define MTK_WED_RX_QUEUES             2
-@@ -180,6 +181,8 @@ struct mtk_wed_ops {
-       u32 (*irq_get)(struct mtk_wed_device *dev, u32 mask);
-       void (*irq_set_mask)(struct mtk_wed_device *dev, u32 mask);
-+      int (*setup_tc)(struct mtk_wed_device *wed, struct net_device *dev,
-+                      enum tc_setup_type type, void *type_data);
- };
- extern const struct mtk_wed_ops __rcu *mtk_soc_wed_ops;
-@@ -238,6 +241,8 @@ mtk_wed_get_rx_capa(struct mtk_wed_devic
-       (_dev)->ops->msg_update(_dev, _id, _msg, _len)
- #define mtk_wed_device_stop(_dev) (_dev)->ops->stop(_dev)
- #define mtk_wed_device_dma_reset(_dev) (_dev)->ops->reset_dma(_dev)
-+#define mtk_wed_device_setup_tc(_dev, _netdev, _type, _type_data) \
-+      (_dev)->ops->setup_tc(_dev, _netdev, _type, _type_data)
- #else
- static inline bool mtk_wed_device_active(struct mtk_wed_device *dev)
- {
-@@ -256,6 +261,7 @@ static inline bool mtk_wed_device_active
- #define mtk_wed_device_update_msg(_dev, _id, _msg, _len) -ENODEV
- #define mtk_wed_device_stop(_dev) do {} while (0)
- #define mtk_wed_device_dma_reset(_dev) do {} while (0)
-+#define mtk_wed_device_setup_tc(_dev, _netdev, _type, _type_data) -EOPNOTSUPP
- #endif
- #endif
diff --git a/target/linux/generic/backport-5.15/751-02-v6.4-net-ethernet-mediatek-mtk_ppe-prefer-newly-added-l2-.patch b/target/linux/generic/backport-5.15/751-02-v6.4-net-ethernet-mediatek-mtk_ppe-prefer-newly-added-l2-.patch
deleted file mode 100644 (file)
index 84b768b..0000000
+++ /dev/null
@@ -1,37 +0,0 @@
-From: Felix Fietkau <[email protected]>
-Date: Mon, 20 Mar 2023 15:37:55 +0100
-Subject: [PATCH] net: ethernet: mediatek: mtk_ppe: prefer newly added l2
- flows over existing ones
-
-When a device is roaming between interfaces and a new flow entry is created,
-we should assume that its output device is more up to date than whatever
-entry existed already.
-
-Signed-off-by: Felix Fietkau <[email protected]>
----
-
---- a/drivers/net/ethernet/mediatek/mtk_ppe.c
-+++ b/drivers/net/ethernet/mediatek/mtk_ppe.c
-@@ -662,10 +662,20 @@ void mtk_foe_entry_clear(struct mtk_ppe
- static int
- mtk_foe_entry_commit_l2(struct mtk_ppe *ppe, struct mtk_flow_entry *entry)
- {
-+      struct mtk_flow_entry *prev;
-+
-       entry->type = MTK_FLOW_TYPE_L2;
--      return rhashtable_insert_fast(&ppe->l2_flows, &entry->l2_node,
--                                    mtk_flow_l2_ht_params);
-+      prev = rhashtable_lookup_get_insert_fast(&ppe->l2_flows, &entry->l2_node,
-+                                               mtk_flow_l2_ht_params);
-+      if (likely(!prev))
-+              return 0;
-+
-+      if (IS_ERR(prev))
-+              return PTR_ERR(prev);
-+
-+      return rhashtable_replace_fast(&ppe->l2_flows, &prev->l2_node,
-+                                     &entry->l2_node, mtk_flow_l2_ht_params);
- }
- int mtk_foe_entry_commit(struct mtk_ppe *ppe, struct mtk_flow_entry *entry)
diff --git a/target/linux/generic/backport-5.15/751-03-v6.4-net-ethernet-mtk_eth_soc-improve-keeping-track-of-of.patch b/target/linux/generic/backport-5.15/751-03-v6.4-net-ethernet-mtk_eth_soc-improve-keeping-track-of-of.patch
deleted file mode 100644 (file)
index a9f82ca..0000000
+++ /dev/null
@@ -1,334 +0,0 @@
-From: Felix Fietkau <[email protected]>
-Date: Thu, 23 Mar 2023 10:24:11 +0100
-Subject: [PATCH] net: ethernet: mtk_eth_soc: improve keeping track of
- offloaded flows
-
-Unify tracking of L2 and L3 flows. Use the generic list field in struct
-mtk_foe_entry for tracking L2 subflows. Preparation for improving
-flow accounting support.
-
-Signed-off-by: Felix Fietkau <[email protected]>
----
- drivers/net/ethernet/mediatek/mtk_ppe.c | 162 ++++++++++++------------
- drivers/net/ethernet/mediatek/mtk_ppe.h |  15 +--
- 2 files changed, 86 insertions(+), 91 deletions(-)
-
---- a/drivers/net/ethernet/mediatek/mtk_ppe.c
-+++ b/drivers/net/ethernet/mediatek/mtk_ppe.c
-@@ -482,42 +482,43 @@ int mtk_foe_entry_set_queue(struct mtk_e
-       return 0;
- }
-+static int
-+mtk_flow_entry_match_len(struct mtk_eth *eth, struct mtk_foe_entry *entry)
-+{
-+      int type = mtk_get_ib1_pkt_type(eth, entry->ib1);
-+
-+      if (type > MTK_PPE_PKT_TYPE_IPV4_DSLITE)
-+              return offsetof(struct mtk_foe_entry, ipv6._rsv);
-+      else
-+              return offsetof(struct mtk_foe_entry, ipv4.ib2);
-+}
-+
- static bool
- mtk_flow_entry_match(struct mtk_eth *eth, struct mtk_flow_entry *entry,
--                   struct mtk_foe_entry *data)
-+                   struct mtk_foe_entry *data, int len)
- {
--      int type, len;
--
-       if ((data->ib1 ^ entry->data.ib1) & MTK_FOE_IB1_UDP)
-               return false;
--      type = mtk_get_ib1_pkt_type(eth, entry->data.ib1);
--      if (type > MTK_PPE_PKT_TYPE_IPV4_DSLITE)
--              len = offsetof(struct mtk_foe_entry, ipv6._rsv);
--      else
--              len = offsetof(struct mtk_foe_entry, ipv4.ib2);
--
-       return !memcmp(&entry->data.data, &data->data, len - 4);
- }
- static void
--__mtk_foe_entry_clear(struct mtk_ppe *ppe, struct mtk_flow_entry *entry)
-+__mtk_foe_entry_clear(struct mtk_ppe *ppe, struct mtk_flow_entry *entry,
-+                    bool set_state)
- {
--      struct hlist_head *head;
-       struct hlist_node *tmp;
-       if (entry->type == MTK_FLOW_TYPE_L2) {
-               rhashtable_remove_fast(&ppe->l2_flows, &entry->l2_node,
-                                      mtk_flow_l2_ht_params);
--              head = &entry->l2_flows;
--              hlist_for_each_entry_safe(entry, tmp, head, l2_data.list)
--                      __mtk_foe_entry_clear(ppe, entry);
-+              hlist_for_each_entry_safe(entry, tmp, &entry->l2_flows, l2_list)
-+                      __mtk_foe_entry_clear(ppe, entry, set_state);
-               return;
-       }
--      hlist_del_init(&entry->list);
--      if (entry->hash != 0xffff) {
-+      if (entry->hash != 0xffff && set_state) {
-               struct mtk_foe_entry *hwe = mtk_foe_get_entry(ppe, entry->hash);
-               hwe->ib1 &= ~MTK_FOE_IB1_STATE;
-@@ -537,7 +538,8 @@ __mtk_foe_entry_clear(struct mtk_ppe *pp
-       if (entry->type != MTK_FLOW_TYPE_L2_SUBFLOW)
-               return;
--      hlist_del_init(&entry->l2_data.list);
-+      hlist_del_init(&entry->l2_list);
-+      hlist_del_init(&entry->list);
-       kfree(entry);
- }
-@@ -553,66 +555,55 @@ static int __mtk_foe_entry_idle_time(str
-               return now - timestamp;
- }
-+static bool
-+mtk_flow_entry_update(struct mtk_ppe *ppe, struct mtk_flow_entry *entry)
-+{
-+      struct mtk_foe_entry foe = {};
-+      struct mtk_foe_entry *hwe;
-+      u16 hash = entry->hash;
-+      int len;
-+
-+      if (hash == 0xffff)
-+              return false;
-+
-+      hwe = mtk_foe_get_entry(ppe, hash);
-+      len = mtk_flow_entry_match_len(ppe->eth, &entry->data);
-+      memcpy(&foe, hwe, len);
-+
-+      if (!mtk_flow_entry_match(ppe->eth, entry, &foe, len) ||
-+          FIELD_GET(MTK_FOE_IB1_STATE, foe.ib1) != MTK_FOE_STATE_BIND)
-+              return false;
-+
-+      entry->data.ib1 = foe.ib1;
-+
-+      return true;
-+}
-+
- static void
- mtk_flow_entry_update_l2(struct mtk_ppe *ppe, struct mtk_flow_entry *entry)
- {
-       u32 ib1_ts_mask = mtk_get_ib1_ts_mask(ppe->eth);
-       struct mtk_flow_entry *cur;
--      struct mtk_foe_entry *hwe;
-       struct hlist_node *tmp;
-       int idle;
-       idle = __mtk_foe_entry_idle_time(ppe, entry->data.ib1);
--      hlist_for_each_entry_safe(cur, tmp, &entry->l2_flows, l2_data.list) {
-+      hlist_for_each_entry_safe(cur, tmp, &entry->l2_flows, l2_list) {
-               int cur_idle;
--              u32 ib1;
--
--              hwe = mtk_foe_get_entry(ppe, cur->hash);
--              ib1 = READ_ONCE(hwe->ib1);
--              if (FIELD_GET(MTK_FOE_IB1_STATE, ib1) != MTK_FOE_STATE_BIND) {
--                      cur->hash = 0xffff;
--                      __mtk_foe_entry_clear(ppe, cur);
-+              if (!mtk_flow_entry_update(ppe, cur)) {
-+                      __mtk_foe_entry_clear(ppe, entry, false);
-                       continue;
-               }
--              cur_idle = __mtk_foe_entry_idle_time(ppe, ib1);
-+              cur_idle = __mtk_foe_entry_idle_time(ppe, cur->data.ib1);
-               if (cur_idle >= idle)
-                       continue;
-               idle = cur_idle;
-               entry->data.ib1 &= ~ib1_ts_mask;
--              entry->data.ib1 |= hwe->ib1 & ib1_ts_mask;
--      }
--}
--
--static void
--mtk_flow_entry_update(struct mtk_ppe *ppe, struct mtk_flow_entry *entry)
--{
--      struct mtk_foe_entry foe = {};
--      struct mtk_foe_entry *hwe;
--
--      spin_lock_bh(&ppe_lock);
--
--      if (entry->type == MTK_FLOW_TYPE_L2) {
--              mtk_flow_entry_update_l2(ppe, entry);
--              goto out;
-+              entry->data.ib1 |= cur->data.ib1 & ib1_ts_mask;
-       }
--
--      if (entry->hash == 0xffff)
--              goto out;
--
--      hwe = mtk_foe_get_entry(ppe, entry->hash);
--      memcpy(&foe, hwe, ppe->eth->soc->foe_entry_size);
--      if (!mtk_flow_entry_match(ppe->eth, entry, &foe)) {
--              entry->hash = 0xffff;
--              goto out;
--      }
--
--      entry->data.ib1 = foe.ib1;
--
--out:
--      spin_unlock_bh(&ppe_lock);
- }
- static void
-@@ -655,7 +646,8 @@ __mtk_foe_entry_commit(struct mtk_ppe *p
- void mtk_foe_entry_clear(struct mtk_ppe *ppe, struct mtk_flow_entry *entry)
- {
-       spin_lock_bh(&ppe_lock);
--      __mtk_foe_entry_clear(ppe, entry);
-+      __mtk_foe_entry_clear(ppe, entry, true);
-+      hlist_del_init(&entry->list);
-       spin_unlock_bh(&ppe_lock);
- }
-@@ -702,8 +694,8 @@ mtk_foe_entry_commit_subflow(struct mtk_
- {
-       const struct mtk_soc_data *soc = ppe->eth->soc;
-       struct mtk_flow_entry *flow_info;
--      struct mtk_foe_entry foe = {}, *hwe;
-       struct mtk_foe_mac_info *l2;
-+      struct mtk_foe_entry *hwe;
-       u32 ib1_mask = mtk_get_ib1_pkt_type_mask(ppe->eth) | MTK_FOE_IB1_UDP;
-       int type;
-@@ -711,30 +703,30 @@ mtk_foe_entry_commit_subflow(struct mtk_
-       if (!flow_info)
-               return;
--      flow_info->l2_data.base_flow = entry;
-       flow_info->type = MTK_FLOW_TYPE_L2_SUBFLOW;
-       flow_info->hash = hash;
-       hlist_add_head(&flow_info->list,
-                      &ppe->foe_flow[hash / soc->hash_offset]);
--      hlist_add_head(&flow_info->l2_data.list, &entry->l2_flows);
-+      hlist_add_head(&flow_info->l2_list, &entry->l2_flows);
-       hwe = mtk_foe_get_entry(ppe, hash);
--      memcpy(&foe, hwe, soc->foe_entry_size);
--      foe.ib1 &= ib1_mask;
--      foe.ib1 |= entry->data.ib1 & ~ib1_mask;
-+      memcpy(&flow_info->data, hwe, soc->foe_entry_size);
-+      flow_info->data.ib1 &= ib1_mask;
-+      flow_info->data.ib1 |= entry->data.ib1 & ~ib1_mask;
--      l2 = mtk_foe_entry_l2(ppe->eth, &foe);
-+      l2 = mtk_foe_entry_l2(ppe->eth, &flow_info->data);
-       memcpy(l2, &entry->data.bridge.l2, sizeof(*l2));
--      type = mtk_get_ib1_pkt_type(ppe->eth, foe.ib1);
-+      type = mtk_get_ib1_pkt_type(ppe->eth, flow_info->data.ib1);
-       if (type == MTK_PPE_PKT_TYPE_IPV4_HNAPT)
--              memcpy(&foe.ipv4.new, &foe.ipv4.orig, sizeof(foe.ipv4.new));
-+              memcpy(&flow_info->data.ipv4.new, &flow_info->data.ipv4.orig,
-+                     sizeof(flow_info->data.ipv4.new));
-       else if (type >= MTK_PPE_PKT_TYPE_IPV6_ROUTE_3T && l2->etype == ETH_P_IP)
-               l2->etype = ETH_P_IPV6;
--      *mtk_foe_entry_ib2(ppe->eth, &foe) = entry->data.bridge.ib2;
-+      *mtk_foe_entry_ib2(ppe->eth, &flow_info->data) = entry->data.bridge.ib2;
--      __mtk_foe_entry_commit(ppe, &foe, hash);
-+      __mtk_foe_entry_commit(ppe, &flow_info->data, hash);
- }
- void __mtk_ppe_check_skb(struct mtk_ppe *ppe, struct sk_buff *skb, u16 hash)
-@@ -744,9 +736,11 @@ void __mtk_ppe_check_skb(struct mtk_ppe
-       struct mtk_foe_entry *hwe = mtk_foe_get_entry(ppe, hash);
-       struct mtk_flow_entry *entry;
-       struct mtk_foe_bridge key = {};
-+      struct mtk_foe_entry foe = {};
-       struct hlist_node *n;
-       struct ethhdr *eh;
-       bool found = false;
-+      int entry_len;
-       u8 *tag;
-       spin_lock_bh(&ppe_lock);
-@@ -754,20 +748,14 @@ void __mtk_ppe_check_skb(struct mtk_ppe
-       if (FIELD_GET(MTK_FOE_IB1_STATE, hwe->ib1) == MTK_FOE_STATE_BIND)
-               goto out;
--      hlist_for_each_entry_safe(entry, n, head, list) {
--              if (entry->type == MTK_FLOW_TYPE_L2_SUBFLOW) {
--                      if (unlikely(FIELD_GET(MTK_FOE_IB1_STATE, hwe->ib1) ==
--                                   MTK_FOE_STATE_BIND))
--                              continue;
--
--                      entry->hash = 0xffff;
--                      __mtk_foe_entry_clear(ppe, entry);
--                      continue;
--              }
-+      entry_len = mtk_flow_entry_match_len(ppe->eth, hwe);
-+      memcpy(&foe, hwe, entry_len);
--              if (found || !mtk_flow_entry_match(ppe->eth, entry, hwe)) {
-+      hlist_for_each_entry_safe(entry, n, head, list) {
-+              if (found ||
-+                  !mtk_flow_entry_match(ppe->eth, entry, &foe, entry_len)) {
-                       if (entry->hash != 0xffff)
--                              entry->hash = 0xffff;
-+                              __mtk_foe_entry_clear(ppe, entry, false);
-                       continue;
-               }
-@@ -816,9 +804,17 @@ out:
- int mtk_foe_entry_idle_time(struct mtk_ppe *ppe, struct mtk_flow_entry *entry)
- {
--      mtk_flow_entry_update(ppe, entry);
-+      int idle;
-+
-+      spin_lock_bh(&ppe_lock);
-+      if (entry->type == MTK_FLOW_TYPE_L2)
-+              mtk_flow_entry_update_l2(ppe, entry);
-+      else
-+              mtk_flow_entry_update(ppe, entry);
-+      idle = __mtk_foe_entry_idle_time(ppe, entry->data.ib1);
-+      spin_unlock_bh(&ppe_lock);
--      return __mtk_foe_entry_idle_time(ppe, entry->data.ib1);
-+      return idle;
- }
- int mtk_ppe_prepare_reset(struct mtk_ppe *ppe)
---- a/drivers/net/ethernet/mediatek/mtk_ppe.h
-+++ b/drivers/net/ethernet/mediatek/mtk_ppe.h
-@@ -286,7 +286,12 @@ enum {
- struct mtk_flow_entry {
-       union {
--              struct hlist_node list;
-+              /* regular flows + L2 subflows */
-+              struct {
-+                      struct hlist_node list;
-+                      struct hlist_node l2_list;
-+              };
-+              /* L2 flows */
-               struct {
-                       struct rhash_head l2_node;
-                       struct hlist_head l2_flows;
-@@ -296,13 +301,7 @@ struct mtk_flow_entry {
-       s8 wed_index;
-       u8 ppe_index;
-       u16 hash;
--      union {
--              struct mtk_foe_entry data;
--              struct {
--                      struct mtk_flow_entry *base_flow;
--                      struct hlist_node list;
--              } l2_data;
--      };
-+      struct mtk_foe_entry data;
-       struct rhash_head node;
-       unsigned long cookie;
- };
diff --git a/target/linux/generic/backport-5.15/751-04-v6.4-net-ethernet-mediatek-fix-ppe-flow-accounting-for-L2.patch b/target/linux/generic/backport-5.15/751-04-v6.4-net-ethernet-mediatek-fix-ppe-flow-accounting-for-L2.patch
deleted file mode 100644 (file)
index 2ea6d34..0000000
+++ /dev/null
@@ -1,342 +0,0 @@
-From: Felix Fietkau <[email protected]>
-Date: Thu, 23 Mar 2023 11:05:22 +0100
-Subject: [PATCH] net: ethernet: mediatek: fix ppe flow accounting for L2
- flows
-
-For L2 flows, the packet/byte counters should report the sum of the
-counters of their subflows, both current and expired.
-In order to make this work, change the way that accounting data is tracked.
-Reset counters when a flow enters bind. Once it expires (or enters unbind),
-store the last counter value in struct mtk_flow_entry.
-
-Signed-off-by: Felix Fietkau <[email protected]>
----
-
---- a/drivers/net/ethernet/mediatek/mtk_ppe.c
-+++ b/drivers/net/ethernet/mediatek/mtk_ppe.c
-@@ -79,9 +79,9 @@ static int mtk_ppe_mib_wait_busy(struct
-       int ret;
-       u32 val;
--      ret = readl_poll_timeout(ppe->base + MTK_PPE_MIB_SER_CR, val,
--                               !(val & MTK_PPE_MIB_SER_CR_ST),
--                               20, MTK_PPE_WAIT_TIMEOUT_US);
-+      ret = readl_poll_timeout_atomic(ppe->base + MTK_PPE_MIB_SER_CR, val,
-+                                      !(val & MTK_PPE_MIB_SER_CR_ST),
-+                                      20, MTK_PPE_WAIT_TIMEOUT_US);
-       if (ret)
-               dev_err(ppe->dev, "MIB table busy");
-@@ -89,17 +89,31 @@ static int mtk_ppe_mib_wait_busy(struct
-       return ret;
- }
--static int mtk_mib_entry_read(struct mtk_ppe *ppe, u16 index, u64 *bytes, u64 *packets)
-+static inline struct mtk_foe_accounting *
-+mtk_ppe_acct_data(struct mtk_ppe *ppe, u16 index)
-+{
-+      if (!ppe->acct_table)
-+              return NULL;
-+
-+      return ppe->acct_table + index * sizeof(struct mtk_foe_accounting);
-+}
-+
-+struct mtk_foe_accounting *mtk_ppe_mib_entry_read(struct mtk_ppe *ppe, u16 index)
- {
-       u32 val, cnt_r0, cnt_r1, cnt_r2;
-+      struct mtk_foe_accounting *acct;
-       int ret;
-       val = FIELD_PREP(MTK_PPE_MIB_SER_CR_ADDR, index) | MTK_PPE_MIB_SER_CR_ST;
-       ppe_w32(ppe, MTK_PPE_MIB_SER_CR, val);
-+      acct = mtk_ppe_acct_data(ppe, index);
-+      if (!acct)
-+              return NULL;
-+
-       ret = mtk_ppe_mib_wait_busy(ppe);
-       if (ret)
--              return ret;
-+              return acct;
-       cnt_r0 = readl(ppe->base + MTK_PPE_MIB_SER_R0);
-       cnt_r1 = readl(ppe->base + MTK_PPE_MIB_SER_R1);
-@@ -108,19 +122,19 @@ static int mtk_mib_entry_read(struct mtk
-       if (mtk_is_netsys_v3_or_greater(ppe->eth)) {
-               /* 64 bit for each counter */
-               u32 cnt_r3 = readl(ppe->base + MTK_PPE_MIB_SER_R3);
--              *bytes = ((u64)cnt_r1 << 32) | cnt_r0;
--              *packets = ((u64)cnt_r3 << 32) | cnt_r2;
-+              acct->bytes += ((u64)cnt_r1 << 32) | cnt_r0;
-+              acct->packets += ((u64)cnt_r3 << 32) | cnt_r2;
-       } else {
-               /* 48 bit byte counter, 40 bit packet counter */
-               u32 byte_cnt_low = FIELD_GET(MTK_PPE_MIB_SER_R0_BYTE_CNT_LOW, cnt_r0);
-               u32 byte_cnt_high = FIELD_GET(MTK_PPE_MIB_SER_R1_BYTE_CNT_HIGH, cnt_r1);
-               u32 pkt_cnt_low = FIELD_GET(MTK_PPE_MIB_SER_R1_PKT_CNT_LOW, cnt_r1);
-               u32 pkt_cnt_high = FIELD_GET(MTK_PPE_MIB_SER_R2_PKT_CNT_HIGH, cnt_r2);
--              *bytes = ((u64)byte_cnt_high << 32) | byte_cnt_low;
--              *packets = (pkt_cnt_high << 16) | pkt_cnt_low;
-+              acct->bytes += ((u64)byte_cnt_high << 32) | byte_cnt_low;
-+              acct->packets += (pkt_cnt_high << 16) | pkt_cnt_low;
-       }
--      return 0;
-+      return acct;
- }
- static void mtk_ppe_cache_clear(struct mtk_ppe *ppe)
-@@ -525,13 +539,6 @@ __mtk_foe_entry_clear(struct mtk_ppe *pp
-               hwe->ib1 |= FIELD_PREP(MTK_FOE_IB1_STATE, MTK_FOE_STATE_INVALID);
-               dma_wmb();
-               mtk_ppe_cache_clear(ppe);
--              if (ppe->accounting) {
--                      struct mtk_foe_accounting *acct;
--
--                      acct = ppe->acct_table + entry->hash * sizeof(*acct);
--                      acct->packets = 0;
--                      acct->bytes = 0;
--              }
-       }
-       entry->hash = 0xffff;
-@@ -556,11 +563,14 @@ static int __mtk_foe_entry_idle_time(str
- }
- static bool
--mtk_flow_entry_update(struct mtk_ppe *ppe, struct mtk_flow_entry *entry)
-+mtk_flow_entry_update(struct mtk_ppe *ppe, struct mtk_flow_entry *entry,
-+                    u64 *packets, u64 *bytes)
- {
-+      struct mtk_foe_accounting *acct;
-       struct mtk_foe_entry foe = {};
-       struct mtk_foe_entry *hwe;
-       u16 hash = entry->hash;
-+      bool ret = false;
-       int len;
-       if (hash == 0xffff)
-@@ -571,18 +581,35 @@ mtk_flow_entry_update(struct mtk_ppe *pp
-       memcpy(&foe, hwe, len);
-       if (!mtk_flow_entry_match(ppe->eth, entry, &foe, len) ||
--          FIELD_GET(MTK_FOE_IB1_STATE, foe.ib1) != MTK_FOE_STATE_BIND)
--              return false;
-+          FIELD_GET(MTK_FOE_IB1_STATE, foe.ib1) != MTK_FOE_STATE_BIND) {
-+              acct = mtk_ppe_acct_data(ppe, hash);
-+              if (acct) {
-+                      entry->prev_packets += acct->packets;
-+                      entry->prev_bytes += acct->bytes;
-+              }
-+
-+              goto out;
-+      }
-       entry->data.ib1 = foe.ib1;
-+      acct = mtk_ppe_mib_entry_read(ppe, hash);
-+      ret = true;
-+
-+out:
-+      if (acct) {
-+              *packets += acct->packets;
-+              *bytes += acct->bytes;
-+      }
--      return true;
-+      return ret;
- }
- static void
- mtk_flow_entry_update_l2(struct mtk_ppe *ppe, struct mtk_flow_entry *entry)
- {
-       u32 ib1_ts_mask = mtk_get_ib1_ts_mask(ppe->eth);
-+      u64 *packets = &entry->packets;
-+      u64 *bytes = &entry->bytes;
-       struct mtk_flow_entry *cur;
-       struct hlist_node *tmp;
-       int idle;
-@@ -591,7 +618,9 @@ mtk_flow_entry_update_l2(struct mtk_ppe
-       hlist_for_each_entry_safe(cur, tmp, &entry->l2_flows, l2_list) {
-               int cur_idle;
--              if (!mtk_flow_entry_update(ppe, cur)) {
-+              if (!mtk_flow_entry_update(ppe, cur, packets, bytes)) {
-+                      entry->prev_packets += cur->prev_packets;
-+                      entry->prev_bytes += cur->prev_bytes;
-                       __mtk_foe_entry_clear(ppe, entry, false);
-                       continue;
-               }
-@@ -606,10 +635,29 @@ mtk_flow_entry_update_l2(struct mtk_ppe
-       }
- }
-+void mtk_foe_entry_get_stats(struct mtk_ppe *ppe, struct mtk_flow_entry *entry,
-+                           int *idle)
-+{
-+      entry->packets = entry->prev_packets;
-+      entry->bytes = entry->prev_bytes;
-+
-+      spin_lock_bh(&ppe_lock);
-+
-+      if (entry->type == MTK_FLOW_TYPE_L2)
-+              mtk_flow_entry_update_l2(ppe, entry);
-+      else
-+              mtk_flow_entry_update(ppe, entry, &entry->packets, &entry->bytes);
-+
-+      *idle = __mtk_foe_entry_idle_time(ppe, entry->data.ib1);
-+
-+      spin_unlock_bh(&ppe_lock);
-+}
-+
- static void
- __mtk_foe_entry_commit(struct mtk_ppe *ppe, struct mtk_foe_entry *entry,
-                      u16 hash)
- {
-+      struct mtk_foe_accounting *acct;
-       struct mtk_eth *eth = ppe->eth;
-       u16 timestamp = mtk_eth_timestamp(eth);
-       struct mtk_foe_entry *hwe;
-@@ -640,6 +688,12 @@ __mtk_foe_entry_commit(struct mtk_ppe *p
-       dma_wmb();
-+      acct = mtk_ppe_mib_entry_read(ppe, hash);
-+      if (acct) {
-+              acct->packets = 0;
-+              acct->bytes = 0;
-+      }
-+
-       mtk_ppe_cache_clear(ppe);
- }
-@@ -802,21 +856,6 @@ out:
-       spin_unlock_bh(&ppe_lock);
- }
--int mtk_foe_entry_idle_time(struct mtk_ppe *ppe, struct mtk_flow_entry *entry)
--{
--      int idle;
--
--      spin_lock_bh(&ppe_lock);
--      if (entry->type == MTK_FLOW_TYPE_L2)
--              mtk_flow_entry_update_l2(ppe, entry);
--      else
--              mtk_flow_entry_update(ppe, entry);
--      idle = __mtk_foe_entry_idle_time(ppe, entry->data.ib1);
--      spin_unlock_bh(&ppe_lock);
--
--      return idle;
--}
--
- int mtk_ppe_prepare_reset(struct mtk_ppe *ppe)
- {
-       if (!ppe)
-@@ -844,32 +883,6 @@ int mtk_ppe_prepare_reset(struct mtk_ppe
-       return mtk_ppe_wait_busy(ppe);
- }
--struct mtk_foe_accounting *mtk_foe_entry_get_mib(struct mtk_ppe *ppe, u32 index,
--                                               struct mtk_foe_accounting *diff)
--{
--      struct mtk_foe_accounting *acct;
--      int size = sizeof(struct mtk_foe_accounting);
--      u64 bytes, packets;
--
--      if (!ppe->accounting)
--              return NULL;
--
--      if (mtk_mib_entry_read(ppe, index, &bytes, &packets))
--              return NULL;
--
--      acct = ppe->acct_table + index * size;
--
--      acct->bytes += bytes;
--      acct->packets += packets;
--
--      if (diff) {
--              diff->bytes = bytes;
--              diff->packets = packets;
--      }
--
--      return acct;
--}
--
- struct mtk_ppe *mtk_ppe_init(struct mtk_eth *eth, void __iomem *base, int index)
- {
-       bool accounting = eth->soc->has_accounting;
---- a/drivers/net/ethernet/mediatek/mtk_ppe.h
-+++ b/drivers/net/ethernet/mediatek/mtk_ppe.h
-@@ -304,6 +304,8 @@ struct mtk_flow_entry {
-       struct mtk_foe_entry data;
-       struct rhash_head node;
-       unsigned long cookie;
-+      u64 prev_packets, prev_bytes;
-+      u64 packets, bytes;
- };
- struct mtk_mib_entry {
-@@ -347,6 +349,7 @@ void mtk_ppe_deinit(struct mtk_eth *eth)
- void mtk_ppe_start(struct mtk_ppe *ppe);
- int mtk_ppe_stop(struct mtk_ppe *ppe);
- int mtk_ppe_prepare_reset(struct mtk_ppe *ppe);
-+struct mtk_foe_accounting *mtk_ppe_mib_entry_read(struct mtk_ppe *ppe, u16 index);
- void __mtk_ppe_check_skb(struct mtk_ppe *ppe, struct sk_buff *skb, u16 hash);
-@@ -395,9 +398,8 @@ int mtk_foe_entry_set_queue(struct mtk_e
-                           unsigned int queue);
- int mtk_foe_entry_commit(struct mtk_ppe *ppe, struct mtk_flow_entry *entry);
- void mtk_foe_entry_clear(struct mtk_ppe *ppe, struct mtk_flow_entry *entry);
--int mtk_foe_entry_idle_time(struct mtk_ppe *ppe, struct mtk_flow_entry *entry);
- int mtk_ppe_debugfs_init(struct mtk_ppe *ppe, int index);
--struct mtk_foe_accounting *mtk_foe_entry_get_mib(struct mtk_ppe *ppe, u32 index,
--                                               struct mtk_foe_accounting *diff);
-+void mtk_foe_entry_get_stats(struct mtk_ppe *ppe, struct mtk_flow_entry *entry,
-+                           int *idle);
- #endif
---- a/drivers/net/ethernet/mediatek/mtk_ppe_debugfs.c
-+++ b/drivers/net/ethernet/mediatek/mtk_ppe_debugfs.c
-@@ -96,7 +96,7 @@ mtk_ppe_debugfs_foe_show(struct seq_file
-               if (bind && state != MTK_FOE_STATE_BIND)
-                       continue;
--              acct = mtk_foe_entry_get_mib(ppe, i, NULL);
-+              acct = mtk_ppe_mib_entry_read(ppe, i);
-               type = mtk_get_ib1_pkt_type(ppe->eth, entry->ib1);
-               seq_printf(m, "%05x %s %7s", i,
---- a/drivers/net/ethernet/mediatek/mtk_ppe_offload.c
-+++ b/drivers/net/ethernet/mediatek/mtk_ppe_offload.c
-@@ -501,24 +501,21 @@ static int
- mtk_flow_offload_stats(struct mtk_eth *eth, struct flow_cls_offload *f)
- {
-       struct mtk_flow_entry *entry;
--      struct mtk_foe_accounting diff;
--      u32 idle;
-+      u64 packets, bytes;
-+      int idle;
-       entry = rhashtable_lookup(&eth->flow_table, &f->cookie,
-                                 mtk_flow_ht_params);
-       if (!entry)
-               return -ENOENT;
--      idle = mtk_foe_entry_idle_time(eth->ppe[entry->ppe_index], entry);
-+      packets = entry->packets;
-+      bytes = entry->bytes;
-+      mtk_foe_entry_get_stats(eth->ppe[entry->ppe_index], entry, &idle);
-+      f->stats.pkts += entry->packets - packets;
-+      f->stats.bytes += entry->bytes - bytes;
-       f->stats.lastused = jiffies - idle * HZ;
--      if (entry->hash != 0xFFFF &&
--          mtk_foe_entry_get_mib(eth->ppe[entry->ppe_index], entry->hash,
--                                &diff)) {
--              f->stats.pkts += diff.packets;
--              f->stats.bytes += diff.bytes;
--      }
--
-       return 0;
- }
diff --git a/target/linux/generic/backport-5.15/752-01-v6.6-net-ethernet-mtk_wed-add-some-more-info-in-wed_txinf.patch b/target/linux/generic/backport-5.15/752-01-v6.6-net-ethernet-mtk_wed-add-some-more-info-in-wed_txinf.patch
deleted file mode 100644 (file)
index a224b62..0000000
+++ /dev/null
@@ -1,45 +0,0 @@
-From: Lorenzo Bianconi <[email protected]>
-Date: Sun, 27 Aug 2023 19:31:41 +0200
-Subject: [PATCH] net: ethernet: mtk_wed: add some more info in wed_txinfo_show
- handler
-
-Add some new info in Wireless Ethernet Dispatcher wed_txinfo_show
-debugfs handler useful during debugging.
-
-Signed-off-by: Lorenzo Bianconi <[email protected]>
-Link: https://lore.kernel.org/r/3390292655d568180b73d2a25576f61aa63310e5.1693157377.git.lorenzo@kernel.org
-Signed-off-by: Jakub Kicinski <[email protected]>
----
-
---- a/drivers/net/ethernet/mediatek/mtk_wed_debugfs.c
-+++ b/drivers/net/ethernet/mediatek/mtk_wed_debugfs.c
-@@ -127,8 +127,17 @@ wed_txinfo_show(struct seq_file *s, void
-               DUMP_WDMA_RING(WDMA_RING_RX(0)),
-               DUMP_WDMA_RING(WDMA_RING_RX(1)),
--              DUMP_STR("TX FREE"),
-+              DUMP_STR("WED TX FREE"),
-               DUMP_WED(WED_RX_MIB(0)),
-+              DUMP_WED_RING(WED_RING_RX(0)),
-+              DUMP_WED(WED_WPDMA_RX_COHERENT_MIB(0)),
-+              DUMP_WED(WED_RX_MIB(1)),
-+              DUMP_WED_RING(WED_RING_RX(1)),
-+              DUMP_WED(WED_WPDMA_RX_COHERENT_MIB(1)),
-+
-+              DUMP_STR("WED WPDMA TX FREE"),
-+              DUMP_WED_RING(WED_WPDMA_RING_RX(0)),
-+              DUMP_WED_RING(WED_WPDMA_RING_RX(1)),
-       };
-       struct mtk_wed_hw *hw = s->private;
-       struct mtk_wed_device *dev = hw->wed_dev;
---- a/drivers/net/ethernet/mediatek/mtk_wed_regs.h
-+++ b/drivers/net/ethernet/mediatek/mtk_wed_regs.h
-@@ -266,6 +266,8 @@ struct mtk_wdma_desc {
- #define MTK_WED_WPDMA_TX_MIB(_n)                      (0x5a0 + (_n) * 4)
- #define MTK_WED_WPDMA_TX_COHERENT_MIB(_n)             (0x5d0 + (_n) * 4)
-+#define MTK_WED_WPDMA_RX_MIB(_n)                      (0x5e0 + (_n) * 4)
-+#define MTK_WED_WPDMA_RX_COHERENT_MIB(_n)             (0x5f0 + (_n) * 4)
- #define MTK_WED_WPDMA_RING_TX(_n)                     (0x600 + (_n) * 0x10)
- #define MTK_WED_WPDMA_RING_RX(_n)                     (0x700 + (_n) * 0x10)
diff --git a/target/linux/generic/backport-5.15/752-02-v6.6-net-ethernet-mtk_wed-minor-change-in-wed_-tx-rx-info.patch b/target/linux/generic/backport-5.15/752-02-v6.6-net-ethernet-mtk_wed-minor-change-in-wed_-tx-rx-info.patch
deleted file mode 100644 (file)
index df6edfd..0000000
+++ /dev/null
@@ -1,47 +0,0 @@
-From: Lorenzo Bianconi <[email protected]>
-Date: Sun, 27 Aug 2023 19:33:47 +0200
-Subject: [PATCH] net: ethernet: mtk_wed: minor change in wed_{tx,rx}info_show
-
-No functional changes, just cosmetic ones.
-
-Signed-off-by: Lorenzo Bianconi <[email protected]>
-Link: https://lore.kernel.org/r/71e046c72a978745f0435af265dda610aa9bfbcf.1693157578.git.lorenzo@kernel.org
-Signed-off-by: Jakub Kicinski <[email protected]>
----
-
---- a/drivers/net/ethernet/mediatek/mtk_wed_debugfs.c
-+++ b/drivers/net/ethernet/mediatek/mtk_wed_debugfs.c
-@@ -84,7 +84,6 @@ dump_wed_regs(struct seq_file *s, struct
-       }
- }
--
- static int
- wed_txinfo_show(struct seq_file *s, void *data)
- {
-@@ -142,10 +141,8 @@ wed_txinfo_show(struct seq_file *s, void
-       struct mtk_wed_hw *hw = s->private;
-       struct mtk_wed_device *dev = hw->wed_dev;
--      if (!dev)
--              return 0;
--
--      dump_wed_regs(s, dev, regs, ARRAY_SIZE(regs));
-+      if (dev)
-+              dump_wed_regs(s, dev, regs, ARRAY_SIZE(regs));
-       return 0;
- }
-@@ -217,10 +214,8 @@ wed_rxinfo_show(struct seq_file *s, void
-       struct mtk_wed_hw *hw = s->private;
-       struct mtk_wed_device *dev = hw->wed_dev;
--      if (!dev)
--              return 0;
--
--      dump_wed_regs(s, dev, regs, ARRAY_SIZE(regs));
-+      if (dev)
-+              dump_wed_regs(s, dev, regs, ARRAY_SIZE(regs));
-       return 0;
- }
diff --git a/target/linux/generic/backport-5.15/752-03-v6.6-net-ethernet-mtk_eth_soc-rely-on-mtk_pse_port-defini.patch b/target/linux/generic/backport-5.15/752-03-v6.6-net-ethernet-mtk_eth_soc-rely-on-mtk_pse_port-defini.patch
deleted file mode 100644 (file)
index 0bf9dea..0000000
+++ /dev/null
@@ -1,29 +0,0 @@
-From: Lorenzo Bianconi <[email protected]>
-Date: Tue, 12 Sep 2023 10:22:56 +0200
-Subject: [PATCH] net: ethernet: mtk_eth_soc: rely on mtk_pse_port definitions
- in mtk_flow_set_output_device
-
-Similar to ethernet ports, rely on mtk_pse_port definitions for
-pse wdma ports as well.
-
-Signed-off-by: Lorenzo Bianconi <[email protected]>
-Reviewed-by: Simon Horman <[email protected]>
-Link: https://lore.kernel.org/r/b86bdb717e963e3246c1dec5f736c810703cf056.1694506814.git.lorenzo@kernel.org
-Signed-off-by: Paolo Abeni <[email protected]>
----
-
---- a/drivers/net/ethernet/mediatek/mtk_ppe_offload.c
-+++ b/drivers/net/ethernet/mediatek/mtk_ppe_offload.c
-@@ -196,10 +196,10 @@ mtk_flow_set_output_device(struct mtk_et
-               if (mtk_is_netsys_v2_or_greater(eth)) {
-                       switch (info.wdma_idx) {
-                       case 0:
--                              pse_port = 8;
-+                              pse_port = PSE_WDMA0_PORT;
-                               break;
-                       case 1:
--                              pse_port = 9;
-+                              pse_port = PSE_WDMA1_PORT;
-                               break;
-                       default:
-                               return -EINVAL;
diff --git a/target/linux/generic/backport-5.15/752-04-v6.6-net-ethernet-mtk_wed-check-update_wo_rx_stats-in-mtk.patch b/target/linux/generic/backport-5.15/752-04-v6.6-net-ethernet-mtk_wed-check-update_wo_rx_stats-in-mtk.patch
deleted file mode 100644 (file)
index c99e133..0000000
+++ /dev/null
@@ -1,26 +0,0 @@
-From: Lorenzo Bianconi <[email protected]>
-Date: Tue, 12 Sep 2023 10:28:00 +0200
-Subject: [PATCH] net: ethernet: mtk_wed: check update_wo_rx_stats in
- mtk_wed_update_rx_stats()
-
-Check if update_wo_rx_stats function pointer is properly set in
-mtk_wed_update_rx_stats routine before accessing it.
-
-Signed-off-by: Lorenzo Bianconi <[email protected]>
-Reviewed-by: Simon Horman <[email protected]>
-Link: https://lore.kernel.org/r/b0d233386e059bccb59f18f69afb79a7806e5ded.1694507226.git.lorenzo@kernel.org
-Signed-off-by: Paolo Abeni <[email protected]>
----
-
---- a/drivers/net/ethernet/mediatek/mtk_wed_mcu.c
-+++ b/drivers/net/ethernet/mediatek/mtk_wed_mcu.c
-@@ -68,6 +68,9 @@ mtk_wed_update_rx_stats(struct mtk_wed_d
-       struct mtk_wed_wo_rx_stats *stats;
-       int i;
-+      if (!wed->wlan.update_wo_rx_stats)
-+              return;
-+
-       if (count * sizeof(*stats) > skb->len - sizeof(u32))
-               return;
diff --git a/target/linux/generic/backport-5.15/752-05-v6.7-net-ethernet-mtk_wed-do-not-assume-offload-callbacks.patch b/target/linux/generic/backport-5.15/752-05-v6.7-net-ethernet-mtk_wed-do-not-assume-offload-callbacks.patch
deleted file mode 100644 (file)
index cd7fb92..0000000
+++ /dev/null
@@ -1,68 +0,0 @@
-From: Lorenzo Bianconi <[email protected]>
-Date: Wed, 13 Sep 2023 20:42:47 +0200
-Subject: [PATCH] net: ethernet: mtk_wed: do not assume offload callbacks are
- always set
-
-Check if wlan.offload_enable and wlan.offload_disable callbacks are set
-in mtk_wed_flow_add/mtk_wed_flow_remove since mt7996 will not rely
-on them.
-
-Signed-off-by: Lorenzo Bianconi <[email protected]>
-Reviewed-by: Simon Horman <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
-
---- a/drivers/net/ethernet/mediatek/mtk_wed.c
-+++ b/drivers/net/ethernet/mediatek/mtk_wed.c
-@@ -1712,19 +1712,20 @@ mtk_wed_irq_set_mask(struct mtk_wed_devi
- int mtk_wed_flow_add(int index)
- {
-       struct mtk_wed_hw *hw = hw_list[index];
--      int ret;
-+      int ret = 0;
--      if (!hw || !hw->wed_dev)
--              return -ENODEV;
-+      mutex_lock(&hw_lock);
--      if (hw->num_flows) {
--              hw->num_flows++;
--              return 0;
-+      if (!hw || !hw->wed_dev) {
-+              ret = -ENODEV;
-+              goto out;
-       }
--      mutex_lock(&hw_lock);
--      if (!hw->wed_dev) {
--              ret = -ENODEV;
-+      if (!hw->wed_dev->wlan.offload_enable)
-+              goto out;
-+
-+      if (hw->num_flows) {
-+              hw->num_flows++;
-               goto out;
-       }
-@@ -1743,14 +1744,15 @@ void mtk_wed_flow_remove(int index)
- {
-       struct mtk_wed_hw *hw = hw_list[index];
--      if (!hw)
--              return;
-+      mutex_lock(&hw_lock);
--      if (--hw->num_flows)
--              return;
-+      if (!hw || !hw->wed_dev)
-+              goto out;
--      mutex_lock(&hw_lock);
--      if (!hw->wed_dev)
-+      if (!hw->wed_dev->wlan.offload_disable)
-+              goto out;
-+
-+      if (--hw->num_flows)
-               goto out;
-       hw->wed_dev->wlan.offload_disable(hw->wed_dev);
diff --git a/target/linux/generic/backport-5.15/752-06-v6.7-net-ethernet-mtk_wed-introduce-versioning-utility-ro.patch b/target/linux/generic/backport-5.15/752-06-v6.7-net-ethernet-mtk_wed-introduce-versioning-utility-ro.patch
deleted file mode 100644 (file)
index 2948188..0000000
+++ /dev/null
@@ -1,232 +0,0 @@
-From: Lorenzo Bianconi <[email protected]>
-Date: Mon, 18 Sep 2023 12:29:05 +0200
-Subject: [PATCH] net: ethernet: mtk_wed: introduce versioning utility routines
-
-Similar to mtk_eth_soc, introduce the following wed versioning
-utility routines:
-- mtk_wed_is_v1
-- mtk_wed_is_v2
-
-This is a preliminary patch to introduce WED support for MT7988 SoC
-
-Signed-off-by: Lorenzo Bianconi <[email protected]>
-Signed-off-by: Paolo Abeni <[email protected]>
----
-
---- a/drivers/net/ethernet/mediatek/mtk_wed.c
-+++ b/drivers/net/ethernet/mediatek/mtk_wed.c
-@@ -277,7 +277,7 @@ mtk_wed_assign(struct mtk_wed_device *de
-               if (!hw->wed_dev)
-                       goto out;
--              if (hw->version == 1)
-+              if (mtk_wed_is_v1(hw))
-                       return NULL;
-               /* MT7986 WED devices do not have any pcie slot restrictions */
-@@ -358,7 +358,7 @@ mtk_wed_tx_buffer_alloc(struct mtk_wed_d
-                       desc->buf0 = cpu_to_le32(buf_phys);
-                       desc->buf1 = cpu_to_le32(buf_phys + txd_size);
--                      if (dev->hw->version == 1)
-+                      if (mtk_wed_is_v1(dev->hw))
-                               ctrl = FIELD_PREP(MTK_WDMA_DESC_CTRL_LEN0, txd_size) |
-                                      FIELD_PREP(MTK_WDMA_DESC_CTRL_LEN1,
-                                                 MTK_WED_BUF_SIZE - txd_size) |
-@@ -497,7 +497,7 @@ mtk_wed_set_ext_int(struct mtk_wed_devic
- {
-       u32 mask = MTK_WED_EXT_INT_STATUS_ERROR_MASK;
--      if (dev->hw->version == 1)
-+      if (mtk_wed_is_v1(dev->hw))
-               mask |= MTK_WED_EXT_INT_STATUS_TX_DRV_R_RESP_ERR;
-       else
-               mask |= MTK_WED_EXT_INT_STATUS_RX_FBUF_LO_TH |
-@@ -576,7 +576,7 @@ mtk_wed_dma_disable(struct mtk_wed_devic
-                MTK_WDMA_GLO_CFG_RX_INFO1_PRERES |
-                MTK_WDMA_GLO_CFG_RX_INFO2_PRERES);
--      if (dev->hw->version == 1) {
-+      if (mtk_wed_is_v1(dev->hw)) {
-               regmap_write(dev->hw->mirror, dev->hw->index * 4, 0);
-               wdma_clr(dev, MTK_WDMA_GLO_CFG,
-                        MTK_WDMA_GLO_CFG_RX_INFO3_PRERES);
-@@ -605,7 +605,7 @@ mtk_wed_stop(struct mtk_wed_device *dev)
-       wdma_w32(dev, MTK_WDMA_INT_GRP2, 0);
-       wed_w32(dev, MTK_WED_WPDMA_INT_MASK, 0);
--      if (dev->hw->version == 1)
-+      if (mtk_wed_is_v1(dev->hw))
-               return;
-       wed_w32(dev, MTK_WED_EXT_INT_MASK1, 0);
-@@ -624,7 +624,7 @@ mtk_wed_deinit(struct mtk_wed_device *de
-               MTK_WED_CTRL_WED_TX_BM_EN |
-               MTK_WED_CTRL_WED_TX_FREE_AGENT_EN);
--      if (dev->hw->version == 1)
-+      if (mtk_wed_is_v1(dev->hw))
-               return;
-       wed_clr(dev, MTK_WED_CTRL,
-@@ -730,7 +730,7 @@ mtk_wed_bus_init(struct mtk_wed_device *
- static void
- mtk_wed_set_wpdma(struct mtk_wed_device *dev)
- {
--      if (dev->hw->version == 1) {
-+      if (mtk_wed_is_v1(dev->hw)) {
-               wed_w32(dev, MTK_WED_WPDMA_CFG_BASE,  dev->wlan.wpdma_phys);
-       } else {
-               mtk_wed_bus_init(dev);
-@@ -761,7 +761,7 @@ mtk_wed_hw_init_early(struct mtk_wed_dev
-             MTK_WED_WDMA_GLO_CFG_IDLE_DMAD_SUPPLY;
-       wed_m32(dev, MTK_WED_WDMA_GLO_CFG, mask, set);
--      if (dev->hw->version == 1) {
-+      if (mtk_wed_is_v1(dev->hw)) {
-               u32 offset = dev->hw->index ? 0x04000400 : 0;
-               wdma_set(dev, MTK_WDMA_GLO_CFG,
-@@ -934,7 +934,7 @@ mtk_wed_hw_init(struct mtk_wed_device *d
-       wed_w32(dev, MTK_WED_TX_BM_BUF_LEN, MTK_WED_PKT_SIZE);
--      if (dev->hw->version == 1) {
-+      if (mtk_wed_is_v1(dev->hw)) {
-               wed_w32(dev, MTK_WED_TX_BM_TKID,
-                       FIELD_PREP(MTK_WED_TX_BM_TKID_START,
-                                  dev->wlan.token_start) |
-@@ -967,7 +967,7 @@ mtk_wed_hw_init(struct mtk_wed_device *d
-       mtk_wed_reset(dev, MTK_WED_RESET_TX_BM);
--      if (dev->hw->version == 1) {
-+      if (mtk_wed_is_v1(dev->hw)) {
-               wed_set(dev, MTK_WED_CTRL,
-                       MTK_WED_CTRL_WED_TX_BM_EN |
-                       MTK_WED_CTRL_WED_TX_FREE_AGENT_EN);
-@@ -1217,7 +1217,7 @@ mtk_wed_reset_dma(struct mtk_wed_device
-       }
-       dev->init_done = false;
--      if (dev->hw->version == 1)
-+      if (mtk_wed_is_v1(dev->hw))
-               return;
-       if (!busy) {
-@@ -1343,7 +1343,7 @@ mtk_wed_configure_irq(struct mtk_wed_dev
-               MTK_WED_CTRL_WED_TX_BM_EN |
-               MTK_WED_CTRL_WED_TX_FREE_AGENT_EN);
--      if (dev->hw->version == 1) {
-+      if (mtk_wed_is_v1(dev->hw)) {
-               wed_w32(dev, MTK_WED_PCIE_INT_TRIGGER,
-                       MTK_WED_PCIE_INT_TRIGGER_STATUS);
-@@ -1416,7 +1416,7 @@ mtk_wed_dma_enable(struct mtk_wed_device
-                MTK_WDMA_GLO_CFG_RX_INFO1_PRERES |
-                MTK_WDMA_GLO_CFG_RX_INFO2_PRERES);
--      if (dev->hw->version == 1) {
-+      if (mtk_wed_is_v1(dev->hw)) {
-               wdma_set(dev, MTK_WDMA_GLO_CFG,
-                        MTK_WDMA_GLO_CFG_RX_INFO3_PRERES);
-       } else {
-@@ -1465,7 +1465,7 @@ mtk_wed_start(struct mtk_wed_device *dev
-       mtk_wed_set_ext_int(dev, true);
--      if (dev->hw->version == 1) {
-+      if (mtk_wed_is_v1(dev->hw)) {
-               u32 val = dev->wlan.wpdma_phys | MTK_PCIE_MIRROR_MAP_EN |
-                         FIELD_PREP(MTK_PCIE_MIRROR_MAP_WED_ID,
-                                    dev->hw->index);
-@@ -1550,7 +1550,7 @@ mtk_wed_attach(struct mtk_wed_device *de
-       }
-       mtk_wed_hw_init_early(dev);
--      if (hw->version == 1) {
-+      if (mtk_wed_is_v1(hw)) {
-               regmap_update_bits(hw->hifsys, HIFSYS_DMA_AG_MAP,
-                                  BIT(hw->index), 0);
-       } else {
-@@ -1618,7 +1618,7 @@ static int
- mtk_wed_txfree_ring_setup(struct mtk_wed_device *dev, void __iomem *regs)
- {
-       struct mtk_wed_ring *ring = &dev->txfree_ring;
--      int i, index = dev->hw->version == 1;
-+      int i, index = mtk_wed_is_v1(dev->hw);
-       /*
-        * For txfree event handling, the same DMA ring is shared between WED
-@@ -1676,7 +1676,7 @@ mtk_wed_irq_get(struct mtk_wed_device *d
- {
-       u32 val, ext_mask = MTK_WED_EXT_INT_STATUS_ERROR_MASK;
--      if (dev->hw->version == 1)
-+      if (mtk_wed_is_v1(dev->hw))
-               ext_mask |= MTK_WED_EXT_INT_STATUS_TX_DRV_R_RESP_ERR;
-       else
-               ext_mask |= MTK_WED_EXT_INT_STATUS_RX_FBUF_LO_TH |
-@@ -1843,7 +1843,7 @@ mtk_wed_setup_tc(struct mtk_wed_device *
- {
-       struct mtk_wed_hw *hw = wed->hw;
--      if (hw->version < 2)
-+      if (mtk_wed_is_v1(hw))
-               return -EOPNOTSUPP;
-       switch (type) {
-@@ -1917,9 +1917,9 @@ void mtk_wed_add_hw(struct device_node *
-       hw->wdma = wdma;
-       hw->index = index;
-       hw->irq = irq;
--      hw->version = mtk_is_netsys_v1(eth) ? 1 : 2;
-+      hw->version = eth->soc->version;
--      if (hw->version == 1) {
-+      if (mtk_wed_is_v1(hw)) {
-               hw->mirror = syscon_regmap_lookup_by_phandle(eth_np,
-                               "mediatek,pcie-mirror");
-               hw->hifsys = syscon_regmap_lookup_by_phandle(eth_np,
---- a/drivers/net/ethernet/mediatek/mtk_wed.h
-+++ b/drivers/net/ethernet/mediatek/mtk_wed.h
-@@ -40,6 +40,16 @@ struct mtk_wdma_info {
- };
- #ifdef CONFIG_NET_MEDIATEK_SOC_WED
-+static inline bool mtk_wed_is_v1(struct mtk_wed_hw *hw)
-+{
-+      return hw->version == 1;
-+}
-+
-+static inline bool mtk_wed_is_v2(struct mtk_wed_hw *hw)
-+{
-+      return hw->version == 2;
-+}
-+
- static inline void
- wed_w32(struct mtk_wed_device *dev, u32 reg, u32 val)
- {
---- a/drivers/net/ethernet/mediatek/mtk_wed_debugfs.c
-+++ b/drivers/net/ethernet/mediatek/mtk_wed_debugfs.c
-@@ -263,7 +263,7 @@ void mtk_wed_hw_add_debugfs(struct mtk_w
-       debugfs_create_u32("regidx", 0600, dir, &hw->debugfs_reg);
-       debugfs_create_file_unsafe("regval", 0600, dir, hw, &fops_regval);
-       debugfs_create_file_unsafe("txinfo", 0400, dir, hw, &wed_txinfo_fops);
--      if (hw->version != 1)
-+      if (!mtk_wed_is_v1(hw))
-               debugfs_create_file_unsafe("rxinfo", 0400, dir, hw,
-                                          &wed_rxinfo_fops);
- }
---- a/drivers/net/ethernet/mediatek/mtk_wed_mcu.c
-+++ b/drivers/net/ethernet/mediatek/mtk_wed_mcu.c
-@@ -207,7 +207,7 @@ int mtk_wed_mcu_msg_update(struct mtk_we
- {
-       struct mtk_wed_wo *wo = dev->hw->wed_wo;
--      if (dev->hw->version == 1)
-+      if (mtk_wed_is_v1(dev->hw))
-               return 0;
-       if (WARN_ON(!wo))
diff --git a/target/linux/generic/backport-5.15/752-07-v6.7-net-ethernet-mtk_wed-do-not-configure-rx-offload-if-.patch b/target/linux/generic/backport-5.15/752-07-v6.7-net-ethernet-mtk_wed-do-not-configure-rx-offload-if-.patch
deleted file mode 100644 (file)
index bc34aa3..0000000
+++ /dev/null
@@ -1,234 +0,0 @@
-From: Lorenzo Bianconi <[email protected]>
-Date: Mon, 18 Sep 2023 12:29:06 +0200
-Subject: [PATCH] net: ethernet: mtk_wed: do not configure rx offload if not
- supported
-
-Check if rx offload is supported running mtk_wed_get_rx_capa routine
-before configuring it. This is a preliminary patch to introduce Wireless
-Ethernet Dispatcher (WED) support for MT7988 SoC.
-
-Co-developed-by: Sujuan Chen <[email protected]>
-Signed-off-by: Sujuan Chen <[email protected]>
-Signed-off-by: Lorenzo Bianconi <[email protected]>
-Signed-off-by: Paolo Abeni <[email protected]>
----
-
---- a/drivers/net/ethernet/mediatek/mtk_wed.c
-+++ b/drivers/net/ethernet/mediatek/mtk_wed.c
-@@ -605,7 +605,7 @@ mtk_wed_stop(struct mtk_wed_device *dev)
-       wdma_w32(dev, MTK_WDMA_INT_GRP2, 0);
-       wed_w32(dev, MTK_WED_WPDMA_INT_MASK, 0);
--      if (mtk_wed_is_v1(dev->hw))
-+      if (!mtk_wed_get_rx_capa(dev))
-               return;
-       wed_w32(dev, MTK_WED_EXT_INT_MASK1, 0);
-@@ -732,16 +732,21 @@ mtk_wed_set_wpdma(struct mtk_wed_device
- {
-       if (mtk_wed_is_v1(dev->hw)) {
-               wed_w32(dev, MTK_WED_WPDMA_CFG_BASE,  dev->wlan.wpdma_phys);
--      } else {
--              mtk_wed_bus_init(dev);
--
--              wed_w32(dev, MTK_WED_WPDMA_CFG_BASE, dev->wlan.wpdma_int);
--              wed_w32(dev, MTK_WED_WPDMA_CFG_INT_MASK, dev->wlan.wpdma_mask);
--              wed_w32(dev, MTK_WED_WPDMA_CFG_TX, dev->wlan.wpdma_tx);
--              wed_w32(dev, MTK_WED_WPDMA_CFG_TX_FREE, dev->wlan.wpdma_txfree);
--              wed_w32(dev, MTK_WED_WPDMA_RX_GLO_CFG, dev->wlan.wpdma_rx_glo);
--              wed_w32(dev, MTK_WED_WPDMA_RX_RING, dev->wlan.wpdma_rx);
-+              return;
-       }
-+
-+      mtk_wed_bus_init(dev);
-+
-+      wed_w32(dev, MTK_WED_WPDMA_CFG_BASE, dev->wlan.wpdma_int);
-+      wed_w32(dev, MTK_WED_WPDMA_CFG_INT_MASK, dev->wlan.wpdma_mask);
-+      wed_w32(dev, MTK_WED_WPDMA_CFG_TX, dev->wlan.wpdma_tx);
-+      wed_w32(dev, MTK_WED_WPDMA_CFG_TX_FREE, dev->wlan.wpdma_txfree);
-+
-+      if (!mtk_wed_get_rx_capa(dev))
-+              return;
-+
-+      wed_w32(dev, MTK_WED_WPDMA_RX_GLO_CFG, dev->wlan.wpdma_rx_glo);
-+      wed_w32(dev, MTK_WED_WPDMA_RX_RING, dev->wlan.wpdma_rx);
- }
- static void
-@@ -973,15 +978,17 @@ mtk_wed_hw_init(struct mtk_wed_device *d
-                       MTK_WED_CTRL_WED_TX_FREE_AGENT_EN);
-       } else {
-               wed_clr(dev, MTK_WED_TX_TKID_CTRL, MTK_WED_TX_TKID_CTRL_PAUSE);
--              /* rx hw init */
--              wed_w32(dev, MTK_WED_WPDMA_RX_D_RST_IDX,
--                      MTK_WED_WPDMA_RX_D_RST_CRX_IDX |
--                      MTK_WED_WPDMA_RX_D_RST_DRV_IDX);
--              wed_w32(dev, MTK_WED_WPDMA_RX_D_RST_IDX, 0);
--
--              mtk_wed_rx_buffer_hw_init(dev);
--              mtk_wed_rro_hw_init(dev);
--              mtk_wed_route_qm_hw_init(dev);
-+              if (mtk_wed_get_rx_capa(dev)) {
-+                      /* rx hw init */
-+                      wed_w32(dev, MTK_WED_WPDMA_RX_D_RST_IDX,
-+                              MTK_WED_WPDMA_RX_D_RST_CRX_IDX |
-+                              MTK_WED_WPDMA_RX_D_RST_DRV_IDX);
-+                      wed_w32(dev, MTK_WED_WPDMA_RX_D_RST_IDX, 0);
-+
-+                      mtk_wed_rx_buffer_hw_init(dev);
-+                      mtk_wed_rro_hw_init(dev);
-+                      mtk_wed_route_qm_hw_init(dev);
-+              }
-       }
-       wed_clr(dev, MTK_WED_TX_BM_CTRL, MTK_WED_TX_BM_CTRL_PAUSE);
-@@ -1353,8 +1360,6 @@ mtk_wed_configure_irq(struct mtk_wed_dev
-               wed_clr(dev, MTK_WED_WDMA_INT_CTRL, wdma_mask);
-       } else {
--              wdma_mask |= FIELD_PREP(MTK_WDMA_INT_MASK_TX_DONE,
--                                      GENMASK(1, 0));
-               /* initail tx interrupt trigger */
-               wed_w32(dev, MTK_WED_WPDMA_INT_CTRL_TX,
-                       MTK_WED_WPDMA_INT_CTRL_TX0_DONE_EN |
-@@ -1373,15 +1378,20 @@ mtk_wed_configure_irq(struct mtk_wed_dev
-                       FIELD_PREP(MTK_WED_WPDMA_INT_CTRL_TX_FREE_DONE_TRIG,
-                                  dev->wlan.txfree_tbit));
--              wed_w32(dev, MTK_WED_WPDMA_INT_CTRL_RX,
--                      MTK_WED_WPDMA_INT_CTRL_RX0_EN |
--                      MTK_WED_WPDMA_INT_CTRL_RX0_CLR |
--                      MTK_WED_WPDMA_INT_CTRL_RX1_EN |
--                      MTK_WED_WPDMA_INT_CTRL_RX1_CLR |
--                      FIELD_PREP(MTK_WED_WPDMA_INT_CTRL_RX0_DONE_TRIG,
--                                 dev->wlan.rx_tbit[0]) |
--                      FIELD_PREP(MTK_WED_WPDMA_INT_CTRL_RX1_DONE_TRIG,
--                                 dev->wlan.rx_tbit[1]));
-+              if (mtk_wed_get_rx_capa(dev)) {
-+                      wed_w32(dev, MTK_WED_WPDMA_INT_CTRL_RX,
-+                              MTK_WED_WPDMA_INT_CTRL_RX0_EN |
-+                              MTK_WED_WPDMA_INT_CTRL_RX0_CLR |
-+                              MTK_WED_WPDMA_INT_CTRL_RX1_EN |
-+                              MTK_WED_WPDMA_INT_CTRL_RX1_CLR |
-+                              FIELD_PREP(MTK_WED_WPDMA_INT_CTRL_RX0_DONE_TRIG,
-+                                         dev->wlan.rx_tbit[0]) |
-+                              FIELD_PREP(MTK_WED_WPDMA_INT_CTRL_RX1_DONE_TRIG,
-+                                         dev->wlan.rx_tbit[1]));
-+
-+                      wdma_mask |= FIELD_PREP(MTK_WDMA_INT_MASK_TX_DONE,
-+                                              GENMASK(1, 0));
-+              }
-               wed_w32(dev, MTK_WED_WDMA_INT_CLR, wdma_mask);
-               wed_set(dev, MTK_WED_WDMA_INT_CTRL,
-@@ -1400,6 +1410,8 @@ mtk_wed_configure_irq(struct mtk_wed_dev
- static void
- mtk_wed_dma_enable(struct mtk_wed_device *dev)
- {
-+      int i;
-+
-       wed_set(dev, MTK_WED_WPDMA_INT_CTRL, MTK_WED_WPDMA_INT_CTRL_SUBRT_ADV);
-       wed_set(dev, MTK_WED_GLO_CFG,
-@@ -1419,33 +1431,33 @@ mtk_wed_dma_enable(struct mtk_wed_device
-       if (mtk_wed_is_v1(dev->hw)) {
-               wdma_set(dev, MTK_WDMA_GLO_CFG,
-                        MTK_WDMA_GLO_CFG_RX_INFO3_PRERES);
--      } else {
--              int i;
-+              return;
-+      }
--              wed_set(dev, MTK_WED_WPDMA_CTRL,
--                      MTK_WED_WPDMA_CTRL_SDL1_FIXED);
-+      wed_set(dev, MTK_WED_WPDMA_CTRL,
-+              MTK_WED_WPDMA_CTRL_SDL1_FIXED);
-+      wed_set(dev, MTK_WED_WPDMA_GLO_CFG,
-+              MTK_WED_WPDMA_GLO_CFG_RX_DRV_R0_PKT_PROC |
-+              MTK_WED_WPDMA_GLO_CFG_RX_DRV_R0_CRX_SYNC);
-+      wed_clr(dev, MTK_WED_WPDMA_GLO_CFG,
-+              MTK_WED_WPDMA_GLO_CFG_TX_TKID_KEEP |
-+              MTK_WED_WPDMA_GLO_CFG_TX_DMAD_DW3_PREV);
--              wed_set(dev, MTK_WED_WDMA_GLO_CFG,
--                      MTK_WED_WDMA_GLO_CFG_TX_DRV_EN |
--                      MTK_WED_WDMA_GLO_CFG_TX_DDONE_CHK);
-+      if (!mtk_wed_get_rx_capa(dev))
-+              return;
--              wed_set(dev, MTK_WED_WPDMA_GLO_CFG,
--                      MTK_WED_WPDMA_GLO_CFG_RX_DRV_R0_PKT_PROC |
--                      MTK_WED_WPDMA_GLO_CFG_RX_DRV_R0_CRX_SYNC);
--
--              wed_clr(dev, MTK_WED_WPDMA_GLO_CFG,
--                      MTK_WED_WPDMA_GLO_CFG_TX_TKID_KEEP |
--                      MTK_WED_WPDMA_GLO_CFG_TX_DMAD_DW3_PREV);
-+      wed_set(dev, MTK_WED_WDMA_GLO_CFG,
-+              MTK_WED_WDMA_GLO_CFG_TX_DRV_EN |
-+              MTK_WED_WDMA_GLO_CFG_TX_DDONE_CHK);
--              wed_set(dev, MTK_WED_WPDMA_RX_D_GLO_CFG,
--                      MTK_WED_WPDMA_RX_D_RX_DRV_EN |
--                      FIELD_PREP(MTK_WED_WPDMA_RX_D_RXD_READ_LEN, 0x18) |
--                      FIELD_PREP(MTK_WED_WPDMA_RX_D_INIT_PHASE_RXEN_SEL,
--                                 0x2));
-+      wed_set(dev, MTK_WED_WPDMA_RX_D_GLO_CFG,
-+              MTK_WED_WPDMA_RX_D_RX_DRV_EN |
-+              FIELD_PREP(MTK_WED_WPDMA_RX_D_RXD_READ_LEN, 0x18) |
-+              FIELD_PREP(MTK_WED_WPDMA_RX_D_INIT_PHASE_RXEN_SEL,
-+                         0x2));
--              for (i = 0; i < MTK_WED_RX_QUEUES; i++)
--                      mtk_wed_check_wfdma_rx_fill(dev, i);
--      }
-+      for (i = 0; i < MTK_WED_RX_QUEUES; i++)
-+              mtk_wed_check_wfdma_rx_fill(dev, i);
- }
- static void
-@@ -1472,7 +1484,7 @@ mtk_wed_start(struct mtk_wed_device *dev
-               val |= BIT(0) | (BIT(1) * !!dev->hw->index);
-               regmap_write(dev->hw->mirror, dev->hw->index * 4, val);
--      } else {
-+      } else if (mtk_wed_get_rx_capa(dev)) {
-               /* driver set mid ready and only once */
-               wed_w32(dev, MTK_WED_EXT_INT_MASK1,
-                       MTK_WED_EXT_INT_STATUS_WPDMA_MID_RDY);
-@@ -1484,7 +1496,6 @@ mtk_wed_start(struct mtk_wed_device *dev
-               if (mtk_wed_rro_cfg(dev))
-                       return;
--
-       }
-       mtk_wed_set_512_support(dev, dev->wlan.wcid_512);
-@@ -1550,13 +1561,14 @@ mtk_wed_attach(struct mtk_wed_device *de
-       }
-       mtk_wed_hw_init_early(dev);
--      if (mtk_wed_is_v1(hw)) {
-+      if (mtk_wed_is_v1(hw))
-               regmap_update_bits(hw->hifsys, HIFSYS_DMA_AG_MAP,
-                                  BIT(hw->index), 0);
--      } else {
-+      else
-               dev->rev_id = wed_r32(dev, MTK_WED_REV_ID);
-+
-+      if (mtk_wed_get_rx_capa(dev))
-               ret = mtk_wed_wo_init(hw);
--      }
- out:
-       if (ret) {
-               dev_err(dev->hw->dev, "failed to attach wed device\n");
---- a/drivers/net/ethernet/mediatek/mtk_wed_mcu.c
-+++ b/drivers/net/ethernet/mediatek/mtk_wed_mcu.c
-@@ -207,7 +207,7 @@ int mtk_wed_mcu_msg_update(struct mtk_we
- {
-       struct mtk_wed_wo *wo = dev->hw->wed_wo;
--      if (mtk_wed_is_v1(dev->hw))
-+      if (!mtk_wed_get_rx_capa(dev))
-               return 0;
-       if (WARN_ON(!wo))
diff --git a/target/linux/generic/backport-5.15/752-08-v6.7-net-ethernet-mtk_wed-rename-mtk_rxbm_desc-in-mtk_wed.patch b/target/linux/generic/backport-5.15/752-08-v6.7-net-ethernet-mtk_wed-rename-mtk_rxbm_desc-in-mtk_wed.patch
deleted file mode 100644 (file)
index d83434f..0000000
+++ /dev/null
@@ -1,52 +0,0 @@
-From: Lorenzo Bianconi <[email protected]>
-Date: Mon, 18 Sep 2023 12:29:07 +0200
-Subject: [PATCH] net: ethernet: mtk_wed: rename mtk_rxbm_desc in
- mtk_wed_bm_desc
-
-Rename mtk_rxbm_desc structure in mtk_wed_bm_desc since it will be used
-even on tx side by MT7988 SoC.
-
-Signed-off-by: Lorenzo Bianconi <[email protected]>
-Signed-off-by: Paolo Abeni <[email protected]>
----
-
---- a/drivers/net/ethernet/mediatek/mtk_wed.c
-+++ b/drivers/net/ethernet/mediatek/mtk_wed.c
-@@ -421,7 +421,7 @@ free_pagelist:
- static int
- mtk_wed_rx_buffer_alloc(struct mtk_wed_device *dev)
- {
--      struct mtk_rxbm_desc *desc;
-+      struct mtk_wed_bm_desc *desc;
-       dma_addr_t desc_phys;
-       dev->rx_buf_ring.size = dev->wlan.rx_nbuf;
-@@ -441,7 +441,7 @@ mtk_wed_rx_buffer_alloc(struct mtk_wed_d
- static void
- mtk_wed_free_rx_buffer(struct mtk_wed_device *dev)
- {
--      struct mtk_rxbm_desc *desc = dev->rx_buf_ring.desc;
-+      struct mtk_wed_bm_desc *desc = dev->rx_buf_ring.desc;
-       if (!desc)
-               return;
---- a/include/linux/soc/mediatek/mtk_wed.h
-+++ b/include/linux/soc/mediatek/mtk_wed.h
-@@ -45,7 +45,7 @@ enum mtk_wed_wo_cmd {
-       MTK_WED_WO_CMD_WED_END
- };
--struct mtk_rxbm_desc {
-+struct mtk_wed_bm_desc {
-       __le32 buf0;
-       __le32 token;
- } __packed __aligned(4);
-@@ -105,7 +105,7 @@ struct mtk_wed_device {
-       struct {
-               int size;
-               struct page_frag_cache rx_page;
--              struct mtk_rxbm_desc *desc;
-+              struct mtk_wed_bm_desc *desc;
-               dma_addr_t desc_phys;
-       } rx_buf_ring;
diff --git a/target/linux/generic/backport-5.15/752-09-v6.7-net-ethernet-mtk_wed-introduce-mtk_wed_buf-structure.patch b/target/linux/generic/backport-5.15/752-09-v6.7-net-ethernet-mtk_wed-introduce-mtk_wed_buf-structure.patch
deleted file mode 100644 (file)
index 8000a87..0000000
+++ /dev/null
@@ -1,87 +0,0 @@
-From: Lorenzo Bianconi <[email protected]>
-Date: Mon, 18 Sep 2023 12:29:08 +0200
-Subject: [PATCH] net: ethernet: mtk_wed: introduce mtk_wed_buf structure
-
-Introduce mtk_wed_buf structure to store both virtual and physical
-addresses allocated in mtk_wed_tx_buffer_alloc() routine. This is a
-preliminary patch to add WED support for MT7988 SoC since it relies on a
-different dma descriptor layout not storing page dma addresses.
-
-Co-developed-by: Sujuan Chen <[email protected]>
-Signed-off-by: Sujuan Chen <[email protected]>
-Signed-off-by: Lorenzo Bianconi <[email protected]>
-Signed-off-by: Paolo Abeni <[email protected]>
----
-
---- a/drivers/net/ethernet/mediatek/mtk_wed.c
-+++ b/drivers/net/ethernet/mediatek/mtk_wed.c
-@@ -299,9 +299,9 @@ out:
- static int
- mtk_wed_tx_buffer_alloc(struct mtk_wed_device *dev)
- {
-+      struct mtk_wed_buf *page_list;
-       struct mtk_wdma_desc *desc;
-       dma_addr_t desc_phys;
--      void **page_list;
-       int token = dev->wlan.token_start;
-       int ring_size;
-       int n_pages;
-@@ -342,7 +342,8 @@ mtk_wed_tx_buffer_alloc(struct mtk_wed_d
-                       return -ENOMEM;
-               }
--              page_list[page_idx++] = page;
-+              page_list[page_idx].p = page;
-+              page_list[page_idx++].phy_addr = page_phys;
-               dma_sync_single_for_cpu(dev->hw->dev, page_phys, PAGE_SIZE,
-                                       DMA_BIDIRECTIONAL);
-@@ -386,8 +387,8 @@ mtk_wed_tx_buffer_alloc(struct mtk_wed_d
- static void
- mtk_wed_free_tx_buffer(struct mtk_wed_device *dev)
- {
-+      struct mtk_wed_buf *page_list = dev->tx_buf_ring.pages;
-       struct mtk_wdma_desc *desc = dev->tx_buf_ring.desc;
--      void **page_list = dev->tx_buf_ring.pages;
-       int page_idx;
-       int i;
-@@ -399,13 +400,12 @@ mtk_wed_free_tx_buffer(struct mtk_wed_de
-       for (i = 0, page_idx = 0; i < dev->tx_buf_ring.size;
-            i += MTK_WED_BUF_PER_PAGE) {
--              void *page = page_list[page_idx++];
--              dma_addr_t buf_addr;
-+              dma_addr_t buf_addr = page_list[page_idx].phy_addr;
-+              void *page = page_list[page_idx++].p;
-               if (!page)
-                       break;
--              buf_addr = le32_to_cpu(desc[i].buf0);
-               dma_unmap_page(dev->hw->dev, buf_addr, PAGE_SIZE,
-                              DMA_BIDIRECTIONAL);
-               __free_page(page);
---- a/include/linux/soc/mediatek/mtk_wed.h
-+++ b/include/linux/soc/mediatek/mtk_wed.h
-@@ -76,6 +76,11 @@ struct mtk_wed_wo_rx_stats {
-       __le32 rx_drop_cnt;
- };
-+struct mtk_wed_buf {
-+      void *p;
-+      dma_addr_t phy_addr;
-+};
-+
- struct mtk_wed_device {
- #ifdef CONFIG_NET_MEDIATEK_SOC_WED
-       const struct mtk_wed_ops *ops;
-@@ -97,7 +102,7 @@ struct mtk_wed_device {
-       struct {
-               int size;
--              void **pages;
-+              struct mtk_wed_buf *pages;
-               struct mtk_wdma_desc *desc;
-               dma_addr_t desc_phys;
-       } tx_buf_ring;
diff --git a/target/linux/generic/backport-5.15/752-10-v6.7-net-ethernet-mtk_wed-move-mem_region-array-out-of-mt.patch b/target/linux/generic/backport-5.15/752-10-v6.7-net-ethernet-mtk_wed-move-mem_region-array-out-of-mt.patch
deleted file mode 100644 (file)
index 98d782b..0000000
+++ /dev/null
@@ -1,88 +0,0 @@
-From: Lorenzo Bianconi <[email protected]>
-Date: Mon, 18 Sep 2023 12:29:09 +0200
-Subject: [PATCH] net: ethernet: mtk_wed: move mem_region array out of
- mtk_wed_mcu_load_firmware
-
-Remove mtk_wed_wo_memory_region boot structure in mtk_wed_wo.
-This is a preliminary patch to introduce WED support for MT7988 SoC.
-
-Signed-off-by: Lorenzo Bianconi <[email protected]>
-Signed-off-by: Paolo Abeni <[email protected]>
----
-
---- a/drivers/net/ethernet/mediatek/mtk_wed_mcu.c
-+++ b/drivers/net/ethernet/mediatek/mtk_wed_mcu.c
-@@ -16,14 +16,30 @@
- #include "mtk_wed_wo.h"
- #include "mtk_wed.h"
-+static struct mtk_wed_wo_memory_region mem_region[] = {
-+      [MTK_WED_WO_REGION_EMI] = {
-+              .name = "wo-emi",
-+      },
-+      [MTK_WED_WO_REGION_ILM] = {
-+              .name = "wo-ilm",
-+      },
-+      [MTK_WED_WO_REGION_DATA] = {
-+              .name = "wo-data",
-+              .shared = true,
-+      },
-+      [MTK_WED_WO_REGION_BOOT] = {
-+              .name = "wo-boot",
-+      },
-+};
-+
- static u32 wo_r32(struct mtk_wed_wo *wo, u32 reg)
- {
--      return readl(wo->boot.addr + reg);
-+      return readl(mem_region[MTK_WED_WO_REGION_BOOT].addr + reg);
- }
- static void wo_w32(struct mtk_wed_wo *wo, u32 reg, u32 val)
- {
--      writel(val, wo->boot.addr + reg);
-+      writel(val, mem_region[MTK_WED_WO_REGION_BOOT].addr + reg);
- }
- static struct sk_buff *
-@@ -294,18 +310,6 @@ next:
- static int
- mtk_wed_mcu_load_firmware(struct mtk_wed_wo *wo)
- {
--      static struct mtk_wed_wo_memory_region mem_region[] = {
--              [MTK_WED_WO_REGION_EMI] = {
--                      .name = "wo-emi",
--              },
--              [MTK_WED_WO_REGION_ILM] = {
--                      .name = "wo-ilm",
--              },
--              [MTK_WED_WO_REGION_DATA] = {
--                      .name = "wo-data",
--                      .shared = true,
--              },
--      };
-       const struct mtk_wed_fw_trailer *trailer;
-       const struct firmware *fw;
-       const char *fw_name;
-@@ -319,11 +323,6 @@ mtk_wed_mcu_load_firmware(struct mtk_wed
-                       return ret;
-       }
--      wo->boot.name = "wo-boot";
--      ret = mtk_wed_get_memory_region(wo, &wo->boot);
--      if (ret)
--              return ret;
--
-       /* set dummy cr */
-       wed_w32(wo->hw->wed_dev, MTK_WED_SCR0 + 4 * MTK_WED_DUMMY_CR_FWDL,
-               wo->hw->index + 1);
---- a/drivers/net/ethernet/mediatek/mtk_wed_wo.h
-+++ b/drivers/net/ethernet/mediatek/mtk_wed_wo.h
-@@ -228,7 +228,6 @@ struct mtk_wed_wo_queue {
- struct mtk_wed_wo {
-       struct mtk_wed_hw *hw;
--      struct mtk_wed_wo_memory_region boot;
-       struct mtk_wed_wo_queue q_tx;
-       struct mtk_wed_wo_queue q_rx;
diff --git a/target/linux/generic/backport-5.15/752-11-v6.7-net-ethernet-mtk_wed-make-memory-region-optional.patch b/target/linux/generic/backport-5.15/752-11-v6.7-net-ethernet-mtk_wed-make-memory-region-optional.patch
deleted file mode 100644 (file)
index 48b0d02..0000000
+++ /dev/null
@@ -1,71 +0,0 @@
-From: Lorenzo Bianconi <[email protected]>
-Date: Mon, 18 Sep 2023 12:29:10 +0200
-Subject: [PATCH] net: ethernet: mtk_wed: make memory region optional
-
-Make mtk_wed_wo_memory_region optionals.
-This is a preliminary patch to introduce Wireless Ethernet Dispatcher
-support for MT7988 SoC since MT7988 WED fw image will have a different
-layout.
-
-Signed-off-by: Lorenzo Bianconi <[email protected]>
-Signed-off-by: Paolo Abeni <[email protected]>
----
-
---- a/drivers/net/ethernet/mediatek/mtk_wed_mcu.c
-+++ b/drivers/net/ethernet/mediatek/mtk_wed_mcu.c
-@@ -234,19 +234,13 @@ int mtk_wed_mcu_msg_update(struct mtk_we
- }
- static int
--mtk_wed_get_memory_region(struct mtk_wed_wo *wo,
-+mtk_wed_get_memory_region(struct mtk_wed_hw *hw, int index,
-                         struct mtk_wed_wo_memory_region *region)
- {
-       struct reserved_mem *rmem;
-       struct device_node *np;
--      int index;
--      index = of_property_match_string(wo->hw->node, "memory-region-names",
--                                       region->name);
--      if (index < 0)
--              return index;
--
--      np = of_parse_phandle(wo->hw->node, "memory-region", index);
-+      np = of_parse_phandle(hw->node, "memory-region", index);
-       if (!np)
-               return -ENODEV;
-@@ -258,7 +252,7 @@ mtk_wed_get_memory_region(struct mtk_wed
-       region->phy_addr = rmem->base;
-       region->size = rmem->size;
--      region->addr = devm_ioremap(wo->hw->dev, region->phy_addr, region->size);
-+      region->addr = devm_ioremap(hw->dev, region->phy_addr, region->size);
-       return !region->addr ? -EINVAL : 0;
- }
-@@ -271,6 +265,9 @@ mtk_wed_mcu_run_firmware(struct mtk_wed_
-       const struct mtk_wed_fw_trailer *trailer;
-       const struct mtk_wed_fw_region *fw_region;
-+      if (!region->phy_addr || !region->size)
-+              return 0;
-+
-       trailer_ptr = fw->data + fw->size - sizeof(*trailer);
-       trailer = (const struct mtk_wed_fw_trailer *)trailer_ptr;
-       region_ptr = trailer_ptr - trailer->num_region * sizeof(*fw_region);
-@@ -318,7 +315,13 @@ mtk_wed_mcu_load_firmware(struct mtk_wed
-       /* load firmware region metadata */
-       for (i = 0; i < ARRAY_SIZE(mem_region); i++) {
--              ret = mtk_wed_get_memory_region(wo, &mem_region[i]);
-+              int index = of_property_match_string(wo->hw->node,
-+                                                   "memory-region-names",
-+                                                   mem_region[i].name);
-+              if (index < 0)
-+                      continue;
-+
-+              ret = mtk_wed_get_memory_region(wo->hw, index, &mem_region[i]);
-               if (ret)
-                       return ret;
-       }
diff --git a/target/linux/generic/backport-5.15/752-12-v6.7-net-ethernet-mtk_wed-fix-EXT_INT_STATUS_RX_FBUF-defi.patch b/target/linux/generic/backport-5.15/752-12-v6.7-net-ethernet-mtk_wed-fix-EXT_INT_STATUS_RX_FBUF-defi.patch
deleted file mode 100644 (file)
index 878e8fe..0000000
+++ /dev/null
@@ -1,27 +0,0 @@
-From: Lorenzo Bianconi <[email protected]>
-Date: Mon, 18 Sep 2023 12:29:11 +0200
-Subject: [PATCH] net: ethernet: mtk_wed: fix EXT_INT_STATUS_RX_FBUF
- definitions for MT7986 SoC
-
-Fix MTK_WED_EXT_INT_STATUS_RX_FBUF_LO_TH and
-MTK_WED_EXT_INT_STATUS_RX_FBUF_HI_TH definitions for MT7986 (MT7986 is
-the only SoC to use them).
-
-Fixes: de84a090d99a ("net: ethernet: mtk_eth_wed: add wed support for mt7986 chipset")
-Signed-off-by: Lorenzo Bianconi <[email protected]>
-Signed-off-by: Paolo Abeni <[email protected]>
----
-
---- a/drivers/net/ethernet/mediatek/mtk_wed_regs.h
-+++ b/drivers/net/ethernet/mediatek/mtk_wed_regs.h
-@@ -64,8 +64,8 @@ struct mtk_wdma_desc {
- #define MTK_WED_EXT_INT_STATUS_TKID_TITO_INVALID      BIT(4)
- #define MTK_WED_EXT_INT_STATUS_TX_FBUF_LO_TH          BIT(8)
- #define MTK_WED_EXT_INT_STATUS_TX_FBUF_HI_TH          BIT(9)
--#define MTK_WED_EXT_INT_STATUS_RX_FBUF_LO_TH          BIT(12)
--#define MTK_WED_EXT_INT_STATUS_RX_FBUF_HI_TH          BIT(13)
-+#define MTK_WED_EXT_INT_STATUS_RX_FBUF_LO_TH          BIT(10) /* wed v2 */
-+#define MTK_WED_EXT_INT_STATUS_RX_FBUF_HI_TH          BIT(11) /* wed v2 */
- #define MTK_WED_EXT_INT_STATUS_RX_DRV_R_RESP_ERR      BIT(16)
- #define MTK_WED_EXT_INT_STATUS_RX_DRV_W_RESP_ERR      BIT(17)
- #define MTK_WED_EXT_INT_STATUS_RX_DRV_COHERENT                BIT(18)
diff --git a/target/linux/generic/backport-5.15/752-13-v6.7-net-ethernet-mtk_wed-add-mtk_wed_soc_data-structure.patch b/target/linux/generic/backport-5.15/752-13-v6.7-net-ethernet-mtk_wed-add-mtk_wed_soc_data-structure.patch
deleted file mode 100644 (file)
index c43114f..0000000
+++ /dev/null
@@ -1,217 +0,0 @@
-From: Lorenzo Bianconi <[email protected]>
-Date: Mon, 18 Sep 2023 12:29:12 +0200
-Subject: [PATCH] net: ethernet: mtk_wed: add mtk_wed_soc_data structure
-
-Introduce mtk_wed_soc_data utility structure to contain per-SoC
-definitions.
-
-Signed-off-by: Lorenzo Bianconi <[email protected]>
-Signed-off-by: Paolo Abeni <[email protected]>
----
-
---- a/drivers/net/ethernet/mediatek/mtk_wed.c
-+++ b/drivers/net/ethernet/mediatek/mtk_wed.c
-@@ -48,6 +48,26 @@ struct mtk_wed_flow_block_priv {
-       struct net_device *dev;
- };
-+static const struct mtk_wed_soc_data mt7622_data = {
-+      .regmap = {
-+              .tx_bm_tkid             = 0x088,
-+              .wpdma_rx_ring0         = 0x770,
-+              .reset_idx_tx_mask      = GENMASK(3, 0),
-+              .reset_idx_rx_mask      = GENMASK(17, 16),
-+      },
-+      .wdma_desc_size = sizeof(struct mtk_wdma_desc),
-+};
-+
-+static const struct mtk_wed_soc_data mt7986_data = {
-+      .regmap = {
-+              .tx_bm_tkid             = 0x0c8,
-+              .wpdma_rx_ring0         = 0x770,
-+              .reset_idx_tx_mask      = GENMASK(1, 0),
-+              .reset_idx_rx_mask      = GENMASK(7, 6),
-+      },
-+      .wdma_desc_size = 2 * sizeof(struct mtk_wdma_desc),
-+};
-+
- static void
- wed_m32(struct mtk_wed_device *dev, u32 reg, u32 mask, u32 val)
- {
-@@ -746,7 +766,7 @@ mtk_wed_set_wpdma(struct mtk_wed_device
-               return;
-       wed_w32(dev, MTK_WED_WPDMA_RX_GLO_CFG, dev->wlan.wpdma_rx_glo);
--      wed_w32(dev, MTK_WED_WPDMA_RX_RING, dev->wlan.wpdma_rx);
-+      wed_w32(dev, dev->hw->soc->regmap.wpdma_rx_ring0, dev->wlan.wpdma_rx);
- }
- static void
-@@ -940,22 +960,10 @@ mtk_wed_hw_init(struct mtk_wed_device *d
-       wed_w32(dev, MTK_WED_TX_BM_BUF_LEN, MTK_WED_PKT_SIZE);
-       if (mtk_wed_is_v1(dev->hw)) {
--              wed_w32(dev, MTK_WED_TX_BM_TKID,
--                      FIELD_PREP(MTK_WED_TX_BM_TKID_START,
--                                 dev->wlan.token_start) |
--                      FIELD_PREP(MTK_WED_TX_BM_TKID_END,
--                                 dev->wlan.token_start +
--                                 dev->wlan.nbuf - 1));
-               wed_w32(dev, MTK_WED_TX_BM_DYN_THR,
-                       FIELD_PREP(MTK_WED_TX_BM_DYN_THR_LO, 1) |
-                       MTK_WED_TX_BM_DYN_THR_HI);
-       } else {
--              wed_w32(dev, MTK_WED_TX_BM_TKID_V2,
--                      FIELD_PREP(MTK_WED_TX_BM_TKID_START,
--                                 dev->wlan.token_start) |
--                      FIELD_PREP(MTK_WED_TX_BM_TKID_END,
--                                 dev->wlan.token_start +
--                                 dev->wlan.nbuf - 1));
-               wed_w32(dev, MTK_WED_TX_BM_DYN_THR,
-                       FIELD_PREP(MTK_WED_TX_BM_DYN_THR_LO_V2, 0) |
-                       MTK_WED_TX_BM_DYN_THR_HI_V2);
-@@ -970,6 +978,11 @@ mtk_wed_hw_init(struct mtk_wed_device *d
-                       MTK_WED_TX_TKID_DYN_THR_HI);
-       }
-+      wed_w32(dev, dev->hw->soc->regmap.tx_bm_tkid,
-+              FIELD_PREP(MTK_WED_TX_BM_TKID_START, dev->wlan.token_start) |
-+              FIELD_PREP(MTK_WED_TX_BM_TKID_END,
-+                         dev->wlan.token_start + dev->wlan.nbuf - 1));
-+
-       mtk_wed_reset(dev, MTK_WED_RESET_TX_BM);
-       if (mtk_wed_is_v1(dev->hw)) {
-@@ -1104,13 +1117,8 @@ mtk_wed_rx_reset(struct mtk_wed_device *
-       if (ret) {
-               mtk_wed_reset(dev, MTK_WED_RESET_WED_RX_DMA);
-       } else {
--              struct mtk_eth *eth = dev->hw->eth;
--
--              if (mtk_is_netsys_v2_or_greater(eth))
--                      wed_set(dev, MTK_WED_RESET_IDX,
--                              MTK_WED_RESET_IDX_RX_V2);
--              else
--                      wed_set(dev, MTK_WED_RESET_IDX, MTK_WED_RESET_IDX_RX);
-+              wed_set(dev, MTK_WED_RESET_IDX,
-+                      dev->hw->soc->regmap.reset_idx_rx_mask);
-               wed_w32(dev, MTK_WED_RESET_IDX, 0);
-       }
-@@ -1163,7 +1171,8 @@ mtk_wed_reset_dma(struct mtk_wed_device
-       if (busy) {
-               mtk_wed_reset(dev, MTK_WED_RESET_WED_TX_DMA);
-       } else {
--              wed_w32(dev, MTK_WED_RESET_IDX, MTK_WED_RESET_IDX_TX);
-+              wed_w32(dev, MTK_WED_RESET_IDX,
-+                      dev->hw->soc->regmap.reset_idx_tx_mask);
-               wed_w32(dev, MTK_WED_RESET_IDX, 0);
-       }
-@@ -1255,7 +1264,6 @@ static int
- mtk_wed_wdma_rx_ring_setup(struct mtk_wed_device *dev, int idx, int size,
-                          bool reset)
- {
--      u32 desc_size = sizeof(struct mtk_wdma_desc) * dev->hw->version;
-       struct mtk_wed_ring *wdma;
-       if (idx >= ARRAY_SIZE(dev->rx_wdma))
-@@ -1263,7 +1271,7 @@ mtk_wed_wdma_rx_ring_setup(struct mtk_we
-       wdma = &dev->rx_wdma[idx];
-       if (!reset && mtk_wed_ring_alloc(dev, wdma, MTK_WED_WDMA_RING_SIZE,
--                                       desc_size, true))
-+                                       dev->hw->soc->wdma_desc_size, true))
-               return -ENOMEM;
-       wdma_w32(dev, MTK_WDMA_RING_RX(idx) + MTK_WED_RING_OFS_BASE,
-@@ -1284,7 +1292,6 @@ static int
- mtk_wed_wdma_tx_ring_setup(struct mtk_wed_device *dev, int idx, int size,
-                          bool reset)
- {
--      u32 desc_size = sizeof(struct mtk_wdma_desc) * dev->hw->version;
-       struct mtk_wed_ring *wdma;
-       if (idx >= ARRAY_SIZE(dev->tx_wdma))
-@@ -1292,7 +1299,7 @@ mtk_wed_wdma_tx_ring_setup(struct mtk_we
-       wdma = &dev->tx_wdma[idx];
-       if (!reset && mtk_wed_ring_alloc(dev, wdma, MTK_WED_WDMA_RING_SIZE,
--                                       desc_size, true))
-+                                       dev->hw->soc->wdma_desc_size, true))
-               return -ENOMEM;
-       wdma_w32(dev, MTK_WDMA_RING_TX(idx) + MTK_WED_RING_OFS_BASE,
-@@ -1931,7 +1938,12 @@ void mtk_wed_add_hw(struct device_node *
-       hw->irq = irq;
-       hw->version = eth->soc->version;
--      if (mtk_wed_is_v1(hw)) {
-+      switch (hw->version) {
-+      case 2:
-+              hw->soc = &mt7986_data;
-+              break;
-+      default:
-+      case 1:
-               hw->mirror = syscon_regmap_lookup_by_phandle(eth_np,
-                               "mediatek,pcie-mirror");
-               hw->hifsys = syscon_regmap_lookup_by_phandle(eth_np,
-@@ -1945,6 +1957,8 @@ void mtk_wed_add_hw(struct device_node *
-                       regmap_write(hw->mirror, 0, 0);
-                       regmap_write(hw->mirror, 4, 0);
-               }
-+              hw->soc = &mt7622_data;
-+              break;
-       }
-       mtk_wed_hw_add_debugfs(hw);
---- a/drivers/net/ethernet/mediatek/mtk_wed.h
-+++ b/drivers/net/ethernet/mediatek/mtk_wed.h
-@@ -12,7 +12,18 @@
- struct mtk_eth;
- struct mtk_wed_wo;
-+struct mtk_wed_soc_data {
-+      struct {
-+              u32 tx_bm_tkid;
-+              u32 wpdma_rx_ring0;
-+              u32 reset_idx_tx_mask;
-+              u32 reset_idx_rx_mask;
-+      } regmap;
-+      u32 wdma_desc_size;
-+};
-+
- struct mtk_wed_hw {
-+      const struct mtk_wed_soc_data *soc;
-       struct device_node *node;
-       struct mtk_eth *eth;
-       struct regmap *regs;
---- a/drivers/net/ethernet/mediatek/mtk_wed_regs.h
-+++ b/drivers/net/ethernet/mediatek/mtk_wed_regs.h
-@@ -100,8 +100,6 @@ struct mtk_wdma_desc {
- #define MTK_WED_TX_BM_BASE                            0x084
--#define MTK_WED_TX_BM_TKID                            0x088
--#define MTK_WED_TX_BM_TKID_V2                         0x0c8
- #define MTK_WED_TX_BM_TKID_START                      GENMASK(15, 0)
- #define MTK_WED_TX_BM_TKID_END                                GENMASK(31, 16)
-@@ -160,9 +158,6 @@ struct mtk_wdma_desc {
- #define MTK_WED_GLO_CFG_RX_2B_OFFSET                  BIT(31)
- #define MTK_WED_RESET_IDX                             0x20c
--#define MTK_WED_RESET_IDX_TX                          GENMASK(3, 0)
--#define MTK_WED_RESET_IDX_RX                          GENMASK(17, 16)
--#define MTK_WED_RESET_IDX_RX_V2                               GENMASK(7, 6)
- #define MTK_WED_RESET_WPDMA_IDX_RX                    GENMASK(31, 30)
- #define MTK_WED_TX_MIB(_n)                            (0x2a0 + (_n) * 4)
-@@ -286,7 +281,6 @@ struct mtk_wdma_desc {
- #define MTK_WED_WPDMA_RX_D_RST_DRV_IDX                        GENMASK(25, 24)
- #define MTK_WED_WPDMA_RX_GLO_CFG                      0x76c
--#define MTK_WED_WPDMA_RX_RING                         0x770
- #define MTK_WED_WPDMA_RX_D_MIB(_n)                    (0x774 + (_n) * 4)
- #define MTK_WED_WPDMA_RX_D_PROCESSED_MIB(_n)          (0x784 + (_n) * 4)
diff --git a/target/linux/generic/backport-5.15/752-14-v6.7-net-ethernet-mtk_wed-introduce-WED-support-for-MT798.patch b/target/linux/generic/backport-5.15/752-14-v6.7-net-ethernet-mtk_wed-introduce-WED-support-for-MT798.patch
deleted file mode 100644 (file)
index f53b822..0000000
+++ /dev/null
@@ -1,1280 +0,0 @@
-From: Sujuan Chen <[email protected]>
-Date: Mon, 18 Sep 2023 12:29:13 +0200
-Subject: [PATCH] net: ethernet: mtk_wed: introduce WED support for MT7988
-
-Similar to MT7986 and MT7622, enable Wireless Ethernet Ditpatcher for
-MT7988 in order to offload traffic forwarded from LAN/WLAN to WLAN/LAN
-
-Co-developed-by: Lorenzo Bianconi <[email protected]>
-Signed-off-by: Lorenzo Bianconi <[email protected]>
-Signed-off-by: Sujuan Chen <[email protected]>
-Signed-off-by: Paolo Abeni <[email protected]>
----
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-@@ -195,6 +195,7 @@ static const struct mtk_reg_map mt7988_r
-       .wdma_base = {
-               [0]             = 0x4800,
-               [1]             = 0x4c00,
-+              [2]             = 0x5000,
-       },
-       .pse_iq_sta             = 0x0180,
-       .pse_oq_sta             = 0x01a0,
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-@@ -1129,7 +1129,7 @@ struct mtk_reg_map {
-       u32     gdm1_cnt;
-       u32     gdma_to_ppe0;
-       u32     ppe_base;
--      u32     wdma_base[2];
-+      u32     wdma_base[3];
-       u32     pse_iq_sta;
-       u32     pse_oq_sta;
- };
---- a/drivers/net/ethernet/mediatek/mtk_ppe_offload.c
-+++ b/drivers/net/ethernet/mediatek/mtk_ppe_offload.c
-@@ -201,6 +201,9 @@ mtk_flow_set_output_device(struct mtk_et
-                       case 1:
-                               pse_port = PSE_WDMA1_PORT;
-                               break;
-+                      case 2:
-+                              pse_port = PSE_WDMA2_PORT;
-+                              break;
-                       default:
-                               return -EINVAL;
-                       }
---- a/drivers/net/ethernet/mediatek/mtk_wed.c
-+++ b/drivers/net/ethernet/mediatek/mtk_wed.c
-@@ -16,17 +16,19 @@
- #include <net/flow_offload.h>
- #include <net/pkt_cls.h>
- #include "mtk_eth_soc.h"
--#include "mtk_wed_regs.h"
- #include "mtk_wed.h"
- #include "mtk_ppe.h"
- #include "mtk_wed_wo.h"
- #define MTK_PCIE_BASE(n)              (0x1a143000 + (n) * 0x2000)
--#define MTK_WED_PKT_SIZE              1900
-+#define MTK_WED_PKT_SIZE              1920
- #define MTK_WED_BUF_SIZE              2048
-+#define MTK_WED_PAGE_BUF_SIZE         128
- #define MTK_WED_BUF_PER_PAGE          (PAGE_SIZE / 2048)
-+#define MTK_WED_RX_PAGE_BUF_PER_PAGE  (PAGE_SIZE / 128)
- #define MTK_WED_RX_RING_SIZE          1536
-+#define MTK_WED_RX_PG_BM_CNT          8192
- #define MTK_WED_TX_RING_SIZE          2048
- #define MTK_WED_WDMA_RING_SIZE                1024
-@@ -40,7 +42,10 @@
- #define MTK_WED_RRO_QUE_CNT           8192
- #define MTK_WED_MIOD_ENTRY_CNT                128
--static struct mtk_wed_hw *hw_list[2];
-+#define MTK_WED_TX_BM_DMA_SIZE                65536
-+#define MTK_WED_TX_BM_PKT_CNT         32768
-+
-+static struct mtk_wed_hw *hw_list[3];
- static DEFINE_MUTEX(hw_lock);
- struct mtk_wed_flow_block_priv {
-@@ -55,6 +60,7 @@ static const struct mtk_wed_soc_data mt7
-               .reset_idx_tx_mask      = GENMASK(3, 0),
-               .reset_idx_rx_mask      = GENMASK(17, 16),
-       },
-+      .tx_ring_desc_size = sizeof(struct mtk_wdma_desc),
-       .wdma_desc_size = sizeof(struct mtk_wdma_desc),
- };
-@@ -65,6 +71,18 @@ static const struct mtk_wed_soc_data mt7
-               .reset_idx_tx_mask      = GENMASK(1, 0),
-               .reset_idx_rx_mask      = GENMASK(7, 6),
-       },
-+      .tx_ring_desc_size = sizeof(struct mtk_wdma_desc),
-+      .wdma_desc_size = 2 * sizeof(struct mtk_wdma_desc),
-+};
-+
-+static const struct mtk_wed_soc_data mt7988_data = {
-+      .regmap = {
-+              .tx_bm_tkid             = 0x0c8,
-+              .wpdma_rx_ring0         = 0x7d0,
-+              .reset_idx_tx_mask      = GENMASK(1, 0),
-+              .reset_idx_rx_mask      = GENMASK(7, 6),
-+      },
-+      .tx_ring_desc_size = sizeof(struct mtk_wed_bm_desc),
-       .wdma_desc_size = 2 * sizeof(struct mtk_wdma_desc),
- };
-@@ -319,33 +337,38 @@ out:
- static int
- mtk_wed_tx_buffer_alloc(struct mtk_wed_device *dev)
- {
-+      u32 desc_size = dev->hw->soc->tx_ring_desc_size;
-+      int i, page_idx = 0, n_pages, ring_size;
-+      int token = dev->wlan.token_start;
-       struct mtk_wed_buf *page_list;
--      struct mtk_wdma_desc *desc;
-       dma_addr_t desc_phys;
--      int token = dev->wlan.token_start;
--      int ring_size;
--      int n_pages;
--      int i, page_idx;
-+      void *desc_ptr;
--      ring_size = dev->wlan.nbuf & ~(MTK_WED_BUF_PER_PAGE - 1);
--      n_pages = ring_size / MTK_WED_BUF_PER_PAGE;
-+      if (!mtk_wed_is_v3_or_greater(dev->hw)) {
-+              ring_size = dev->wlan.nbuf & ~(MTK_WED_BUF_PER_PAGE - 1);
-+              dev->tx_buf_ring.size = ring_size;
-+      } else {
-+              dev->tx_buf_ring.size = MTK_WED_TX_BM_DMA_SIZE;
-+              ring_size = MTK_WED_TX_BM_PKT_CNT;
-+      }
-+      n_pages = dev->tx_buf_ring.size / MTK_WED_BUF_PER_PAGE;
-       page_list = kcalloc(n_pages, sizeof(*page_list), GFP_KERNEL);
-       if (!page_list)
-               return -ENOMEM;
--      dev->tx_buf_ring.size = ring_size;
-       dev->tx_buf_ring.pages = page_list;
--      desc = dma_alloc_coherent(dev->hw->dev, ring_size * sizeof(*desc),
--                                &desc_phys, GFP_KERNEL);
--      if (!desc)
-+      desc_ptr = dma_alloc_coherent(dev->hw->dev,
-+                                    dev->tx_buf_ring.size * desc_size,
-+                                    &desc_phys, GFP_KERNEL);
-+      if (!desc_ptr)
-               return -ENOMEM;
--      dev->tx_buf_ring.desc = desc;
-+      dev->tx_buf_ring.desc = desc_ptr;
-       dev->tx_buf_ring.desc_phys = desc_phys;
--      for (i = 0, page_idx = 0; i < ring_size; i += MTK_WED_BUF_PER_PAGE) {
-+      for (i = 0; i < ring_size; i += MTK_WED_BUF_PER_PAGE) {
-               dma_addr_t page_phys, buf_phys;
-               struct page *page;
-               void *buf;
-@@ -371,28 +394,31 @@ mtk_wed_tx_buffer_alloc(struct mtk_wed_d
-               buf_phys = page_phys;
-               for (s = 0; s < MTK_WED_BUF_PER_PAGE; s++) {
--                      u32 txd_size;
--                      u32 ctrl;
--
--                      txd_size = dev->wlan.init_buf(buf, buf_phys, token++);
-+                      struct mtk_wdma_desc *desc = desc_ptr;
-                       desc->buf0 = cpu_to_le32(buf_phys);
--                      desc->buf1 = cpu_to_le32(buf_phys + txd_size);
-+                      if (!mtk_wed_is_v3_or_greater(dev->hw)) {
-+                              u32 txd_size, ctrl;
--                      if (mtk_wed_is_v1(dev->hw))
--                              ctrl = FIELD_PREP(MTK_WDMA_DESC_CTRL_LEN0, txd_size) |
--                                     FIELD_PREP(MTK_WDMA_DESC_CTRL_LEN1,
--                                                MTK_WED_BUF_SIZE - txd_size) |
--                                     MTK_WDMA_DESC_CTRL_LAST_SEG1;
--                      else
--                              ctrl = FIELD_PREP(MTK_WDMA_DESC_CTRL_LEN0, txd_size) |
--                                     FIELD_PREP(MTK_WDMA_DESC_CTRL_LEN1_V2,
--                                                MTK_WED_BUF_SIZE - txd_size) |
--                                     MTK_WDMA_DESC_CTRL_LAST_SEG0;
--                      desc->ctrl = cpu_to_le32(ctrl);
--                      desc->info = 0;
--                      desc++;
-+                              txd_size = dev->wlan.init_buf(buf, buf_phys,
-+                                                            token++);
-+                              desc->buf1 = cpu_to_le32(buf_phys + txd_size);
-+                              ctrl = FIELD_PREP(MTK_WDMA_DESC_CTRL_LEN0, txd_size);
-+                              if (mtk_wed_is_v1(dev->hw))
-+                                      ctrl |= MTK_WDMA_DESC_CTRL_LAST_SEG1 |
-+                                              FIELD_PREP(MTK_WDMA_DESC_CTRL_LEN1,
-+                                                         MTK_WED_BUF_SIZE - txd_size);
-+                              else
-+                                      ctrl |= MTK_WDMA_DESC_CTRL_LAST_SEG0 |
-+                                              FIELD_PREP(MTK_WDMA_DESC_CTRL_LEN1_V2,
-+                                                         MTK_WED_BUF_SIZE - txd_size);
-+                              desc->ctrl = cpu_to_le32(ctrl);
-+                              desc->info = 0;
-+                      } else {
-+                              desc->ctrl = cpu_to_le32(token << 16);
-+                      }
-+                      desc_ptr += desc_size;
-                       buf += MTK_WED_BUF_SIZE;
-                       buf_phys += MTK_WED_BUF_SIZE;
-               }
-@@ -408,31 +434,31 @@ static void
- mtk_wed_free_tx_buffer(struct mtk_wed_device *dev)
- {
-       struct mtk_wed_buf *page_list = dev->tx_buf_ring.pages;
--      struct mtk_wdma_desc *desc = dev->tx_buf_ring.desc;
--      int page_idx;
--      int i;
-+      struct mtk_wed_hw *hw = dev->hw;
-+      int i, page_idx = 0;
-       if (!page_list)
-               return;
--      if (!desc)
-+      if (!dev->tx_buf_ring.desc)
-               goto free_pagelist;
--      for (i = 0, page_idx = 0; i < dev->tx_buf_ring.size;
--           i += MTK_WED_BUF_PER_PAGE) {
--              dma_addr_t buf_addr = page_list[page_idx].phy_addr;
-+      for (i = 0; i < dev->tx_buf_ring.size; i += MTK_WED_BUF_PER_PAGE) {
-+              dma_addr_t page_phy = page_list[page_idx].phy_addr;
-               void *page = page_list[page_idx++].p;
-               if (!page)
-                       break;
--              dma_unmap_page(dev->hw->dev, buf_addr, PAGE_SIZE,
-+              dma_unmap_page(dev->hw->dev, page_phy, PAGE_SIZE,
-                              DMA_BIDIRECTIONAL);
-               __free_page(page);
-       }
--      dma_free_coherent(dev->hw->dev, dev->tx_buf_ring.size * sizeof(*desc),
--                        desc, dev->tx_buf_ring.desc_phys);
-+      dma_free_coherent(dev->hw->dev,
-+                        dev->tx_buf_ring.size * hw->soc->tx_ring_desc_size,
-+                        dev->tx_buf_ring.desc,
-+                        dev->tx_buf_ring.desc_phys);
- free_pagelist:
-       kfree(page_list);
-@@ -517,13 +543,23 @@ mtk_wed_set_ext_int(struct mtk_wed_devic
- {
-       u32 mask = MTK_WED_EXT_INT_STATUS_ERROR_MASK;
--      if (mtk_wed_is_v1(dev->hw))
-+      switch (dev->hw->version) {
-+      case 1:
-               mask |= MTK_WED_EXT_INT_STATUS_TX_DRV_R_RESP_ERR;
--      else
-+              break;
-+      case 2:
-               mask |= MTK_WED_EXT_INT_STATUS_RX_FBUF_LO_TH |
-                       MTK_WED_EXT_INT_STATUS_RX_FBUF_HI_TH |
-                       MTK_WED_EXT_INT_STATUS_RX_DRV_COHERENT |
-                       MTK_WED_EXT_INT_STATUS_TX_DMA_W_RESP_ERR;
-+              break;
-+      case 3:
-+              mask = MTK_WED_EXT_INT_STATUS_RX_DRV_COHERENT |
-+                     MTK_WED_EXT_INT_STATUS_TKID_WO_PYLD;
-+              break;
-+      default:
-+              break;
-+      }
-       if (!dev->hw->num_flows)
-               mask &= ~MTK_WED_EXT_INT_STATUS_TKID_WO_PYLD;
-@@ -535,6 +571,9 @@ mtk_wed_set_ext_int(struct mtk_wed_devic
- static void
- mtk_wed_set_512_support(struct mtk_wed_device *dev, bool enable)
- {
-+      if (!mtk_wed_is_v2(dev->hw))
-+              return;
-+
-       if (enable) {
-               wed_w32(dev, MTK_WED_TXDP_CTRL, MTK_WED_TXDP_DW9_OVERWR);
-               wed_w32(dev, MTK_WED_TXP_DW1,
-@@ -609,6 +648,14 @@ mtk_wed_dma_disable(struct mtk_wed_devic
-                       MTK_WED_WPDMA_RX_D_RX_DRV_EN);
-               wed_clr(dev, MTK_WED_WDMA_GLO_CFG,
-                       MTK_WED_WDMA_GLO_CFG_TX_DDONE_CHK);
-+
-+              if (mtk_wed_is_v3_or_greater(dev->hw) &&
-+                  mtk_wed_get_rx_capa(dev)) {
-+                      wdma_clr(dev, MTK_WDMA_PREF_TX_CFG,
-+                               MTK_WDMA_PREF_TX_CFG_PREF_EN);
-+                      wdma_clr(dev, MTK_WDMA_PREF_RX_CFG,
-+                               MTK_WDMA_PREF_RX_CFG_PREF_EN);
-+              }
-       }
-       mtk_wed_set_512_support(dev, false);
-@@ -651,6 +698,14 @@ mtk_wed_deinit(struct mtk_wed_device *de
-               MTK_WED_CTRL_RX_ROUTE_QM_EN |
-               MTK_WED_CTRL_WED_RX_BM_EN |
-               MTK_WED_CTRL_RX_RRO_QM_EN);
-+
-+      if (mtk_wed_is_v3_or_greater(dev->hw)) {
-+              wed_clr(dev, MTK_WED_CTRL, MTK_WED_CTRL_TX_AMSDU_EN);
-+              wed_clr(dev, MTK_WED_RESET, MTK_WED_RESET_TX_AMSDU);
-+              wed_clr(dev, MTK_WED_PCIE_INT_CTRL,
-+                      MTK_WED_PCIE_INT_CTRL_MSK_EN_POLA |
-+                      MTK_WED_PCIE_INT_CTRL_MSK_IRQ_FILTER);
-+      }
- }
- static void
-@@ -700,21 +755,37 @@ mtk_wed_detach(struct mtk_wed_device *de
-       mutex_unlock(&hw_lock);
- }
--#define PCIE_BASE_ADDR0               0x11280000
- static void
- mtk_wed_bus_init(struct mtk_wed_device *dev)
- {
-       switch (dev->wlan.bus_type) {
-       case MTK_WED_BUS_PCIE: {
-               struct device_node *np = dev->hw->eth->dev->of_node;
--              struct regmap *regs;
--              regs = syscon_regmap_lookup_by_phandle(np,
--                                                     "mediatek,wed-pcie");
--              if (IS_ERR(regs))
--                      break;
-+              if (mtk_wed_is_v2(dev->hw)) {
-+                      struct regmap *regs;
-+
-+                      regs = syscon_regmap_lookup_by_phandle(np,
-+                                                             "mediatek,wed-pcie");
-+                      if (IS_ERR(regs))
-+                              break;
--              regmap_update_bits(regs, 0, BIT(0), BIT(0));
-+                      regmap_update_bits(regs, 0, BIT(0), BIT(0));
-+              }
-+
-+              if (dev->wlan.msi) {
-+                      wed_w32(dev, MTK_WED_PCIE_CFG_INTM,
-+                              dev->hw->pcie_base | 0xc08);
-+                      wed_w32(dev, MTK_WED_PCIE_CFG_BASE,
-+                              dev->hw->pcie_base | 0xc04);
-+                      wed_w32(dev, MTK_WED_PCIE_INT_TRIGGER, BIT(8));
-+              } else {
-+                      wed_w32(dev, MTK_WED_PCIE_CFG_INTM,
-+                              dev->hw->pcie_base | 0x180);
-+                      wed_w32(dev, MTK_WED_PCIE_CFG_BASE,
-+                              dev->hw->pcie_base | 0x184);
-+                      wed_w32(dev, MTK_WED_PCIE_INT_TRIGGER, BIT(24));
-+              }
-               wed_w32(dev, MTK_WED_PCIE_INT_CTRL,
-                       FIELD_PREP(MTK_WED_PCIE_INT_CTRL_POLL_EN, 2));
-@@ -722,19 +793,9 @@ mtk_wed_bus_init(struct mtk_wed_device *
-               /* pcie interrupt control: pola/source selection */
-               wed_set(dev, MTK_WED_PCIE_INT_CTRL,
-                       MTK_WED_PCIE_INT_CTRL_MSK_EN_POLA |
--                      FIELD_PREP(MTK_WED_PCIE_INT_CTRL_SRC_SEL, 1));
--              wed_r32(dev, MTK_WED_PCIE_INT_CTRL);
--
--              wed_w32(dev, MTK_WED_PCIE_CFG_INTM, PCIE_BASE_ADDR0 | 0x180);
--              wed_w32(dev, MTK_WED_PCIE_CFG_BASE, PCIE_BASE_ADDR0 | 0x184);
--
--              /* pcie interrupt status trigger register */
--              wed_w32(dev, MTK_WED_PCIE_INT_TRIGGER, BIT(24));
--              wed_r32(dev, MTK_WED_PCIE_INT_TRIGGER);
--
--              /* pola setting */
--              wed_set(dev, MTK_WED_PCIE_INT_CTRL,
--                      MTK_WED_PCIE_INT_CTRL_MSK_EN_POLA);
-+                      MTK_WED_PCIE_INT_CTRL_MSK_IRQ_FILTER  |
-+                      FIELD_PREP(MTK_WED_PCIE_INT_CTRL_SRC_SEL,
-+                                 dev->hw->index));
-               break;
-       }
-       case MTK_WED_BUS_AXI:
-@@ -772,18 +833,19 @@ mtk_wed_set_wpdma(struct mtk_wed_device
- static void
- mtk_wed_hw_init_early(struct mtk_wed_device *dev)
- {
--      u32 mask, set;
-+      u32 set = FIELD_PREP(MTK_WED_WDMA_GLO_CFG_BT_SIZE, 2);
-+      u32 mask = MTK_WED_WDMA_GLO_CFG_BT_SIZE;
-       mtk_wed_deinit(dev);
-       mtk_wed_reset(dev, MTK_WED_RESET_WED);
-       mtk_wed_set_wpdma(dev);
--      mask = MTK_WED_WDMA_GLO_CFG_BT_SIZE |
--             MTK_WED_WDMA_GLO_CFG_DYNAMIC_DMAD_RECYCLE |
--             MTK_WED_WDMA_GLO_CFG_RX_DIS_FSM_AUTO_IDLE;
--      set = FIELD_PREP(MTK_WED_WDMA_GLO_CFG_BT_SIZE, 2) |
--            MTK_WED_WDMA_GLO_CFG_DYNAMIC_SKIP_DMAD_PREP |
--            MTK_WED_WDMA_GLO_CFG_IDLE_DMAD_SUPPLY;
-+      if (!mtk_wed_is_v3_or_greater(dev->hw)) {
-+              mask |= MTK_WED_WDMA_GLO_CFG_DYNAMIC_DMAD_RECYCLE |
-+                      MTK_WED_WDMA_GLO_CFG_RX_DIS_FSM_AUTO_IDLE;
-+              set |= MTK_WED_WDMA_GLO_CFG_DYNAMIC_SKIP_DMAD_PREP |
-+                     MTK_WED_WDMA_GLO_CFG_IDLE_DMAD_SUPPLY;
-+      }
-       wed_m32(dev, MTK_WED_WDMA_GLO_CFG, mask, set);
-       if (mtk_wed_is_v1(dev->hw)) {
-@@ -931,11 +993,18 @@ mtk_wed_route_qm_hw_init(struct mtk_wed_
-       }
-       /* configure RX_ROUTE_QM */
--      wed_clr(dev, MTK_WED_RTQM_GLO_CFG, MTK_WED_RTQM_Q_RST);
--      wed_clr(dev, MTK_WED_RTQM_GLO_CFG, MTK_WED_RTQM_TXDMAD_FPORT);
--      wed_set(dev, MTK_WED_RTQM_GLO_CFG,
--              FIELD_PREP(MTK_WED_RTQM_TXDMAD_FPORT, 0x3 + dev->hw->index));
--      wed_clr(dev, MTK_WED_RTQM_GLO_CFG, MTK_WED_RTQM_Q_RST);
-+      if (mtk_wed_is_v2(dev->hw)) {
-+              wed_clr(dev, MTK_WED_RTQM_GLO_CFG, MTK_WED_RTQM_Q_RST);
-+              wed_clr(dev, MTK_WED_RTQM_GLO_CFG, MTK_WED_RTQM_TXDMAD_FPORT);
-+              wed_set(dev, MTK_WED_RTQM_GLO_CFG,
-+                      FIELD_PREP(MTK_WED_RTQM_TXDMAD_FPORT,
-+                                 0x3 + dev->hw->index));
-+              wed_clr(dev, MTK_WED_RTQM_GLO_CFG, MTK_WED_RTQM_Q_RST);
-+      } else {
-+              wed_set(dev, MTK_WED_RTQM_ENQ_CFG0,
-+                      FIELD_PREP(MTK_WED_RTQM_ENQ_CFG_TXDMAD_FPORT,
-+                                 0x3 + dev->hw->index));
-+      }
-       /* enable RX_ROUTE_QM */
-       wed_set(dev, MTK_WED_CTRL, MTK_WED_CTRL_RX_ROUTE_QM_EN);
- }
-@@ -948,22 +1017,30 @@ mtk_wed_hw_init(struct mtk_wed_device *d
-       dev->init_done = true;
-       mtk_wed_set_ext_int(dev, false);
--      wed_w32(dev, MTK_WED_TX_BM_CTRL,
--              MTK_WED_TX_BM_CTRL_PAUSE |
--              FIELD_PREP(MTK_WED_TX_BM_CTRL_VLD_GRP_NUM,
--                         dev->tx_buf_ring.size / 128) |
--              FIELD_PREP(MTK_WED_TX_BM_CTRL_RSV_GRP_NUM,
--                         MTK_WED_TX_RING_SIZE / 256));
-       wed_w32(dev, MTK_WED_TX_BM_BASE, dev->tx_buf_ring.desc_phys);
--
-       wed_w32(dev, MTK_WED_TX_BM_BUF_LEN, MTK_WED_PKT_SIZE);
-       if (mtk_wed_is_v1(dev->hw)) {
-+              wed_w32(dev, MTK_WED_TX_BM_CTRL,
-+                      MTK_WED_TX_BM_CTRL_PAUSE |
-+                      FIELD_PREP(MTK_WED_TX_BM_CTRL_VLD_GRP_NUM,
-+                                 dev->tx_buf_ring.size / 128) |
-+                      FIELD_PREP(MTK_WED_TX_BM_CTRL_RSV_GRP_NUM,
-+                                 MTK_WED_TX_RING_SIZE / 256));
-               wed_w32(dev, MTK_WED_TX_BM_DYN_THR,
-                       FIELD_PREP(MTK_WED_TX_BM_DYN_THR_LO, 1) |
-                       MTK_WED_TX_BM_DYN_THR_HI);
--      } else {
-+      } else if (mtk_wed_is_v2(dev->hw)) {
-+              wed_w32(dev, MTK_WED_TX_BM_CTRL,
-+                      MTK_WED_TX_BM_CTRL_PAUSE |
-+                      FIELD_PREP(MTK_WED_TX_BM_CTRL_VLD_GRP_NUM,
-+                                 dev->tx_buf_ring.size / 128) |
-+                      FIELD_PREP(MTK_WED_TX_BM_CTRL_RSV_GRP_NUM,
-+                                 MTK_WED_TX_RING_SIZE / 256));
-+              wed_w32(dev, MTK_WED_TX_TKID_DYN_THR,
-+                      FIELD_PREP(MTK_WED_TX_TKID_DYN_THR_LO, 0) |
-+                      MTK_WED_TX_TKID_DYN_THR_HI);
-               wed_w32(dev, MTK_WED_TX_BM_DYN_THR,
-                       FIELD_PREP(MTK_WED_TX_BM_DYN_THR_LO_V2, 0) |
-                       MTK_WED_TX_BM_DYN_THR_HI_V2);
-@@ -973,9 +1050,6 @@ mtk_wed_hw_init(struct mtk_wed_device *d
-                                  dev->tx_buf_ring.size / 128) |
-                       FIELD_PREP(MTK_WED_TX_TKID_CTRL_RSV_GRP_NUM,
-                                  dev->tx_buf_ring.size / 128));
--              wed_w32(dev, MTK_WED_TX_TKID_DYN_THR,
--                      FIELD_PREP(MTK_WED_TX_TKID_DYN_THR_LO, 0) |
--                      MTK_WED_TX_TKID_DYN_THR_HI);
-       }
-       wed_w32(dev, dev->hw->soc->regmap.tx_bm_tkid,
-@@ -985,26 +1059,62 @@ mtk_wed_hw_init(struct mtk_wed_device *d
-       mtk_wed_reset(dev, MTK_WED_RESET_TX_BM);
-+      if (mtk_wed_is_v3_or_greater(dev->hw)) {
-+              /* switch to new bm architecture */
-+              wed_clr(dev, MTK_WED_TX_BM_CTRL,
-+                      MTK_WED_TX_BM_CTRL_LEGACY_EN);
-+
-+              wed_w32(dev, MTK_WED_TX_TKID_CTRL,
-+                      MTK_WED_TX_TKID_CTRL_PAUSE |
-+                      FIELD_PREP(MTK_WED_TX_TKID_CTRL_VLD_GRP_NUM_V3,
-+                                 dev->wlan.nbuf / 128) |
-+                      FIELD_PREP(MTK_WED_TX_TKID_CTRL_RSV_GRP_NUM_V3,
-+                                 dev->wlan.nbuf / 128));
-+              /* return SKBID + SDP back to bm */
-+              wed_set(dev, MTK_WED_TX_TKID_CTRL,
-+                      MTK_WED_TX_TKID_CTRL_FREE_FORMAT);
-+
-+              wed_w32(dev, MTK_WED_TX_BM_INIT_PTR,
-+                      MTK_WED_TX_BM_PKT_CNT |
-+                      MTK_WED_TX_BM_INIT_SW_TAIL_IDX);
-+      }
-+
-       if (mtk_wed_is_v1(dev->hw)) {
-               wed_set(dev, MTK_WED_CTRL,
-                       MTK_WED_CTRL_WED_TX_BM_EN |
-                       MTK_WED_CTRL_WED_TX_FREE_AGENT_EN);
--      } else {
--              wed_clr(dev, MTK_WED_TX_TKID_CTRL, MTK_WED_TX_TKID_CTRL_PAUSE);
--              if (mtk_wed_get_rx_capa(dev)) {
--                      /* rx hw init */
--                      wed_w32(dev, MTK_WED_WPDMA_RX_D_RST_IDX,
--                              MTK_WED_WPDMA_RX_D_RST_CRX_IDX |
--                              MTK_WED_WPDMA_RX_D_RST_DRV_IDX);
--                      wed_w32(dev, MTK_WED_WPDMA_RX_D_RST_IDX, 0);
--
--                      mtk_wed_rx_buffer_hw_init(dev);
--                      mtk_wed_rro_hw_init(dev);
--                      mtk_wed_route_qm_hw_init(dev);
--              }
-+      } else if (mtk_wed_get_rx_capa(dev)) {
-+              /* rx hw init */
-+              wed_w32(dev, MTK_WED_WPDMA_RX_D_RST_IDX,
-+                      MTK_WED_WPDMA_RX_D_RST_CRX_IDX |
-+                      MTK_WED_WPDMA_RX_D_RST_DRV_IDX);
-+              wed_w32(dev, MTK_WED_WPDMA_RX_D_RST_IDX, 0);
-+
-+              /* reset prefetch index of ring */
-+              wed_set(dev, MTK_WED_WPDMA_RX_D_PREF_RX0_SIDX,
-+                      MTK_WED_WPDMA_RX_D_PREF_SIDX_IDX_CLR);
-+              wed_clr(dev, MTK_WED_WPDMA_RX_D_PREF_RX0_SIDX,
-+                      MTK_WED_WPDMA_RX_D_PREF_SIDX_IDX_CLR);
-+
-+              wed_set(dev, MTK_WED_WPDMA_RX_D_PREF_RX1_SIDX,
-+                      MTK_WED_WPDMA_RX_D_PREF_SIDX_IDX_CLR);
-+              wed_clr(dev, MTK_WED_WPDMA_RX_D_PREF_RX1_SIDX,
-+                      MTK_WED_WPDMA_RX_D_PREF_SIDX_IDX_CLR);
-+
-+              /* reset prefetch FIFO of ring */
-+              wed_set(dev, MTK_WED_WPDMA_RX_D_PREF_FIFO_CFG,
-+                      MTK_WED_WPDMA_RX_D_PREF_FIFO_CFG_R0_CLR |
-+                      MTK_WED_WPDMA_RX_D_PREF_FIFO_CFG_R1_CLR);
-+              wed_w32(dev, MTK_WED_WPDMA_RX_D_PREF_FIFO_CFG, 0);
-+
-+              mtk_wed_rx_buffer_hw_init(dev);
-+              mtk_wed_rro_hw_init(dev);
-+              mtk_wed_route_qm_hw_init(dev);
-       }
-       wed_clr(dev, MTK_WED_TX_BM_CTRL, MTK_WED_TX_BM_CTRL_PAUSE);
-+      if (!mtk_wed_is_v1(dev->hw))
-+              wed_clr(dev, MTK_WED_TX_TKID_CTRL, MTK_WED_TX_TKID_CTRL_PAUSE);
- }
- static void
-@@ -1302,6 +1412,24 @@ mtk_wed_wdma_tx_ring_setup(struct mtk_we
-                                        dev->hw->soc->wdma_desc_size, true))
-               return -ENOMEM;
-+      if (mtk_wed_is_v3_or_greater(dev->hw)) {
-+              struct mtk_wdma_desc *desc = wdma->desc;
-+              int i;
-+
-+              for (i = 0; i < MTK_WED_WDMA_RING_SIZE; i++) {
-+                      desc->buf0 = 0;
-+                      desc->ctrl = cpu_to_le32(MTK_WDMA_DESC_CTRL_DMA_DONE);
-+                      desc->buf1 = 0;
-+                      desc->info = cpu_to_le32(MTK_WDMA_TXD0_DESC_INFO_DMA_DONE);
-+                      desc++;
-+                      desc->buf0 = 0;
-+                      desc->ctrl = cpu_to_le32(MTK_WDMA_DESC_CTRL_DMA_DONE);
-+                      desc->buf1 = 0;
-+                      desc->info = cpu_to_le32(MTK_WDMA_TXD1_DESC_INFO_DMA_DONE);
-+                      desc++;
-+              }
-+      }
-+
-       wdma_w32(dev, MTK_WDMA_RING_TX(idx) + MTK_WED_RING_OFS_BASE,
-                wdma->desc_phys);
-       wdma_w32(dev, MTK_WDMA_RING_TX(idx) + MTK_WED_RING_OFS_COUNT,
-@@ -1367,6 +1495,9 @@ mtk_wed_configure_irq(struct mtk_wed_dev
-               wed_clr(dev, MTK_WED_WDMA_INT_CTRL, wdma_mask);
-       } else {
-+              if (mtk_wed_is_v3_or_greater(dev->hw))
-+                      wed_set(dev, MTK_WED_CTRL, MTK_WED_CTRL_TX_TKID_ALI_EN);
-+
-               /* initail tx interrupt trigger */
-               wed_w32(dev, MTK_WED_WPDMA_INT_CTRL_TX,
-                       MTK_WED_WPDMA_INT_CTRL_TX0_DONE_EN |
-@@ -1419,33 +1550,60 @@ mtk_wed_dma_enable(struct mtk_wed_device
- {
-       int i;
--      wed_set(dev, MTK_WED_WPDMA_INT_CTRL, MTK_WED_WPDMA_INT_CTRL_SUBRT_ADV);
-+      if (!mtk_wed_is_v3_or_greater(dev->hw)) {
-+              wed_set(dev, MTK_WED_WPDMA_INT_CTRL,
-+                      MTK_WED_WPDMA_INT_CTRL_SUBRT_ADV);
-+              wed_set(dev, MTK_WED_WPDMA_GLO_CFG,
-+                      MTK_WED_WPDMA_GLO_CFG_TX_DRV_EN |
-+                      MTK_WED_WPDMA_GLO_CFG_RX_DRV_EN);
-+              wdma_set(dev, MTK_WDMA_GLO_CFG,
-+                       MTK_WDMA_GLO_CFG_TX_DMA_EN |
-+                       MTK_WDMA_GLO_CFG_RX_INFO1_PRERES |
-+                       MTK_WDMA_GLO_CFG_RX_INFO2_PRERES);
-+              wed_set(dev, MTK_WED_WPDMA_CTRL, MTK_WED_WPDMA_CTRL_SDL1_FIXED);
-+      } else {
-+              wed_set(dev, MTK_WED_WPDMA_GLO_CFG,
-+                      MTK_WED_WPDMA_GLO_CFG_TX_DRV_EN |
-+                      MTK_WED_WPDMA_GLO_CFG_RX_DRV_EN |
-+                      MTK_WED_WPDMA_GLO_CFG_RX_DDONE2_WR);
-+              wdma_set(dev, MTK_WDMA_GLO_CFG, MTK_WDMA_GLO_CFG_TX_DMA_EN);
-+      }
-       wed_set(dev, MTK_WED_GLO_CFG,
-               MTK_WED_GLO_CFG_TX_DMA_EN |
-               MTK_WED_GLO_CFG_RX_DMA_EN);
--      wed_set(dev, MTK_WED_WPDMA_GLO_CFG,
--              MTK_WED_WPDMA_GLO_CFG_TX_DRV_EN |
--              MTK_WED_WPDMA_GLO_CFG_RX_DRV_EN);
-+
-       wed_set(dev, MTK_WED_WDMA_GLO_CFG,
-               MTK_WED_WDMA_GLO_CFG_RX_DRV_EN);
--      wdma_set(dev, MTK_WDMA_GLO_CFG,
--               MTK_WDMA_GLO_CFG_TX_DMA_EN |
--               MTK_WDMA_GLO_CFG_RX_INFO1_PRERES |
--               MTK_WDMA_GLO_CFG_RX_INFO2_PRERES);
--
-       if (mtk_wed_is_v1(dev->hw)) {
-               wdma_set(dev, MTK_WDMA_GLO_CFG,
-                        MTK_WDMA_GLO_CFG_RX_INFO3_PRERES);
-               return;
-       }
--      wed_set(dev, MTK_WED_WPDMA_CTRL,
--              MTK_WED_WPDMA_CTRL_SDL1_FIXED);
-       wed_set(dev, MTK_WED_WPDMA_GLO_CFG,
-               MTK_WED_WPDMA_GLO_CFG_RX_DRV_R0_PKT_PROC |
-               MTK_WED_WPDMA_GLO_CFG_RX_DRV_R0_CRX_SYNC);
-+
-+      if (mtk_wed_is_v3_or_greater(dev->hw)) {
-+              wed_set(dev, MTK_WED_WDMA_RX_PREF_CFG,
-+                      FIELD_PREP(MTK_WED_WDMA_RX_PREF_BURST_SIZE, 0x10) |
-+                      FIELD_PREP(MTK_WED_WDMA_RX_PREF_LOW_THRES, 0x8));
-+              wed_clr(dev, MTK_WED_WDMA_RX_PREF_CFG,
-+                      MTK_WED_WDMA_RX_PREF_DDONE2_EN);
-+              wed_set(dev, MTK_WED_WDMA_RX_PREF_CFG, MTK_WED_WDMA_RX_PREF_EN);
-+
-+              wed_clr(dev, MTK_WED_WPDMA_GLO_CFG,
-+                      MTK_WED_WPDMA_GLO_CFG_TX_DDONE_CHK_LAST);
-+              wed_set(dev, MTK_WED_WPDMA_GLO_CFG,
-+                      MTK_WED_WPDMA_GLO_CFG_TX_DDONE_CHK |
-+                      MTK_WED_WPDMA_GLO_CFG_RX_DRV_EVENT_PKT_FMT_CHK |
-+                      MTK_WED_WPDMA_GLO_CFG_RX_DRV_UNS_VER_FORCE_4);
-+
-+              wdma_set(dev, MTK_WDMA_PREF_RX_CFG, MTK_WDMA_PREF_RX_CFG_PREF_EN);
-+      }
-+
-       wed_clr(dev, MTK_WED_WPDMA_GLO_CFG,
-               MTK_WED_WPDMA_GLO_CFG_TX_TKID_KEEP |
-               MTK_WED_WPDMA_GLO_CFG_TX_DMAD_DW3_PREV);
-@@ -1457,11 +1615,22 @@ mtk_wed_dma_enable(struct mtk_wed_device
-               MTK_WED_WDMA_GLO_CFG_TX_DRV_EN |
-               MTK_WED_WDMA_GLO_CFG_TX_DDONE_CHK);
-+      wed_clr(dev, MTK_WED_WPDMA_RX_D_GLO_CFG, MTK_WED_WPDMA_RX_D_RXD_READ_LEN);
-       wed_set(dev, MTK_WED_WPDMA_RX_D_GLO_CFG,
-               MTK_WED_WPDMA_RX_D_RX_DRV_EN |
-               FIELD_PREP(MTK_WED_WPDMA_RX_D_RXD_READ_LEN, 0x18) |
--              FIELD_PREP(MTK_WED_WPDMA_RX_D_INIT_PHASE_RXEN_SEL,
--                         0x2));
-+              FIELD_PREP(MTK_WED_WPDMA_RX_D_INIT_PHASE_RXEN_SEL, 0x2));
-+
-+      if (mtk_wed_is_v3_or_greater(dev->hw)) {
-+              wed_set(dev, MTK_WED_WPDMA_RX_D_PREF_CFG,
-+                      MTK_WED_WPDMA_RX_D_PREF_EN |
-+                      FIELD_PREP(MTK_WED_WPDMA_RX_D_PREF_BURST_SIZE, 0x10) |
-+                      FIELD_PREP(MTK_WED_WPDMA_RX_D_PREF_LOW_THRES, 0x8));
-+
-+              wed_set(dev, MTK_WED_RRO_RX_D_CFG(2), MTK_WED_RRO_RX_D_DRV_EN);
-+              wdma_set(dev, MTK_WDMA_PREF_TX_CFG, MTK_WDMA_PREF_TX_CFG_PREF_EN);
-+              wdma_set(dev, MTK_WDMA_WRBK_TX_CFG, MTK_WDMA_WRBK_TX_CFG_WRBK_EN);
-+      }
-       for (i = 0; i < MTK_WED_RX_QUEUES; i++)
-               mtk_wed_check_wfdma_rx_fill(dev, i);
-@@ -1501,6 +1670,12 @@ mtk_wed_start(struct mtk_wed_device *dev
-               wed_r32(dev, MTK_WED_EXT_INT_MASK1);
-               wed_r32(dev, MTK_WED_EXT_INT_MASK2);
-+              if (mtk_wed_is_v3_or_greater(dev->hw)) {
-+                      wed_w32(dev, MTK_WED_EXT_INT_MASK3,
-+                              MTK_WED_EXT_INT_STATUS_WPDMA_MID_RDY);
-+                      wed_r32(dev, MTK_WED_EXT_INT_MASK3);
-+              }
-+
-               if (mtk_wed_rro_cfg(dev))
-                       return;
-       }
-@@ -1552,6 +1727,7 @@ mtk_wed_attach(struct mtk_wed_device *de
-       dev->irq = hw->irq;
-       dev->wdma_idx = hw->index;
-       dev->version = hw->version;
-+      dev->hw->pcie_base = mtk_wed_get_pcie_base(dev);
-       if (hw->eth->dma_dev == hw->eth->dev &&
-           of_dma_is_coherent(hw->eth->dev->of_node))
-@@ -1619,6 +1795,23 @@ mtk_wed_tx_ring_setup(struct mtk_wed_dev
-       ring->reg_base = MTK_WED_RING_TX(idx);
-       ring->wpdma = regs;
-+      if (mtk_wed_is_v3_or_greater(dev->hw) && idx == 1) {
-+              /* reset prefetch index */
-+              wed_set(dev, MTK_WED_WDMA_RX_PREF_CFG,
-+                      MTK_WED_WDMA_RX_PREF_RX0_SIDX_CLR |
-+                      MTK_WED_WDMA_RX_PREF_RX1_SIDX_CLR);
-+
-+              wed_clr(dev, MTK_WED_WDMA_RX_PREF_CFG,
-+                      MTK_WED_WDMA_RX_PREF_RX0_SIDX_CLR |
-+                      MTK_WED_WDMA_RX_PREF_RX1_SIDX_CLR);
-+
-+              /* reset prefetch FIFO */
-+              wed_w32(dev, MTK_WED_WDMA_RX_PREF_FIFO_CFG,
-+                      MTK_WED_WDMA_RX_PREF_FIFO_RX0_CLR |
-+                      MTK_WED_WDMA_RX_PREF_FIFO_RX1_CLR);
-+              wed_w32(dev, MTK_WED_WDMA_RX_PREF_FIFO_CFG, 0);
-+      }
-+
-       /* WED -> WPDMA */
-       wpdma_tx_w32(dev, idx, MTK_WED_RING_OFS_BASE, ring->desc_phys);
-       wpdma_tx_w32(dev, idx, MTK_WED_RING_OFS_COUNT, MTK_WED_TX_RING_SIZE);
-@@ -1693,15 +1886,13 @@ mtk_wed_rx_ring_setup(struct mtk_wed_dev
- static u32
- mtk_wed_irq_get(struct mtk_wed_device *dev, u32 mask)
- {
--      u32 val, ext_mask = MTK_WED_EXT_INT_STATUS_ERROR_MASK;
-+      u32 val, ext_mask;
--      if (mtk_wed_is_v1(dev->hw))
--              ext_mask |= MTK_WED_EXT_INT_STATUS_TX_DRV_R_RESP_ERR;
-+      if (mtk_wed_is_v3_or_greater(dev->hw))
-+              ext_mask = MTK_WED_EXT_INT_STATUS_RX_DRV_COHERENT |
-+                         MTK_WED_EXT_INT_STATUS_TKID_WO_PYLD;
-       else
--              ext_mask |= MTK_WED_EXT_INT_STATUS_RX_FBUF_LO_TH |
--                          MTK_WED_EXT_INT_STATUS_RX_FBUF_HI_TH |
--                          MTK_WED_EXT_INT_STATUS_RX_DRV_COHERENT |
--                          MTK_WED_EXT_INT_STATUS_TX_DMA_W_RESP_ERR;
-+              ext_mask = MTK_WED_EXT_INT_STATUS_ERROR_MASK;
-       val = wed_r32(dev, MTK_WED_EXT_INT_STATUS);
-       wed_w32(dev, MTK_WED_EXT_INT_STATUS, val);
-@@ -1942,6 +2133,9 @@ void mtk_wed_add_hw(struct device_node *
-       case 2:
-               hw->soc = &mt7986_data;
-               break;
-+      case 3:
-+              hw->soc = &mt7988_data;
-+              break;
-       default:
-       case 1:
-               hw->mirror = syscon_regmap_lookup_by_phandle(eth_np,
---- a/drivers/net/ethernet/mediatek/mtk_wed.h
-+++ b/drivers/net/ethernet/mediatek/mtk_wed.h
-@@ -9,6 +9,8 @@
- #include <linux/regmap.h>
- #include <linux/netdevice.h>
-+#include "mtk_wed_regs.h"
-+
- struct mtk_eth;
- struct mtk_wed_wo;
-@@ -19,6 +21,7 @@ struct mtk_wed_soc_data {
-               u32 reset_idx_tx_mask;
-               u32 reset_idx_rx_mask;
-       } regmap;
-+      u32 tx_ring_desc_size;
-       u32 wdma_desc_size;
- };
-@@ -35,6 +38,7 @@ struct mtk_wed_hw {
-       struct dentry *debugfs_dir;
-       struct mtk_wed_device *wed_dev;
-       struct mtk_wed_wo *wed_wo;
-+      u32 pcie_base;
-       u32 debugfs_reg;
-       u32 num_flows;
-       u8 version;
-@@ -61,6 +65,16 @@ static inline bool mtk_wed_is_v2(struct
-       return hw->version == 2;
- }
-+static inline bool mtk_wed_is_v3(struct mtk_wed_hw *hw)
-+{
-+      return hw->version == 3;
-+}
-+
-+static inline bool mtk_wed_is_v3_or_greater(struct mtk_wed_hw *hw)
-+{
-+      return hw->version > 2;
-+}
-+
- static inline void
- wed_w32(struct mtk_wed_device *dev, u32 reg, u32 val)
- {
-@@ -143,6 +157,21 @@ wpdma_txfree_w32(struct mtk_wed_device *
-       writel(val, dev->txfree_ring.wpdma + reg);
- }
-+static inline u32 mtk_wed_get_pcie_base(struct mtk_wed_device *dev)
-+{
-+      if (!mtk_wed_is_v3_or_greater(dev->hw))
-+              return MTK_WED_PCIE_BASE;
-+
-+      switch (dev->hw->index) {
-+      case 1:
-+              return MTK_WED_PCIE_BASE1;
-+      case 2:
-+              return MTK_WED_PCIE_BASE2;
-+      default:
-+              return MTK_WED_PCIE_BASE0;
-+      }
-+}
-+
- void mtk_wed_add_hw(struct device_node *np, struct mtk_eth *eth,
-                   void __iomem *wdma, phys_addr_t wdma_phy,
-                   int index);
---- a/drivers/net/ethernet/mediatek/mtk_wed_mcu.c
-+++ b/drivers/net/ethernet/mediatek/mtk_wed_mcu.c
-@@ -331,10 +331,22 @@ mtk_wed_mcu_load_firmware(struct mtk_wed
-               wo->hw->index + 1);
-       /* load firmware */
--      if (of_device_is_compatible(wo->hw->node, "mediatek,mt7981-wed"))
--              fw_name = MT7981_FIRMWARE_WO;
--      else
--              fw_name = wo->hw->index ? MT7986_FIRMWARE_WO1 : MT7986_FIRMWARE_WO0;
-+      switch (wo->hw->version) {
-+      case 2:
-+              if (of_device_is_compatible(wo->hw->node,
-+                                          "mediatek,mt7981-wed"))
-+                      fw_name = MT7981_FIRMWARE_WO;
-+              else
-+                      fw_name = wo->hw->index ? MT7986_FIRMWARE_WO1
-+                                              : MT7986_FIRMWARE_WO0;
-+              break;
-+      case 3:
-+              fw_name = wo->hw->index ? MT7988_FIRMWARE_WO1
-+                                      : MT7988_FIRMWARE_WO0;
-+              break;
-+      default:
-+              return -EINVAL;
-+      }
-       ret = request_firmware(&fw, fw_name, wo->hw->dev);
-       if (ret)
-@@ -355,15 +367,16 @@ mtk_wed_mcu_load_firmware(struct mtk_wed
-       }
-       /* set the start address */
--      boot_cr = wo->hw->index ? MTK_WO_MCU_CFG_LS_WA_BOOT_ADDR_ADDR
--                              : MTK_WO_MCU_CFG_LS_WM_BOOT_ADDR_ADDR;
-+      if (!mtk_wed_is_v3_or_greater(wo->hw) && wo->hw->index)
-+              boot_cr = MTK_WO_MCU_CFG_LS_WA_BOOT_ADDR_ADDR;
-+      else
-+              boot_cr = MTK_WO_MCU_CFG_LS_WM_BOOT_ADDR_ADDR;
-       wo_w32(wo, boot_cr, mem_region[MTK_WED_WO_REGION_EMI].phy_addr >> 16);
-       /* wo firmware reset */
-       wo_w32(wo, MTK_WO_MCU_CFG_LS_WF_MCCR_CLR_ADDR, 0xc00);
--      val = wo_r32(wo, MTK_WO_MCU_CFG_LS_WF_MCU_CFG_WM_WA_ADDR);
--      val |= wo->hw->index ? MTK_WO_MCU_CFG_LS_WF_WM_WA_WA_CPU_RSTB_MASK
--                           : MTK_WO_MCU_CFG_LS_WF_WM_WA_WM_CPU_RSTB_MASK;
-+      val = wo_r32(wo, MTK_WO_MCU_CFG_LS_WF_MCU_CFG_WM_WA_ADDR) |
-+            MTK_WO_MCU_CFG_LS_WF_WM_WA_WM_CPU_RSTB_MASK;
-       wo_w32(wo, MTK_WO_MCU_CFG_LS_WF_MCU_CFG_WM_WA_ADDR, val);
- out:
-       release_firmware(fw);
-@@ -398,3 +411,5 @@ int mtk_wed_mcu_init(struct mtk_wed_wo *
- MODULE_FIRMWARE(MT7981_FIRMWARE_WO);
- MODULE_FIRMWARE(MT7986_FIRMWARE_WO0);
- MODULE_FIRMWARE(MT7986_FIRMWARE_WO1);
-+MODULE_FIRMWARE(MT7988_FIRMWARE_WO0);
-+MODULE_FIRMWARE(MT7988_FIRMWARE_WO1);
---- a/drivers/net/ethernet/mediatek/mtk_wed_regs.h
-+++ b/drivers/net/ethernet/mediatek/mtk_wed_regs.h
-@@ -13,6 +13,9 @@
- #define MTK_WDMA_DESC_CTRL_LAST_SEG0          BIT(30)
- #define MTK_WDMA_DESC_CTRL_DMA_DONE           BIT(31)
-+#define MTK_WDMA_TXD0_DESC_INFO_DMA_DONE      BIT(29)
-+#define MTK_WDMA_TXD1_DESC_INFO_DMA_DONE      BIT(31)
-+
- struct mtk_wdma_desc {
-       __le32 buf0;
-       __le32 ctrl;
-@@ -37,6 +40,7 @@ struct mtk_wdma_desc {
- #define MTK_WED_RESET_WDMA_INT_AGENT                  BIT(19)
- #define MTK_WED_RESET_RX_RRO_QM                               BIT(20)
- #define MTK_WED_RESET_RX_ROUTE_QM                     BIT(21)
-+#define MTK_WED_RESET_TX_AMSDU                                BIT(22)
- #define MTK_WED_RESET_WED                             BIT(31)
- #define MTK_WED_CTRL                                  0x00c
-@@ -44,6 +48,9 @@ struct mtk_wdma_desc {
- #define MTK_WED_CTRL_WPDMA_INT_AGENT_BUSY             BIT(1)
- #define MTK_WED_CTRL_WDMA_INT_AGENT_EN                        BIT(2)
- #define MTK_WED_CTRL_WDMA_INT_AGENT_BUSY              BIT(3)
-+#define MTK_WED_CTRL_WED_RX_IND_CMD_EN                        BIT(5)
-+#define MTK_WED_CTRL_WED_RX_PG_BM_EN                  BIT(6)
-+#define MTK_WED_CTRL_WED_RX_PG_BM_BUSY                        BIT(7)
- #define MTK_WED_CTRL_WED_TX_BM_EN                     BIT(8)
- #define MTK_WED_CTRL_WED_TX_BM_BUSY                   BIT(9)
- #define MTK_WED_CTRL_WED_TX_FREE_AGENT_EN             BIT(10)
-@@ -54,9 +61,14 @@ struct mtk_wdma_desc {
- #define MTK_WED_CTRL_RX_RRO_QM_BUSY                   BIT(15)
- #define MTK_WED_CTRL_RX_ROUTE_QM_EN                   BIT(16)
- #define MTK_WED_CTRL_RX_ROUTE_QM_BUSY                 BIT(17)
-+#define MTK_WED_CTRL_TX_TKID_ALI_EN                   BIT(20)
-+#define MTK_WED_CTRL_TX_TKID_ALI_BUSY                 BIT(21)
-+#define MTK_WED_CTRL_TX_AMSDU_EN                      BIT(22)
-+#define MTK_WED_CTRL_TX_AMSDU_BUSY                    BIT(23)
- #define MTK_WED_CTRL_FINAL_DIDX_READ                  BIT(24)
- #define MTK_WED_CTRL_ETH_DMAD_FMT                     BIT(25)
- #define MTK_WED_CTRL_MIB_READ_CLEAR                   BIT(28)
-+#define MTK_WED_CTRL_FLD_MIB_RD_CLR                   BIT(28)
- #define MTK_WED_EXT_INT_STATUS                                0x020
- #define MTK_WED_EXT_INT_STATUS_TF_LEN_ERR             BIT(0)
-@@ -89,6 +101,7 @@ struct mtk_wdma_desc {
- #define MTK_WED_EXT_INT_MASK                          0x028
- #define MTK_WED_EXT_INT_MASK1                         0x02c
- #define MTK_WED_EXT_INT_MASK2                         0x030
-+#define MTK_WED_EXT_INT_MASK3                         0x034
- #define MTK_WED_STATUS                                        0x060
- #define MTK_WED_STATUS_TX                             GENMASK(15, 8)
-@@ -96,9 +109,14 @@ struct mtk_wdma_desc {
- #define MTK_WED_TX_BM_CTRL                            0x080
- #define MTK_WED_TX_BM_CTRL_VLD_GRP_NUM                        GENMASK(6, 0)
- #define MTK_WED_TX_BM_CTRL_RSV_GRP_NUM                        GENMASK(22, 16)
-+#define MTK_WED_TX_BM_CTRL_LEGACY_EN                  BIT(26)
-+#define MTK_WED_TX_TKID_CTRL_FREE_FORMAT              BIT(27)
- #define MTK_WED_TX_BM_CTRL_PAUSE                      BIT(28)
- #define MTK_WED_TX_BM_BASE                            0x084
-+#define MTK_WED_TX_BM_INIT_PTR                                0x088
-+#define MTK_WED_TX_BM_SW_TAIL_IDX                     GENMASK(16, 0)
-+#define MTK_WED_TX_BM_INIT_SW_TAIL_IDX                        BIT(16)
- #define MTK_WED_TX_BM_TKID_START                      GENMASK(15, 0)
- #define MTK_WED_TX_BM_TKID_END                                GENMASK(31, 16)
-@@ -122,6 +140,9 @@ struct mtk_wdma_desc {
- #define MTK_WED_TX_TKID_CTRL_RSV_GRP_NUM              GENMASK(22, 16)
- #define MTK_WED_TX_TKID_CTRL_PAUSE                    BIT(28)
-+#define MTK_WED_TX_TKID_CTRL_VLD_GRP_NUM_V3           GENMASK(7, 0)
-+#define MTK_WED_TX_TKID_CTRL_RSV_GRP_NUM_V3           GENMASK(23, 16)
-+
- #define MTK_WED_TX_TKID_DYN_THR                               0x0e0
- #define MTK_WED_TX_TKID_DYN_THR_LO                    GENMASK(6, 0)
- #define MTK_WED_TX_TKID_DYN_THR_HI                    GENMASK(22, 16)
-@@ -199,12 +220,15 @@ struct mtk_wdma_desc {
- #define MTK_WED_WPDMA_GLO_CFG_RX_DRV_R1_PKT_PROC      BIT(5)
- #define MTK_WED_WPDMA_GLO_CFG_RX_DRV_R0_CRX_SYNC      BIT(6)
- #define MTK_WED_WPDMA_GLO_CFG_RX_DRV_R1_CRX_SYNC      BIT(7)
--#define MTK_WED_WPDMA_GLO_CFG_RX_DRV_EVENT_PKT_FMT_VER        GENMASK(18, 16)
-+#define MTK_WED_WPDMA_GLO_CFG_RX_DRV_EVENT_PKT_FMT_VER        GENMASK(15, 12)
-+#define MTK_WED_WPDMA_GLO_CFG_RX_DRV_UNS_VER_FORCE_4  BIT(18)
- #define MTK_WED_WPDMA_GLO_CFG_RX_DRV_UNSUPPORT_FMT    BIT(19)
--#define MTK_WED_WPDMA_GLO_CFG_RX_DRV_UEVENT_PKT_FMT_CHK BIT(20)
-+#define MTK_WED_WPDMA_GLO_CFG_RX_DRV_EVENT_PKT_FMT_CHK        BIT(20)
- #define MTK_WED_WPDMA_GLO_CFG_RX_DDONE2_WR            BIT(21)
- #define MTK_WED_WPDMA_GLO_CFG_TX_TKID_KEEP            BIT(24)
-+#define MTK_WED_WPDMA_GLO_CFG_TX_DDONE_CHK_LAST               BIT(25)
- #define MTK_WED_WPDMA_GLO_CFG_TX_DMAD_DW3_PREV                BIT(28)
-+#define MTK_WED_WPDMA_GLO_CFG_TX_DDONE_CHK            BIT(30)
- #define MTK_WED_WPDMA_RESET_IDX                               0x50c
- #define MTK_WED_WPDMA_RESET_IDX_TX                    GENMASK(3, 0)
-@@ -250,9 +274,10 @@ struct mtk_wdma_desc {
- #define MTK_WED_PCIE_INT_TRIGGER_STATUS                       BIT(16)
- #define MTK_WED_PCIE_INT_CTRL                         0x57c
--#define MTK_WED_PCIE_INT_CTRL_MSK_EN_POLA             BIT(20)
--#define MTK_WED_PCIE_INT_CTRL_SRC_SEL                 GENMASK(17, 16)
- #define MTK_WED_PCIE_INT_CTRL_POLL_EN                 GENMASK(13, 12)
-+#define MTK_WED_PCIE_INT_CTRL_SRC_SEL                 GENMASK(17, 16)
-+#define MTK_WED_PCIE_INT_CTRL_MSK_EN_POLA             BIT(20)
-+#define MTK_WED_PCIE_INT_CTRL_MSK_IRQ_FILTER          BIT(21)
- #define MTK_WED_WPDMA_CFG_BASE                                0x580
- #define MTK_WED_WPDMA_CFG_INT_MASK                    0x584
-@@ -286,6 +311,20 @@ struct mtk_wdma_desc {
- #define MTK_WED_WPDMA_RX_D_PROCESSED_MIB(_n)          (0x784 + (_n) * 4)
- #define MTK_WED_WPDMA_RX_D_COHERENT_MIB                       0x78c
-+#define MTK_WED_WPDMA_RX_D_PREF_CFG                   0x7b4
-+#define MTK_WED_WPDMA_RX_D_PREF_EN                    BIT(0)
-+#define MTK_WED_WPDMA_RX_D_PREF_BURST_SIZE            GENMASK(12, 8)
-+#define MTK_WED_WPDMA_RX_D_PREF_LOW_THRES             GENMASK(21, 16)
-+
-+#define MTK_WED_WPDMA_RX_D_PREF_RX0_SIDX              0x7b8
-+#define MTK_WED_WPDMA_RX_D_PREF_SIDX_IDX_CLR          BIT(15)
-+
-+#define MTK_WED_WPDMA_RX_D_PREF_RX1_SIDX              0x7bc
-+
-+#define MTK_WED_WPDMA_RX_D_PREF_FIFO_CFG              0x7c0
-+#define MTK_WED_WPDMA_RX_D_PREF_FIFO_CFG_R0_CLR               BIT(0)
-+#define MTK_WED_WPDMA_RX_D_PREF_FIFO_CFG_R1_CLR               BIT(16)
-+
- #define MTK_WED_WDMA_RING_TX                          0x800
- #define MTK_WED_WDMA_TX_MIB                           0x810
-@@ -293,6 +332,18 @@ struct mtk_wdma_desc {
- #define MTK_WED_WDMA_RING_RX(_n)                      (0x900 + (_n) * 0x10)
- #define MTK_WED_WDMA_RX_THRES(_n)                     (0x940 + (_n) * 0x4)
-+#define MTK_WED_WDMA_RX_PREF_CFG                      0x950
-+#define MTK_WED_WDMA_RX_PREF_EN                               BIT(0)
-+#define MTK_WED_WDMA_RX_PREF_BURST_SIZE                       GENMASK(12, 8)
-+#define MTK_WED_WDMA_RX_PREF_LOW_THRES                        GENMASK(21, 16)
-+#define MTK_WED_WDMA_RX_PREF_RX0_SIDX_CLR             BIT(24)
-+#define MTK_WED_WDMA_RX_PREF_RX1_SIDX_CLR             BIT(25)
-+#define MTK_WED_WDMA_RX_PREF_DDONE2_EN                        BIT(26)
-+
-+#define MTK_WED_WDMA_RX_PREF_FIFO_CFG                 0x95C
-+#define MTK_WED_WDMA_RX_PREF_FIFO_RX0_CLR             BIT(0)
-+#define MTK_WED_WDMA_RX_PREF_FIFO_RX1_CLR             BIT(16)
-+
- #define MTK_WED_WDMA_GLO_CFG                          0xa04
- #define MTK_WED_WDMA_GLO_CFG_TX_DRV_EN                        BIT(0)
- #define MTK_WED_WDMA_GLO_CFG_TX_DDONE_CHK             BIT(1)
-@@ -325,6 +376,7 @@ struct mtk_wdma_desc {
- #define MTK_WED_WDMA_INT_TRIGGER_RX_DONE              GENMASK(17, 16)
- #define MTK_WED_WDMA_INT_CTRL                         0xa2c
-+#define MTK_WED_WDMA_INT_POLL_PRD                     GENMASK(7, 0)
- #define MTK_WED_WDMA_INT_CTRL_POLL_SRC_SEL            GENMASK(17, 16)
- #define MTK_WED_WDMA_CFG_BASE                         0xaa0
-@@ -388,6 +440,18 @@ struct mtk_wdma_desc {
- #define MTK_WDMA_INT_GRP1                             0x250
- #define MTK_WDMA_INT_GRP2                             0x254
-+#define MTK_WDMA_PREF_TX_CFG                          0x2d0
-+#define MTK_WDMA_PREF_TX_CFG_PREF_EN                  BIT(0)
-+
-+#define MTK_WDMA_PREF_RX_CFG                          0x2dc
-+#define MTK_WDMA_PREF_RX_CFG_PREF_EN                  BIT(0)
-+
-+#define MTK_WDMA_WRBK_TX_CFG                          0x300
-+#define MTK_WDMA_WRBK_TX_CFG_WRBK_EN                  BIT(30)
-+
-+#define MTK_WDMA_WRBK_RX_CFG                          0x344
-+#define MTK_WDMA_WRBK_RX_CFG_WRBK_EN                  BIT(30)
-+
- #define MTK_PCIE_MIRROR_MAP(n)                                ((n) ? 0x4 : 0x0)
- #define MTK_PCIE_MIRROR_MAP_EN                                BIT(0)
- #define MTK_PCIE_MIRROR_MAP_WED_ID                    BIT(1)
-@@ -401,6 +465,30 @@ struct mtk_wdma_desc {
- #define MTK_WED_RTQM_Q_DBG_BYPASS                     BIT(5)
- #define MTK_WED_RTQM_TXDMAD_FPORT                     GENMASK(23, 20)
-+#define MTK_WED_RTQM_IGRS0_I2HW_DMAD_CNT              0xb1c
-+#define MTK_WED_RTQM_IGRS0_I2H_DMAD_CNT(_n)           (0xb20 + (_n) * 0x4)
-+#define       MTK_WED_RTQM_IGRS0_I2HW_PKT_CNT                 0xb28
-+#define MTK_WED_RTQM_IGRS0_I2H_PKT_CNT(_n)            (0xb2c + (_n) * 0x4)
-+#define MTK_WED_RTQM_IGRS0_FDROP_CNT                  0xb34
-+
-+#define MTK_WED_RTQM_IGRS1_I2HW_DMAD_CNT              0xb44
-+#define MTK_WED_RTQM_IGRS1_I2H_DMAD_CNT(_n)           (0xb48 + (_n) * 0x4)
-+#define MTK_WED_RTQM_IGRS1_I2HW_PKT_CNT                       0xb50
-+#define MTK_WED_RTQM_IGRS1_I2H_PKT_CNT(_n)            (0xb54 + (_n) * 0x4)
-+#define MTK_WED_RTQM_IGRS1_FDROP_CNT                  0xb5c
-+
-+#define MTK_WED_RTQM_IGRS2_I2HW_DMAD_CNT              0xb6c
-+#define MTK_WED_RTQM_IGRS2_I2H_DMAD_CNT(_n)           (0xb70 + (_n) * 0x4)
-+#define MTK_WED_RTQM_IGRS2_I2HW_PKT_CNT                       0xb78
-+#define MTK_WED_RTQM_IGRS2_I2H_PKT_CNT(_n)            (0xb7c + (_n) * 0x4)
-+#define MTK_WED_RTQM_IGRS2_FDROP_CNT                  0xb84
-+
-+#define MTK_WED_RTQM_IGRS3_I2HW_DMAD_CNT              0xb94
-+#define MTK_WED_RTQM_IGRS3_I2H_DMAD_CNT(_n)           (0xb98 + (_n) * 0x4)
-+#define MTK_WED_RTQM_IGRS3_I2HW_PKT_CNT                       0xba0
-+#define MTK_WED_RTQM_IGRS3_I2H_PKT_CNT(_n)            (0xba4 + (_n) * 0x4)
-+#define MTK_WED_RTQM_IGRS3_FDROP_CNT                  0xbac
-+
- #define MTK_WED_RTQM_R2H_MIB(_n)                      (0xb70 + (_n) * 0x4)
- #define MTK_WED_RTQM_R2Q_MIB(_n)                      (0xb78 + (_n) * 0x4)
- #define MTK_WED_RTQM_Q2N_MIB                          0xb80
-@@ -409,6 +497,24 @@ struct mtk_wdma_desc {
- #define MTK_WED_RTQM_Q2B_MIB                          0xb8c
- #define MTK_WED_RTQM_PFDBK_MIB                                0xb90
-+#define MTK_WED_RTQM_ENQ_CFG0                         0xbb8
-+#define MTK_WED_RTQM_ENQ_CFG_TXDMAD_FPORT             GENMASK(15, 12)
-+
-+#define MTK_WED_RTQM_FDROP_MIB                                0xb84
-+#define MTK_WED_RTQM_ENQ_I2Q_DMAD_CNT                 0xbbc
-+#define MTK_WED_RTQM_ENQ_I2N_DMAD_CNT                 0xbc0
-+#define MTK_WED_RTQM_ENQ_I2Q_PKT_CNT                  0xbc4
-+#define MTK_WED_RTQM_ENQ_I2N_PKT_CNT                  0xbc8
-+#define MTK_WED_RTQM_ENQ_USED_ENTRY_CNT                       0xbcc
-+#define MTK_WED_RTQM_ENQ_ERR_CNT                      0xbd0
-+
-+#define MTK_WED_RTQM_DEQ_DMAD_CNT                     0xbd8
-+#define MTK_WED_RTQM_DEQ_Q2I_DMAD_CNT                 0xbdc
-+#define MTK_WED_RTQM_DEQ_PKT_CNT                      0xbe0
-+#define MTK_WED_RTQM_DEQ_Q2I_PKT_CNT                  0xbe4
-+#define MTK_WED_RTQM_DEQ_USED_PFDBK_CNT                       0xbe8
-+#define MTK_WED_RTQM_DEQ_ERR_CNT                      0xbec
-+
- #define MTK_WED_RROQM_GLO_CFG                         0xc04
- #define MTK_WED_RROQM_RST_IDX                         0xc08
- #define MTK_WED_RROQM_RST_IDX_MIOD                    BIT(0)
-@@ -458,7 +564,116 @@ struct mtk_wdma_desc {
- #define MTK_WED_RX_BM_INTF                            0xd9c
- #define MTK_WED_RX_BM_ERR_STS                         0xda8
-+#define MTK_RRO_IND_CMD_SIGNATURE                     0xe00
-+#define MTK_RRO_IND_CMD_DMA_IDX                               GENMASK(11, 0)
-+#define MTK_RRO_IND_CMD_MAGIC_CNT                     GENMASK(30, 28)
-+
-+#define MTK_WED_IND_CMD_RX_CTRL0                      0xe04
-+#define MTK_WED_IND_CMD_PROC_IDX                      GENMASK(11, 0)
-+#define MTK_WED_IND_CMD_PREFETCH_FREE_CNT             GENMASK(19, 16)
-+#define MTK_WED_IND_CMD_MAGIC_CNT                     GENMASK(30, 28)
-+
-+#define MTK_WED_IND_CMD_RX_CTRL1                      0xe08
-+#define MTK_WED_IND_CMD_RX_CTRL2                      0xe0c
-+#define MTK_WED_IND_CMD_MAX_CNT                               GENMASK(11, 0)
-+#define MTK_WED_IND_CMD_BASE_M                                GENMASK(19, 16)
-+
-+#define MTK_WED_RRO_CFG0                              0xe10
-+#define MTK_WED_RRO_CFG1                              0xe14
-+#define MTK_WED_RRO_CFG1_MAX_WIN_SZ                   GENMASK(31, 29)
-+#define MTK_WED_RRO_CFG1_ACK_SN_BASE_M                        GENMASK(19, 16)
-+#define MTK_WED_RRO_CFG1_PARTICL_SE_ID                        GENMASK(11, 0)
-+
-+#define MTK_WED_ADDR_ELEM_CFG0                                0xe18
-+#define MTK_WED_ADDR_ELEM_CFG1                                0xe1c
-+#define MTK_WED_ADDR_ELEM_PREFETCH_FREE_CNT           GENMASK(19, 16)
-+
-+#define MTK_WED_ADDR_ELEM_TBL_CFG                     0xe20
-+#define MTK_WED_ADDR_ELEM_TBL_OFFSET                  GENMASK(6, 0)
-+#define MTK_WED_ADDR_ELEM_TBL_RD_RDY                  BIT(28)
-+#define MTK_WED_ADDR_ELEM_TBL_WR_RDY                  BIT(29)
-+#define MTK_WED_ADDR_ELEM_TBL_RD                      BIT(30)
-+#define MTK_WED_ADDR_ELEM_TBL_WR                      BIT(31)
-+
-+#define MTK_WED_RADDR_ELEM_TBL_WDATA                  0xe24
-+#define MTK_WED_RADDR_ELEM_TBL_RDATA                  0xe28
-+
-+#define MTK_WED_PN_CHECK_CFG                          0xe30
-+#define MTK_WED_PN_CHECK_SE_ID                                GENMASK(11, 0)
-+#define MTK_WED_PN_CHECK_RD_RDY                               BIT(28)
-+#define MTK_WED_PN_CHECK_WR_RDY                               BIT(29)
-+#define MTK_WED_PN_CHECK_RD                           BIT(30)
-+#define MTK_WED_PN_CHECK_WR                           BIT(31)
-+
-+#define MTK_WED_PN_CHECK_WDATA_M                      0xe38
-+#define MTK_WED_PN_CHECK_IS_FIRST                     BIT(17)
-+
-+#define MTK_WED_RRO_MSDU_PG_RING_CFG(_n)              (0xe44 + (_n) * 0x8)
-+
-+#define MTK_WED_RRO_MSDU_PG_RING2_CFG                 0xe58
-+#define MTK_WED_RRO_MSDU_PG_DRV_CLR                   BIT(26)
-+#define MTK_WED_RRO_MSDU_PG_DRV_EN                    BIT(31)
-+
-+#define MTK_WED_RRO_MSDU_PG_CTRL0(_n)                 (0xe5c + (_n) * 0xc)
-+#define MTK_WED_RRO_MSDU_PG_CTRL1(_n)                 (0xe60 + (_n) * 0xc)
-+#define MTK_WED_RRO_MSDU_PG_CTRL2(_n)                 (0xe64 + (_n) * 0xc)
-+
-+#define MTK_WED_RRO_RX_D_RX(_n)                               (0xe80 + (_n) * 0x10)
-+
-+#define MTK_WED_RRO_RX_MAGIC_CNT                      BIT(13)
-+
-+#define MTK_WED_RRO_RX_D_CFG(_n)                      (0xea0 + (_n) * 0x4)
-+#define MTK_WED_RRO_RX_D_DRV_CLR                      BIT(26)
-+#define MTK_WED_RRO_RX_D_DRV_EN                               BIT(31)
-+
-+#define MTK_WED_RRO_PG_BM_RX_DMAM                     0xeb0
-+#define MTK_WED_RRO_PG_BM_RX_SDL0                     GENMASK(13, 0)
-+
-+#define MTK_WED_RRO_PG_BM_BASE                                0xeb4
-+#define MTK_WED_RRO_PG_BM_INIT_PTR                    0xeb8
-+#define MTK_WED_RRO_PG_BM_SW_TAIL_IDX                 GENMASK(15, 0)
-+#define MTK_WED_RRO_PG_BM_INIT_SW_TAIL_IDX            BIT(16)
-+
-+#define MTK_WED_WPDMA_INT_CTRL_RRO_RX                 0xeec
-+#define MTK_WED_WPDMA_INT_CTRL_RRO_RX0_EN             BIT(0)
-+#define MTK_WED_WPDMA_INT_CTRL_RRO_RX0_CLR            BIT(1)
-+#define MTK_WED_WPDMA_INT_CTRL_RRO_RX0_DONE_TRIG      GENMASK(6, 2)
-+#define MTK_WED_WPDMA_INT_CTRL_RRO_RX1_EN             BIT(8)
-+#define MTK_WED_WPDMA_INT_CTRL_RRO_RX1_CLR            BIT(9)
-+#define MTK_WED_WPDMA_INT_CTRL_RRO_RX1_DONE_TRIG      GENMASK(14, 10)
-+
-+#define MTK_WED_WPDMA_INT_CTRL_RRO_MSDU_PG            0xef4
-+#define MTK_WED_WPDMA_INT_CTRL_RRO_PG0_EN             BIT(0)
-+#define MTK_WED_WPDMA_INT_CTRL_RRO_PG0_CLR            BIT(1)
-+#define MTK_WED_WPDMA_INT_CTRL_RRO_PG0_DONE_TRIG      GENMASK(6, 2)
-+#define MTK_WED_WPDMA_INT_CTRL_RRO_PG1_EN             BIT(8)
-+#define MTK_WED_WPDMA_INT_CTRL_RRO_PG1_CLR            BIT(9)
-+#define MTK_WED_WPDMA_INT_CTRL_RRO_PG1_DONE_TRIG      GENMASK(14, 10)
-+#define MTK_WED_WPDMA_INT_CTRL_RRO_PG2_EN             BIT(16)
-+#define MTK_WED_WPDMA_INT_CTRL_RRO_PG2_CLR            BIT(17)
-+#define MTK_WED_WPDMA_INT_CTRL_RRO_PG2_DONE_TRIG      GENMASK(22, 18)
-+
-+#define MTK_WED_RX_IND_CMD_CNT0                               0xf20
-+#define MTK_WED_RX_IND_CMD_DBG_CNT_EN                 BIT(31)
-+
-+#define MTK_WED_RX_IND_CMD_CNT(_n)                    (0xf20 + (_n) * 0x4)
-+#define MTK_WED_IND_CMD_MAGIC_CNT_FAIL_CNT            GENMASK(15, 0)
-+
-+#define MTK_WED_RX_ADDR_ELEM_CNT(_n)                  (0xf48 + (_n) * 0x4)
-+#define MTK_WED_ADDR_ELEM_SIG_FAIL_CNT                        GENMASK(15, 0)
-+#define MTK_WED_ADDR_ELEM_FIRST_SIG_FAIL_CNT          GENMASK(31, 16)
-+#define MTK_WED_ADDR_ELEM_ACKSN_CNT                   GENMASK(27, 0)
-+
-+#define MTK_WED_RX_MSDU_PG_CNT(_n)                    (0xf5c + (_n) * 0x4)
-+
-+#define MTK_WED_RX_PN_CHK_CNT                         0xf70
-+#define MTK_WED_PN_CHK_FAIL_CNT                               GENMASK(15, 0)
-+
- #define MTK_WED_WOCPU_VIEW_MIOD_BASE                  0x8000
- #define MTK_WED_PCIE_INT_MASK                         0x0
-+#define MTK_WED_PCIE_BASE                     0x11280000
-+#define MTK_WED_PCIE_BASE0                    0x11300000
-+#define MTK_WED_PCIE_BASE1                    0x11310000
-+#define MTK_WED_PCIE_BASE2                    0x11290000
- #endif
---- a/drivers/net/ethernet/mediatek/mtk_wed_wo.h
-+++ b/drivers/net/ethernet/mediatek/mtk_wed_wo.h
-@@ -91,6 +91,8 @@ enum mtk_wed_dummy_cr_idx {
- #define MT7981_FIRMWARE_WO    "mediatek/mt7981_wo.bin"
- #define MT7986_FIRMWARE_WO0   "mediatek/mt7986_wo_0.bin"
- #define MT7986_FIRMWARE_WO1   "mediatek/mt7986_wo_1.bin"
-+#define MT7988_FIRMWARE_WO0   "mediatek/mt7988_wo_0.bin"
-+#define MT7988_FIRMWARE_WO1   "mediatek/mt7988_wo_1.bin"
- #define MTK_WO_MCU_CFG_LS_BASE                                0
- #define MTK_WO_MCU_CFG_LS_HW_VER_ADDR                 (MTK_WO_MCU_CFG_LS_BASE + 0x000)
---- a/include/linux/soc/mediatek/mtk_wed.h
-+++ b/include/linux/soc/mediatek/mtk_wed.h
-@@ -139,6 +139,8 @@ struct mtk_wed_device {
-               u32 wpdma_rx;
-               bool wcid_512;
-+              bool hw_rro;
-+              bool msi;
-               u16 token_start;
-               unsigned int nbuf;
-@@ -212,10 +214,12 @@ mtk_wed_device_attach(struct mtk_wed_dev
-       return ret;
- }
--static inline bool
--mtk_wed_get_rx_capa(struct mtk_wed_device *dev)
-+static inline bool mtk_wed_get_rx_capa(struct mtk_wed_device *dev)
- {
- #ifdef CONFIG_NET_MEDIATEK_SOC_WED
-+      if (dev->version == 3)
-+              return dev->wlan.hw_rro;
-+
-       return dev->version != 1;
- #else
-       return false;
diff --git a/target/linux/generic/backport-5.15/752-15-v6.7-net-ethernet-mtk_wed-refactor-mtk_wed_check_wfdma_rx.patch b/target/linux/generic/backport-5.15/752-15-v6.7-net-ethernet-mtk_wed-refactor-mtk_wed_check_wfdma_rx.patch
deleted file mode 100644 (file)
index e91ae69..0000000
+++ /dev/null
@@ -1,95 +0,0 @@
-From: Lorenzo Bianconi <[email protected]>
-Date: Mon, 18 Sep 2023 12:29:14 +0200
-Subject: [PATCH] net: ethernet: mtk_wed: refactor mtk_wed_check_wfdma_rx_fill
- routine
-
-Refactor mtk_wed_check_wfdma_rx_fill() in order to be reused adding HW
-receive offload support for MT7988 SoC.
-
-Co-developed-by: Sujuan Chen <[email protected]>
-Signed-off-by: Sujuan Chen <[email protected]>
-Signed-off-by: Lorenzo Bianconi <[email protected]>
-Signed-off-by: Paolo Abeni <[email protected]>
----
-
---- a/drivers/net/ethernet/mediatek/mtk_wed.c
-+++ b/drivers/net/ethernet/mediatek/mtk_wed.c
-@@ -585,22 +585,15 @@ mtk_wed_set_512_support(struct mtk_wed_d
-       }
- }
--#define MTK_WFMDA_RX_DMA_EN   BIT(2)
--static void
--mtk_wed_check_wfdma_rx_fill(struct mtk_wed_device *dev, int idx)
-+static int
-+mtk_wed_check_wfdma_rx_fill(struct mtk_wed_device *dev,
-+                          struct mtk_wed_ring *ring)
- {
--      u32 val;
-       int i;
--      if (!(dev->rx_ring[idx].flags & MTK_WED_RING_CONFIGURED))
--              return; /* queue is not configured by mt76 */
--
-       for (i = 0; i < 3; i++) {
--              u32 cur_idx;
-+              u32 cur_idx = readl(ring->wpdma + MTK_WED_RING_OFS_CPU_IDX);
--              cur_idx = wed_r32(dev,
--                                MTK_WED_WPDMA_RING_RX_DATA(idx) +
--                                MTK_WED_RING_OFS_CPU_IDX);
-               if (cur_idx == MTK_WED_RX_RING_SIZE - 1)
-                       break;
-@@ -609,12 +602,10 @@ mtk_wed_check_wfdma_rx_fill(struct mtk_w
-       if (i == 3) {
-               dev_err(dev->hw->dev, "rx dma enable failed\n");
--              return;
-+              return -ETIMEDOUT;
-       }
--      val = wifi_r32(dev, dev->wlan.wpdma_rx_glo - dev->wlan.phy_base) |
--            MTK_WFMDA_RX_DMA_EN;
--      wifi_w32(dev, dev->wlan.wpdma_rx_glo - dev->wlan.phy_base, val);
-+      return 0;
- }
- static void
-@@ -1545,6 +1536,7 @@ mtk_wed_configure_irq(struct mtk_wed_dev
-       wed_w32(dev, MTK_WED_INT_MASK, irq_mask);
- }
-+#define MTK_WFMDA_RX_DMA_EN   BIT(2)
- static void
- mtk_wed_dma_enable(struct mtk_wed_device *dev)
- {
-@@ -1632,8 +1624,26 @@ mtk_wed_dma_enable(struct mtk_wed_device
-               wdma_set(dev, MTK_WDMA_WRBK_TX_CFG, MTK_WDMA_WRBK_TX_CFG_WRBK_EN);
-       }
--      for (i = 0; i < MTK_WED_RX_QUEUES; i++)
--              mtk_wed_check_wfdma_rx_fill(dev, i);
-+      for (i = 0; i < MTK_WED_RX_QUEUES; i++) {
-+              struct mtk_wed_ring *ring = &dev->rx_ring[i];
-+              u32 val;
-+
-+              if (!(ring->flags & MTK_WED_RING_CONFIGURED))
-+                      continue; /* queue is not configured by mt76 */
-+
-+              if (mtk_wed_check_wfdma_rx_fill(dev, ring)) {
-+                      dev_err(dev->hw->dev,
-+                              "rx_ring(%d) dma enable failed\n", i);
-+                      continue;
-+              }
-+
-+              val = wifi_r32(dev,
-+                             dev->wlan.wpdma_rx_glo -
-+                             dev->wlan.phy_base) | MTK_WFMDA_RX_DMA_EN;
-+              wifi_w32(dev,
-+                       dev->wlan.wpdma_rx_glo - dev->wlan.phy_base,
-+                       val);
-+      }
- }
- static void
diff --git a/target/linux/generic/backport-5.15/752-16-v6.7-net-ethernet-mtk_wed-introduce-partial-AMSDU-offload.patch b/target/linux/generic/backport-5.15/752-16-v6.7-net-ethernet-mtk_wed-introduce-partial-AMSDU-offload.patch
deleted file mode 100644 (file)
index 21a4e07..0000000
+++ /dev/null
@@ -1,465 +0,0 @@
-From: Sujuan Chen <[email protected]>
-Date: Mon, 18 Sep 2023 12:29:15 +0200
-Subject: [PATCH] net: ethernet: mtk_wed: introduce partial AMSDU offload
- support for MT7988
-
-Introduce partial AMSDU offload support for MT7988 SoC in order to merge
-in hw packets belonging to the same AMSDU before passing them to the
-WLAN nic.
-
-Co-developed-by: Lorenzo Bianconi <[email protected]>
-Signed-off-by: Lorenzo Bianconi <[email protected]>
-Signed-off-by: Sujuan Chen <[email protected]>
-Signed-off-by: Paolo Abeni <[email protected]>
----
-
---- a/drivers/net/ethernet/mediatek/mtk_ppe.c
-+++ b/drivers/net/ethernet/mediatek/mtk_ppe.c
-@@ -438,7 +438,8 @@ int mtk_foe_entry_set_pppoe(struct mtk_e
- }
- int mtk_foe_entry_set_wdma(struct mtk_eth *eth, struct mtk_foe_entry *entry,
--                         int wdma_idx, int txq, int bss, int wcid)
-+                         int wdma_idx, int txq, int bss, int wcid,
-+                         bool amsdu_en)
- {
-       struct mtk_foe_mac_info *l2 = mtk_foe_entry_l2(eth, entry);
-       u32 *ib2 = mtk_foe_entry_ib2(eth, entry);
-@@ -450,6 +451,7 @@ int mtk_foe_entry_set_wdma(struct mtk_et
-                        MTK_FOE_IB2_WDMA_WINFO_V2;
-               l2->w3info = FIELD_PREP(MTK_FOE_WINFO_WCID_V3, wcid) |
-                            FIELD_PREP(MTK_FOE_WINFO_BSS_V3, bss);
-+              l2->amsdu = FIELD_PREP(MTK_FOE_WINFO_AMSDU_EN, amsdu_en);
-               break;
-       case 2:
-               *ib2 &= ~MTK_FOE_IB2_PORT_MG_V2;
---- a/drivers/net/ethernet/mediatek/mtk_ppe.h
-+++ b/drivers/net/ethernet/mediatek/mtk_ppe.h
-@@ -88,13 +88,13 @@ enum {
- #define MTK_FOE_WINFO_BSS_V3          GENMASK(23, 16)
- #define MTK_FOE_WINFO_WCID_V3         GENMASK(15, 0)
--#define MTK_FOE_WINFO_PAO_USR_INFO    GENMASK(15, 0)
--#define MTK_FOE_WINFO_PAO_TID         GENMASK(19, 16)
--#define MTK_FOE_WINFO_PAO_IS_FIXEDRATE        BIT(20)
--#define MTK_FOE_WINFO_PAO_IS_PRIOR    BIT(21)
--#define MTK_FOE_WINFO_PAO_IS_SP               BIT(22)
--#define MTK_FOE_WINFO_PAO_HF          BIT(23)
--#define MTK_FOE_WINFO_PAO_AMSDU_EN    BIT(24)
-+#define MTK_FOE_WINFO_AMSDU_USR_INFO  GENMASK(15, 0)
-+#define MTK_FOE_WINFO_AMSDU_TID               GENMASK(19, 16)
-+#define MTK_FOE_WINFO_AMSDU_IS_FIXEDRATE      BIT(20)
-+#define MTK_FOE_WINFO_AMSDU_IS_PRIOR  BIT(21)
-+#define MTK_FOE_WINFO_AMSDU_IS_SP     BIT(22)
-+#define MTK_FOE_WINFO_AMSDU_HF                BIT(23)
-+#define MTK_FOE_WINFO_AMSDU_EN                BIT(24)
- enum {
-       MTK_FOE_STATE_INVALID,
-@@ -123,7 +123,7 @@ struct mtk_foe_mac_info {
-       /* netsys_v3 */
-       u32 w3info;
--      u32 wpao;
-+      u32 amsdu;
- };
- /* software-only entry type */
-@@ -393,7 +393,8 @@ int mtk_foe_entry_set_vlan(struct mtk_et
- int mtk_foe_entry_set_pppoe(struct mtk_eth *eth, struct mtk_foe_entry *entry,
-                           int sid);
- int mtk_foe_entry_set_wdma(struct mtk_eth *eth, struct mtk_foe_entry *entry,
--                         int wdma_idx, int txq, int bss, int wcid);
-+                         int wdma_idx, int txq, int bss, int wcid,
-+                         bool amsdu_en);
- int mtk_foe_entry_set_queue(struct mtk_eth *eth, struct mtk_foe_entry *entry,
-                           unsigned int queue);
- int mtk_foe_entry_commit(struct mtk_ppe *ppe, struct mtk_flow_entry *entry);
---- a/drivers/net/ethernet/mediatek/mtk_ppe_offload.c
-+++ b/drivers/net/ethernet/mediatek/mtk_ppe_offload.c
-@@ -111,6 +111,7 @@ mtk_flow_get_wdma_info(struct net_device
-       info->queue = path->mtk_wdma.queue;
-       info->bss = path->mtk_wdma.bss;
-       info->wcid = path->mtk_wdma.wcid;
-+      info->amsdu = path->mtk_wdma.amsdu;
-       return 0;
- }
-@@ -192,7 +193,7 @@ mtk_flow_set_output_device(struct mtk_et
-       if (mtk_flow_get_wdma_info(dev, dest_mac, &info) == 0) {
-               mtk_foe_entry_set_wdma(eth, foe, info.wdma_idx, info.queue,
--                                     info.bss, info.wcid);
-+                                     info.bss, info.wcid, info.amsdu);
-               if (mtk_is_netsys_v2_or_greater(eth)) {
-                       switch (info.wdma_idx) {
-                       case 0:
---- a/drivers/net/ethernet/mediatek/mtk_wed.c
-+++ b/drivers/net/ethernet/mediatek/mtk_wed.c
-@@ -29,6 +29,8 @@
- #define MTK_WED_RX_PAGE_BUF_PER_PAGE  (PAGE_SIZE / 128)
- #define MTK_WED_RX_RING_SIZE          1536
- #define MTK_WED_RX_PG_BM_CNT          8192
-+#define MTK_WED_AMSDU_BUF_SIZE                (PAGE_SIZE << 4)
-+#define MTK_WED_AMSDU_NPAGES          32
- #define MTK_WED_TX_RING_SIZE          2048
- #define MTK_WED_WDMA_RING_SIZE                1024
-@@ -172,6 +174,23 @@ mtk_wdma_rx_reset(struct mtk_wed_device
-       return ret;
- }
-+static u32
-+mtk_wed_check_busy(struct mtk_wed_device *dev, u32 reg, u32 mask)
-+{
-+      return !!(wed_r32(dev, reg) & mask);
-+}
-+
-+static int
-+mtk_wed_poll_busy(struct mtk_wed_device *dev, u32 reg, u32 mask)
-+{
-+      int sleep = 15000;
-+      int timeout = 100 * sleep;
-+      u32 val;
-+
-+      return read_poll_timeout(mtk_wed_check_busy, val, !val, sleep,
-+                               timeout, false, dev, reg, mask);
-+}
-+
- static void
- mtk_wdma_tx_reset(struct mtk_wed_device *dev)
- {
-@@ -335,6 +354,118 @@ out:
- }
- static int
-+mtk_wed_amsdu_buffer_alloc(struct mtk_wed_device *dev)
-+{
-+      struct mtk_wed_hw *hw = dev->hw;
-+      struct mtk_wed_amsdu *wed_amsdu;
-+      int i;
-+
-+      if (!mtk_wed_is_v3_or_greater(hw))
-+              return 0;
-+
-+      wed_amsdu = devm_kcalloc(hw->dev, MTK_WED_AMSDU_NPAGES,
-+                               sizeof(*wed_amsdu), GFP_KERNEL);
-+      if (!wed_amsdu)
-+              return -ENOMEM;
-+
-+      for (i = 0; i < MTK_WED_AMSDU_NPAGES; i++) {
-+              void *ptr;
-+
-+              /* each segment is 64K */
-+              ptr = (void *)__get_free_pages(GFP_KERNEL | __GFP_NOWARN |
-+                                             __GFP_ZERO | __GFP_COMP |
-+                                             GFP_DMA32,
-+                                             get_order(MTK_WED_AMSDU_BUF_SIZE));
-+              if (!ptr)
-+                      goto error;
-+
-+              wed_amsdu[i].txd = ptr;
-+              wed_amsdu[i].txd_phy = dma_map_single(hw->dev, ptr,
-+                                                    MTK_WED_AMSDU_BUF_SIZE,
-+                                                    DMA_TO_DEVICE);
-+              if (dma_mapping_error(hw->dev, wed_amsdu[i].txd_phy))
-+                      goto error;
-+      }
-+      dev->hw->wed_amsdu = wed_amsdu;
-+
-+      return 0;
-+
-+error:
-+      for (i--; i >= 0; i--)
-+              dma_unmap_single(hw->dev, wed_amsdu[i].txd_phy,
-+                               MTK_WED_AMSDU_BUF_SIZE, DMA_TO_DEVICE);
-+      return -ENOMEM;
-+}
-+
-+static void
-+mtk_wed_amsdu_free_buffer(struct mtk_wed_device *dev)
-+{
-+      struct mtk_wed_amsdu *wed_amsdu = dev->hw->wed_amsdu;
-+      int i;
-+
-+      if (!wed_amsdu)
-+              return;
-+
-+      for (i = 0; i < MTK_WED_AMSDU_NPAGES; i++) {
-+              dma_unmap_single(dev->hw->dev, wed_amsdu[i].txd_phy,
-+                               MTK_WED_AMSDU_BUF_SIZE, DMA_TO_DEVICE);
-+              free_pages((unsigned long)wed_amsdu[i].txd,
-+                         get_order(MTK_WED_AMSDU_BUF_SIZE));
-+      }
-+}
-+
-+static int
-+mtk_wed_amsdu_init(struct mtk_wed_device *dev)
-+{
-+      struct mtk_wed_amsdu *wed_amsdu = dev->hw->wed_amsdu;
-+      int i, ret;
-+
-+      if (!wed_amsdu)
-+              return 0;
-+
-+      for (i = 0; i < MTK_WED_AMSDU_NPAGES; i++)
-+              wed_w32(dev, MTK_WED_AMSDU_HIFTXD_BASE_L(i),
-+                      wed_amsdu[i].txd_phy);
-+
-+      /* init all sta parameter */
-+      wed_w32(dev, MTK_WED_AMSDU_STA_INFO_INIT, MTK_WED_AMSDU_STA_RMVL |
-+              MTK_WED_AMSDU_STA_WTBL_HDRT_MODE |
-+              FIELD_PREP(MTK_WED_AMSDU_STA_MAX_AMSDU_LEN,
-+                         dev->wlan.amsdu_max_len >> 8) |
-+              FIELD_PREP(MTK_WED_AMSDU_STA_MAX_AMSDU_NUM,
-+                         dev->wlan.amsdu_max_subframes));
-+
-+      wed_w32(dev, MTK_WED_AMSDU_STA_INFO, MTK_WED_AMSDU_STA_INFO_DO_INIT);
-+
-+      ret = mtk_wed_poll_busy(dev, MTK_WED_AMSDU_STA_INFO,
-+                              MTK_WED_AMSDU_STA_INFO_DO_INIT);
-+      if (ret) {
-+              dev_err(dev->hw->dev, "amsdu initialization failed\n");
-+              return ret;
-+      }
-+
-+      /* init partial amsdu offload txd src */
-+      wed_set(dev, MTK_WED_AMSDU_HIFTXD_CFG,
-+              FIELD_PREP(MTK_WED_AMSDU_HIFTXD_SRC, dev->hw->index));
-+
-+      /* init qmem */
-+      wed_set(dev, MTK_WED_AMSDU_PSE, MTK_WED_AMSDU_PSE_RESET);
-+      ret = mtk_wed_poll_busy(dev, MTK_WED_MON_AMSDU_QMEM_STS1, BIT(29));
-+      if (ret) {
-+              pr_info("%s: amsdu qmem initialization failed\n", __func__);
-+              return ret;
-+      }
-+
-+      /* eagle E1 PCIE1 tx ring 22 flow control issue */
-+      if (dev->wlan.id == 0x7991)
-+              wed_clr(dev, MTK_WED_AMSDU_FIFO, MTK_WED_AMSDU_IS_PRIOR0_RING);
-+
-+      wed_set(dev, MTK_WED_CTRL, MTK_WED_CTRL_TX_AMSDU_EN);
-+
-+      return 0;
-+}
-+
-+static int
- mtk_wed_tx_buffer_alloc(struct mtk_wed_device *dev)
- {
-       u32 desc_size = dev->hw->soc->tx_ring_desc_size;
-@@ -708,6 +839,7 @@ __mtk_wed_detach(struct mtk_wed_device *
-       mtk_wdma_rx_reset(dev);
-       mtk_wed_reset(dev, MTK_WED_RESET_WED);
-+      mtk_wed_amsdu_free_buffer(dev);
-       mtk_wed_free_tx_buffer(dev);
-       mtk_wed_free_tx_rings(dev);
-@@ -1128,23 +1260,6 @@ mtk_wed_ring_reset(struct mtk_wed_ring *
-       }
- }
--static u32
--mtk_wed_check_busy(struct mtk_wed_device *dev, u32 reg, u32 mask)
--{
--      return !!(wed_r32(dev, reg) & mask);
--}
--
--static int
--mtk_wed_poll_busy(struct mtk_wed_device *dev, u32 reg, u32 mask)
--{
--      int sleep = 15000;
--      int timeout = 100 * sleep;
--      u32 val;
--
--      return read_poll_timeout(mtk_wed_check_busy, val, !val, sleep,
--                               timeout, false, dev, reg, mask);
--}
--
- static int
- mtk_wed_rx_reset(struct mtk_wed_device *dev)
- {
-@@ -1691,6 +1806,7 @@ mtk_wed_start(struct mtk_wed_device *dev
-       }
-       mtk_wed_set_512_support(dev, dev->wlan.wcid_512);
-+      mtk_wed_amsdu_init(dev);
-       mtk_wed_dma_enable(dev);
-       dev->running = true;
-@@ -1747,6 +1863,10 @@ mtk_wed_attach(struct mtk_wed_device *de
-       if (ret)
-               goto out;
-+      ret = mtk_wed_amsdu_buffer_alloc(dev);
-+      if (ret)
-+              goto out;
-+
-       if (mtk_wed_get_rx_capa(dev)) {
-               ret = mtk_wed_rro_alloc(dev);
-               if (ret)
---- a/drivers/net/ethernet/mediatek/mtk_wed.h
-+++ b/drivers/net/ethernet/mediatek/mtk_wed.h
-@@ -25,6 +25,11 @@ struct mtk_wed_soc_data {
-       u32 wdma_desc_size;
- };
-+struct mtk_wed_amsdu {
-+      void *txd;
-+      dma_addr_t txd_phy;
-+};
-+
- struct mtk_wed_hw {
-       const struct mtk_wed_soc_data *soc;
-       struct device_node *node;
-@@ -38,6 +43,7 @@ struct mtk_wed_hw {
-       struct dentry *debugfs_dir;
-       struct mtk_wed_device *wed_dev;
-       struct mtk_wed_wo *wed_wo;
-+      struct mtk_wed_amsdu *wed_amsdu;
-       u32 pcie_base;
-       u32 debugfs_reg;
-       u32 num_flows;
-@@ -52,6 +58,7 @@ struct mtk_wdma_info {
-       u8 queue;
-       u16 wcid;
-       u8 bss;
-+      u8 amsdu;
- };
- #ifdef CONFIG_NET_MEDIATEK_SOC_WED
---- a/drivers/net/ethernet/mediatek/mtk_wed_regs.h
-+++ b/drivers/net/ethernet/mediatek/mtk_wed_regs.h
-@@ -672,6 +672,82 @@ struct mtk_wdma_desc {
- #define MTK_WED_WOCPU_VIEW_MIOD_BASE                  0x8000
- #define MTK_WED_PCIE_INT_MASK                         0x0
-+#define MTK_WED_AMSDU_FIFO                            0x1800
-+#define MTK_WED_AMSDU_IS_PRIOR0_RING                  BIT(10)
-+
-+#define MTK_WED_AMSDU_STA_INFO                                0x01810
-+#define MTK_WED_AMSDU_STA_INFO_DO_INIT                        BIT(0)
-+#define MTK_WED_AMSDU_STA_INFO_SET_INIT                       BIT(1)
-+
-+#define MTK_WED_AMSDU_STA_INFO_INIT                   0x01814
-+#define MTK_WED_AMSDU_STA_WTBL_HDRT_MODE              BIT(0)
-+#define MTK_WED_AMSDU_STA_RMVL                                BIT(1)
-+#define MTK_WED_AMSDU_STA_MAX_AMSDU_LEN                       GENMASK(7, 2)
-+#define MTK_WED_AMSDU_STA_MAX_AMSDU_NUM                       GENMASK(11, 8)
-+
-+#define MTK_WED_AMSDU_HIFTXD_BASE_L(_n)                       (0x1980 + (_n) * 0x4)
-+
-+#define MTK_WED_AMSDU_PSE                             0x1910
-+#define MTK_WED_AMSDU_PSE_RESET                               BIT(16)
-+
-+#define MTK_WED_AMSDU_HIFTXD_CFG                      0x1968
-+#define MTK_WED_AMSDU_HIFTXD_SRC                      GENMASK(16, 15)
-+
-+#define MTK_WED_MON_AMSDU_FIFO_DMAD                   0x1a34
-+
-+#define MTK_WED_MON_AMSDU_ENG_DMAD(_n)                        (0x1a80 + (_n) * 0x50)
-+#define MTK_WED_MON_AMSDU_ENG_QFPL(_n)                        (0x1a84 + (_n) * 0x50)
-+#define MTK_WED_MON_AMSDU_ENG_QENI(_n)                        (0x1a88 + (_n) * 0x50)
-+#define MTK_WED_MON_AMSDU_ENG_QENO(_n)                        (0x1a8c + (_n) * 0x50)
-+#define MTK_WED_MON_AMSDU_ENG_MERG(_n)                        (0x1a90 + (_n) * 0x50)
-+
-+#define MTK_WED_MON_AMSDU_ENG_CNT8(_n)                        (0x1a94 + (_n) * 0x50)
-+#define MTK_WED_AMSDU_ENG_MAX_QGPP_CNT                        GENMASK(10, 0)
-+#define MTK_WED_AMSDU_ENG_MAX_PL_CNT                  GENMASK(27, 16)
-+
-+#define MTK_WED_MON_AMSDU_ENG_CNT9(_n)                        (0x1a98 + (_n) * 0x50)
-+#define MTK_WED_AMSDU_ENG_CUR_ENTRY                   GENMASK(10, 0)
-+#define MTK_WED_AMSDU_ENG_MAX_BUF_MERGED              GENMASK(20, 16)
-+#define MTK_WED_AMSDU_ENG_MAX_MSDU_MERGED             GENMASK(28, 24)
-+
-+#define MTK_WED_MON_AMSDU_QMEM_STS1                   0x1e04
-+
-+#define MTK_WED_MON_AMSDU_QMEM_CNT(_n)                        (0x1e0c + (_n) * 0x4)
-+#define MTK_WED_AMSDU_QMEM_FQ_CNT                     GENMASK(27, 16)
-+#define MTK_WED_AMSDU_QMEM_SP_QCNT                    GENMASK(11, 0)
-+#define MTK_WED_AMSDU_QMEM_TID0_QCNT                  GENMASK(27, 16)
-+#define MTK_WED_AMSDU_QMEM_TID1_QCNT                  GENMASK(11, 0)
-+#define MTK_WED_AMSDU_QMEM_TID2_QCNT                  GENMASK(27, 16)
-+#define MTK_WED_AMSDU_QMEM_TID3_QCNT                  GENMASK(11, 0)
-+#define MTK_WED_AMSDU_QMEM_TID4_QCNT                  GENMASK(27, 16)
-+#define MTK_WED_AMSDU_QMEM_TID5_QCNT                  GENMASK(11, 0)
-+#define MTK_WED_AMSDU_QMEM_TID6_QCNT                  GENMASK(27, 16)
-+#define MTK_WED_AMSDU_QMEM_TID7_QCNT                  GENMASK(11, 0)
-+
-+#define MTK_WED_MON_AMSDU_QMEM_PTR(_n)                        (0x1e20 + (_n) * 0x4)
-+#define MTK_WED_AMSDU_QMEM_FQ_HEAD                    GENMASK(27, 16)
-+#define MTK_WED_AMSDU_QMEM_SP_QHEAD                   GENMASK(11, 0)
-+#define MTK_WED_AMSDU_QMEM_TID0_QHEAD                 GENMASK(27, 16)
-+#define MTK_WED_AMSDU_QMEM_TID1_QHEAD                 GENMASK(11, 0)
-+#define MTK_WED_AMSDU_QMEM_TID2_QHEAD                 GENMASK(27, 16)
-+#define MTK_WED_AMSDU_QMEM_TID3_QHEAD                 GENMASK(11, 0)
-+#define MTK_WED_AMSDU_QMEM_TID4_QHEAD                 GENMASK(27, 16)
-+#define MTK_WED_AMSDU_QMEM_TID5_QHEAD                 GENMASK(11, 0)
-+#define MTK_WED_AMSDU_QMEM_TID6_QHEAD                 GENMASK(27, 16)
-+#define MTK_WED_AMSDU_QMEM_TID7_QHEAD                 GENMASK(11, 0)
-+#define MTK_WED_AMSDU_QMEM_FQ_TAIL                    GENMASK(27, 16)
-+#define MTK_WED_AMSDU_QMEM_SP_QTAIL                   GENMASK(11, 0)
-+#define MTK_WED_AMSDU_QMEM_TID0_QTAIL                 GENMASK(27, 16)
-+#define MTK_WED_AMSDU_QMEM_TID1_QTAIL                 GENMASK(11, 0)
-+#define MTK_WED_AMSDU_QMEM_TID2_QTAIL                 GENMASK(27, 16)
-+#define MTK_WED_AMSDU_QMEM_TID3_QTAIL                 GENMASK(11, 0)
-+#define MTK_WED_AMSDU_QMEM_TID4_QTAIL                 GENMASK(27, 16)
-+#define MTK_WED_AMSDU_QMEM_TID5_QTAIL                 GENMASK(11, 0)
-+#define MTK_WED_AMSDU_QMEM_TID6_QTAIL                 GENMASK(27, 16)
-+#define MTK_WED_AMSDU_QMEM_TID7_QTAIL                 GENMASK(11, 0)
-+
-+#define MTK_WED_MON_AMSDU_HIFTXD_FETCH_MSDU(_n)               (0x1ec4 + (_n) * 0x4)
-+
- #define MTK_WED_PCIE_BASE                     0x11280000
- #define MTK_WED_PCIE_BASE0                    0x11300000
- #define MTK_WED_PCIE_BASE1                    0x11310000
---- a/include/linux/netdevice.h
-+++ b/include/linux/netdevice.h
-@@ -906,6 +906,7 @@ struct net_device_path {
-                       u8 queue;
-                       u16 wcid;
-                       u8 bss;
-+                      u8 amsdu;
-               } mtk_wdma;
-       };
- };
---- a/include/linux/soc/mediatek/mtk_wed.h
-+++ b/include/linux/soc/mediatek/mtk_wed.h
-@@ -129,6 +129,7 @@ struct mtk_wed_device {
-               enum mtk_wed_bus_tye bus_type;
-               void __iomem *base;
-               u32 phy_base;
-+              u32 id;
-               u32 wpdma_phys;
-               u32 wpdma_int;
-@@ -147,10 +148,12 @@ struct mtk_wed_device {
-               unsigned int rx_nbuf;
-               unsigned int rx_npkt;
-               unsigned int rx_size;
-+              unsigned int amsdu_max_len;
-               u8 tx_tbit[MTK_WED_TX_QUEUES];
-               u8 rx_tbit[MTK_WED_RX_QUEUES];
-               u8 txfree_tbit;
-+              u8 amsdu_max_subframes;
-               u32 (*init_buf)(void *ptr, dma_addr_t phys, int token_id);
-               int (*offload_enable)(struct mtk_wed_device *wed);
-@@ -224,6 +227,15 @@ static inline bool mtk_wed_get_rx_capa(s
- #else
-       return false;
- #endif
-+}
-+
-+static inline bool mtk_wed_is_amsdu_supported(struct mtk_wed_device *dev)
-+{
-+#ifdef CONFIG_NET_MEDIATEK_SOC_WED
-+      return dev->version == 3;
-+#else
-+      return false;
-+#endif
- }
- #ifdef CONFIG_NET_MEDIATEK_SOC_WED
diff --git a/target/linux/generic/backport-5.15/752-17-v6.7-net-ethernet-mtk_wed-introduce-hw_rro-support-for-MT.patch b/target/linux/generic/backport-5.15/752-17-v6.7-net-ethernet-mtk_wed-introduce-hw_rro-support-for-MT.patch
deleted file mode 100644 (file)
index 0cf4c18..0000000
+++ /dev/null
@@ -1,483 +0,0 @@
-From: Sujuan Chen <[email protected]>
-Date: Mon, 18 Sep 2023 12:29:16 +0200
-Subject: [PATCH] net: ethernet: mtk_wed: introduce hw_rro support for MT7988
-
-MT7988 SoC support 802.11 receive reordering offload in hw while
-MT7986 SoC implements it through the firmware running on the mcu.
-
-Co-developed-by: Lorenzo Bianconi <[email protected]>
-Signed-off-by: Lorenzo Bianconi <[email protected]>
-Signed-off-by: Sujuan Chen <[email protected]>
-Signed-off-by: Paolo Abeni <[email protected]>
----
-
---- a/drivers/net/ethernet/mediatek/mtk_wed.c
-+++ b/drivers/net/ethernet/mediatek/mtk_wed.c
-@@ -26,7 +26,7 @@
- #define MTK_WED_BUF_SIZE              2048
- #define MTK_WED_PAGE_BUF_SIZE         128
- #define MTK_WED_BUF_PER_PAGE          (PAGE_SIZE / 2048)
--#define MTK_WED_RX_PAGE_BUF_PER_PAGE  (PAGE_SIZE / 128)
-+#define MTK_WED_RX_BUF_PER_PAGE               (PAGE_SIZE / MTK_WED_PAGE_BUF_SIZE)
- #define MTK_WED_RX_RING_SIZE          1536
- #define MTK_WED_RX_PG_BM_CNT          8192
- #define MTK_WED_AMSDU_BUF_SIZE                (PAGE_SIZE << 4)
-@@ -596,6 +596,68 @@ free_pagelist:
- }
- static int
-+mtk_wed_hwrro_buffer_alloc(struct mtk_wed_device *dev)
-+{
-+      int n_pages = MTK_WED_RX_PG_BM_CNT / MTK_WED_RX_BUF_PER_PAGE;
-+      struct mtk_wed_buf *page_list;
-+      struct mtk_wed_bm_desc *desc;
-+      dma_addr_t desc_phys;
-+      int i, page_idx = 0;
-+
-+      if (!dev->wlan.hw_rro)
-+              return 0;
-+
-+      page_list = kcalloc(n_pages, sizeof(*page_list), GFP_KERNEL);
-+      if (!page_list)
-+              return -ENOMEM;
-+
-+      dev->hw_rro.size = dev->wlan.rx_nbuf & ~(MTK_WED_BUF_PER_PAGE - 1);
-+      dev->hw_rro.pages = page_list;
-+      desc = dma_alloc_coherent(dev->hw->dev,
-+                                dev->wlan.rx_nbuf * sizeof(*desc),
-+                                &desc_phys, GFP_KERNEL);
-+      if (!desc)
-+              return -ENOMEM;
-+
-+      dev->hw_rro.desc = desc;
-+      dev->hw_rro.desc_phys = desc_phys;
-+
-+      for (i = 0; i < MTK_WED_RX_PG_BM_CNT; i += MTK_WED_RX_BUF_PER_PAGE) {
-+              dma_addr_t page_phys, buf_phys;
-+              struct page *page;
-+              int s;
-+
-+              page = __dev_alloc_page(GFP_KERNEL);
-+              if (!page)
-+                      return -ENOMEM;
-+
-+              page_phys = dma_map_page(dev->hw->dev, page, 0, PAGE_SIZE,
-+                                       DMA_BIDIRECTIONAL);
-+              if (dma_mapping_error(dev->hw->dev, page_phys)) {
-+                      __free_page(page);
-+                      return -ENOMEM;
-+              }
-+
-+              page_list[page_idx].p = page;
-+              page_list[page_idx++].phy_addr = page_phys;
-+              dma_sync_single_for_cpu(dev->hw->dev, page_phys, PAGE_SIZE,
-+                                      DMA_BIDIRECTIONAL);
-+
-+              buf_phys = page_phys;
-+              for (s = 0; s < MTK_WED_RX_BUF_PER_PAGE; s++) {
-+                      desc->buf0 = cpu_to_le32(buf_phys);
-+                      buf_phys += MTK_WED_PAGE_BUF_SIZE;
-+                      desc++;
-+              }
-+
-+              dma_sync_single_for_device(dev->hw->dev, page_phys, PAGE_SIZE,
-+                                         DMA_BIDIRECTIONAL);
-+      }
-+
-+      return 0;
-+}
-+
-+static int
- mtk_wed_rx_buffer_alloc(struct mtk_wed_device *dev)
- {
-       struct mtk_wed_bm_desc *desc;
-@@ -612,7 +674,42 @@ mtk_wed_rx_buffer_alloc(struct mtk_wed_d
-       dev->rx_buf_ring.desc_phys = desc_phys;
-       dev->wlan.init_rx_buf(dev, dev->wlan.rx_npkt);
--      return 0;
-+      return mtk_wed_hwrro_buffer_alloc(dev);
-+}
-+
-+static void
-+mtk_wed_hwrro_free_buffer(struct mtk_wed_device *dev)
-+{
-+      struct mtk_wed_buf *page_list = dev->hw_rro.pages;
-+      struct mtk_wed_bm_desc *desc = dev->hw_rro.desc;
-+      int i, page_idx = 0;
-+
-+      if (!dev->wlan.hw_rro)
-+              return;
-+
-+      if (!page_list)
-+              return;
-+
-+      if (!desc)
-+              goto free_pagelist;
-+
-+      for (i = 0; i < MTK_WED_RX_PG_BM_CNT; i += MTK_WED_RX_BUF_PER_PAGE) {
-+              dma_addr_t buf_addr = page_list[page_idx].phy_addr;
-+              void *page = page_list[page_idx++].p;
-+
-+              if (!page)
-+                      break;
-+
-+              dma_unmap_page(dev->hw->dev, buf_addr, PAGE_SIZE,
-+                             DMA_BIDIRECTIONAL);
-+              __free_page(page);
-+      }
-+
-+      dma_free_coherent(dev->hw->dev, dev->hw_rro.size * sizeof(*desc),
-+                        desc, dev->hw_rro.desc_phys);
-+
-+free_pagelist:
-+      kfree(page_list);
- }
- static void
-@@ -626,6 +723,28 @@ mtk_wed_free_rx_buffer(struct mtk_wed_de
-       dev->wlan.release_rx_buf(dev);
-       dma_free_coherent(dev->hw->dev, dev->rx_buf_ring.size * sizeof(*desc),
-                         desc, dev->rx_buf_ring.desc_phys);
-+
-+      mtk_wed_hwrro_free_buffer(dev);
-+}
-+
-+static void
-+mtk_wed_hwrro_init(struct mtk_wed_device *dev)
-+{
-+      if (!mtk_wed_get_rx_capa(dev) || !dev->wlan.hw_rro)
-+              return;
-+
-+      wed_set(dev, MTK_WED_RRO_PG_BM_RX_DMAM,
-+              FIELD_PREP(MTK_WED_RRO_PG_BM_RX_SDL0, 128));
-+
-+      wed_w32(dev, MTK_WED_RRO_PG_BM_BASE, dev->hw_rro.desc_phys);
-+
-+      wed_w32(dev, MTK_WED_RRO_PG_BM_INIT_PTR,
-+              MTK_WED_RRO_PG_BM_INIT_SW_TAIL_IDX |
-+              FIELD_PREP(MTK_WED_RRO_PG_BM_SW_TAIL_IDX,
-+                         MTK_WED_RX_PG_BM_CNT));
-+
-+      /* enable rx_page_bm to fetch dmad */
-+      wed_set(dev, MTK_WED_CTRL, MTK_WED_CTRL_WED_RX_PG_BM_EN);
- }
- static void
-@@ -639,6 +758,8 @@ mtk_wed_rx_buffer_hw_init(struct mtk_wed
-       wed_w32(dev, MTK_WED_RX_BM_DYN_ALLOC_TH,
-               FIELD_PREP(MTK_WED_RX_BM_DYN_ALLOC_TH_H, 0xffff));
-       wed_set(dev, MTK_WED_CTRL, MTK_WED_CTRL_WED_RX_BM_EN);
-+
-+      mtk_wed_hwrro_init(dev);
- }
- static void
-@@ -934,6 +1055,8 @@ mtk_wed_bus_init(struct mtk_wed_device *
- static void
- mtk_wed_set_wpdma(struct mtk_wed_device *dev)
- {
-+      int i;
-+
-       if (mtk_wed_is_v1(dev->hw)) {
-               wed_w32(dev, MTK_WED_WPDMA_CFG_BASE,  dev->wlan.wpdma_phys);
-               return;
-@@ -951,6 +1074,15 @@ mtk_wed_set_wpdma(struct mtk_wed_device
-       wed_w32(dev, MTK_WED_WPDMA_RX_GLO_CFG, dev->wlan.wpdma_rx_glo);
-       wed_w32(dev, dev->hw->soc->regmap.wpdma_rx_ring0, dev->wlan.wpdma_rx);
-+
-+      if (!dev->wlan.hw_rro)
-+              return;
-+
-+      wed_w32(dev, MTK_WED_RRO_RX_D_CFG(0), dev->wlan.wpdma_rx_rro[0]);
-+      wed_w32(dev, MTK_WED_RRO_RX_D_CFG(1), dev->wlan.wpdma_rx_rro[1]);
-+      for (i = 0; i < MTK_WED_RX_PAGE_QUEUES; i++)
-+              wed_w32(dev, MTK_WED_RRO_MSDU_PG_RING_CFG(i),
-+                      dev->wlan.wpdma_rx_pg + i * 0x10);
- }
- static void
-@@ -1762,6 +1894,165 @@ mtk_wed_dma_enable(struct mtk_wed_device
- }
- static void
-+mtk_wed_start_hw_rro(struct mtk_wed_device *dev, u32 irq_mask, bool reset)
-+{
-+      int i;
-+
-+      wed_w32(dev, MTK_WED_WPDMA_INT_MASK, irq_mask);
-+      wed_w32(dev, MTK_WED_INT_MASK, irq_mask);
-+
-+      if (!mtk_wed_get_rx_capa(dev) || !dev->wlan.hw_rro)
-+              return;
-+
-+      wed_set(dev, MTK_WED_RRO_RX_D_CFG(2), MTK_WED_RRO_MSDU_PG_DRV_CLR);
-+      wed_w32(dev, MTK_WED_RRO_MSDU_PG_RING2_CFG,
-+              MTK_WED_RRO_MSDU_PG_DRV_CLR);
-+
-+      wed_w32(dev, MTK_WED_WPDMA_INT_CTRL_RRO_RX,
-+              MTK_WED_WPDMA_INT_CTRL_RRO_RX0_EN |
-+              MTK_WED_WPDMA_INT_CTRL_RRO_RX0_CLR |
-+              MTK_WED_WPDMA_INT_CTRL_RRO_RX1_EN |
-+              MTK_WED_WPDMA_INT_CTRL_RRO_RX1_CLR |
-+              FIELD_PREP(MTK_WED_WPDMA_INT_CTRL_RRO_RX0_DONE_TRIG,
-+                         dev->wlan.rro_rx_tbit[0]) |
-+              FIELD_PREP(MTK_WED_WPDMA_INT_CTRL_RRO_RX1_DONE_TRIG,
-+                         dev->wlan.rro_rx_tbit[1]));
-+
-+      wed_w32(dev, MTK_WED_WPDMA_INT_CTRL_RRO_MSDU_PG,
-+              MTK_WED_WPDMA_INT_CTRL_RRO_PG0_EN |
-+              MTK_WED_WPDMA_INT_CTRL_RRO_PG0_CLR |
-+              MTK_WED_WPDMA_INT_CTRL_RRO_PG1_EN |
-+              MTK_WED_WPDMA_INT_CTRL_RRO_PG1_CLR |
-+              MTK_WED_WPDMA_INT_CTRL_RRO_PG2_EN |
-+              MTK_WED_WPDMA_INT_CTRL_RRO_PG2_CLR |
-+              FIELD_PREP(MTK_WED_WPDMA_INT_CTRL_RRO_PG0_DONE_TRIG,
-+                         dev->wlan.rx_pg_tbit[0]) |
-+              FIELD_PREP(MTK_WED_WPDMA_INT_CTRL_RRO_PG1_DONE_TRIG,
-+                         dev->wlan.rx_pg_tbit[1]) |
-+              FIELD_PREP(MTK_WED_WPDMA_INT_CTRL_RRO_PG2_DONE_TRIG,
-+                         dev->wlan.rx_pg_tbit[2]));
-+
-+      /* RRO_MSDU_PG_RING2_CFG1_FLD_DRV_EN should be enabled after
-+       * WM FWDL completed, otherwise RRO_MSDU_PG ring may broken
-+       */
-+      wed_set(dev, MTK_WED_RRO_MSDU_PG_RING2_CFG,
-+              MTK_WED_RRO_MSDU_PG_DRV_EN);
-+
-+      for (i = 0; i < MTK_WED_RX_QUEUES; i++) {
-+              struct mtk_wed_ring *ring = &dev->rx_rro_ring[i];
-+
-+              if (!(ring->flags & MTK_WED_RING_CONFIGURED))
-+                      continue;
-+
-+              if (mtk_wed_check_wfdma_rx_fill(dev, ring))
-+                      dev_err(dev->hw->dev,
-+                              "rx_rro_ring(%d) initialization failed\n", i);
-+      }
-+
-+      for (i = 0; i < MTK_WED_RX_PAGE_QUEUES; i++) {
-+              struct mtk_wed_ring *ring = &dev->rx_page_ring[i];
-+
-+              if (!(ring->flags & MTK_WED_RING_CONFIGURED))
-+                      continue;
-+
-+              if (mtk_wed_check_wfdma_rx_fill(dev, ring))
-+                      dev_err(dev->hw->dev,
-+                              "rx_page_ring(%d) initialization failed\n", i);
-+      }
-+}
-+
-+static void
-+mtk_wed_rro_rx_ring_setup(struct mtk_wed_device *dev, int idx,
-+                        void __iomem *regs)
-+{
-+      struct mtk_wed_ring *ring = &dev->rx_rro_ring[idx];
-+
-+      ring->wpdma = regs;
-+      wed_w32(dev, MTK_WED_RRO_RX_D_RX(idx) + MTK_WED_RING_OFS_BASE,
-+              readl(regs));
-+      wed_w32(dev, MTK_WED_RRO_RX_D_RX(idx) + MTK_WED_RING_OFS_COUNT,
-+              readl(regs + MTK_WED_RING_OFS_COUNT));
-+      ring->flags |= MTK_WED_RING_CONFIGURED;
-+}
-+
-+static void
-+mtk_wed_msdu_pg_rx_ring_setup(struct mtk_wed_device *dev, int idx, void __iomem *regs)
-+{
-+      struct mtk_wed_ring *ring = &dev->rx_page_ring[idx];
-+
-+      ring->wpdma = regs;
-+      wed_w32(dev, MTK_WED_RRO_MSDU_PG_CTRL0(idx) + MTK_WED_RING_OFS_BASE,
-+              readl(regs));
-+      wed_w32(dev, MTK_WED_RRO_MSDU_PG_CTRL0(idx) + MTK_WED_RING_OFS_COUNT,
-+              readl(regs + MTK_WED_RING_OFS_COUNT));
-+      ring->flags |= MTK_WED_RING_CONFIGURED;
-+}
-+
-+static int
-+mtk_wed_ind_rx_ring_setup(struct mtk_wed_device *dev, void __iomem *regs)
-+{
-+      struct mtk_wed_ring *ring = &dev->ind_cmd_ring;
-+      u32 val = readl(regs + MTK_WED_RING_OFS_COUNT);
-+      int i, count = 0;
-+
-+      ring->wpdma = regs;
-+      wed_w32(dev, MTK_WED_IND_CMD_RX_CTRL1 + MTK_WED_RING_OFS_BASE,
-+              readl(regs) & 0xfffffff0);
-+
-+      wed_w32(dev, MTK_WED_IND_CMD_RX_CTRL1 + MTK_WED_RING_OFS_COUNT,
-+              readl(regs + MTK_WED_RING_OFS_COUNT));
-+
-+      /* ack sn cr */
-+      wed_w32(dev, MTK_WED_RRO_CFG0, dev->wlan.phy_base +
-+              dev->wlan.ind_cmd.ack_sn_addr);
-+      wed_w32(dev, MTK_WED_RRO_CFG1,
-+              FIELD_PREP(MTK_WED_RRO_CFG1_MAX_WIN_SZ,
-+                         dev->wlan.ind_cmd.win_size) |
-+              FIELD_PREP(MTK_WED_RRO_CFG1_PARTICL_SE_ID,
-+                         dev->wlan.ind_cmd.particular_sid));
-+
-+      /* particular session addr element */
-+      wed_w32(dev, MTK_WED_ADDR_ELEM_CFG0,
-+              dev->wlan.ind_cmd.particular_se_phys);
-+
-+      for (i = 0; i < dev->wlan.ind_cmd.se_group_nums; i++) {
-+              wed_w32(dev, MTK_WED_RADDR_ELEM_TBL_WDATA,
-+                      dev->wlan.ind_cmd.addr_elem_phys[i] >> 4);
-+              wed_w32(dev, MTK_WED_ADDR_ELEM_TBL_CFG,
-+                      MTK_WED_ADDR_ELEM_TBL_WR | (i & 0x7f));
-+
-+              val = wed_r32(dev, MTK_WED_ADDR_ELEM_TBL_CFG);
-+              while (!(val & MTK_WED_ADDR_ELEM_TBL_WR_RDY) && count++ < 100)
-+                      val = wed_r32(dev, MTK_WED_ADDR_ELEM_TBL_CFG);
-+              if (count >= 100)
-+                      dev_err(dev->hw->dev,
-+                              "write ba session base failed\n");
-+      }
-+
-+      /* pn check init */
-+      for (i = 0; i < dev->wlan.ind_cmd.particular_sid; i++) {
-+              wed_w32(dev, MTK_WED_PN_CHECK_WDATA_M,
-+                      MTK_WED_PN_CHECK_IS_FIRST);
-+
-+              wed_w32(dev, MTK_WED_PN_CHECK_CFG, MTK_WED_PN_CHECK_WR |
-+                      FIELD_PREP(MTK_WED_PN_CHECK_SE_ID, i));
-+
-+              count = 0;
-+              val = wed_r32(dev, MTK_WED_PN_CHECK_CFG);
-+              while (!(val & MTK_WED_PN_CHECK_WR_RDY) && count++ < 100)
-+                      val = wed_r32(dev, MTK_WED_PN_CHECK_CFG);
-+              if (count >= 100)
-+                      dev_err(dev->hw->dev,
-+                              "session(%d) initialization failed\n", i);
-+      }
-+
-+      wed_w32(dev, MTK_WED_RX_IND_CMD_CNT0, MTK_WED_RX_IND_CMD_DBG_CNT_EN);
-+      wed_set(dev, MTK_WED_CTRL, MTK_WED_CTRL_WED_RX_IND_CMD_EN);
-+
-+      return 0;
-+}
-+
-+static void
- mtk_wed_start(struct mtk_wed_device *dev, u32 irq_mask)
- {
-       int i;
-@@ -2215,6 +2506,10 @@ void mtk_wed_add_hw(struct device_node *
-               .detach = mtk_wed_detach,
-               .ppe_check = mtk_wed_ppe_check,
-               .setup_tc = mtk_wed_setup_tc,
-+              .start_hw_rro = mtk_wed_start_hw_rro,
-+              .rro_rx_ring_setup = mtk_wed_rro_rx_ring_setup,
-+              .msdu_pg_rx_ring_setup = mtk_wed_msdu_pg_rx_ring_setup,
-+              .ind_rx_ring_setup = mtk_wed_ind_rx_ring_setup,
-       };
-       struct device_node *eth_np = eth->dev->of_node;
-       struct platform_device *pdev;
---- a/include/linux/soc/mediatek/mtk_wed.h
-+++ b/include/linux/soc/mediatek/mtk_wed.h
-@@ -10,6 +10,7 @@
- #define MTK_WED_TX_QUEUES             2
- #define MTK_WED_RX_QUEUES             2
-+#define MTK_WED_RX_PAGE_QUEUES                3
- #define WED_WO_STA_REC                        0x6
-@@ -99,6 +100,9 @@ struct mtk_wed_device {
-       struct mtk_wed_ring txfree_ring;
-       struct mtk_wed_ring tx_wdma[MTK_WED_TX_QUEUES];
-       struct mtk_wed_ring rx_wdma[MTK_WED_RX_QUEUES];
-+      struct mtk_wed_ring rx_rro_ring[MTK_WED_RX_QUEUES];
-+      struct mtk_wed_ring rx_page_ring[MTK_WED_RX_PAGE_QUEUES];
-+      struct mtk_wed_ring ind_cmd_ring;
-       struct {
-               int size;
-@@ -120,6 +124,13 @@ struct mtk_wed_device {
-               dma_addr_t fdbk_phys;
-       } rro;
-+      struct {
-+              int size;
-+              struct mtk_wed_buf *pages;
-+              struct mtk_wed_bm_desc *desc;
-+              dma_addr_t desc_phys;
-+      } hw_rro;
-+
-       /* filled by driver: */
-       struct {
-               union {
-@@ -138,6 +149,8 @@ struct mtk_wed_device {
-               u32 wpdma_txfree;
-               u32 wpdma_rx_glo;
-               u32 wpdma_rx;
-+              u32 wpdma_rx_rro[MTK_WED_RX_QUEUES];
-+              u32 wpdma_rx_pg;
-               bool wcid_512;
-               bool hw_rro;
-@@ -152,9 +165,20 @@ struct mtk_wed_device {
-               u8 tx_tbit[MTK_WED_TX_QUEUES];
-               u8 rx_tbit[MTK_WED_RX_QUEUES];
-+              u8 rro_rx_tbit[MTK_WED_RX_QUEUES];
-+              u8 rx_pg_tbit[MTK_WED_RX_PAGE_QUEUES];
-               u8 txfree_tbit;
-               u8 amsdu_max_subframes;
-+              struct {
-+                      u8 se_group_nums;
-+                      u16 win_size;
-+                      u16 particular_sid;
-+                      u32 ack_sn_addr;
-+                      dma_addr_t particular_se_phys;
-+                      dma_addr_t addr_elem_phys[1024];
-+              } ind_cmd;
-+
-               u32 (*init_buf)(void *ptr, dma_addr_t phys, int token_id);
-               int (*offload_enable)(struct mtk_wed_device *wed);
-               void (*offload_disable)(struct mtk_wed_device *wed);
-@@ -193,6 +217,14 @@ struct mtk_wed_ops {
-       void (*irq_set_mask)(struct mtk_wed_device *dev, u32 mask);
-       int (*setup_tc)(struct mtk_wed_device *wed, struct net_device *dev,
-                       enum tc_setup_type type, void *type_data);
-+      void (*start_hw_rro)(struct mtk_wed_device *dev, u32 irq_mask,
-+                           bool reset);
-+      void (*rro_rx_ring_setup)(struct mtk_wed_device *dev, int ring,
-+                                void __iomem *regs);
-+      void (*msdu_pg_rx_ring_setup)(struct mtk_wed_device *dev, int ring,
-+                                    void __iomem *regs);
-+      int (*ind_rx_ring_setup)(struct mtk_wed_device *dev,
-+                               void __iomem *regs);
- };
- extern const struct mtk_wed_ops __rcu *mtk_soc_wed_ops;
-@@ -264,6 +296,15 @@ static inline bool mtk_wed_is_amsdu_supp
- #define mtk_wed_device_dma_reset(_dev) (_dev)->ops->reset_dma(_dev)
- #define mtk_wed_device_setup_tc(_dev, _netdev, _type, _type_data) \
-       (_dev)->ops->setup_tc(_dev, _netdev, _type, _type_data)
-+#define mtk_wed_device_start_hw_rro(_dev, _mask, _reset) \
-+      (_dev)->ops->start_hw_rro(_dev, _mask, _reset)
-+#define mtk_wed_device_rro_rx_ring_setup(_dev, _ring, _regs) \
-+      (_dev)->ops->rro_rx_ring_setup(_dev, _ring, _regs)
-+#define mtk_wed_device_msdu_pg_rx_ring_setup(_dev, _ring, _regs) \
-+      (_dev)->ops->msdu_pg_rx_ring_setup(_dev, _ring, _regs)
-+#define mtk_wed_device_ind_rx_ring_setup(_dev, _regs) \
-+      (_dev)->ops->ind_rx_ring_setup(_dev, _regs)
-+
- #else
- static inline bool mtk_wed_device_active(struct mtk_wed_device *dev)
- {
-@@ -283,6 +324,10 @@ static inline bool mtk_wed_device_active
- #define mtk_wed_device_stop(_dev) do {} while (0)
- #define mtk_wed_device_dma_reset(_dev) do {} while (0)
- #define mtk_wed_device_setup_tc(_dev, _netdev, _type, _type_data) -EOPNOTSUPP
-+#define mtk_wed_device_start_hw_rro(_dev, _mask, _reset) do {} while (0)
-+#define mtk_wed_device_rro_rx_ring_setup(_dev, _ring, _regs) -ENODEV
-+#define mtk_wed_device_msdu_pg_rx_ring_setup(_dev, _ring, _regs) -ENODEV
-+#define mtk_wed_device_ind_rx_ring_setup(_dev, _regs) -ENODEV
- #endif
- #endif
diff --git a/target/linux/generic/backport-5.15/752-18-v6.7-net-ethernet-mtk_wed-debugfs-move-wed_v2-specific-re.patch b/target/linux/generic/backport-5.15/752-18-v6.7-net-ethernet-mtk_wed-debugfs-move-wed_v2-specific-re.patch
deleted file mode 100644 (file)
index 5ea43a4..0000000
+++ /dev/null
@@ -1,78 +0,0 @@
-From: Lorenzo Bianconi <[email protected]>
-Date: Mon, 18 Sep 2023 12:29:17 +0200
-Subject: [PATCH] net: ethernet: mtk_wed: debugfs: move wed_v2 specific regs
- out of regs array
-
-Move specific WED2.0 debugfs entries out of regs array. This is a
-preliminary patch to introduce WED 3.0 debugfs info.
-
-Signed-off-by: Lorenzo Bianconi <[email protected]>
-Signed-off-by: Paolo Abeni <[email protected]>
----
-
---- a/drivers/net/ethernet/mediatek/mtk_wed_debugfs.c
-+++ b/drivers/net/ethernet/mediatek/mtk_wed_debugfs.c
-@@ -151,7 +151,7 @@ DEFINE_SHOW_ATTRIBUTE(wed_txinfo);
- static int
- wed_rxinfo_show(struct seq_file *s, void *data)
- {
--      static const struct reg_dump regs[] = {
-+      static const struct reg_dump regs_common[] = {
-               DUMP_STR("WPDMA RX"),
-               DUMP_WPDMA_RX_RING(0),
-               DUMP_WPDMA_RX_RING(1),
-@@ -169,7 +169,7 @@ wed_rxinfo_show(struct seq_file *s, void
-               DUMP_WED_RING(WED_RING_RX_DATA(0)),
-               DUMP_WED_RING(WED_RING_RX_DATA(1)),
--              DUMP_STR("WED RRO"),
-+              DUMP_STR("WED WO RRO"),
-               DUMP_WED_RRO_RING(WED_RROQM_MIOD_CTRL0),
-               DUMP_WED(WED_RROQM_MID_MIB),
-               DUMP_WED(WED_RROQM_MOD_MIB),
-@@ -180,17 +180,6 @@ wed_rxinfo_show(struct seq_file *s, void
-               DUMP_WED(WED_RROQM_FDBK_ANC_MIB),
-               DUMP_WED(WED_RROQM_FDBK_ANC2H_MIB),
--              DUMP_STR("WED Route QM"),
--              DUMP_WED(WED_RTQM_R2H_MIB(0)),
--              DUMP_WED(WED_RTQM_R2Q_MIB(0)),
--              DUMP_WED(WED_RTQM_Q2H_MIB(0)),
--              DUMP_WED(WED_RTQM_R2H_MIB(1)),
--              DUMP_WED(WED_RTQM_R2Q_MIB(1)),
--              DUMP_WED(WED_RTQM_Q2H_MIB(1)),
--              DUMP_WED(WED_RTQM_Q2N_MIB),
--              DUMP_WED(WED_RTQM_Q2B_MIB),
--              DUMP_WED(WED_RTQM_PFDBK_MIB),
--
-               DUMP_STR("WED WDMA TX"),
-               DUMP_WED(WED_WDMA_TX_MIB),
-               DUMP_WED_RING(WED_WDMA_RING_TX),
-@@ -211,11 +200,25 @@ wed_rxinfo_show(struct seq_file *s, void
-               DUMP_WED(WED_RX_BM_INTF),
-               DUMP_WED(WED_RX_BM_ERR_STS),
-       };
-+      static const struct reg_dump regs_wed_v2[] = {
-+              DUMP_STR("WED Route QM"),
-+              DUMP_WED(WED_RTQM_R2H_MIB(0)),
-+              DUMP_WED(WED_RTQM_R2Q_MIB(0)),
-+              DUMP_WED(WED_RTQM_Q2H_MIB(0)),
-+              DUMP_WED(WED_RTQM_R2H_MIB(1)),
-+              DUMP_WED(WED_RTQM_R2Q_MIB(1)),
-+              DUMP_WED(WED_RTQM_Q2H_MIB(1)),
-+              DUMP_WED(WED_RTQM_Q2N_MIB),
-+              DUMP_WED(WED_RTQM_Q2B_MIB),
-+              DUMP_WED(WED_RTQM_PFDBK_MIB),
-+      };
-       struct mtk_wed_hw *hw = s->private;
-       struct mtk_wed_device *dev = hw->wed_dev;
--      if (dev)
--              dump_wed_regs(s, dev, regs, ARRAY_SIZE(regs));
-+      if (dev) {
-+              dump_wed_regs(s, dev, regs_common, ARRAY_SIZE(regs_common));
-+              dump_wed_regs(s, dev, regs_wed_v2, ARRAY_SIZE(regs_wed_v2));
-+      }
-       return 0;
- }
diff --git a/target/linux/generic/backport-5.15/752-19-v6.7-net-ethernet-mtk_wed-debugfs-add-WED-3.0-debugfs-ent.patch b/target/linux/generic/backport-5.15/752-19-v6.7-net-ethernet-mtk_wed-debugfs-add-WED-3.0-debugfs-ent.patch
deleted file mode 100644 (file)
index f491d2f..0000000
+++ /dev/null
@@ -1,432 +0,0 @@
-From: Sujuan Chen <[email protected]>
-Date: Mon, 18 Sep 2023 12:29:18 +0200
-Subject: [PATCH] net: ethernet: mtk_wed: debugfs: add WED 3.0 debugfs entries
-
-Introduce WED3.0 debugfs entries useful for debugging.
-
-Co-developed-by: Lorenzo Bianconi <[email protected]>
-Signed-off-by: Lorenzo Bianconi <[email protected]>
-Signed-off-by: Sujuan Chen <[email protected]>
-Signed-off-by: Paolo Abeni <[email protected]>
----
-
---- a/drivers/net/ethernet/mediatek/mtk_wed_debugfs.c
-+++ b/drivers/net/ethernet/mediatek/mtk_wed_debugfs.c
-@@ -11,6 +11,7 @@ struct reg_dump {
-       u16 offset;
-       u8 type;
-       u8 base;
-+      u32 mask;
- };
- enum {
-@@ -25,6 +26,8 @@ enum {
- #define DUMP_STR(_str) { _str, 0, DUMP_TYPE_STRING }
- #define DUMP_REG(_reg, ...) { #_reg, MTK_##_reg, __VA_ARGS__ }
-+#define DUMP_REG_MASK(_reg, _mask)    \
-+      { #_mask, MTK_##_reg, DUMP_TYPE_WED, 0, MTK_##_mask }
- #define DUMP_RING(_prefix, _base, ...)                                \
-       { _prefix " BASE", _base, __VA_ARGS__ },                \
-       { _prefix " CNT",  _base + 0x4, __VA_ARGS__ },  \
-@@ -32,6 +35,7 @@ enum {
-       { _prefix " DIDX", _base + 0xc, __VA_ARGS__ }
- #define DUMP_WED(_reg) DUMP_REG(_reg, DUMP_TYPE_WED)
-+#define DUMP_WED_MASK(_reg, _mask) DUMP_REG_MASK(_reg, _mask)
- #define DUMP_WED_RING(_base) DUMP_RING(#_base, MTK_##_base, DUMP_TYPE_WED)
- #define DUMP_WDMA(_reg) DUMP_REG(_reg, DUMP_TYPE_WDMA)
-@@ -212,12 +216,58 @@ wed_rxinfo_show(struct seq_file *s, void
-               DUMP_WED(WED_RTQM_Q2B_MIB),
-               DUMP_WED(WED_RTQM_PFDBK_MIB),
-       };
-+      static const struct reg_dump regs_wed_v3[] = {
-+              DUMP_STR("WED RX RRO DATA"),
-+              DUMP_WED_RING(WED_RRO_RX_D_RX(0)),
-+              DUMP_WED_RING(WED_RRO_RX_D_RX(1)),
-+
-+              DUMP_STR("WED RX MSDU PAGE"),
-+              DUMP_WED_RING(WED_RRO_MSDU_PG_CTRL0(0)),
-+              DUMP_WED_RING(WED_RRO_MSDU_PG_CTRL0(1)),
-+              DUMP_WED_RING(WED_RRO_MSDU_PG_CTRL0(2)),
-+
-+              DUMP_STR("WED RX IND CMD"),
-+              DUMP_WED(WED_IND_CMD_RX_CTRL1),
-+              DUMP_WED_MASK(WED_IND_CMD_RX_CTRL2, WED_IND_CMD_MAX_CNT),
-+              DUMP_WED_MASK(WED_IND_CMD_RX_CTRL0, WED_IND_CMD_PROC_IDX),
-+              DUMP_WED_MASK(RRO_IND_CMD_SIGNATURE, RRO_IND_CMD_DMA_IDX),
-+              DUMP_WED_MASK(WED_IND_CMD_RX_CTRL0, WED_IND_CMD_MAGIC_CNT),
-+              DUMP_WED_MASK(RRO_IND_CMD_SIGNATURE, RRO_IND_CMD_MAGIC_CNT),
-+              DUMP_WED_MASK(WED_IND_CMD_RX_CTRL0,
-+                            WED_IND_CMD_PREFETCH_FREE_CNT),
-+              DUMP_WED_MASK(WED_RRO_CFG1, WED_RRO_CFG1_PARTICL_SE_ID),
-+
-+              DUMP_STR("WED ADDR ELEM"),
-+              DUMP_WED(WED_ADDR_ELEM_CFG0),
-+              DUMP_WED_MASK(WED_ADDR_ELEM_CFG1,
-+                            WED_ADDR_ELEM_PREFETCH_FREE_CNT),
-+
-+              DUMP_STR("WED Route QM"),
-+              DUMP_WED(WED_RTQM_ENQ_I2Q_DMAD_CNT),
-+              DUMP_WED(WED_RTQM_ENQ_I2N_DMAD_CNT),
-+              DUMP_WED(WED_RTQM_ENQ_I2Q_PKT_CNT),
-+              DUMP_WED(WED_RTQM_ENQ_I2N_PKT_CNT),
-+              DUMP_WED(WED_RTQM_ENQ_USED_ENTRY_CNT),
-+              DUMP_WED(WED_RTQM_ENQ_ERR_CNT),
-+
-+              DUMP_WED(WED_RTQM_DEQ_DMAD_CNT),
-+              DUMP_WED(WED_RTQM_DEQ_Q2I_DMAD_CNT),
-+              DUMP_WED(WED_RTQM_DEQ_PKT_CNT),
-+              DUMP_WED(WED_RTQM_DEQ_Q2I_PKT_CNT),
-+              DUMP_WED(WED_RTQM_DEQ_USED_PFDBK_CNT),
-+              DUMP_WED(WED_RTQM_DEQ_ERR_CNT),
-+      };
-       struct mtk_wed_hw *hw = s->private;
-       struct mtk_wed_device *dev = hw->wed_dev;
-       if (dev) {
-               dump_wed_regs(s, dev, regs_common, ARRAY_SIZE(regs_common));
--              dump_wed_regs(s, dev, regs_wed_v2, ARRAY_SIZE(regs_wed_v2));
-+              if (mtk_wed_is_v2(hw))
-+                      dump_wed_regs(s, dev,
-+                                    regs_wed_v2, ARRAY_SIZE(regs_wed_v2));
-+              else
-+                      dump_wed_regs(s, dev,
-+                                    regs_wed_v3, ARRAY_SIZE(regs_wed_v3));
-       }
-       return 0;
-@@ -225,6 +275,314 @@ wed_rxinfo_show(struct seq_file *s, void
- DEFINE_SHOW_ATTRIBUTE(wed_rxinfo);
- static int
-+wed_amsdu_show(struct seq_file *s, void *data)
-+{
-+      static const struct reg_dump regs[] = {
-+              DUMP_STR("WED AMDSU INFO"),
-+              DUMP_WED(WED_MON_AMSDU_FIFO_DMAD),
-+
-+              DUMP_STR("WED AMDSU ENG0 INFO"),
-+              DUMP_WED(WED_MON_AMSDU_ENG_DMAD(0)),
-+              DUMP_WED(WED_MON_AMSDU_ENG_QFPL(0)),
-+              DUMP_WED(WED_MON_AMSDU_ENG_QENI(0)),
-+              DUMP_WED(WED_MON_AMSDU_ENG_QENO(0)),
-+              DUMP_WED(WED_MON_AMSDU_ENG_MERG(0)),
-+              DUMP_WED_MASK(WED_MON_AMSDU_ENG_CNT8(0),
-+                            WED_AMSDU_ENG_MAX_PL_CNT),
-+              DUMP_WED_MASK(WED_MON_AMSDU_ENG_CNT8(0),
-+                            WED_AMSDU_ENG_MAX_QGPP_CNT),
-+              DUMP_WED_MASK(WED_MON_AMSDU_ENG_CNT9(0),
-+                            WED_AMSDU_ENG_CUR_ENTRY),
-+              DUMP_WED_MASK(WED_MON_AMSDU_ENG_CNT9(0),
-+                            WED_AMSDU_ENG_MAX_BUF_MERGED),
-+              DUMP_WED_MASK(WED_MON_AMSDU_ENG_CNT9(0),
-+                            WED_AMSDU_ENG_MAX_MSDU_MERGED),
-+
-+              DUMP_STR("WED AMDSU ENG1 INFO"),
-+              DUMP_WED(WED_MON_AMSDU_ENG_DMAD(1)),
-+              DUMP_WED(WED_MON_AMSDU_ENG_QFPL(1)),
-+              DUMP_WED(WED_MON_AMSDU_ENG_QENI(1)),
-+              DUMP_WED(WED_MON_AMSDU_ENG_QENO(1)),
-+              DUMP_WED(WED_MON_AMSDU_ENG_MERG(1)),
-+              DUMP_WED_MASK(WED_MON_AMSDU_ENG_CNT8(1),
-+                            WED_AMSDU_ENG_MAX_PL_CNT),
-+              DUMP_WED_MASK(WED_MON_AMSDU_ENG_CNT8(1),
-+                            WED_AMSDU_ENG_MAX_QGPP_CNT),
-+              DUMP_WED_MASK(WED_MON_AMSDU_ENG_CNT9(1),
-+                            WED_AMSDU_ENG_CUR_ENTRY),
-+              DUMP_WED_MASK(WED_MON_AMSDU_ENG_CNT9(2),
-+                            WED_AMSDU_ENG_MAX_BUF_MERGED),
-+              DUMP_WED_MASK(WED_MON_AMSDU_ENG_CNT9(2),
-+                            WED_AMSDU_ENG_MAX_MSDU_MERGED),
-+
-+              DUMP_STR("WED AMDSU ENG2 INFO"),
-+              DUMP_WED(WED_MON_AMSDU_ENG_DMAD(2)),
-+              DUMP_WED(WED_MON_AMSDU_ENG_QFPL(2)),
-+              DUMP_WED(WED_MON_AMSDU_ENG_QENI(2)),
-+              DUMP_WED(WED_MON_AMSDU_ENG_QENO(2)),
-+              DUMP_WED(WED_MON_AMSDU_ENG_MERG(2)),
-+              DUMP_WED_MASK(WED_MON_AMSDU_ENG_CNT8(2),
-+                            WED_AMSDU_ENG_MAX_PL_CNT),
-+              DUMP_WED_MASK(WED_MON_AMSDU_ENG_CNT8(2),
-+                            WED_AMSDU_ENG_MAX_QGPP_CNT),
-+              DUMP_WED_MASK(WED_MON_AMSDU_ENG_CNT9(2),
-+                            WED_AMSDU_ENG_CUR_ENTRY),
-+              DUMP_WED_MASK(WED_MON_AMSDU_ENG_CNT9(2),
-+                            WED_AMSDU_ENG_MAX_BUF_MERGED),
-+              DUMP_WED_MASK(WED_MON_AMSDU_ENG_CNT9(2),
-+                            WED_AMSDU_ENG_MAX_MSDU_MERGED),
-+
-+              DUMP_STR("WED AMDSU ENG3 INFO"),
-+              DUMP_WED(WED_MON_AMSDU_ENG_DMAD(3)),
-+              DUMP_WED(WED_MON_AMSDU_ENG_QFPL(3)),
-+              DUMP_WED(WED_MON_AMSDU_ENG_QENI(3)),
-+              DUMP_WED(WED_MON_AMSDU_ENG_QENO(3)),
-+              DUMP_WED(WED_MON_AMSDU_ENG_MERG(3)),
-+              DUMP_WED_MASK(WED_MON_AMSDU_ENG_CNT8(3),
-+                            WED_AMSDU_ENG_MAX_PL_CNT),
-+              DUMP_WED_MASK(WED_MON_AMSDU_ENG_CNT8(3),
-+                            WED_AMSDU_ENG_MAX_QGPP_CNT),
-+              DUMP_WED_MASK(WED_MON_AMSDU_ENG_CNT9(3),
-+                            WED_AMSDU_ENG_CUR_ENTRY),
-+              DUMP_WED_MASK(WED_MON_AMSDU_ENG_CNT9(3),
-+                            WED_AMSDU_ENG_MAX_BUF_MERGED),
-+              DUMP_WED_MASK(WED_MON_AMSDU_ENG_CNT9(3),
-+                            WED_AMSDU_ENG_MAX_MSDU_MERGED),
-+
-+              DUMP_STR("WED AMDSU ENG4 INFO"),
-+              DUMP_WED(WED_MON_AMSDU_ENG_DMAD(4)),
-+              DUMP_WED(WED_MON_AMSDU_ENG_QFPL(4)),
-+              DUMP_WED(WED_MON_AMSDU_ENG_QENI(4)),
-+              DUMP_WED(WED_MON_AMSDU_ENG_QENO(4)),
-+              DUMP_WED(WED_MON_AMSDU_ENG_MERG(4)),
-+              DUMP_WED_MASK(WED_MON_AMSDU_ENG_CNT8(4),
-+                            WED_AMSDU_ENG_MAX_PL_CNT),
-+              DUMP_WED_MASK(WED_MON_AMSDU_ENG_CNT8(4),
-+                            WED_AMSDU_ENG_MAX_QGPP_CNT),
-+              DUMP_WED_MASK(WED_MON_AMSDU_ENG_CNT9(4),
-+                            WED_AMSDU_ENG_CUR_ENTRY),
-+              DUMP_WED_MASK(WED_MON_AMSDU_ENG_CNT9(4),
-+                            WED_AMSDU_ENG_MAX_BUF_MERGED),
-+              DUMP_WED_MASK(WED_MON_AMSDU_ENG_CNT9(4),
-+                            WED_AMSDU_ENG_MAX_MSDU_MERGED),
-+
-+              DUMP_STR("WED AMDSU ENG5 INFO"),
-+              DUMP_WED(WED_MON_AMSDU_ENG_DMAD(5)),
-+              DUMP_WED(WED_MON_AMSDU_ENG_QFPL(5)),
-+              DUMP_WED(WED_MON_AMSDU_ENG_QENI(5)),
-+              DUMP_WED(WED_MON_AMSDU_ENG_QENO(5)),
-+              DUMP_WED(WED_MON_AMSDU_ENG_MERG(5)),
-+              DUMP_WED_MASK(WED_MON_AMSDU_ENG_CNT8(5),
-+                            WED_AMSDU_ENG_MAX_PL_CNT),
-+              DUMP_WED_MASK(WED_MON_AMSDU_ENG_CNT8(5),
-+                            WED_AMSDU_ENG_MAX_QGPP_CNT),
-+              DUMP_WED_MASK(WED_MON_AMSDU_ENG_CNT9(5),
-+                            WED_AMSDU_ENG_CUR_ENTRY),
-+              DUMP_WED_MASK(WED_MON_AMSDU_ENG_CNT9(5),
-+                            WED_AMSDU_ENG_MAX_BUF_MERGED),
-+              DUMP_WED_MASK(WED_MON_AMSDU_ENG_CNT9(5),
-+                            WED_AMSDU_ENG_MAX_MSDU_MERGED),
-+
-+              DUMP_STR("WED AMDSU ENG6 INFO"),
-+              DUMP_WED(WED_MON_AMSDU_ENG_DMAD(6)),
-+              DUMP_WED(WED_MON_AMSDU_ENG_QFPL(6)),
-+              DUMP_WED(WED_MON_AMSDU_ENG_QENI(6)),
-+              DUMP_WED(WED_MON_AMSDU_ENG_QENO(6)),
-+              DUMP_WED(WED_MON_AMSDU_ENG_MERG(6)),
-+              DUMP_WED_MASK(WED_MON_AMSDU_ENG_CNT8(6),
-+                            WED_AMSDU_ENG_MAX_PL_CNT),
-+              DUMP_WED_MASK(WED_MON_AMSDU_ENG_CNT8(6),
-+                            WED_AMSDU_ENG_MAX_QGPP_CNT),
-+              DUMP_WED_MASK(WED_MON_AMSDU_ENG_CNT9(6),
-+                            WED_AMSDU_ENG_CUR_ENTRY),
-+              DUMP_WED_MASK(WED_MON_AMSDU_ENG_CNT9(6),
-+                            WED_AMSDU_ENG_MAX_BUF_MERGED),
-+              DUMP_WED_MASK(WED_MON_AMSDU_ENG_CNT9(6),
-+                            WED_AMSDU_ENG_MAX_MSDU_MERGED),
-+
-+              DUMP_STR("WED AMDSU ENG7 INFO"),
-+              DUMP_WED(WED_MON_AMSDU_ENG_DMAD(7)),
-+              DUMP_WED(WED_MON_AMSDU_ENG_QFPL(7)),
-+              DUMP_WED(WED_MON_AMSDU_ENG_QENI(7)),
-+              DUMP_WED(WED_MON_AMSDU_ENG_QENO(7)),
-+              DUMP_WED(WED_MON_AMSDU_ENG_MERG(7)),
-+              DUMP_WED_MASK(WED_MON_AMSDU_ENG_CNT8(7),
-+                            WED_AMSDU_ENG_MAX_PL_CNT),
-+              DUMP_WED_MASK(WED_MON_AMSDU_ENG_CNT8(7),
-+                            WED_AMSDU_ENG_MAX_QGPP_CNT),
-+              DUMP_WED_MASK(WED_MON_AMSDU_ENG_CNT9(7),
-+                            WED_AMSDU_ENG_CUR_ENTRY),
-+              DUMP_WED_MASK(WED_MON_AMSDU_ENG_CNT9(7),
-+                            WED_AMSDU_ENG_MAX_BUF_MERGED),
-+              DUMP_WED_MASK(WED_MON_AMSDU_ENG_CNT9(4),
-+                            WED_AMSDU_ENG_MAX_MSDU_MERGED),
-+
-+              DUMP_STR("WED AMDSU ENG8 INFO"),
-+              DUMP_WED(WED_MON_AMSDU_ENG_DMAD(8)),
-+              DUMP_WED(WED_MON_AMSDU_ENG_QFPL(8)),
-+              DUMP_WED(WED_MON_AMSDU_ENG_QENI(8)),
-+              DUMP_WED(WED_MON_AMSDU_ENG_QENO(8)),
-+              DUMP_WED(WED_MON_AMSDU_ENG_MERG(8)),
-+              DUMP_WED_MASK(WED_MON_AMSDU_ENG_CNT8(8),
-+                            WED_AMSDU_ENG_MAX_PL_CNT),
-+              DUMP_WED_MASK(WED_MON_AMSDU_ENG_CNT8(8),
-+                            WED_AMSDU_ENG_MAX_QGPP_CNT),
-+              DUMP_WED_MASK(WED_MON_AMSDU_ENG_CNT9(8),
-+                            WED_AMSDU_ENG_CUR_ENTRY),
-+              DUMP_WED_MASK(WED_MON_AMSDU_ENG_CNT9(8),
-+                            WED_AMSDU_ENG_MAX_BUF_MERGED),
-+              DUMP_WED_MASK(WED_MON_AMSDU_ENG_CNT9(8),
-+                            WED_AMSDU_ENG_MAX_MSDU_MERGED),
-+
-+              DUMP_STR("WED QMEM INFO"),
-+              DUMP_WED_MASK(WED_MON_AMSDU_QMEM_CNT(0), WED_AMSDU_QMEM_FQ_CNT),
-+              DUMP_WED_MASK(WED_MON_AMSDU_QMEM_CNT(0), WED_AMSDU_QMEM_SP_QCNT),
-+              DUMP_WED_MASK(WED_MON_AMSDU_QMEM_CNT(1), WED_AMSDU_QMEM_TID0_QCNT),
-+              DUMP_WED_MASK(WED_MON_AMSDU_QMEM_CNT(1), WED_AMSDU_QMEM_TID1_QCNT),
-+              DUMP_WED_MASK(WED_MON_AMSDU_QMEM_CNT(2), WED_AMSDU_QMEM_TID2_QCNT),
-+              DUMP_WED_MASK(WED_MON_AMSDU_QMEM_CNT(2), WED_AMSDU_QMEM_TID3_QCNT),
-+              DUMP_WED_MASK(WED_MON_AMSDU_QMEM_CNT(3), WED_AMSDU_QMEM_TID4_QCNT),
-+              DUMP_WED_MASK(WED_MON_AMSDU_QMEM_CNT(3), WED_AMSDU_QMEM_TID5_QCNT),
-+              DUMP_WED_MASK(WED_MON_AMSDU_QMEM_CNT(4), WED_AMSDU_QMEM_TID6_QCNT),
-+              DUMP_WED_MASK(WED_MON_AMSDU_QMEM_CNT(4), WED_AMSDU_QMEM_TID7_QCNT),
-+
-+              DUMP_STR("WED QMEM HEAD INFO"),
-+              DUMP_WED_MASK(WED_MON_AMSDU_QMEM_PTR(0), WED_AMSDU_QMEM_FQ_HEAD),
-+              DUMP_WED_MASK(WED_MON_AMSDU_QMEM_PTR(0), WED_AMSDU_QMEM_SP_QHEAD),
-+              DUMP_WED_MASK(WED_MON_AMSDU_QMEM_PTR(1), WED_AMSDU_QMEM_TID0_QHEAD),
-+              DUMP_WED_MASK(WED_MON_AMSDU_QMEM_PTR(1), WED_AMSDU_QMEM_TID1_QHEAD),
-+              DUMP_WED_MASK(WED_MON_AMSDU_QMEM_PTR(2), WED_AMSDU_QMEM_TID2_QHEAD),
-+              DUMP_WED_MASK(WED_MON_AMSDU_QMEM_PTR(2), WED_AMSDU_QMEM_TID3_QHEAD),
-+              DUMP_WED_MASK(WED_MON_AMSDU_QMEM_PTR(3), WED_AMSDU_QMEM_TID4_QHEAD),
-+              DUMP_WED_MASK(WED_MON_AMSDU_QMEM_PTR(3), WED_AMSDU_QMEM_TID5_QHEAD),
-+              DUMP_WED_MASK(WED_MON_AMSDU_QMEM_PTR(4), WED_AMSDU_QMEM_TID6_QHEAD),
-+              DUMP_WED_MASK(WED_MON_AMSDU_QMEM_PTR(4), WED_AMSDU_QMEM_TID7_QHEAD),
-+
-+              DUMP_STR("WED QMEM TAIL INFO"),
-+              DUMP_WED_MASK(WED_MON_AMSDU_QMEM_PTR(5), WED_AMSDU_QMEM_FQ_TAIL),
-+              DUMP_WED_MASK(WED_MON_AMSDU_QMEM_PTR(5), WED_AMSDU_QMEM_SP_QTAIL),
-+              DUMP_WED_MASK(WED_MON_AMSDU_QMEM_PTR(6), WED_AMSDU_QMEM_TID0_QTAIL),
-+              DUMP_WED_MASK(WED_MON_AMSDU_QMEM_PTR(6), WED_AMSDU_QMEM_TID1_QTAIL),
-+              DUMP_WED_MASK(WED_MON_AMSDU_QMEM_PTR(7), WED_AMSDU_QMEM_TID2_QTAIL),
-+              DUMP_WED_MASK(WED_MON_AMSDU_QMEM_PTR(7), WED_AMSDU_QMEM_TID3_QTAIL),
-+              DUMP_WED_MASK(WED_MON_AMSDU_QMEM_PTR(8), WED_AMSDU_QMEM_TID4_QTAIL),
-+              DUMP_WED_MASK(WED_MON_AMSDU_QMEM_PTR(8), WED_AMSDU_QMEM_TID5_QTAIL),
-+              DUMP_WED_MASK(WED_MON_AMSDU_QMEM_PTR(9), WED_AMSDU_QMEM_TID6_QTAIL),
-+              DUMP_WED_MASK(WED_MON_AMSDU_QMEM_PTR(9), WED_AMSDU_QMEM_TID7_QTAIL),
-+
-+              DUMP_STR("WED HIFTXD MSDU INFO"),
-+              DUMP_WED(WED_MON_AMSDU_HIFTXD_FETCH_MSDU(1)),
-+              DUMP_WED(WED_MON_AMSDU_HIFTXD_FETCH_MSDU(2)),
-+              DUMP_WED(WED_MON_AMSDU_HIFTXD_FETCH_MSDU(3)),
-+              DUMP_WED(WED_MON_AMSDU_HIFTXD_FETCH_MSDU(4)),
-+              DUMP_WED(WED_MON_AMSDU_HIFTXD_FETCH_MSDU(5)),
-+              DUMP_WED(WED_MON_AMSDU_HIFTXD_FETCH_MSDU(6)),
-+              DUMP_WED(WED_MON_AMSDU_HIFTXD_FETCH_MSDU(7)),
-+              DUMP_WED(WED_MON_AMSDU_HIFTXD_FETCH_MSDU(8)),
-+              DUMP_WED(WED_MON_AMSDU_HIFTXD_FETCH_MSDU(9)),
-+              DUMP_WED(WED_MON_AMSDU_HIFTXD_FETCH_MSDU(10)),
-+              DUMP_WED(WED_MON_AMSDU_HIFTXD_FETCH_MSDU(11)),
-+              DUMP_WED(WED_MON_AMSDU_HIFTXD_FETCH_MSDU(12)),
-+              DUMP_WED(WED_MON_AMSDU_HIFTXD_FETCH_MSDU(13)),
-+      };
-+      struct mtk_wed_hw *hw = s->private;
-+      struct mtk_wed_device *dev = hw->wed_dev;
-+
-+      if (dev)
-+              dump_wed_regs(s, dev, regs, ARRAY_SIZE(regs));
-+
-+      return 0;
-+}
-+DEFINE_SHOW_ATTRIBUTE(wed_amsdu);
-+
-+static int
-+wed_rtqm_show(struct seq_file *s, void *data)
-+{
-+      static const struct reg_dump regs[] = {
-+              DUMP_STR("WED Route QM IGRS0(N2H + Recycle)"),
-+              DUMP_WED(WED_RTQM_IGRS0_I2HW_DMAD_CNT),
-+              DUMP_WED(WED_RTQM_IGRS0_I2H_DMAD_CNT(0)),
-+              DUMP_WED(WED_RTQM_IGRS0_I2H_DMAD_CNT(1)),
-+              DUMP_WED(WED_RTQM_IGRS0_I2HW_PKT_CNT),
-+              DUMP_WED(WED_RTQM_IGRS0_I2H_PKT_CNT(0)),
-+              DUMP_WED(WED_RTQM_IGRS0_I2H_PKT_CNT(0)),
-+              DUMP_WED(WED_RTQM_IGRS0_FDROP_CNT),
-+
-+              DUMP_STR("WED Route QM IGRS1(Legacy)"),
-+              DUMP_WED(WED_RTQM_IGRS1_I2HW_DMAD_CNT),
-+              DUMP_WED(WED_RTQM_IGRS1_I2H_DMAD_CNT(0)),
-+              DUMP_WED(WED_RTQM_IGRS1_I2H_DMAD_CNT(1)),
-+              DUMP_WED(WED_RTQM_IGRS1_I2HW_PKT_CNT),
-+              DUMP_WED(WED_RTQM_IGRS1_I2H_PKT_CNT(0)),
-+              DUMP_WED(WED_RTQM_IGRS1_I2H_PKT_CNT(1)),
-+              DUMP_WED(WED_RTQM_IGRS1_FDROP_CNT),
-+
-+              DUMP_STR("WED Route QM IGRS2(RRO3.0)"),
-+              DUMP_WED(WED_RTQM_IGRS2_I2HW_DMAD_CNT),
-+              DUMP_WED(WED_RTQM_IGRS2_I2H_DMAD_CNT(0)),
-+              DUMP_WED(WED_RTQM_IGRS2_I2H_DMAD_CNT(1)),
-+              DUMP_WED(WED_RTQM_IGRS2_I2HW_PKT_CNT),
-+              DUMP_WED(WED_RTQM_IGRS2_I2H_PKT_CNT(0)),
-+              DUMP_WED(WED_RTQM_IGRS2_I2H_PKT_CNT(1)),
-+              DUMP_WED(WED_RTQM_IGRS2_FDROP_CNT),
-+
-+              DUMP_STR("WED Route QM IGRS3(DEBUG)"),
-+              DUMP_WED(WED_RTQM_IGRS2_I2HW_DMAD_CNT),
-+              DUMP_WED(WED_RTQM_IGRS3_I2H_DMAD_CNT(0)),
-+              DUMP_WED(WED_RTQM_IGRS3_I2H_DMAD_CNT(1)),
-+              DUMP_WED(WED_RTQM_IGRS3_I2HW_PKT_CNT),
-+              DUMP_WED(WED_RTQM_IGRS3_I2H_PKT_CNT(0)),
-+              DUMP_WED(WED_RTQM_IGRS3_I2H_PKT_CNT(1)),
-+              DUMP_WED(WED_RTQM_IGRS3_FDROP_CNT),
-+      };
-+      struct mtk_wed_hw *hw = s->private;
-+      struct mtk_wed_device *dev = hw->wed_dev;
-+
-+      if (dev)
-+              dump_wed_regs(s, dev, regs, ARRAY_SIZE(regs));
-+
-+      return 0;
-+}
-+DEFINE_SHOW_ATTRIBUTE(wed_rtqm);
-+
-+static int
-+wed_rro_show(struct seq_file *s, void *data)
-+{
-+      static const struct reg_dump regs[] = {
-+              DUMP_STR("RRO/IND CMD CNT"),
-+              DUMP_WED(WED_RX_IND_CMD_CNT(1)),
-+              DUMP_WED(WED_RX_IND_CMD_CNT(2)),
-+              DUMP_WED(WED_RX_IND_CMD_CNT(3)),
-+              DUMP_WED(WED_RX_IND_CMD_CNT(4)),
-+              DUMP_WED(WED_RX_IND_CMD_CNT(5)),
-+              DUMP_WED(WED_RX_IND_CMD_CNT(6)),
-+              DUMP_WED(WED_RX_IND_CMD_CNT(7)),
-+              DUMP_WED(WED_RX_IND_CMD_CNT(8)),
-+              DUMP_WED_MASK(WED_RX_IND_CMD_CNT(9),
-+                            WED_IND_CMD_MAGIC_CNT_FAIL_CNT),
-+
-+              DUMP_WED(WED_RX_ADDR_ELEM_CNT(0)),
-+              DUMP_WED_MASK(WED_RX_ADDR_ELEM_CNT(1),
-+                            WED_ADDR_ELEM_SIG_FAIL_CNT),
-+              DUMP_WED(WED_RX_MSDU_PG_CNT(1)),
-+              DUMP_WED(WED_RX_MSDU_PG_CNT(2)),
-+              DUMP_WED(WED_RX_MSDU_PG_CNT(3)),
-+              DUMP_WED(WED_RX_MSDU_PG_CNT(4)),
-+              DUMP_WED(WED_RX_MSDU_PG_CNT(5)),
-+              DUMP_WED_MASK(WED_RX_PN_CHK_CNT,
-+                            WED_PN_CHK_FAIL_CNT),
-+      };
-+      struct mtk_wed_hw *hw = s->private;
-+      struct mtk_wed_device *dev = hw->wed_dev;
-+
-+      if (dev)
-+              dump_wed_regs(s, dev, regs, ARRAY_SIZE(regs));
-+
-+      return 0;
-+}
-+DEFINE_SHOW_ATTRIBUTE(wed_rro);
-+
-+static int
- mtk_wed_reg_set(void *data, u64 val)
- {
-       struct mtk_wed_hw *hw = data;
-@@ -266,7 +624,16 @@ void mtk_wed_hw_add_debugfs(struct mtk_w
-       debugfs_create_u32("regidx", 0600, dir, &hw->debugfs_reg);
-       debugfs_create_file_unsafe("regval", 0600, dir, hw, &fops_regval);
-       debugfs_create_file_unsafe("txinfo", 0400, dir, hw, &wed_txinfo_fops);
--      if (!mtk_wed_is_v1(hw))
-+      if (!mtk_wed_is_v1(hw)) {
-               debugfs_create_file_unsafe("rxinfo", 0400, dir, hw,
-                                          &wed_rxinfo_fops);
-+              if (mtk_wed_is_v3_or_greater(hw)) {
-+                      debugfs_create_file_unsafe("amsdu", 0400, dir, hw,
-+                                                 &wed_amsdu_fops);
-+                      debugfs_create_file_unsafe("rtqm", 0400, dir, hw,
-+                                                 &wed_rtqm_fops);
-+                      debugfs_create_file_unsafe("rro", 0400, dir, hw,
-+                                                 &wed_rro_fops);
-+              }
-+      }
- }
diff --git a/target/linux/generic/backport-5.15/752-20-v6.7-net-ethernet-mtk_wed-add-wed-3.0-reset-support.patch b/target/linux/generic/backport-5.15/752-20-v6.7-net-ethernet-mtk_wed-add-wed-3.0-reset-support.patch
deleted file mode 100644 (file)
index aaaabf0..0000000
+++ /dev/null
@@ -1,587 +0,0 @@
-From: Sujuan Chen <[email protected]>
-Date: Mon, 18 Sep 2023 12:29:19 +0200
-Subject: [PATCH] net: ethernet: mtk_wed: add wed 3.0 reset support
-
-Introduce support for resetting Wireless Ethernet Dispatcher 3.0
-available on MT988 SoC.
-
-Co-developed-by: Lorenzo Bianconi <[email protected]>
-Signed-off-by: Lorenzo Bianconi <[email protected]>
-Signed-off-by: Sujuan Chen <[email protected]>
-Signed-off-by: Paolo Abeni <[email protected]>
----
-
---- a/drivers/net/ethernet/mediatek/mtk_wed.c
-+++ b/drivers/net/ethernet/mediatek/mtk_wed.c
-@@ -148,6 +148,90 @@ mtk_wdma_read_reset(struct mtk_wed_devic
-       return wdma_r32(dev, MTK_WDMA_GLO_CFG);
- }
-+static void
-+mtk_wdma_v3_rx_reset(struct mtk_wed_device *dev)
-+{
-+      u32 status;
-+
-+      if (!mtk_wed_is_v3_or_greater(dev->hw))
-+              return;
-+
-+      wdma_clr(dev, MTK_WDMA_PREF_TX_CFG, MTK_WDMA_PREF_TX_CFG_PREF_EN);
-+      wdma_clr(dev, MTK_WDMA_PREF_RX_CFG, MTK_WDMA_PREF_RX_CFG_PREF_EN);
-+
-+      if (read_poll_timeout(wdma_r32, status,
-+                            !(status & MTK_WDMA_PREF_TX_CFG_PREF_BUSY),
-+                            0, 10000, false, dev, MTK_WDMA_PREF_TX_CFG))
-+              dev_err(dev->hw->dev, "rx reset failed\n");
-+
-+      if (read_poll_timeout(wdma_r32, status,
-+                            !(status & MTK_WDMA_PREF_RX_CFG_PREF_BUSY),
-+                            0, 10000, false, dev, MTK_WDMA_PREF_RX_CFG))
-+              dev_err(dev->hw->dev, "rx reset failed\n");
-+
-+      wdma_clr(dev, MTK_WDMA_WRBK_TX_CFG, MTK_WDMA_WRBK_TX_CFG_WRBK_EN);
-+      wdma_clr(dev, MTK_WDMA_WRBK_RX_CFG, MTK_WDMA_WRBK_RX_CFG_WRBK_EN);
-+
-+      if (read_poll_timeout(wdma_r32, status,
-+                            !(status & MTK_WDMA_WRBK_TX_CFG_WRBK_BUSY),
-+                            0, 10000, false, dev, MTK_WDMA_WRBK_TX_CFG))
-+              dev_err(dev->hw->dev, "rx reset failed\n");
-+
-+      if (read_poll_timeout(wdma_r32, status,
-+                            !(status & MTK_WDMA_WRBK_RX_CFG_WRBK_BUSY),
-+                            0, 10000, false, dev, MTK_WDMA_WRBK_RX_CFG))
-+              dev_err(dev->hw->dev, "rx reset failed\n");
-+
-+      /* prefetch FIFO */
-+      wdma_w32(dev, MTK_WDMA_PREF_RX_FIFO_CFG,
-+               MTK_WDMA_PREF_RX_FIFO_CFG_RING0_CLEAR |
-+               MTK_WDMA_PREF_RX_FIFO_CFG_RING1_CLEAR);
-+      wdma_clr(dev, MTK_WDMA_PREF_RX_FIFO_CFG,
-+               MTK_WDMA_PREF_RX_FIFO_CFG_RING0_CLEAR |
-+               MTK_WDMA_PREF_RX_FIFO_CFG_RING1_CLEAR);
-+
-+      /* core FIFO */
-+      wdma_w32(dev, MTK_WDMA_XDMA_RX_FIFO_CFG,
-+               MTK_WDMA_XDMA_RX_FIFO_CFG_RX_PAR_FIFO_CLEAR |
-+               MTK_WDMA_XDMA_RX_FIFO_CFG_RX_CMD_FIFO_CLEAR |
-+               MTK_WDMA_XDMA_RX_FIFO_CFG_RX_DMAD_FIFO_CLEAR |
-+               MTK_WDMA_XDMA_RX_FIFO_CFG_RX_ARR_FIFO_CLEAR |
-+               MTK_WDMA_XDMA_RX_FIFO_CFG_RX_LEN_FIFO_CLEAR |
-+               MTK_WDMA_XDMA_RX_FIFO_CFG_RX_WID_FIFO_CLEAR |
-+               MTK_WDMA_XDMA_RX_FIFO_CFG_RX_BID_FIFO_CLEAR);
-+      wdma_clr(dev, MTK_WDMA_XDMA_RX_FIFO_CFG,
-+               MTK_WDMA_XDMA_RX_FIFO_CFG_RX_PAR_FIFO_CLEAR |
-+               MTK_WDMA_XDMA_RX_FIFO_CFG_RX_CMD_FIFO_CLEAR |
-+               MTK_WDMA_XDMA_RX_FIFO_CFG_RX_DMAD_FIFO_CLEAR |
-+               MTK_WDMA_XDMA_RX_FIFO_CFG_RX_ARR_FIFO_CLEAR |
-+               MTK_WDMA_XDMA_RX_FIFO_CFG_RX_LEN_FIFO_CLEAR |
-+               MTK_WDMA_XDMA_RX_FIFO_CFG_RX_WID_FIFO_CLEAR |
-+               MTK_WDMA_XDMA_RX_FIFO_CFG_RX_BID_FIFO_CLEAR);
-+
-+      /* writeback FIFO */
-+      wdma_w32(dev, MTK_WDMA_WRBK_RX_FIFO_CFG(0),
-+               MTK_WDMA_WRBK_RX_FIFO_CFG_RING_CLEAR);
-+      wdma_w32(dev, MTK_WDMA_WRBK_RX_FIFO_CFG(1),
-+               MTK_WDMA_WRBK_RX_FIFO_CFG_RING_CLEAR);
-+
-+      wdma_clr(dev, MTK_WDMA_WRBK_RX_FIFO_CFG(0),
-+               MTK_WDMA_WRBK_RX_FIFO_CFG_RING_CLEAR);
-+      wdma_clr(dev, MTK_WDMA_WRBK_RX_FIFO_CFG(1),
-+               MTK_WDMA_WRBK_RX_FIFO_CFG_RING_CLEAR);
-+
-+      /* prefetch ring status */
-+      wdma_w32(dev, MTK_WDMA_PREF_SIDX_CFG,
-+               MTK_WDMA_PREF_SIDX_CFG_RX_RING_CLEAR);
-+      wdma_clr(dev, MTK_WDMA_PREF_SIDX_CFG,
-+               MTK_WDMA_PREF_SIDX_CFG_RX_RING_CLEAR);
-+
-+      /* writeback ring status */
-+      wdma_w32(dev, MTK_WDMA_WRBK_SIDX_CFG,
-+               MTK_WDMA_WRBK_SIDX_CFG_RX_RING_CLEAR);
-+      wdma_clr(dev, MTK_WDMA_WRBK_SIDX_CFG,
-+               MTK_WDMA_WRBK_SIDX_CFG_RX_RING_CLEAR);
-+}
-+
- static int
- mtk_wdma_rx_reset(struct mtk_wed_device *dev)
- {
-@@ -160,6 +244,7 @@ mtk_wdma_rx_reset(struct mtk_wed_device
-       if (ret)
-               dev_err(dev->hw->dev, "rx reset failed\n");
-+      mtk_wdma_v3_rx_reset(dev);
-       wdma_w32(dev, MTK_WDMA_RESET_IDX, MTK_WDMA_RESET_IDX_RX);
-       wdma_w32(dev, MTK_WDMA_RESET_IDX, 0);
-@@ -192,6 +277,84 @@ mtk_wed_poll_busy(struct mtk_wed_device
- }
- static void
-+mtk_wdma_v3_tx_reset(struct mtk_wed_device *dev)
-+{
-+      u32 status;
-+
-+      if (!mtk_wed_is_v3_or_greater(dev->hw))
-+              return;
-+
-+      wdma_clr(dev, MTK_WDMA_PREF_TX_CFG, MTK_WDMA_PREF_TX_CFG_PREF_EN);
-+      wdma_clr(dev, MTK_WDMA_PREF_RX_CFG, MTK_WDMA_PREF_RX_CFG_PREF_EN);
-+
-+      if (read_poll_timeout(wdma_r32, status,
-+                            !(status & MTK_WDMA_PREF_TX_CFG_PREF_BUSY),
-+                            0, 10000, false, dev, MTK_WDMA_PREF_TX_CFG))
-+              dev_err(dev->hw->dev, "tx reset failed\n");
-+
-+      if (read_poll_timeout(wdma_r32, status,
-+                            !(status & MTK_WDMA_PREF_RX_CFG_PREF_BUSY),
-+                            0, 10000, false, dev, MTK_WDMA_PREF_RX_CFG))
-+              dev_err(dev->hw->dev, "tx reset failed\n");
-+
-+      wdma_clr(dev, MTK_WDMA_WRBK_TX_CFG, MTK_WDMA_WRBK_TX_CFG_WRBK_EN);
-+      wdma_clr(dev, MTK_WDMA_WRBK_RX_CFG, MTK_WDMA_WRBK_RX_CFG_WRBK_EN);
-+
-+      if (read_poll_timeout(wdma_r32, status,
-+                            !(status & MTK_WDMA_WRBK_TX_CFG_WRBK_BUSY),
-+                            0, 10000, false, dev, MTK_WDMA_WRBK_TX_CFG))
-+              dev_err(dev->hw->dev, "tx reset failed\n");
-+
-+      if (read_poll_timeout(wdma_r32, status,
-+                            !(status & MTK_WDMA_WRBK_RX_CFG_WRBK_BUSY),
-+                            0, 10000, false, dev, MTK_WDMA_WRBK_RX_CFG))
-+              dev_err(dev->hw->dev, "tx reset failed\n");
-+
-+      /* prefetch FIFO */
-+      wdma_w32(dev, MTK_WDMA_PREF_TX_FIFO_CFG,
-+               MTK_WDMA_PREF_TX_FIFO_CFG_RING0_CLEAR |
-+               MTK_WDMA_PREF_TX_FIFO_CFG_RING1_CLEAR);
-+      wdma_clr(dev, MTK_WDMA_PREF_TX_FIFO_CFG,
-+               MTK_WDMA_PREF_TX_FIFO_CFG_RING0_CLEAR |
-+               MTK_WDMA_PREF_TX_FIFO_CFG_RING1_CLEAR);
-+
-+      /* core FIFO */
-+      wdma_w32(dev, MTK_WDMA_XDMA_TX_FIFO_CFG,
-+               MTK_WDMA_XDMA_TX_FIFO_CFG_TX_PAR_FIFO_CLEAR |
-+               MTK_WDMA_XDMA_TX_FIFO_CFG_TX_CMD_FIFO_CLEAR |
-+               MTK_WDMA_XDMA_TX_FIFO_CFG_TX_DMAD_FIFO_CLEAR |
-+               MTK_WDMA_XDMA_TX_FIFO_CFG_TX_ARR_FIFO_CLEAR);
-+      wdma_clr(dev, MTK_WDMA_XDMA_TX_FIFO_CFG,
-+               MTK_WDMA_XDMA_TX_FIFO_CFG_TX_PAR_FIFO_CLEAR |
-+               MTK_WDMA_XDMA_TX_FIFO_CFG_TX_CMD_FIFO_CLEAR |
-+               MTK_WDMA_XDMA_TX_FIFO_CFG_TX_DMAD_FIFO_CLEAR |
-+               MTK_WDMA_XDMA_TX_FIFO_CFG_TX_ARR_FIFO_CLEAR);
-+
-+      /* writeback FIFO */
-+      wdma_w32(dev, MTK_WDMA_WRBK_TX_FIFO_CFG(0),
-+               MTK_WDMA_WRBK_TX_FIFO_CFG_RING_CLEAR);
-+      wdma_w32(dev, MTK_WDMA_WRBK_TX_FIFO_CFG(1),
-+               MTK_WDMA_WRBK_TX_FIFO_CFG_RING_CLEAR);
-+
-+      wdma_clr(dev, MTK_WDMA_WRBK_TX_FIFO_CFG(0),
-+               MTK_WDMA_WRBK_TX_FIFO_CFG_RING_CLEAR);
-+      wdma_clr(dev, MTK_WDMA_WRBK_TX_FIFO_CFG(1),
-+               MTK_WDMA_WRBK_TX_FIFO_CFG_RING_CLEAR);
-+
-+      /* prefetch ring status */
-+      wdma_w32(dev, MTK_WDMA_PREF_SIDX_CFG,
-+               MTK_WDMA_PREF_SIDX_CFG_TX_RING_CLEAR);
-+      wdma_clr(dev, MTK_WDMA_PREF_SIDX_CFG,
-+               MTK_WDMA_PREF_SIDX_CFG_TX_RING_CLEAR);
-+
-+      /* writeback ring status */
-+      wdma_w32(dev, MTK_WDMA_WRBK_SIDX_CFG,
-+               MTK_WDMA_WRBK_SIDX_CFG_TX_RING_CLEAR);
-+      wdma_clr(dev, MTK_WDMA_WRBK_SIDX_CFG,
-+               MTK_WDMA_WRBK_SIDX_CFG_TX_RING_CLEAR);
-+}
-+
-+static void
- mtk_wdma_tx_reset(struct mtk_wed_device *dev)
- {
-       u32 status, mask = MTK_WDMA_GLO_CFG_TX_DMA_BUSY;
-@@ -202,6 +365,7 @@ mtk_wdma_tx_reset(struct mtk_wed_device
-                              !(status & mask), 0, 10000))
-               dev_err(dev->hw->dev, "tx reset failed\n");
-+      mtk_wdma_v3_tx_reset(dev);
-       wdma_w32(dev, MTK_WDMA_RESET_IDX, MTK_WDMA_RESET_IDX_TX);
-       wdma_w32(dev, MTK_WDMA_RESET_IDX, 0);
-@@ -1405,13 +1569,33 @@ mtk_wed_rx_reset(struct mtk_wed_device *
-       if (ret)
-               return ret;
-+      if (dev->wlan.hw_rro) {
-+              wed_clr(dev, MTK_WED_CTRL, MTK_WED_CTRL_WED_RX_IND_CMD_EN);
-+              mtk_wed_poll_busy(dev, MTK_WED_RRO_RX_HW_STS,
-+                                MTK_WED_RX_IND_CMD_BUSY);
-+              mtk_wed_reset(dev, MTK_WED_RESET_RRO_RX_TO_PG);
-+      }
-+
-       wed_clr(dev, MTK_WED_WPDMA_RX_D_GLO_CFG, MTK_WED_WPDMA_RX_D_RX_DRV_EN);
-       ret = mtk_wed_poll_busy(dev, MTK_WED_WPDMA_RX_D_GLO_CFG,
-                               MTK_WED_WPDMA_RX_D_RX_DRV_BUSY);
-+      if (!ret && mtk_wed_is_v3_or_greater(dev->hw))
-+              ret = mtk_wed_poll_busy(dev, MTK_WED_WPDMA_RX_D_PREF_CFG,
-+                                      MTK_WED_WPDMA_RX_D_PREF_BUSY);
-       if (ret) {
-               mtk_wed_reset(dev, MTK_WED_RESET_WPDMA_INT_AGENT);
-               mtk_wed_reset(dev, MTK_WED_RESET_WPDMA_RX_D_DRV);
-       } else {
-+              if (mtk_wed_is_v3_or_greater(dev->hw)) {
-+                      /* 1.a. disable prefetch HW */
-+                      wed_clr(dev, MTK_WED_WPDMA_RX_D_PREF_CFG,
-+                              MTK_WED_WPDMA_RX_D_PREF_EN);
-+                      mtk_wed_poll_busy(dev, MTK_WED_WPDMA_RX_D_PREF_CFG,
-+                                        MTK_WED_WPDMA_RX_D_PREF_BUSY);
-+                      wed_w32(dev, MTK_WED_WPDMA_RX_D_RST_IDX,
-+                              MTK_WED_WPDMA_RX_D_RST_DRV_IDX_ALL);
-+              }
-+
-               wed_w32(dev, MTK_WED_WPDMA_RX_D_RST_IDX,
-                       MTK_WED_WPDMA_RX_D_RST_CRX_IDX |
-                       MTK_WED_WPDMA_RX_D_RST_DRV_IDX);
-@@ -1439,23 +1623,52 @@ mtk_wed_rx_reset(struct mtk_wed_device *
-               wed_w32(dev, MTK_WED_RROQM_RST_IDX, 0);
-       }
-+      if (dev->wlan.hw_rro) {
-+              /* disable rro msdu page drv */
-+              wed_clr(dev, MTK_WED_RRO_MSDU_PG_RING2_CFG,
-+                      MTK_WED_RRO_MSDU_PG_DRV_EN);
-+
-+              /* disable rro data drv */
-+              wed_clr(dev, MTK_WED_RRO_RX_D_CFG(2), MTK_WED_RRO_RX_D_DRV_EN);
-+
-+              /* rro msdu page drv reset */
-+              wed_w32(dev, MTK_WED_RRO_MSDU_PG_RING2_CFG,
-+                      MTK_WED_RRO_MSDU_PG_DRV_CLR);
-+              mtk_wed_poll_busy(dev, MTK_WED_RRO_MSDU_PG_RING2_CFG,
-+                                MTK_WED_RRO_MSDU_PG_DRV_CLR);
-+
-+              /* rro data drv reset */
-+              wed_w32(dev, MTK_WED_RRO_RX_D_CFG(2),
-+                      MTK_WED_RRO_RX_D_DRV_CLR);
-+              mtk_wed_poll_busy(dev, MTK_WED_RRO_RX_D_CFG(2),
-+                                MTK_WED_RRO_RX_D_DRV_CLR);
-+      }
-+
-       /* reset route qm */
-       wed_clr(dev, MTK_WED_CTRL, MTK_WED_CTRL_RX_ROUTE_QM_EN);
-       ret = mtk_wed_poll_busy(dev, MTK_WED_CTRL,
-                               MTK_WED_CTRL_RX_ROUTE_QM_BUSY);
--      if (ret)
-+      if (ret) {
-               mtk_wed_reset(dev, MTK_WED_RESET_RX_ROUTE_QM);
--      else
--              wed_set(dev, MTK_WED_RTQM_GLO_CFG,
--                      MTK_WED_RTQM_Q_RST);
-+      } else if (mtk_wed_is_v3_or_greater(dev->hw)) {
-+              wed_set(dev, MTK_WED_RTQM_RST, BIT(0));
-+              wed_clr(dev, MTK_WED_RTQM_RST, BIT(0));
-+              mtk_wed_reset(dev, MTK_WED_RESET_RX_ROUTE_QM);
-+      } else {
-+              wed_set(dev, MTK_WED_RTQM_GLO_CFG, MTK_WED_RTQM_Q_RST);
-+      }
-       /* reset tx wdma */
-       mtk_wdma_tx_reset(dev);
-       /* reset tx wdma drv */
-       wed_clr(dev, MTK_WED_WDMA_GLO_CFG, MTK_WED_WDMA_GLO_CFG_TX_DRV_EN);
--      mtk_wed_poll_busy(dev, MTK_WED_CTRL,
--                        MTK_WED_CTRL_WDMA_INT_AGENT_BUSY);
-+      if (mtk_wed_is_v3_or_greater(dev->hw))
-+              mtk_wed_poll_busy(dev, MTK_WED_WPDMA_STATUS,
-+                                MTK_WED_WPDMA_STATUS_TX_DRV);
-+      else
-+              mtk_wed_poll_busy(dev, MTK_WED_CTRL,
-+                                MTK_WED_CTRL_WDMA_INT_AGENT_BUSY);
-       mtk_wed_reset(dev, MTK_WED_RESET_WDMA_TX_DRV);
-       /* reset wed rx dma */
-@@ -1476,6 +1689,14 @@ mtk_wed_rx_reset(struct mtk_wed_device *
-                         MTK_WED_CTRL_WED_RX_BM_BUSY);
-       mtk_wed_reset(dev, MTK_WED_RESET_RX_BM);
-+      if (dev->wlan.hw_rro) {
-+              wed_clr(dev, MTK_WED_CTRL, MTK_WED_CTRL_WED_RX_PG_BM_EN);
-+              mtk_wed_poll_busy(dev, MTK_WED_CTRL,
-+                                MTK_WED_CTRL_WED_RX_PG_BM_BUSY);
-+              wed_set(dev, MTK_WED_RESET, MTK_WED_RESET_RX_PG_BM);
-+              wed_clr(dev, MTK_WED_RESET, MTK_WED_RESET_RX_PG_BM);
-+      }
-+
-       /* wo change to enable state */
-       val = MTK_WED_WO_STATE_ENABLE;
-       ret = mtk_wed_mcu_send_msg(wo, MTK_WED_MODULE_ID_WO,
-@@ -1493,6 +1714,7 @@ mtk_wed_rx_reset(struct mtk_wed_device *
-                                  false);
-       }
-       mtk_wed_free_rx_buffer(dev);
-+      mtk_wed_hwrro_free_buffer(dev);
-       return 0;
- }
-@@ -1526,15 +1748,41 @@ mtk_wed_reset_dma(struct mtk_wed_device
-       /* 2. reset WDMA rx DMA */
-       busy = !!mtk_wdma_rx_reset(dev);
--      wed_clr(dev, MTK_WED_WDMA_GLO_CFG, MTK_WED_WDMA_GLO_CFG_RX_DRV_EN);
-+      if (mtk_wed_is_v3_or_greater(dev->hw)) {
-+              val = MTK_WED_WDMA_GLO_CFG_RX_DIS_FSM_AUTO_IDLE |
-+                    wed_r32(dev, MTK_WED_WDMA_GLO_CFG);
-+              val &= ~MTK_WED_WDMA_GLO_CFG_RX_DRV_EN;
-+              wed_w32(dev, MTK_WED_WDMA_GLO_CFG, val);
-+      } else {
-+              wed_clr(dev, MTK_WED_WDMA_GLO_CFG,
-+                      MTK_WED_WDMA_GLO_CFG_RX_DRV_EN);
-+      }
-+
-       if (!busy)
-               busy = mtk_wed_poll_busy(dev, MTK_WED_WDMA_GLO_CFG,
-                                        MTK_WED_WDMA_GLO_CFG_RX_DRV_BUSY);
-+      if (!busy && mtk_wed_is_v3_or_greater(dev->hw))
-+              busy = mtk_wed_poll_busy(dev, MTK_WED_WDMA_RX_PREF_CFG,
-+                                       MTK_WED_WDMA_RX_PREF_BUSY);
-       if (busy) {
-               mtk_wed_reset(dev, MTK_WED_RESET_WDMA_INT_AGENT);
-               mtk_wed_reset(dev, MTK_WED_RESET_WDMA_RX_DRV);
-       } else {
-+              if (mtk_wed_is_v3_or_greater(dev->hw)) {
-+                      /* 1.a. disable prefetch HW */
-+                      wed_clr(dev, MTK_WED_WDMA_RX_PREF_CFG,
-+                              MTK_WED_WDMA_RX_PREF_EN);
-+                      mtk_wed_poll_busy(dev, MTK_WED_WDMA_RX_PREF_CFG,
-+                                        MTK_WED_WDMA_RX_PREF_BUSY);
-+                      wed_clr(dev, MTK_WED_WDMA_RX_PREF_CFG,
-+                              MTK_WED_WDMA_RX_PREF_DDONE2_EN);
-+
-+                      /* 2. Reset dma index */
-+                      wed_w32(dev, MTK_WED_WDMA_RESET_IDX,
-+                              MTK_WED_WDMA_RESET_IDX_RX_ALL);
-+              }
-+
-               wed_w32(dev, MTK_WED_WDMA_RESET_IDX,
-                       MTK_WED_WDMA_RESET_IDX_RX | MTK_WED_WDMA_RESET_IDX_DRV);
-               wed_w32(dev, MTK_WED_WDMA_RESET_IDX, 0);
-@@ -1550,8 +1798,13 @@ mtk_wed_reset_dma(struct mtk_wed_device
-       wed_clr(dev, MTK_WED_CTRL, MTK_WED_CTRL_WED_TX_FREE_AGENT_EN);
-       for (i = 0; i < 100; i++) {
--              val = wed_r32(dev, MTK_WED_TX_BM_INTF);
--              if (FIELD_GET(MTK_WED_TX_BM_INTF_TKFIFO_FDEP, val) == 0x40)
-+              if (mtk_wed_is_v1(dev->hw))
-+                      val = FIELD_GET(MTK_WED_TX_BM_INTF_TKFIFO_FDEP,
-+                                      wed_r32(dev, MTK_WED_TX_BM_INTF));
-+              else
-+                      val = FIELD_GET(MTK_WED_TX_TKID_INTF_TKFIFO_FDEP,
-+                                      wed_r32(dev, MTK_WED_TX_TKID_INTF));
-+              if (val == 0x40)
-                       break;
-       }
-@@ -1573,6 +1826,8 @@ mtk_wed_reset_dma(struct mtk_wed_device
-               mtk_wed_reset(dev, MTK_WED_RESET_WPDMA_INT_AGENT);
-               mtk_wed_reset(dev, MTK_WED_RESET_WPDMA_TX_DRV);
-               mtk_wed_reset(dev, MTK_WED_RESET_WPDMA_RX_DRV);
-+              if (mtk_wed_is_v3_or_greater(dev->hw))
-+                      wed_w32(dev, MTK_WED_RX1_CTRL2, 0);
-       } else {
-               wed_w32(dev, MTK_WED_WPDMA_RESET_IDX,
-                       MTK_WED_WPDMA_RESET_IDX_TX |
-@@ -1589,7 +1844,14 @@ mtk_wed_reset_dma(struct mtk_wed_device
-               wed_w32(dev, MTK_WED_RESET_IDX, 0);
-       }
--      mtk_wed_rx_reset(dev);
-+      if (mtk_wed_is_v3_or_greater(dev->hw)) {
-+              /* reset amsdu engine */
-+              wed_clr(dev, MTK_WED_CTRL, MTK_WED_CTRL_TX_AMSDU_EN);
-+              mtk_wed_reset(dev, MTK_WED_RESET_TX_AMSDU);
-+      }
-+
-+      if (mtk_wed_get_rx_capa(dev))
-+              mtk_wed_rx_reset(dev);
- }
- static int
-@@ -1841,6 +2103,7 @@ mtk_wed_dma_enable(struct mtk_wed_device
-                       MTK_WED_WPDMA_GLO_CFG_RX_DRV_UNS_VER_FORCE_4);
-               wdma_set(dev, MTK_WDMA_PREF_RX_CFG, MTK_WDMA_PREF_RX_CFG_PREF_EN);
-+              wdma_set(dev, MTK_WDMA_WRBK_RX_CFG, MTK_WDMA_WRBK_RX_CFG_WRBK_EN);
-       }
-       wed_clr(dev, MTK_WED_WPDMA_GLO_CFG,
-@@ -1904,6 +2167,12 @@ mtk_wed_start_hw_rro(struct mtk_wed_devi
-       if (!mtk_wed_get_rx_capa(dev) || !dev->wlan.hw_rro)
-               return;
-+      if (reset) {
-+              wed_set(dev, MTK_WED_RRO_MSDU_PG_RING2_CFG,
-+                      MTK_WED_RRO_MSDU_PG_DRV_EN);
-+              return;
-+      }
-+
-       wed_set(dev, MTK_WED_RRO_RX_D_CFG(2), MTK_WED_RRO_MSDU_PG_DRV_CLR);
-       wed_w32(dev, MTK_WED_RRO_MSDU_PG_RING2_CFG,
-               MTK_WED_RRO_MSDU_PG_DRV_CLR);
---- a/drivers/net/ethernet/mediatek/mtk_wed_regs.h
-+++ b/drivers/net/ethernet/mediatek/mtk_wed_regs.h
-@@ -28,6 +28,8 @@ struct mtk_wdma_desc {
- #define MTK_WED_RESET                                 0x008
- #define MTK_WED_RESET_TX_BM                           BIT(0)
- #define MTK_WED_RESET_RX_BM                           BIT(1)
-+#define MTK_WED_RESET_RX_PG_BM                                BIT(2)
-+#define MTK_WED_RESET_RRO_RX_TO_PG                    BIT(3)
- #define MTK_WED_RESET_TX_FREE_AGENT                   BIT(4)
- #define MTK_WED_RESET_WPDMA_TX_DRV                    BIT(8)
- #define MTK_WED_RESET_WPDMA_RX_DRV                    BIT(9)
-@@ -106,6 +108,9 @@ struct mtk_wdma_desc {
- #define MTK_WED_STATUS                                        0x060
- #define MTK_WED_STATUS_TX                             GENMASK(15, 8)
-+#define MTK_WED_WPDMA_STATUS                          0x068
-+#define MTK_WED_WPDMA_STATUS_TX_DRV                   GENMASK(15, 8)
-+
- #define MTK_WED_TX_BM_CTRL                            0x080
- #define MTK_WED_TX_BM_CTRL_VLD_GRP_NUM                        GENMASK(6, 0)
- #define MTK_WED_TX_BM_CTRL_RSV_GRP_NUM                        GENMASK(22, 16)
-@@ -140,6 +145,9 @@ struct mtk_wdma_desc {
- #define MTK_WED_TX_TKID_CTRL_RSV_GRP_NUM              GENMASK(22, 16)
- #define MTK_WED_TX_TKID_CTRL_PAUSE                    BIT(28)
-+#define MTK_WED_TX_TKID_INTF                          0x0dc
-+#define MTK_WED_TX_TKID_INTF_TKFIFO_FDEP              GENMASK(25, 16)
-+
- #define MTK_WED_TX_TKID_CTRL_VLD_GRP_NUM_V3           GENMASK(7, 0)
- #define MTK_WED_TX_TKID_CTRL_RSV_GRP_NUM_V3           GENMASK(23, 16)
-@@ -190,6 +198,7 @@ struct mtk_wdma_desc {
- #define MTK_WED_RING_RX_DATA(_n)                      (0x420 + (_n) * 0x10)
- #define MTK_WED_SCR0                                  0x3c0
-+#define MTK_WED_RX1_CTRL2                             0x418
- #define MTK_WED_WPDMA_INT_TRIGGER                     0x504
- #define MTK_WED_WPDMA_INT_TRIGGER_RX_DONE             BIT(1)
- #define MTK_WED_WPDMA_INT_TRIGGER_TX_DONE             GENMASK(5, 4)
-@@ -303,6 +312,7 @@ struct mtk_wdma_desc {
- #define MTK_WED_WPDMA_RX_D_RST_IDX                    0x760
- #define MTK_WED_WPDMA_RX_D_RST_CRX_IDX                        GENMASK(17, 16)
-+#define MTK_WED_WPDMA_RX_D_RST_DRV_IDX_ALL            BIT(20)
- #define MTK_WED_WPDMA_RX_D_RST_DRV_IDX                        GENMASK(25, 24)
- #define MTK_WED_WPDMA_RX_GLO_CFG                      0x76c
-@@ -313,6 +323,7 @@ struct mtk_wdma_desc {
- #define MTK_WED_WPDMA_RX_D_PREF_CFG                   0x7b4
- #define MTK_WED_WPDMA_RX_D_PREF_EN                    BIT(0)
-+#define MTK_WED_WPDMA_RX_D_PREF_BUSY                  BIT(1)
- #define MTK_WED_WPDMA_RX_D_PREF_BURST_SIZE            GENMASK(12, 8)
- #define MTK_WED_WPDMA_RX_D_PREF_LOW_THRES             GENMASK(21, 16)
-@@ -334,11 +345,13 @@ struct mtk_wdma_desc {
- #define MTK_WED_WDMA_RX_PREF_CFG                      0x950
- #define MTK_WED_WDMA_RX_PREF_EN                               BIT(0)
-+#define MTK_WED_WDMA_RX_PREF_BUSY                     BIT(1)
- #define MTK_WED_WDMA_RX_PREF_BURST_SIZE                       GENMASK(12, 8)
- #define MTK_WED_WDMA_RX_PREF_LOW_THRES                        GENMASK(21, 16)
- #define MTK_WED_WDMA_RX_PREF_RX0_SIDX_CLR             BIT(24)
- #define MTK_WED_WDMA_RX_PREF_RX1_SIDX_CLR             BIT(25)
- #define MTK_WED_WDMA_RX_PREF_DDONE2_EN                        BIT(26)
-+#define MTK_WED_WDMA_RX_PREF_DDONE2_BUSY              BIT(27)
- #define MTK_WED_WDMA_RX_PREF_FIFO_CFG                 0x95C
- #define MTK_WED_WDMA_RX_PREF_FIFO_RX0_CLR             BIT(0)
-@@ -367,6 +380,7 @@ struct mtk_wdma_desc {
- #define MTK_WED_WDMA_RESET_IDX                                0xa08
- #define MTK_WED_WDMA_RESET_IDX_RX                     GENMASK(17, 16)
-+#define MTK_WED_WDMA_RESET_IDX_RX_ALL                 BIT(20)
- #define MTK_WED_WDMA_RESET_IDX_DRV                    GENMASK(25, 24)
- #define MTK_WED_WDMA_INT_CLR                          0xa24
-@@ -437,21 +451,62 @@ struct mtk_wdma_desc {
- #define MTK_WDMA_INT_MASK_RX_DELAY                    BIT(30)
- #define MTK_WDMA_INT_MASK_RX_COHERENT                 BIT(31)
-+#define MTK_WDMA_XDMA_TX_FIFO_CFG                     0x238
-+#define MTK_WDMA_XDMA_TX_FIFO_CFG_TX_PAR_FIFO_CLEAR   BIT(0)
-+#define MTK_WDMA_XDMA_TX_FIFO_CFG_TX_CMD_FIFO_CLEAR   BIT(4)
-+#define MTK_WDMA_XDMA_TX_FIFO_CFG_TX_DMAD_FIFO_CLEAR  BIT(8)
-+#define MTK_WDMA_XDMA_TX_FIFO_CFG_TX_ARR_FIFO_CLEAR   BIT(12)
-+
-+#define MTK_WDMA_XDMA_RX_FIFO_CFG                     0x23c
-+#define MTK_WDMA_XDMA_RX_FIFO_CFG_RX_PAR_FIFO_CLEAR   BIT(0)
-+#define MTK_WDMA_XDMA_RX_FIFO_CFG_RX_CMD_FIFO_CLEAR   BIT(4)
-+#define MTK_WDMA_XDMA_RX_FIFO_CFG_RX_DMAD_FIFO_CLEAR  BIT(8)
-+#define MTK_WDMA_XDMA_RX_FIFO_CFG_RX_ARR_FIFO_CLEAR   BIT(12)
-+#define MTK_WDMA_XDMA_RX_FIFO_CFG_RX_LEN_FIFO_CLEAR   BIT(15)
-+#define MTK_WDMA_XDMA_RX_FIFO_CFG_RX_WID_FIFO_CLEAR   BIT(18)
-+#define MTK_WDMA_XDMA_RX_FIFO_CFG_RX_BID_FIFO_CLEAR   BIT(21)
-+
- #define MTK_WDMA_INT_GRP1                             0x250
- #define MTK_WDMA_INT_GRP2                             0x254
- #define MTK_WDMA_PREF_TX_CFG                          0x2d0
- #define MTK_WDMA_PREF_TX_CFG_PREF_EN                  BIT(0)
-+#define MTK_WDMA_PREF_TX_CFG_PREF_BUSY                        BIT(1)
- #define MTK_WDMA_PREF_RX_CFG                          0x2dc
- #define MTK_WDMA_PREF_RX_CFG_PREF_EN                  BIT(0)
-+#define MTK_WDMA_PREF_RX_CFG_PREF_BUSY                        BIT(1)
-+
-+#define MTK_WDMA_PREF_RX_FIFO_CFG                     0x2e0
-+#define MTK_WDMA_PREF_RX_FIFO_CFG_RING0_CLEAR         BIT(0)
-+#define MTK_WDMA_PREF_RX_FIFO_CFG_RING1_CLEAR         BIT(16)
-+
-+#define MTK_WDMA_PREF_TX_FIFO_CFG                     0x2d4
-+#define MTK_WDMA_PREF_TX_FIFO_CFG_RING0_CLEAR         BIT(0)
-+#define MTK_WDMA_PREF_TX_FIFO_CFG_RING1_CLEAR         BIT(16)
-+
-+#define MTK_WDMA_PREF_SIDX_CFG                                0x2e4
-+#define MTK_WDMA_PREF_SIDX_CFG_TX_RING_CLEAR          GENMASK(3, 0)
-+#define MTK_WDMA_PREF_SIDX_CFG_RX_RING_CLEAR          GENMASK(5, 4)
- #define MTK_WDMA_WRBK_TX_CFG                          0x300
-+#define MTK_WDMA_WRBK_TX_CFG_WRBK_BUSY                        BIT(0)
- #define MTK_WDMA_WRBK_TX_CFG_WRBK_EN                  BIT(30)
-+#define MTK_WDMA_WRBK_TX_FIFO_CFG(_n)                 (0x304 + (_n) * 0x4)
-+#define MTK_WDMA_WRBK_TX_FIFO_CFG_RING_CLEAR          BIT(0)
-+
- #define MTK_WDMA_WRBK_RX_CFG                          0x344
-+#define MTK_WDMA_WRBK_RX_CFG_WRBK_BUSY                        BIT(0)
- #define MTK_WDMA_WRBK_RX_CFG_WRBK_EN                  BIT(30)
-+#define MTK_WDMA_WRBK_RX_FIFO_CFG(_n)                 (0x348 + (_n) * 0x4)
-+#define MTK_WDMA_WRBK_RX_FIFO_CFG_RING_CLEAR          BIT(0)
-+
-+#define MTK_WDMA_WRBK_SIDX_CFG                                0x388
-+#define MTK_WDMA_WRBK_SIDX_CFG_TX_RING_CLEAR          GENMASK(3, 0)
-+#define MTK_WDMA_WRBK_SIDX_CFG_RX_RING_CLEAR          GENMASK(5, 4)
-+
- #define MTK_PCIE_MIRROR_MAP(n)                                ((n) ? 0x4 : 0x0)
- #define MTK_PCIE_MIRROR_MAP_EN                                BIT(0)
- #define MTK_PCIE_MIRROR_MAP_WED_ID                    BIT(1)
-@@ -465,6 +520,8 @@ struct mtk_wdma_desc {
- #define MTK_WED_RTQM_Q_DBG_BYPASS                     BIT(5)
- #define MTK_WED_RTQM_TXDMAD_FPORT                     GENMASK(23, 20)
-+#define MTK_WED_RTQM_RST                              0xb04
-+
- #define MTK_WED_RTQM_IGRS0_I2HW_DMAD_CNT              0xb1c
- #define MTK_WED_RTQM_IGRS0_I2H_DMAD_CNT(_n)           (0xb20 + (_n) * 0x4)
- #define       MTK_WED_RTQM_IGRS0_I2HW_PKT_CNT                 0xb28
-@@ -653,6 +710,9 @@ struct mtk_wdma_desc {
- #define MTK_WED_WPDMA_INT_CTRL_RRO_PG2_CLR            BIT(17)
- #define MTK_WED_WPDMA_INT_CTRL_RRO_PG2_DONE_TRIG      GENMASK(22, 18)
-+#define MTK_WED_RRO_RX_HW_STS                         0xf00
-+#define MTK_WED_RX_IND_CMD_BUSY                               GENMASK(31, 0)
-+
- #define MTK_WED_RX_IND_CMD_CNT0                               0xf20
- #define MTK_WED_RX_IND_CMD_DBG_CNT_EN                 BIT(31)
diff --git a/target/linux/generic/backport-5.15/764-01-v5.16-net-dsa-qca8k-fix-internal-delay-applied-to-the-wrong-PAD.patch b/target/linux/generic/backport-5.15/764-01-v5.16-net-dsa-qca8k-fix-internal-delay-applied-to-the-wrong-PAD.patch
deleted file mode 100644 (file)
index df9518d..0000000
+++ /dev/null
@@ -1,48 +0,0 @@
-From 3b00a07c2443745d62babfe08dbb2ad8e649526e Mon Sep 17 00:00:00 2001
-From: Ansuel Smith <[email protected]>
-Date: Fri, 19 Nov 2021 03:03:49 +0100
-Subject: [PATCH] net: dsa: qca8k: fix internal delay applied to the wrong PAD
- config
-
-With SGMII phy the internal delay is always applied to the PAD0 config.
-This is caused by the falling edge configuration that hardcode the reg
-to PAD0 (as the falling edge bits are present only in PAD0 reg)
-Move the delay configuration before the reg overwrite to correctly apply
-the delay.
-
-Fixes: cef08115846e ("net: dsa: qca8k: set internal delay also for sgmii")
-Signed-off-by: Ansuel Smith <[email protected]>
-Reviewed-by: Vladimir Oltean <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/dsa/qca8k.c | 12 ++++++------
- 1 file changed, 6 insertions(+), 6 deletions(-)
-
---- a/drivers/net/dsa/qca8k.c
-+++ b/drivers/net/dsa/qca8k.c
-@@ -1433,6 +1433,12 @@ qca8k_phylink_mac_config(struct dsa_swit
-               qca8k_write(priv, QCA8K_REG_SGMII_CTRL, val);
-+              /* From original code is reported port instability as SGMII also
-+               * require delay set. Apply advised values here or take them from DT.
-+               */
-+              if (state->interface == PHY_INTERFACE_MODE_SGMII)
-+                      qca8k_mac_config_setup_internal_delay(priv, cpu_port_index, reg);
-+
-               /* For qca8327/qca8328/qca8334/qca8338 sgmii is unique and
-                * falling edge is set writing in the PORT0 PAD reg
-                */
-@@ -1455,12 +1461,6 @@ qca8k_phylink_mac_config(struct dsa_swit
-                                       QCA8K_PORT0_PAD_SGMII_TXCLK_FALLING_EDGE,
-                                       val);
--              /* From original code is reported port instability as SGMII also
--               * require delay set. Apply advised values here or take them from DT.
--               */
--              if (state->interface == PHY_INTERFACE_MODE_SGMII)
--                      qca8k_mac_config_setup_internal_delay(priv, cpu_port_index, reg);
--
-               break;
-       default:
-               dev_err(ds->dev, "xMII mode %s not supported for port %d\n",
diff --git a/target/linux/generic/backport-5.15/764-02-v5.16-net-dsa-qca8k-fix-MTU-calculation.patch b/target/linux/generic/backport-5.15/764-02-v5.16-net-dsa-qca8k-fix-MTU-calculation.patch
deleted file mode 100644 (file)
index 7348d93..0000000
+++ /dev/null
@@ -1,46 +0,0 @@
-From 65258b9d8cde45689bdc86ca39b50f01f983733b Mon Sep 17 00:00:00 2001
-From: Robert Marko <[email protected]>
-Date: Fri, 19 Nov 2021 03:03:50 +0100
-Subject: [PATCH] net: dsa: qca8k: fix MTU calculation
-
-qca8k has a global MTU, so its tracking the MTU per port to make sure
-that the largest MTU gets applied.
-Since it uses the frame size instead of MTU the driver MTU change function
-will then add the size of Ethernet header and checksum on top of MTU.
-
-The driver currently populates the per port MTU size as Ethernet frame
-length + checksum which equals 1518.
-
-The issue is that then MTU change function will go through all of the
-ports, find the largest MTU and apply the Ethernet header + checksum on
-top of it again, so for a desired MTU of 1500 you will end up with 1536.
-
-This is obviously incorrect, so to correct it populate the per port struct
-MTU with just the MTU and not include the Ethernet header + checksum size
-as those will be added by the MTU change function.
-
-Fixes: f58d2598cf70 ("net: dsa: qca8k: implement the port MTU callbacks")
-Signed-off-by: Robert Marko <[email protected]>
-Signed-off-by: Ansuel Smith <[email protected]>
-Reviewed-by: Vladimir Oltean <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/dsa/qca8k.c | 6 +++++-
- 1 file changed, 5 insertions(+), 1 deletion(-)
-
---- a/drivers/net/dsa/qca8k.c
-+++ b/drivers/net/dsa/qca8k.c
-@@ -1256,8 +1256,12 @@ qca8k_setup(struct dsa_switch *ds)
-               /* Set initial MTU for every port.
-                * We have only have a general MTU setting. So track
-                * every port and set the max across all port.
-+               * Set per port MTU to 1500 as the MTU change function
-+               * will add the overhead and if its set to 1518 then it
-+               * will apply the overhead again and we will end up with
-+               * MTU of 1536 instead of 1518
-                */
--              priv->port_mtu[i] = ETH_FRAME_LEN + ETH_FCS_LEN;
-+              priv->port_mtu[i] = ETH_DATA_LEN;
-       }
-       /* Special GLOBAL_FC_THRESH value are needed for ar8327 switch */
diff --git a/target/linux/generic/backport-5.15/764-03-v5.17-net-next-net-dsa-qca8k-remove-redundant-check-in-parse_port_config.patch b/target/linux/generic/backport-5.15/764-03-v5.17-net-next-net-dsa-qca8k-remove-redundant-check-in-parse_port_config.patch
deleted file mode 100644 (file)
index f477b1b..0000000
+++ /dev/null
@@ -1,29 +0,0 @@
-From b9133f3ef5a2659730cf47a74bd0a9259f1cf8ff Mon Sep 17 00:00:00 2001
-From: Ansuel Smith <[email protected]>
-Date: Mon, 22 Nov 2021 16:23:40 +0100
-Subject: net: dsa: qca8k: remove redundant check in parse_port_config
-
-The very next check for port 0 and 6 already makes sure we don't go out
-of bounds with the ports_config delay table.
-Remove the redundant check.
-
-Reported-by: kernel test robot <[email protected]>
-Reported-by: Dan Carpenter <[email protected]>
-Signed-off-by: Ansuel Smith <[email protected]>
-Reviewed-by: Vladimir Oltean <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/dsa/qca8k.c | 2 +-
- 1 file changed, 1 insertion(+), 1 deletion(-)
-
---- a/drivers/net/dsa/qca8k.c
-+++ b/drivers/net/dsa/qca8k.c
-@@ -983,7 +983,7 @@ qca8k_parse_port_config(struct qca8k_pri
-       u32 delay;
-       /* We have 2 CPU port. Check them */
--      for (port = 0; port < QCA8K_NUM_PORTS && cpu_port_index < QCA8K_NUM_CPU_PORTS; port++) {
-+      for (port = 0; port < QCA8K_NUM_PORTS; port++) {
-               /* Skip every other port */
-               if (port != 0 && port != 6)
-                       continue;
diff --git a/target/linux/generic/backport-5.15/764-04-v5.17-net-next-net-dsa-qca8k-convert-to-GENMASK_FIELD_PREP_FIELD_GET.patch b/target/linux/generic/backport-5.15/764-04-v5.17-net-next-net-dsa-qca8k-convert-to-GENMASK_FIELD_PREP_FIELD_GET.patch
deleted file mode 100644 (file)
index 2cea880..0000000
+++ /dev/null
@@ -1,507 +0,0 @@
-From 90ae68bfc2ffcb54a4ba4f64edbeb84a80cbb57c Mon Sep 17 00:00:00 2001
-From: Ansuel Smith <[email protected]>
-Date: Mon, 22 Nov 2021 16:23:41 +0100
-Subject: net: dsa: qca8k: convert to GENMASK/FIELD_PREP/FIELD_GET
-
-Convert and try to standardize bit fields using
-GENMASK/FIELD_PREP/FIELD_GET macros. Rework some logic to support the
-standard macro and tidy things up. No functional change intended.
-
-Signed-off-by: Ansuel Smith <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/dsa/qca8k.c |  98 +++++++++++++++----------------
- drivers/net/dsa/qca8k.h | 153 ++++++++++++++++++++++++++----------------------
- 2 files changed, 130 insertions(+), 121 deletions(-)
-
---- a/drivers/net/dsa/qca8k.c
-+++ b/drivers/net/dsa/qca8k.c
-@@ -9,6 +9,7 @@
- #include <linux/module.h>
- #include <linux/phy.h>
- #include <linux/netdevice.h>
-+#include <linux/bitfield.h>
- #include <net/dsa.h>
- #include <linux/of_net.h>
- #include <linux/of_mdio.h>
-@@ -319,18 +320,18 @@ qca8k_fdb_read(struct qca8k_priv *priv,
-       }
-       /* vid - 83:72 */
--      fdb->vid = (reg[2] >> QCA8K_ATU_VID_S) & QCA8K_ATU_VID_M;
-+      fdb->vid = FIELD_GET(QCA8K_ATU_VID_MASK, reg[2]);
-       /* aging - 67:64 */
--      fdb->aging = reg[2] & QCA8K_ATU_STATUS_M;
-+      fdb->aging = FIELD_GET(QCA8K_ATU_STATUS_MASK, reg[2]);
-       /* portmask - 54:48 */
--      fdb->port_mask = (reg[1] >> QCA8K_ATU_PORT_S) & QCA8K_ATU_PORT_M;
-+      fdb->port_mask = FIELD_GET(QCA8K_ATU_PORT_MASK, reg[1]);
-       /* mac - 47:0 */
--      fdb->mac[0] = (reg[1] >> QCA8K_ATU_ADDR0_S) & 0xff;
--      fdb->mac[1] = reg[1] & 0xff;
--      fdb->mac[2] = (reg[0] >> QCA8K_ATU_ADDR2_S) & 0xff;
--      fdb->mac[3] = (reg[0] >> QCA8K_ATU_ADDR3_S) & 0xff;
--      fdb->mac[4] = (reg[0] >> QCA8K_ATU_ADDR4_S) & 0xff;
--      fdb->mac[5] = reg[0] & 0xff;
-+      fdb->mac[0] = FIELD_GET(QCA8K_ATU_ADDR0_MASK, reg[1]);
-+      fdb->mac[1] = FIELD_GET(QCA8K_ATU_ADDR1_MASK, reg[1]);
-+      fdb->mac[2] = FIELD_GET(QCA8K_ATU_ADDR2_MASK, reg[0]);
-+      fdb->mac[3] = FIELD_GET(QCA8K_ATU_ADDR3_MASK, reg[0]);
-+      fdb->mac[4] = FIELD_GET(QCA8K_ATU_ADDR4_MASK, reg[0]);
-+      fdb->mac[5] = FIELD_GET(QCA8K_ATU_ADDR5_MASK, reg[0]);
-       return 0;
- }
-@@ -343,18 +344,18 @@ qca8k_fdb_write(struct qca8k_priv *priv,
-       int i;
-       /* vid - 83:72 */
--      reg[2] = (vid & QCA8K_ATU_VID_M) << QCA8K_ATU_VID_S;
-+      reg[2] = FIELD_PREP(QCA8K_ATU_VID_MASK, vid);
-       /* aging - 67:64 */
--      reg[2] |= aging & QCA8K_ATU_STATUS_M;
-+      reg[2] |= FIELD_PREP(QCA8K_ATU_STATUS_MASK, aging);
-       /* portmask - 54:48 */
--      reg[1] = (port_mask & QCA8K_ATU_PORT_M) << QCA8K_ATU_PORT_S;
-+      reg[1] = FIELD_PREP(QCA8K_ATU_PORT_MASK, port_mask);
-       /* mac - 47:0 */
--      reg[1] |= mac[0] << QCA8K_ATU_ADDR0_S;
--      reg[1] |= mac[1];
--      reg[0] |= mac[2] << QCA8K_ATU_ADDR2_S;
--      reg[0] |= mac[3] << QCA8K_ATU_ADDR3_S;
--      reg[0] |= mac[4] << QCA8K_ATU_ADDR4_S;
--      reg[0] |= mac[5];
-+      reg[1] |= FIELD_PREP(QCA8K_ATU_ADDR0_MASK, mac[0]);
-+      reg[1] |= FIELD_PREP(QCA8K_ATU_ADDR1_MASK, mac[1]);
-+      reg[0] |= FIELD_PREP(QCA8K_ATU_ADDR2_MASK, mac[2]);
-+      reg[0] |= FIELD_PREP(QCA8K_ATU_ADDR3_MASK, mac[3]);
-+      reg[0] |= FIELD_PREP(QCA8K_ATU_ADDR4_MASK, mac[4]);
-+      reg[0] |= FIELD_PREP(QCA8K_ATU_ADDR5_MASK, mac[5]);
-       /* load the array into the ARL table */
-       for (i = 0; i < 3; i++)
-@@ -372,7 +373,7 @@ qca8k_fdb_access(struct qca8k_priv *priv
-       reg |= cmd;
-       if (port >= 0) {
-               reg |= QCA8K_ATU_FUNC_PORT_EN;
--              reg |= (port & QCA8K_ATU_FUNC_PORT_M) << QCA8K_ATU_FUNC_PORT_S;
-+              reg |= FIELD_PREP(QCA8K_ATU_FUNC_PORT_MASK, port);
-       }
-       /* Write the function register triggering the table access */
-@@ -454,7 +455,7 @@ qca8k_vlan_access(struct qca8k_priv *pri
-       /* Set the command and VLAN index */
-       reg = QCA8K_VTU_FUNC1_BUSY;
-       reg |= cmd;
--      reg |= vid << QCA8K_VTU_FUNC1_VID_S;
-+      reg |= FIELD_PREP(QCA8K_VTU_FUNC1_VID_MASK, vid);
-       /* Write the function register triggering the table access */
-       ret = qca8k_write(priv, QCA8K_REG_VTU_FUNC1, reg);
-@@ -500,13 +501,11 @@ qca8k_vlan_add(struct qca8k_priv *priv,
-       if (ret < 0)
-               goto out;
-       reg |= QCA8K_VTU_FUNC0_VALID | QCA8K_VTU_FUNC0_IVL_EN;
--      reg &= ~(QCA8K_VTU_FUNC0_EG_MODE_MASK << QCA8K_VTU_FUNC0_EG_MODE_S(port));
-+      reg &= ~QCA8K_VTU_FUNC0_EG_MODE_PORT_MASK(port);
-       if (untagged)
--              reg |= QCA8K_VTU_FUNC0_EG_MODE_UNTAG <<
--                              QCA8K_VTU_FUNC0_EG_MODE_S(port);
-+              reg |= QCA8K_VTU_FUNC0_EG_MODE_PORT_UNTAG(port);
-       else
--              reg |= QCA8K_VTU_FUNC0_EG_MODE_TAG <<
--                              QCA8K_VTU_FUNC0_EG_MODE_S(port);
-+              reg |= QCA8K_VTU_FUNC0_EG_MODE_PORT_TAG(port);
-       ret = qca8k_write(priv, QCA8K_REG_VTU_FUNC0, reg);
-       if (ret)
-@@ -534,15 +533,13 @@ qca8k_vlan_del(struct qca8k_priv *priv,
-       ret = qca8k_read(priv, QCA8K_REG_VTU_FUNC0, &reg);
-       if (ret < 0)
-               goto out;
--      reg &= ~(3 << QCA8K_VTU_FUNC0_EG_MODE_S(port));
--      reg |= QCA8K_VTU_FUNC0_EG_MODE_NOT <<
--                      QCA8K_VTU_FUNC0_EG_MODE_S(port);
-+      reg &= ~QCA8K_VTU_FUNC0_EG_MODE_PORT_MASK(port);
-+      reg |= QCA8K_VTU_FUNC0_EG_MODE_PORT_NOT(port);
-       /* Check if we're the last member to be removed */
-       del = true;
-       for (i = 0; i < QCA8K_NUM_PORTS; i++) {
--              mask = QCA8K_VTU_FUNC0_EG_MODE_NOT;
--              mask <<= QCA8K_VTU_FUNC0_EG_MODE_S(i);
-+              mask = QCA8K_VTU_FUNC0_EG_MODE_PORT_NOT(i);
-               if ((reg & mask) != mask) {
-                       del = false;
-@@ -1014,7 +1011,7 @@ qca8k_parse_port_config(struct qca8k_pri
-                                mode == PHY_INTERFACE_MODE_RGMII_TXID)
-                               delay = 1;
--                      if (delay > QCA8K_MAX_DELAY) {
-+                      if (!FIELD_FIT(QCA8K_PORT_PAD_RGMII_TX_DELAY_MASK, delay)) {
-                               dev_err(priv->dev, "rgmii tx delay is limited to a max value of 3ns, setting to the max value");
-                               delay = 3;
-                       }
-@@ -1030,7 +1027,7 @@ qca8k_parse_port_config(struct qca8k_pri
-                                mode == PHY_INTERFACE_MODE_RGMII_RXID)
-                               delay = 2;
--                      if (delay > QCA8K_MAX_DELAY) {
-+                      if (!FIELD_FIT(QCA8K_PORT_PAD_RGMII_RX_DELAY_MASK, delay)) {
-                               dev_err(priv->dev, "rgmii rx delay is limited to a max value of 3ns, setting to the max value");
-                               delay = 3;
-                       }
-@@ -1141,8 +1138,8 @@ qca8k_setup(struct dsa_switch *ds)
-               /* Enable QCA header mode on all cpu ports */
-               if (dsa_is_cpu_port(ds, i)) {
-                       ret = qca8k_write(priv, QCA8K_REG_PORT_HDR_CTRL(i),
--                                        QCA8K_PORT_HDR_CTRL_ALL << QCA8K_PORT_HDR_CTRL_TX_S |
--                                        QCA8K_PORT_HDR_CTRL_ALL << QCA8K_PORT_HDR_CTRL_RX_S);
-+                                        FIELD_PREP(QCA8K_PORT_HDR_CTRL_TX_MASK, QCA8K_PORT_HDR_CTRL_ALL) |
-+                                        FIELD_PREP(QCA8K_PORT_HDR_CTRL_RX_MASK, QCA8K_PORT_HDR_CTRL_ALL));
-                       if (ret) {
-                               dev_err(priv->dev, "failed enabling QCA header mode");
-                               return ret;
-@@ -1159,10 +1156,10 @@ qca8k_setup(struct dsa_switch *ds)
-        * for igmp, unknown, multicast and broadcast packet
-        */
-       ret = qca8k_write(priv, QCA8K_REG_GLOBAL_FW_CTRL1,
--                        BIT(cpu_port) << QCA8K_GLOBAL_FW_CTRL1_IGMP_DP_S |
--                        BIT(cpu_port) << QCA8K_GLOBAL_FW_CTRL1_BC_DP_S |
--                        BIT(cpu_port) << QCA8K_GLOBAL_FW_CTRL1_MC_DP_S |
--                        BIT(cpu_port) << QCA8K_GLOBAL_FW_CTRL1_UC_DP_S);
-+                        FIELD_PREP(QCA8K_GLOBAL_FW_CTRL1_IGMP_DP_MASK, BIT(cpu_port)) |
-+                        FIELD_PREP(QCA8K_GLOBAL_FW_CTRL1_BC_DP_MASK, BIT(cpu_port)) |
-+                        FIELD_PREP(QCA8K_GLOBAL_FW_CTRL1_MC_DP_MASK, BIT(cpu_port)) |
-+                        FIELD_PREP(QCA8K_GLOBAL_FW_CTRL1_UC_DP_MASK, BIT(cpu_port)));
-       if (ret)
-               return ret;
-@@ -1180,8 +1177,6 @@ qca8k_setup(struct dsa_switch *ds)
-               /* Individual user ports get connected to CPU port only */
-               if (dsa_is_user_port(ds, i)) {
--                      int shift = 16 * (i % 2);
--
-                       ret = qca8k_rmw(priv, QCA8K_PORT_LOOKUP_CTRL(i),
-                                       QCA8K_PORT_LOOKUP_MEMBER,
-                                       BIT(cpu_port));
-@@ -1198,8 +1193,8 @@ qca8k_setup(struct dsa_switch *ds)
-                        * default egress vid
-                        */
-                       ret = qca8k_rmw(priv, QCA8K_EGRESS_VLAN(i),
--                                      0xfff << shift,
--                                      QCA8K_PORT_VID_DEF << shift);
-+                                      QCA8K_EGREES_VLAN_PORT_MASK(i),
-+                                      QCA8K_EGREES_VLAN_PORT(i, QCA8K_PORT_VID_DEF));
-                       if (ret)
-                               return ret;
-@@ -1246,7 +1241,7 @@ qca8k_setup(struct dsa_switch *ds)
-                       QCA8K_PORT_HOL_CTRL1_EG_PORT_BUF_EN |
-                       QCA8K_PORT_HOL_CTRL1_WRED_EN;
-                       qca8k_rmw(priv, QCA8K_REG_PORT_HOL_CTRL1(i),
--                                QCA8K_PORT_HOL_CTRL1_ING_BUF |
-+                                QCA8K_PORT_HOL_CTRL1_ING_BUF_MASK |
-                                 QCA8K_PORT_HOL_CTRL1_EG_PRI_BUF_EN |
-                                 QCA8K_PORT_HOL_CTRL1_EG_PORT_BUF_EN |
-                                 QCA8K_PORT_HOL_CTRL1_WRED_EN,
-@@ -1269,8 +1264,8 @@ qca8k_setup(struct dsa_switch *ds)
-               mask = QCA8K_GLOBAL_FC_GOL_XON_THRES(288) |
-                      QCA8K_GLOBAL_FC_GOL_XOFF_THRES(496);
-               qca8k_rmw(priv, QCA8K_REG_GLOBAL_FC_THRESH,
--                        QCA8K_GLOBAL_FC_GOL_XON_THRES_S |
--                        QCA8K_GLOBAL_FC_GOL_XOFF_THRES_S,
-+                        QCA8K_GLOBAL_FC_GOL_XON_THRES_MASK |
-+                        QCA8K_GLOBAL_FC_GOL_XOFF_THRES_MASK,
-                         mask);
-       }
-@@ -1935,11 +1930,11 @@ qca8k_port_vlan_filtering(struct dsa_swi
-       if (vlan_filtering) {
-               ret = qca8k_rmw(priv, QCA8K_PORT_LOOKUP_CTRL(port),
--                              QCA8K_PORT_LOOKUP_VLAN_MODE,
-+                              QCA8K_PORT_LOOKUP_VLAN_MODE_MASK,
-                               QCA8K_PORT_LOOKUP_VLAN_MODE_SECURE);
-       } else {
-               ret = qca8k_rmw(priv, QCA8K_PORT_LOOKUP_CTRL(port),
--                              QCA8K_PORT_LOOKUP_VLAN_MODE,
-+                              QCA8K_PORT_LOOKUP_VLAN_MODE_MASK,
-                               QCA8K_PORT_LOOKUP_VLAN_MODE_NONE);
-       }
-@@ -1963,10 +1958,9 @@ qca8k_port_vlan_add(struct dsa_switch *d
-       }
-       if (pvid) {
--              int shift = 16 * (port % 2);
--
-               ret = qca8k_rmw(priv, QCA8K_EGRESS_VLAN(port),
--                              0xfff << shift, vlan->vid << shift);
-+                              QCA8K_EGREES_VLAN_PORT_MASK(port),
-+                              QCA8K_EGREES_VLAN_PORT(port, vlan->vid));
-               if (ret)
-                       return ret;
-@@ -2060,7 +2054,7 @@ static int qca8k_read_switch_id(struct q
-       if (ret < 0)
-               return -ENODEV;
--      id = QCA8K_MASK_CTRL_DEVICE_ID(val & QCA8K_MASK_CTRL_DEVICE_ID_MASK);
-+      id = QCA8K_MASK_CTRL_DEVICE_ID(val);
-       if (id != data->id) {
-               dev_err(priv->dev, "Switch id detected %x but expected %x", id, data->id);
-               return -ENODEV;
-@@ -2069,7 +2063,7 @@ static int qca8k_read_switch_id(struct q
-       priv->switch_id = id;
-       /* Save revision to communicate to the internal PHY driver */
--      priv->switch_revision = (val & QCA8K_MASK_CTRL_REV_ID_MASK);
-+      priv->switch_revision = QCA8K_MASK_CTRL_REV_ID(val);
-       return 0;
- }
---- a/drivers/net/dsa/qca8k.h
-+++ b/drivers/net/dsa/qca8k.h
-@@ -30,9 +30,9 @@
- /* Global control registers */
- #define QCA8K_REG_MASK_CTRL                           0x000
- #define   QCA8K_MASK_CTRL_REV_ID_MASK                 GENMASK(7, 0)
--#define   QCA8K_MASK_CTRL_REV_ID(x)                   ((x) >> 0)
-+#define   QCA8K_MASK_CTRL_REV_ID(x)                   FIELD_GET(QCA8K_MASK_CTRL_REV_ID_MASK, x)
- #define   QCA8K_MASK_CTRL_DEVICE_ID_MASK              GENMASK(15, 8)
--#define   QCA8K_MASK_CTRL_DEVICE_ID(x)                        ((x) >> 8)
-+#define   QCA8K_MASK_CTRL_DEVICE_ID(x)                        FIELD_GET(QCA8K_MASK_CTRL_DEVICE_ID_MASK, x)
- #define QCA8K_REG_PORT0_PAD_CTRL                      0x004
- #define   QCA8K_PORT0_PAD_MAC06_EXCHANGE_EN           BIT(31)
- #define   QCA8K_PORT0_PAD_SGMII_RXCLK_FALLING_EDGE    BIT(19)
-@@ -41,12 +41,11 @@
- #define QCA8K_REG_PORT6_PAD_CTRL                      0x00c
- #define   QCA8K_PORT_PAD_RGMII_EN                     BIT(26)
- #define   QCA8K_PORT_PAD_RGMII_TX_DELAY_MASK          GENMASK(23, 22)
--#define   QCA8K_PORT_PAD_RGMII_TX_DELAY(x)            ((x) << 22)
-+#define   QCA8K_PORT_PAD_RGMII_TX_DELAY(x)            FIELD_PREP(QCA8K_PORT_PAD_RGMII_TX_DELAY_MASK, x)
- #define   QCA8K_PORT_PAD_RGMII_RX_DELAY_MASK          GENMASK(21, 20)
--#define   QCA8K_PORT_PAD_RGMII_RX_DELAY(x)            ((x) << 20)
-+#define   QCA8K_PORT_PAD_RGMII_RX_DELAY(x)            FIELD_PREP(QCA8K_PORT_PAD_RGMII_RX_DELAY_MASK, x)
- #define         QCA8K_PORT_PAD_RGMII_TX_DELAY_EN              BIT(25)
- #define   QCA8K_PORT_PAD_RGMII_RX_DELAY_EN            BIT(24)
--#define   QCA8K_MAX_DELAY                             3
- #define   QCA8K_PORT_PAD_SGMII_EN                     BIT(7)
- #define QCA8K_REG_PWS                                 0x010
- #define   QCA8K_PWS_POWER_ON_SEL                      BIT(31)
-@@ -68,10 +67,12 @@
- #define   QCA8K_MDIO_MASTER_READ                      BIT(27)
- #define   QCA8K_MDIO_MASTER_WRITE                     0
- #define   QCA8K_MDIO_MASTER_SUP_PRE                   BIT(26)
--#define   QCA8K_MDIO_MASTER_PHY_ADDR(x)                       ((x) << 21)
--#define   QCA8K_MDIO_MASTER_REG_ADDR(x)                       ((x) << 16)
--#define   QCA8K_MDIO_MASTER_DATA(x)                   (x)
-+#define   QCA8K_MDIO_MASTER_PHY_ADDR_MASK             GENMASK(25, 21)
-+#define   QCA8K_MDIO_MASTER_PHY_ADDR(x)                       FIELD_PREP(QCA8K_MDIO_MASTER_PHY_ADDR_MASK, x)
-+#define   QCA8K_MDIO_MASTER_REG_ADDR_MASK             GENMASK(20, 16)
-+#define   QCA8K_MDIO_MASTER_REG_ADDR(x)                       FIELD_PREP(QCA8K_MDIO_MASTER_REG_ADDR_MASK, x)
- #define   QCA8K_MDIO_MASTER_DATA_MASK                 GENMASK(15, 0)
-+#define   QCA8K_MDIO_MASTER_DATA(x)                   FIELD_PREP(QCA8K_MDIO_MASTER_DATA_MASK, x)
- #define   QCA8K_MDIO_MASTER_MAX_PORTS                 5
- #define   QCA8K_MDIO_MASTER_MAX_REG                   32
- #define QCA8K_GOL_MAC_ADDR0                           0x60
-@@ -93,9 +94,7 @@
- #define   QCA8K_PORT_STATUS_FLOW_AUTO                 BIT(12)
- #define QCA8K_REG_PORT_HDR_CTRL(_i)                   (0x9c + (_i * 4))
- #define   QCA8K_PORT_HDR_CTRL_RX_MASK                 GENMASK(3, 2)
--#define   QCA8K_PORT_HDR_CTRL_RX_S                    2
- #define   QCA8K_PORT_HDR_CTRL_TX_MASK                 GENMASK(1, 0)
--#define   QCA8K_PORT_HDR_CTRL_TX_S                    0
- #define   QCA8K_PORT_HDR_CTRL_ALL                     2
- #define   QCA8K_PORT_HDR_CTRL_MGMT                    1
- #define   QCA8K_PORT_HDR_CTRL_NONE                    0
-@@ -105,10 +104,11 @@
- #define   QCA8K_SGMII_EN_TX                           BIT(3)
- #define   QCA8K_SGMII_EN_SD                           BIT(4)
- #define   QCA8K_SGMII_CLK125M_DELAY                   BIT(7)
--#define   QCA8K_SGMII_MODE_CTRL_MASK                  (BIT(22) | BIT(23))
--#define   QCA8K_SGMII_MODE_CTRL_BASEX                 (0 << 22)
--#define   QCA8K_SGMII_MODE_CTRL_PHY                   (1 << 22)
--#define   QCA8K_SGMII_MODE_CTRL_MAC                   (2 << 22)
-+#define   QCA8K_SGMII_MODE_CTRL_MASK                  GENMASK(23, 22)
-+#define   QCA8K_SGMII_MODE_CTRL(x)                    FIELD_PREP(QCA8K_SGMII_MODE_CTRL_MASK, x)
-+#define   QCA8K_SGMII_MODE_CTRL_BASEX                 QCA8K_SGMII_MODE_CTRL(0x0)
-+#define   QCA8K_SGMII_MODE_CTRL_PHY                   QCA8K_SGMII_MODE_CTRL(0x1)
-+#define   QCA8K_SGMII_MODE_CTRL_MAC                   QCA8K_SGMII_MODE_CTRL(0x2)
- /* MAC_PWR_SEL registers */
- #define QCA8K_REG_MAC_PWR_SEL                         0x0e4
-@@ -121,100 +121,115 @@
- /* ACL registers */
- #define QCA8K_REG_PORT_VLAN_CTRL0(_i)                 (0x420 + (_i * 8))
--#define   QCA8K_PORT_VLAN_CVID(x)                     (x << 16)
--#define   QCA8K_PORT_VLAN_SVID(x)                     x
-+#define   QCA8K_PORT_VLAN_CVID_MASK                   GENMASK(27, 16)
-+#define   QCA8K_PORT_VLAN_CVID(x)                     FIELD_PREP(QCA8K_PORT_VLAN_CVID_MASK, x)
-+#define   QCA8K_PORT_VLAN_SVID_MASK                   GENMASK(11, 0)
-+#define   QCA8K_PORT_VLAN_SVID(x)                     FIELD_PREP(QCA8K_PORT_VLAN_SVID_MASK, x)
- #define QCA8K_REG_PORT_VLAN_CTRL1(_i)                 (0x424 + (_i * 8))
- #define QCA8K_REG_IPV4_PRI_BASE_ADDR                  0x470
- #define QCA8K_REG_IPV4_PRI_ADDR_MASK                  0x474
- /* Lookup registers */
- #define QCA8K_REG_ATU_DATA0                           0x600
--#define   QCA8K_ATU_ADDR2_S                           24
--#define   QCA8K_ATU_ADDR3_S                           16
--#define   QCA8K_ATU_ADDR4_S                           8
-+#define   QCA8K_ATU_ADDR2_MASK                                GENMASK(31, 24)
-+#define   QCA8K_ATU_ADDR3_MASK                                GENMASK(23, 16)
-+#define   QCA8K_ATU_ADDR4_MASK                                GENMASK(15, 8)
-+#define   QCA8K_ATU_ADDR5_MASK                                GENMASK(7, 0)
- #define QCA8K_REG_ATU_DATA1                           0x604
--#define   QCA8K_ATU_PORT_M                            0x7f
--#define   QCA8K_ATU_PORT_S                            16
--#define   QCA8K_ATU_ADDR0_S                           8
-+#define   QCA8K_ATU_PORT_MASK                         GENMASK(22, 16)
-+#define   QCA8K_ATU_ADDR0_MASK                                GENMASK(15, 8)
-+#define   QCA8K_ATU_ADDR1_MASK                                GENMASK(7, 0)
- #define QCA8K_REG_ATU_DATA2                           0x608
--#define   QCA8K_ATU_VID_M                             0xfff
--#define   QCA8K_ATU_VID_S                             8
--#define   QCA8K_ATU_STATUS_M                          0xf
-+#define   QCA8K_ATU_VID_MASK                          GENMASK(19, 8)
-+#define   QCA8K_ATU_STATUS_MASK                               GENMASK(3, 0)
- #define   QCA8K_ATU_STATUS_STATIC                     0xf
- #define QCA8K_REG_ATU_FUNC                            0x60c
- #define   QCA8K_ATU_FUNC_BUSY                         BIT(31)
- #define   QCA8K_ATU_FUNC_PORT_EN                      BIT(14)
- #define   QCA8K_ATU_FUNC_MULTI_EN                     BIT(13)
- #define   QCA8K_ATU_FUNC_FULL                         BIT(12)
--#define   QCA8K_ATU_FUNC_PORT_M                               0xf
--#define   QCA8K_ATU_FUNC_PORT_S                               8
-+#define   QCA8K_ATU_FUNC_PORT_MASK                    GENMASK(11, 8)
- #define QCA8K_REG_VTU_FUNC0                           0x610
- #define   QCA8K_VTU_FUNC0_VALID                               BIT(20)
- #define   QCA8K_VTU_FUNC0_IVL_EN                      BIT(19)
--#define   QCA8K_VTU_FUNC0_EG_MODE_S(_i)                       (4 + (_i) * 2)
--#define   QCA8K_VTU_FUNC0_EG_MODE_MASK                        3
--#define   QCA8K_VTU_FUNC0_EG_MODE_UNMOD                       0
--#define   QCA8K_VTU_FUNC0_EG_MODE_UNTAG                       1
--#define   QCA8K_VTU_FUNC0_EG_MODE_TAG                 2
--#define   QCA8K_VTU_FUNC0_EG_MODE_NOT                 3
-+/*        QCA8K_VTU_FUNC0_EG_MODE_MASK                        GENMASK(17, 4)
-+ *          It does contain VLAN_MODE for each port [5:4] for port0,
-+ *          [7:6] for port1 ... [17:16] for port6. Use virtual port
-+ *          define to handle this.
-+ */
-+#define   QCA8K_VTU_FUNC0_EG_MODE_PORT_SHIFT(_i)      (4 + (_i) * 2)
-+#define   QCA8K_VTU_FUNC0_EG_MODE_MASK                        GENMASK(1, 0)
-+#define   QCA8K_VTU_FUNC0_EG_MODE_PORT_MASK(_i)               (GENMASK(1, 0) << QCA8K_VTU_FUNC0_EG_MODE_PORT_SHIFT(_i))
-+#define   QCA8K_VTU_FUNC0_EG_MODE_UNMOD                       FIELD_PREP(QCA8K_VTU_FUNC0_EG_MODE_MASK, 0x0)
-+#define   QCA8K_VTU_FUNC0_EG_MODE_PORT_UNMOD(_i)      (QCA8K_VTU_FUNC0_EG_MODE_UNMOD << QCA8K_VTU_FUNC0_EG_MODE_PORT_SHIFT(_i))
-+#define   QCA8K_VTU_FUNC0_EG_MODE_UNTAG                       FIELD_PREP(QCA8K_VTU_FUNC0_EG_MODE_MASK, 0x1)
-+#define   QCA8K_VTU_FUNC0_EG_MODE_PORT_UNTAG(_i)      (QCA8K_VTU_FUNC0_EG_MODE_UNTAG << QCA8K_VTU_FUNC0_EG_MODE_PORT_SHIFT(_i))
-+#define   QCA8K_VTU_FUNC0_EG_MODE_TAG                 FIELD_PREP(QCA8K_VTU_FUNC0_EG_MODE_MASK, 0x2)
-+#define   QCA8K_VTU_FUNC0_EG_MODE_PORT_TAG(_i)                (QCA8K_VTU_FUNC0_EG_MODE_TAG << QCA8K_VTU_FUNC0_EG_MODE_PORT_SHIFT(_i))
-+#define   QCA8K_VTU_FUNC0_EG_MODE_NOT                 FIELD_PREP(QCA8K_VTU_FUNC0_EG_MODE_MASK, 0x3)
-+#define   QCA8K_VTU_FUNC0_EG_MODE_PORT_NOT(_i)                (QCA8K_VTU_FUNC0_EG_MODE_NOT << QCA8K_VTU_FUNC0_EG_MODE_PORT_SHIFT(_i))
- #define QCA8K_REG_VTU_FUNC1                           0x614
- #define   QCA8K_VTU_FUNC1_BUSY                                BIT(31)
--#define   QCA8K_VTU_FUNC1_VID_S                               16
-+#define   QCA8K_VTU_FUNC1_VID_MASK                    GENMASK(27, 16)
- #define   QCA8K_VTU_FUNC1_FULL                                BIT(4)
- #define QCA8K_REG_GLOBAL_FW_CTRL0                     0x620
- #define   QCA8K_GLOBAL_FW_CTRL0_CPU_PORT_EN           BIT(10)
- #define QCA8K_REG_GLOBAL_FW_CTRL1                     0x624
--#define   QCA8K_GLOBAL_FW_CTRL1_IGMP_DP_S             24
--#define   QCA8K_GLOBAL_FW_CTRL1_BC_DP_S                       16
--#define   QCA8K_GLOBAL_FW_CTRL1_MC_DP_S                       8
--#define   QCA8K_GLOBAL_FW_CTRL1_UC_DP_S                       0
-+#define   QCA8K_GLOBAL_FW_CTRL1_IGMP_DP_MASK          GENMASK(30, 24)
-+#define   QCA8K_GLOBAL_FW_CTRL1_BC_DP_MASK            GENMASK(22, 16)
-+#define   QCA8K_GLOBAL_FW_CTRL1_MC_DP_MASK            GENMASK(14, 8)
-+#define   QCA8K_GLOBAL_FW_CTRL1_UC_DP_MASK            GENMASK(6, 0)
- #define QCA8K_PORT_LOOKUP_CTRL(_i)                    (0x660 + (_i) * 0xc)
- #define   QCA8K_PORT_LOOKUP_MEMBER                    GENMASK(6, 0)
--#define   QCA8K_PORT_LOOKUP_VLAN_MODE                 GENMASK(9, 8)
--#define   QCA8K_PORT_LOOKUP_VLAN_MODE_NONE            (0 << 8)
--#define   QCA8K_PORT_LOOKUP_VLAN_MODE_FALLBACK                (1 << 8)
--#define   QCA8K_PORT_LOOKUP_VLAN_MODE_CHECK           (2 << 8)
--#define   QCA8K_PORT_LOOKUP_VLAN_MODE_SECURE          (3 << 8)
-+#define   QCA8K_PORT_LOOKUP_VLAN_MODE_MASK            GENMASK(9, 8)
-+#define   QCA8K_PORT_LOOKUP_VLAN_MODE(x)              FIELD_PREP(QCA8K_PORT_LOOKUP_VLAN_MODE_MASK, x)
-+#define   QCA8K_PORT_LOOKUP_VLAN_MODE_NONE            QCA8K_PORT_LOOKUP_VLAN_MODE(0x0)
-+#define   QCA8K_PORT_LOOKUP_VLAN_MODE_FALLBACK                QCA8K_PORT_LOOKUP_VLAN_MODE(0x1)
-+#define   QCA8K_PORT_LOOKUP_VLAN_MODE_CHECK           QCA8K_PORT_LOOKUP_VLAN_MODE(0x2)
-+#define   QCA8K_PORT_LOOKUP_VLAN_MODE_SECURE          QCA8K_PORT_LOOKUP_VLAN_MODE(0x3)
- #define   QCA8K_PORT_LOOKUP_STATE_MASK                        GENMASK(18, 16)
--#define   QCA8K_PORT_LOOKUP_STATE_DISABLED            (0 << 16)
--#define   QCA8K_PORT_LOOKUP_STATE_BLOCKING            (1 << 16)
--#define   QCA8K_PORT_LOOKUP_STATE_LISTENING           (2 << 16)
--#define   QCA8K_PORT_LOOKUP_STATE_LEARNING            (3 << 16)
--#define   QCA8K_PORT_LOOKUP_STATE_FORWARD             (4 << 16)
--#define   QCA8K_PORT_LOOKUP_STATE                     GENMASK(18, 16)
-+#define   QCA8K_PORT_LOOKUP_STATE(x)                  FIELD_PREP(QCA8K_PORT_LOOKUP_STATE_MASK, x)
-+#define   QCA8K_PORT_LOOKUP_STATE_DISABLED            QCA8K_PORT_LOOKUP_STATE(0x0)
-+#define   QCA8K_PORT_LOOKUP_STATE_BLOCKING            QCA8K_PORT_LOOKUP_STATE(0x1)
-+#define   QCA8K_PORT_LOOKUP_STATE_LISTENING           QCA8K_PORT_LOOKUP_STATE(0x2)
-+#define   QCA8K_PORT_LOOKUP_STATE_LEARNING            QCA8K_PORT_LOOKUP_STATE(0x3)
-+#define   QCA8K_PORT_LOOKUP_STATE_FORWARD             QCA8K_PORT_LOOKUP_STATE(0x4)
- #define   QCA8K_PORT_LOOKUP_LEARN                     BIT(20)
- #define QCA8K_REG_GLOBAL_FC_THRESH                    0x800
--#define   QCA8K_GLOBAL_FC_GOL_XON_THRES(x)            ((x) << 16)
--#define   QCA8K_GLOBAL_FC_GOL_XON_THRES_S             GENMASK(24, 16)
--#define   QCA8K_GLOBAL_FC_GOL_XOFF_THRES(x)           ((x) << 0)
--#define   QCA8K_GLOBAL_FC_GOL_XOFF_THRES_S            GENMASK(8, 0)
-+#define   QCA8K_GLOBAL_FC_GOL_XON_THRES_MASK          GENMASK(24, 16)
-+#define   QCA8K_GLOBAL_FC_GOL_XON_THRES(x)            FIELD_PREP(QCA8K_GLOBAL_FC_GOL_XON_THRES_MASK, x)
-+#define   QCA8K_GLOBAL_FC_GOL_XOFF_THRES_MASK         GENMASK(8, 0)
-+#define   QCA8K_GLOBAL_FC_GOL_XOFF_THRES(x)           FIELD_PREP(QCA8K_GLOBAL_FC_GOL_XOFF_THRES_MASK, x)
- #define QCA8K_REG_PORT_HOL_CTRL0(_i)                  (0x970 + (_i) * 0x8)
--#define   QCA8K_PORT_HOL_CTRL0_EG_PRI0_BUF            GENMASK(3, 0)
--#define   QCA8K_PORT_HOL_CTRL0_EG_PRI0(x)             ((x) << 0)
--#define   QCA8K_PORT_HOL_CTRL0_EG_PRI1_BUF            GENMASK(7, 4)
--#define   QCA8K_PORT_HOL_CTRL0_EG_PRI1(x)             ((x) << 4)
--#define   QCA8K_PORT_HOL_CTRL0_EG_PRI2_BUF            GENMASK(11, 8)
--#define   QCA8K_PORT_HOL_CTRL0_EG_PRI2(x)             ((x) << 8)
--#define   QCA8K_PORT_HOL_CTRL0_EG_PRI3_BUF            GENMASK(15, 12)
--#define   QCA8K_PORT_HOL_CTRL0_EG_PRI3(x)             ((x) << 12)
--#define   QCA8K_PORT_HOL_CTRL0_EG_PRI4_BUF            GENMASK(19, 16)
--#define   QCA8K_PORT_HOL_CTRL0_EG_PRI4(x)             ((x) << 16)
--#define   QCA8K_PORT_HOL_CTRL0_EG_PRI5_BUF            GENMASK(23, 20)
--#define   QCA8K_PORT_HOL_CTRL0_EG_PRI5(x)             ((x) << 20)
--#define   QCA8K_PORT_HOL_CTRL0_EG_PORT_BUF            GENMASK(29, 24)
--#define   QCA8K_PORT_HOL_CTRL0_EG_PORT(x)             ((x) << 24)
-+#define   QCA8K_PORT_HOL_CTRL0_EG_PRI0_BUF_MASK               GENMASK(3, 0)
-+#define   QCA8K_PORT_HOL_CTRL0_EG_PRI0(x)             FIELD_PREP(QCA8K_PORT_HOL_CTRL0_EG_PRI0_BUF_MASK, x)
-+#define   QCA8K_PORT_HOL_CTRL0_EG_PRI1_BUF_MASK               GENMASK(7, 4)
-+#define   QCA8K_PORT_HOL_CTRL0_EG_PRI1(x)             FIELD_PREP(QCA8K_PORT_HOL_CTRL0_EG_PRI1_BUF_MASK, x)
-+#define   QCA8K_PORT_HOL_CTRL0_EG_PRI2_BUF_MASK               GENMASK(11, 8)
-+#define   QCA8K_PORT_HOL_CTRL0_EG_PRI2(x)             FIELD_PREP(QCA8K_PORT_HOL_CTRL0_EG_PRI2_BUF_MASK, x)
-+#define   QCA8K_PORT_HOL_CTRL0_EG_PRI3_BUF_MASK               GENMASK(15, 12)
-+#define   QCA8K_PORT_HOL_CTRL0_EG_PRI3(x)             FIELD_PREP(QCA8K_PORT_HOL_CTRL0_EG_PRI3_BUF_MASK, x)
-+#define   QCA8K_PORT_HOL_CTRL0_EG_PRI4_BUF_MASK               GENMASK(19, 16)
-+#define   QCA8K_PORT_HOL_CTRL0_EG_PRI4(x)             FIELD_PREP(QCA8K_PORT_HOL_CTRL0_EG_PRI4_BUF_MASK, x)
-+#define   QCA8K_PORT_HOL_CTRL0_EG_PRI5_BUF_MASK               GENMASK(23, 20)
-+#define   QCA8K_PORT_HOL_CTRL0_EG_PRI5(x)             FIELD_PREP(QCA8K_PORT_HOL_CTRL0_EG_PRI5_BUF_MASK, x)
-+#define   QCA8K_PORT_HOL_CTRL0_EG_PORT_BUF_MASK               GENMASK(29, 24)
-+#define   QCA8K_PORT_HOL_CTRL0_EG_PORT(x)             FIELD_PREP(QCA8K_PORT_HOL_CTRL0_EG_PORT_BUF_MASK, x)
- #define QCA8K_REG_PORT_HOL_CTRL1(_i)                  (0x974 + (_i) * 0x8)
--#define   QCA8K_PORT_HOL_CTRL1_ING_BUF                        GENMASK(3, 0)
--#define   QCA8K_PORT_HOL_CTRL1_ING(x)                 ((x) << 0)
-+#define   QCA8K_PORT_HOL_CTRL1_ING_BUF_MASK           GENMASK(3, 0)
-+#define   QCA8K_PORT_HOL_CTRL1_ING(x)                 FIELD_PREP(QCA8K_PORT_HOL_CTRL1_ING_BUF_MASK, x)
- #define   QCA8K_PORT_HOL_CTRL1_EG_PRI_BUF_EN          BIT(6)
- #define   QCA8K_PORT_HOL_CTRL1_EG_PORT_BUF_EN         BIT(7)
- #define   QCA8K_PORT_HOL_CTRL1_WRED_EN                        BIT(8)
- #define   QCA8K_PORT_HOL_CTRL1_EG_MIRROR_EN           BIT(16)
- /* Pkt edit registers */
-+#define QCA8K_EGREES_VLAN_PORT_SHIFT(_i)              (16 * ((_i) % 2))
-+#define QCA8K_EGREES_VLAN_PORT_MASK(_i)                       (GENMASK(11, 0) << QCA8K_EGREES_VLAN_PORT_SHIFT(_i))
-+#define QCA8K_EGREES_VLAN_PORT(_i, x)                 ((x) << QCA8K_EGREES_VLAN_PORT_SHIFT(_i))
- #define QCA8K_EGRESS_VLAN(x)                          (0x0c70 + (4 * (x / 2)))
- /* L3 registers */
diff --git a/target/linux/generic/backport-5.15/764-05-v5.17-net-next-net-dsa-qca8k-remove-extra-mutex_init-in-qca8k_setup.patch b/target/linux/generic/backport-5.15/764-05-v5.17-net-next-net-dsa-qca8k-remove-extra-mutex_init-in-qca8k_setup.patch
deleted file mode 100644 (file)
index 8c39b8e..0000000
+++ /dev/null
@@ -1,25 +0,0 @@
-From 994c28b6f971fa5db8ae977daea37eee87d93d51 Mon Sep 17 00:00:00 2001
-From: Ansuel Smith <[email protected]>
-Date: Mon, 22 Nov 2021 16:23:42 +0100
-Subject: net: dsa: qca8k: remove extra mutex_init in qca8k_setup
-
-Mutex is already init in sw_probe. Remove the extra init in qca8k_setup.
-
-Signed-off-by: Ansuel Smith <[email protected]>
-Reviewed-by: Vladimir Oltean <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/dsa/qca8k.c | 2 --
- 1 file changed, 2 deletions(-)
-
---- a/drivers/net/dsa/qca8k.c
-+++ b/drivers/net/dsa/qca8k.c
-@@ -1086,8 +1086,6 @@ qca8k_setup(struct dsa_switch *ds)
-       if (ret)
-               return ret;
--      mutex_init(&priv->reg_mutex);
--
-       /* Start by setting up the register mapping */
-       priv->regmap = devm_regmap_init(ds->dev, NULL, priv,
-                                       &qca8k_regmap_config);
diff --git a/target/linux/generic/backport-5.15/764-06-v5.17-net-next-net-dsa-qca8k-move-regmap-init-in-probe-and-set-it.patch b/target/linux/generic/backport-5.15/764-06-v5.17-net-next-net-dsa-qca8k-move-regmap-init-in-probe-and-set-it.patch
deleted file mode 100644 (file)
index 44d938c..0000000
+++ /dev/null
@@ -1,46 +0,0 @@
-From 36b8af12f424e7a7f60a935c60a0fd4aa0822378 Mon Sep 17 00:00:00 2001
-From: Ansuel Smith <[email protected]>
-Date: Mon, 22 Nov 2021 16:23:43 +0100
-Subject: net: dsa: qca8k: move regmap init in probe and set it mandatory
-
-In preparation for regmap conversion, move regmap init in the probe
-function and make it mandatory as any read/write/rmw operation will be
-converted to regmap API.
-
-Signed-off-by: Ansuel Smith <[email protected]>
-Reviewed-by: Vladimir Oltean <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/dsa/qca8k.c | 14 ++++++++------
- 1 file changed, 8 insertions(+), 6 deletions(-)
-
---- a/drivers/net/dsa/qca8k.c
-+++ b/drivers/net/dsa/qca8k.c
-@@ -1086,12 +1086,6 @@ qca8k_setup(struct dsa_switch *ds)
-       if (ret)
-               return ret;
--      /* Start by setting up the register mapping */
--      priv->regmap = devm_regmap_init(ds->dev, NULL, priv,
--                                      &qca8k_regmap_config);
--      if (IS_ERR(priv->regmap))
--              dev_warn(priv->dev, "regmap initialization failed");
--
-       ret = qca8k_setup_mdio_bus(priv);
-       if (ret)
-               return ret;
-@@ -2096,6 +2090,14 @@ qca8k_sw_probe(struct mdio_device *mdiod
-               gpiod_set_value_cansleep(priv->reset_gpio, 0);
-       }
-+      /* Start by setting up the register mapping */
-+      priv->regmap = devm_regmap_init(&mdiodev->dev, NULL, priv,
-+                                      &qca8k_regmap_config);
-+      if (IS_ERR(priv->regmap)) {
-+              dev_err(priv->dev, "regmap initialization failed");
-+              return PTR_ERR(priv->regmap);
-+      }
-+
-       /* Check the detected switch id */
-       ret = qca8k_read_switch_id(priv);
-       if (ret)
diff --git a/target/linux/generic/backport-5.15/764-07-v5.17-net-next-net-dsa-qca8k-initial-conversion-to-regmap-heper.patch b/target/linux/generic/backport-5.15/764-07-v5.17-net-next-net-dsa-qca8k-initial-conversion-to-regmap-heper.patch
deleted file mode 100644 (file)
index 4ca9c8b..0000000
+++ /dev/null
@@ -1,249 +0,0 @@
-From 8b5f3f29a81a71934d004e21a1292c1148b05926 Mon Sep 17 00:00:00 2001
-From: Ansuel Smith <[email protected]>
-Date: Mon, 22 Nov 2021 16:23:44 +0100
-Subject: net: dsa: qca8k: initial conversion to regmap helper
-
-Convert any qca8k set/clear/pool to regmap helper and add
-missing config to regmap_config struct.
-Read/write/rmw operation are reworked to use the regmap helper
-internally to keep the delta of this patch low. These additional
-function will then be dropped when the code split will be proposed.
-
-Ipq40xx SoC have the internal switch based on the qca8k regmap but use
-mmio for read/write/rmw operation instead of mdio.
-In preparation for the support of this internal switch, convert the
-driver to regmap API to later split the driver to common and specific
-code. The overhead introduced by the use of regamp API is marginal as the
-internal mdio will bypass it by using its direct access and regmap will be
-used only by configuration functions or fdb access.
-
-Signed-off-by: Ansuel Smith <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/dsa/qca8k.c | 107 +++++++++++++++++++++---------------------------
- 1 file changed, 47 insertions(+), 60 deletions(-)
-
---- a/drivers/net/dsa/qca8k.c
-+++ b/drivers/net/dsa/qca8k.c
-@@ -10,6 +10,7 @@
- #include <linux/phy.h>
- #include <linux/netdevice.h>
- #include <linux/bitfield.h>
-+#include <linux/regmap.h>
- #include <net/dsa.h>
- #include <linux/of_net.h>
- #include <linux/of_mdio.h>
-@@ -152,6 +153,25 @@ qca8k_set_page(struct mii_bus *bus, u16
- static int
- qca8k_read(struct qca8k_priv *priv, u32 reg, u32 *val)
- {
-+      return regmap_read(priv->regmap, reg, val);
-+}
-+
-+static int
-+qca8k_write(struct qca8k_priv *priv, u32 reg, u32 val)
-+{
-+      return regmap_write(priv->regmap, reg, val);
-+}
-+
-+static int
-+qca8k_rmw(struct qca8k_priv *priv, u32 reg, u32 mask, u32 write_val)
-+{
-+      return regmap_update_bits(priv->regmap, reg, mask, write_val);
-+}
-+
-+static int
-+qca8k_regmap_read(void *ctx, uint32_t reg, uint32_t *val)
-+{
-+      struct qca8k_priv *priv = (struct qca8k_priv *)ctx;
-       struct mii_bus *bus = priv->bus;
-       u16 r1, r2, page;
-       int ret;
-@@ -172,8 +192,9 @@ exit:
- }
- static int
--qca8k_write(struct qca8k_priv *priv, u32 reg, u32 val)
-+qca8k_regmap_write(void *ctx, uint32_t reg, uint32_t val)
- {
-+      struct qca8k_priv *priv = (struct qca8k_priv *)ctx;
-       struct mii_bus *bus = priv->bus;
-       u16 r1, r2, page;
-       int ret;
-@@ -194,8 +215,9 @@ exit:
- }
- static int
--qca8k_rmw(struct qca8k_priv *priv, u32 reg, u32 mask, u32 write_val)
-+qca8k_regmap_update_bits(void *ctx, uint32_t reg, uint32_t mask, uint32_t write_val)
- {
-+      struct qca8k_priv *priv = (struct qca8k_priv *)ctx;
-       struct mii_bus *bus = priv->bus;
-       u16 r1, r2, page;
-       u32 val;
-@@ -223,34 +245,6 @@ exit:
-       return ret;
- }
--static int
--qca8k_reg_set(struct qca8k_priv *priv, u32 reg, u32 val)
--{
--      return qca8k_rmw(priv, reg, 0, val);
--}
--
--static int
--qca8k_reg_clear(struct qca8k_priv *priv, u32 reg, u32 val)
--{
--      return qca8k_rmw(priv, reg, val, 0);
--}
--
--static int
--qca8k_regmap_read(void *ctx, uint32_t reg, uint32_t *val)
--{
--      struct qca8k_priv *priv = (struct qca8k_priv *)ctx;
--
--      return qca8k_read(priv, reg, val);
--}
--
--static int
--qca8k_regmap_write(void *ctx, uint32_t reg, uint32_t val)
--{
--      struct qca8k_priv *priv = (struct qca8k_priv *)ctx;
--
--      return qca8k_write(priv, reg, val);
--}
--
- static const struct regmap_range qca8k_readable_ranges[] = {
-       regmap_reg_range(0x0000, 0x00e4), /* Global control */
-       regmap_reg_range(0x0100, 0x0168), /* EEE control */
-@@ -282,26 +276,19 @@ static struct regmap_config qca8k_regmap
-       .max_register = 0x16ac, /* end MIB - Port6 range */
-       .reg_read = qca8k_regmap_read,
-       .reg_write = qca8k_regmap_write,
-+      .reg_update_bits = qca8k_regmap_update_bits,
-       .rd_table = &qca8k_readable_table,
-+      .disable_locking = true, /* Locking is handled by qca8k read/write */
-+      .cache_type = REGCACHE_NONE, /* Explicitly disable CACHE */
- };
- static int
- qca8k_busy_wait(struct qca8k_priv *priv, u32 reg, u32 mask)
- {
--      int ret, ret1;
-       u32 val;
--      ret = read_poll_timeout(qca8k_read, ret1, !(val & mask),
--                              0, QCA8K_BUSY_WAIT_TIMEOUT * USEC_PER_MSEC, false,
--                              priv, reg, &val);
--
--      /* Check if qca8k_read has failed for a different reason
--       * before returning -ETIMEDOUT
--       */
--      if (ret < 0 && ret1 < 0)
--              return ret1;
--
--      return ret;
-+      return regmap_read_poll_timeout(priv->regmap, reg, val, !(val & mask), 0,
-+                                     QCA8K_BUSY_WAIT_TIMEOUT * USEC_PER_MSEC);
- }
- static int
-@@ -568,7 +555,7 @@ qca8k_mib_init(struct qca8k_priv *priv)
-       int ret;
-       mutex_lock(&priv->reg_mutex);
--      ret = qca8k_reg_set(priv, QCA8K_REG_MIB, QCA8K_MIB_FLUSH | QCA8K_MIB_BUSY);
-+      ret = regmap_set_bits(priv->regmap, QCA8K_REG_MIB, QCA8K_MIB_FLUSH | QCA8K_MIB_BUSY);
-       if (ret)
-               goto exit;
-@@ -576,7 +563,7 @@ qca8k_mib_init(struct qca8k_priv *priv)
-       if (ret)
-               goto exit;
--      ret = qca8k_reg_set(priv, QCA8K_REG_MIB, QCA8K_MIB_CPU_KEEP);
-+      ret = regmap_set_bits(priv->regmap, QCA8K_REG_MIB, QCA8K_MIB_CPU_KEEP);
-       if (ret)
-               goto exit;
-@@ -597,9 +584,9 @@ qca8k_port_set_status(struct qca8k_priv
-               mask |= QCA8K_PORT_STATUS_LINK_AUTO;
-       if (enable)
--              qca8k_reg_set(priv, QCA8K_REG_PORT_STATUS(port), mask);
-+              regmap_set_bits(priv->regmap, QCA8K_REG_PORT_STATUS(port), mask);
-       else
--              qca8k_reg_clear(priv, QCA8K_REG_PORT_STATUS(port), mask);
-+              regmap_clear_bits(priv->regmap, QCA8K_REG_PORT_STATUS(port), mask);
- }
- static u32
-@@ -861,8 +848,8 @@ qca8k_setup_mdio_bus(struct qca8k_priv *
-                * a dt-overlay and driver reload changed the configuration
-                */
--              return qca8k_reg_clear(priv, QCA8K_MDIO_MASTER_CTRL,
--                                     QCA8K_MDIO_MASTER_EN);
-+              return regmap_clear_bits(priv->regmap, QCA8K_MDIO_MASTER_CTRL,
-+                                       QCA8K_MDIO_MASTER_EN);
-       }
-       /* Check if the devicetree declare the port:phy mapping */
-@@ -1099,16 +1086,16 @@ qca8k_setup(struct dsa_switch *ds)
-               return ret;
-       /* Make sure MAC06 is disabled */
--      ret = qca8k_reg_clear(priv, QCA8K_REG_PORT0_PAD_CTRL,
--                            QCA8K_PORT0_PAD_MAC06_EXCHANGE_EN);
-+      ret = regmap_clear_bits(priv->regmap, QCA8K_REG_PORT0_PAD_CTRL,
-+                              QCA8K_PORT0_PAD_MAC06_EXCHANGE_EN);
-       if (ret) {
-               dev_err(priv->dev, "failed disabling MAC06 exchange");
-               return ret;
-       }
-       /* Enable CPU Port */
--      ret = qca8k_reg_set(priv, QCA8K_REG_GLOBAL_FW_CTRL0,
--                          QCA8K_GLOBAL_FW_CTRL0_CPU_PORT_EN);
-+      ret = regmap_set_bits(priv->regmap, QCA8K_REG_GLOBAL_FW_CTRL0,
-+                            QCA8K_GLOBAL_FW_CTRL0_CPU_PORT_EN);
-       if (ret) {
-               dev_err(priv->dev, "failed enabling CPU port");
-               return ret;
-@@ -1176,8 +1163,8 @@ qca8k_setup(struct dsa_switch *ds)
-                               return ret;
-                       /* Enable ARP Auto-learning by default */
--                      ret = qca8k_reg_set(priv, QCA8K_PORT_LOOKUP_CTRL(i),
--                                          QCA8K_PORT_LOOKUP_LEARN);
-+                      ret = regmap_set_bits(priv->regmap, QCA8K_PORT_LOOKUP_CTRL(i),
-+                                            QCA8K_PORT_LOOKUP_LEARN);
-                       if (ret)
-                               return ret;
-@@ -1745,9 +1732,9 @@ qca8k_port_bridge_join(struct dsa_switch
-               /* Add this port to the portvlan mask of the other ports
-                * in the bridge
-                */
--              ret = qca8k_reg_set(priv,
--                                  QCA8K_PORT_LOOKUP_CTRL(i),
--                                  BIT(port));
-+              ret = regmap_set_bits(priv->regmap,
-+                                    QCA8K_PORT_LOOKUP_CTRL(i),
-+                                    BIT(port));
-               if (ret)
-                       return ret;
-               if (i != port)
-@@ -1777,9 +1764,9 @@ qca8k_port_bridge_leave(struct dsa_switc
-               /* Remove this port to the portvlan mask of the other ports
-                * in the bridge
-                */
--              qca8k_reg_clear(priv,
--                              QCA8K_PORT_LOOKUP_CTRL(i),
--                              BIT(port));
-+              regmap_clear_bits(priv->regmap,
-+                                QCA8K_PORT_LOOKUP_CTRL(i),
-+                                BIT(port));
-       }
-       /* Set the cpu port to be the only one in the portvlan mask of
diff --git a/target/linux/generic/backport-5.15/764-08-v5.17-net-next-net-dsa-qca8k-add-additional-MIB-counter-and-.patch b/target/linux/generic/backport-5.15/764-08-v5.17-net-next-net-dsa-qca8k-add-additional-MIB-counter-and-.patch
deleted file mode 100644 (file)
index c8c0509..0000000
+++ /dev/null
@@ -1,120 +0,0 @@
-From c126f118b330ccf0db0dda4a4bd6c729865a205f Mon Sep 17 00:00:00 2001
-From: Ansuel Smith <[email protected]>
-Date: Mon, 22 Nov 2021 16:23:45 +0100
-Subject: net: dsa: qca8k: add additional MIB counter and make it dynamic
-
-We are currently missing 2 additionals MIB counter present in QCA833x
-switch.
-QC832x switch have 39 MIB counter and QCA833X have 41 MIB counter.
-Add the additional MIB counter and rework the MIB function to print the
-correct supported counter from the match_data struct.
-
-Signed-off-by: Ansuel Smith <[email protected]>
-Reviewed-by: Vladimir Oltean <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/dsa/qca8k.c | 23 ++++++++++++++++++++---
- drivers/net/dsa/qca8k.h |  4 ++++
- 2 files changed, 24 insertions(+), 3 deletions(-)
-
---- a/drivers/net/dsa/qca8k.c
-+++ b/drivers/net/dsa/qca8k.c
-@@ -70,6 +70,8 @@ static const struct qca8k_mib_desc ar832
-       MIB_DESC(1, 0x9c, "TxExcDefer"),
-       MIB_DESC(1, 0xa0, "TxDefer"),
-       MIB_DESC(1, 0xa4, "TxLateCol"),
-+      MIB_DESC(1, 0xa8, "RXUnicast"),
-+      MIB_DESC(1, 0xac, "TXUnicast"),
- };
- /* The 32bit switch registers are accessed indirectly. To achieve this we need
-@@ -1605,12 +1607,16 @@ qca8k_phylink_mac_link_up(struct dsa_swi
- static void
- qca8k_get_strings(struct dsa_switch *ds, int port, u32 stringset, uint8_t *data)
- {
-+      const struct qca8k_match_data *match_data;
-+      struct qca8k_priv *priv = ds->priv;
-       int i;
-       if (stringset != ETH_SS_STATS)
-               return;
--      for (i = 0; i < ARRAY_SIZE(ar8327_mib); i++)
-+      match_data = of_device_get_match_data(priv->dev);
-+
-+      for (i = 0; i < match_data->mib_count; i++)
-               strncpy(data + i * ETH_GSTRING_LEN, ar8327_mib[i].name,
-                       ETH_GSTRING_LEN);
- }
-@@ -1620,12 +1626,15 @@ qca8k_get_ethtool_stats(struct dsa_switc
-                       uint64_t *data)
- {
-       struct qca8k_priv *priv = (struct qca8k_priv *)ds->priv;
-+      const struct qca8k_match_data *match_data;
-       const struct qca8k_mib_desc *mib;
-       u32 reg, i, val;
-       u32 hi = 0;
-       int ret;
--      for (i = 0; i < ARRAY_SIZE(ar8327_mib); i++) {
-+      match_data = of_device_get_match_data(priv->dev);
-+
-+      for (i = 0; i < match_data->mib_count; i++) {
-               mib = &ar8327_mib[i];
-               reg = QCA8K_PORT_MIB_COUNTER(port) + mib->offset;
-@@ -1648,10 +1657,15 @@ qca8k_get_ethtool_stats(struct dsa_switc
- static int
- qca8k_get_sset_count(struct dsa_switch *ds, int port, int sset)
- {
-+      const struct qca8k_match_data *match_data;
-+      struct qca8k_priv *priv = ds->priv;
-+
-       if (sset != ETH_SS_STATS)
-               return 0;
--      return ARRAY_SIZE(ar8327_mib);
-+      match_data = of_device_get_match_data(priv->dev);
-+
-+      return match_data->mib_count;
- }
- static int
-@@ -2173,14 +2187,17 @@ static SIMPLE_DEV_PM_OPS(qca8k_pm_ops,
- static const struct qca8k_match_data qca8327 = {
-       .id = QCA8K_ID_QCA8327,
-       .reduced_package = true,
-+      .mib_count = QCA8K_QCA832X_MIB_COUNT,
- };
- static const struct qca8k_match_data qca8328 = {
-       .id = QCA8K_ID_QCA8327,
-+      .mib_count = QCA8K_QCA832X_MIB_COUNT,
- };
- static const struct qca8k_match_data qca833x = {
-       .id = QCA8K_ID_QCA8337,
-+      .mib_count = QCA8K_QCA833X_MIB_COUNT,
- };
- static const struct of_device_id qca8k_of_match[] = {
---- a/drivers/net/dsa/qca8k.h
-+++ b/drivers/net/dsa/qca8k.h
-@@ -21,6 +21,9 @@
- #define PHY_ID_QCA8337                                        0x004dd036
- #define QCA8K_ID_QCA8337                              0x13
-+#define QCA8K_QCA832X_MIB_COUNT                               39
-+#define QCA8K_QCA833X_MIB_COUNT                               41
-+
- #define QCA8K_BUSY_WAIT_TIMEOUT                               2000
- #define QCA8K_NUM_FDB_RECORDS                         2048
-@@ -279,6 +282,7 @@ struct ar8xxx_port_status {
- struct qca8k_match_data {
-       u8 id;
-       bool reduced_package;
-+      u8 mib_count;
- };
- enum {
diff --git a/target/linux/generic/backport-5.15/764-09-v5.17-net-next-net-dsa-qca8k-add-support-for-port-fast-aging.patch b/target/linux/generic/backport-5.15/764-09-v5.17-net-next-net-dsa-qca8k-add-support-for-port-fast-aging.patch
deleted file mode 100644 (file)
index 8ad7ab4..0000000
+++ /dev/null
@@ -1,53 +0,0 @@
-From 4592538bfb0d5d3c3c8a1d7071724d081412ac91 Mon Sep 17 00:00:00 2001
-From: Ansuel Smith <[email protected]>
-Date: Mon, 22 Nov 2021 16:23:46 +0100
-Subject: net: dsa: qca8k: add support for port fast aging
-
-The switch supports fast aging by flushing any rule in the ARL
-table for a specific port.
-
-Signed-off-by: Ansuel Smith <[email protected]>
-Reviewed-by: Vladimir Oltean <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/dsa/qca8k.c | 11 +++++++++++
- drivers/net/dsa/qca8k.h |  1 +
- 2 files changed, 12 insertions(+)
-
---- a/drivers/net/dsa/qca8k.c
-+++ b/drivers/net/dsa/qca8k.c
-@@ -1790,6 +1790,16 @@ qca8k_port_bridge_leave(struct dsa_switc
-                 QCA8K_PORT_LOOKUP_MEMBER, BIT(cpu_port));
- }
-+static void
-+qca8k_port_fast_age(struct dsa_switch *ds, int port)
-+{
-+      struct qca8k_priv *priv = ds->priv;
-+
-+      mutex_lock(&priv->reg_mutex);
-+      qca8k_fdb_access(priv, QCA8K_FDB_FLUSH_PORT, port);
-+      mutex_unlock(&priv->reg_mutex);
-+}
-+
- static int
- qca8k_port_enable(struct dsa_switch *ds, int port,
-                 struct phy_device *phy)
-@@ -2017,6 +2027,7 @@ static const struct dsa_switch_ops qca8k
-       .port_stp_state_set     = qca8k_port_stp_state_set,
-       .port_bridge_join       = qca8k_port_bridge_join,
-       .port_bridge_leave      = qca8k_port_bridge_leave,
-+      .port_fast_age          = qca8k_port_fast_age,
-       .port_fdb_add           = qca8k_port_fdb_add,
-       .port_fdb_del           = qca8k_port_fdb_del,
-       .port_fdb_dump          = qca8k_port_fdb_dump,
---- a/drivers/net/dsa/qca8k.h
-+++ b/drivers/net/dsa/qca8k.h
-@@ -262,6 +262,7 @@ enum qca8k_fdb_cmd {
-       QCA8K_FDB_FLUSH = 1,
-       QCA8K_FDB_LOAD = 2,
-       QCA8K_FDB_PURGE = 3,
-+      QCA8K_FDB_FLUSH_PORT = 5,
-       QCA8K_FDB_NEXT = 6,
-       QCA8K_FDB_SEARCH = 7,
- };
diff --git a/target/linux/generic/backport-5.15/764-10-v5.17-net-next-net-dsa-qca8k-add-set_ageing_time-support.patch b/target/linux/generic/backport-5.15/764-10-v5.17-net-next-net-dsa-qca8k-add-set_ageing_time-support.patch
deleted file mode 100644 (file)
index 659e482..0000000
+++ /dev/null
@@ -1,78 +0,0 @@
-From 6a3bdc5209f45d2af83aa92433ab6e5cf2297aa4 Mon Sep 17 00:00:00 2001
-From: Ansuel Smith <[email protected]>
-Date: Mon, 22 Nov 2021 16:23:47 +0100
-Subject: net: dsa: qca8k: add set_ageing_time support
-
-qca8k support setting ageing time in step of 7s. Add support for it and
-set the max value accepted of 7645m.
-Documentation talks about support for 10000m but that values doesn't
-make sense as the value doesn't match the max value in the reg.
-
-Signed-off-by: Ansuel Smith <[email protected]>
-Reviewed-by: Vladimir Oltean <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/dsa/qca8k.c | 25 +++++++++++++++++++++++++
- drivers/net/dsa/qca8k.h |  3 +++
- 2 files changed, 28 insertions(+)
-
---- a/drivers/net/dsa/qca8k.c
-+++ b/drivers/net/dsa/qca8k.c
-@@ -1261,6 +1261,10 @@ qca8k_setup(struct dsa_switch *ds)
-       /* We don't have interrupts for link changes, so we need to poll */
-       ds->pcs_poll = true;
-+      /* Set min a max ageing value supported */
-+      ds->ageing_time_min = 7000;
-+      ds->ageing_time_max = 458745000;
-+
-       return 0;
- }
-@@ -1801,6 +1805,26 @@ qca8k_port_fast_age(struct dsa_switch *d
- }
- static int
-+qca8k_set_ageing_time(struct dsa_switch *ds, unsigned int msecs)
-+{
-+      struct qca8k_priv *priv = ds->priv;
-+      unsigned int secs = msecs / 1000;
-+      u32 val;
-+
-+      /* AGE_TIME reg is set in 7s step */
-+      val = secs / 7;
-+
-+      /* Handle case with 0 as val to NOT disable
-+       * learning
-+       */
-+      if (!val)
-+              val = 1;
-+
-+      return regmap_update_bits(priv->regmap, QCA8K_REG_ATU_CTRL, QCA8K_ATU_AGE_TIME_MASK,
-+                                QCA8K_ATU_AGE_TIME(val));
-+}
-+
-+static int
- qca8k_port_enable(struct dsa_switch *ds, int port,
-                 struct phy_device *phy)
- {
-@@ -2018,6 +2042,7 @@ static const struct dsa_switch_ops qca8k
-       .get_strings            = qca8k_get_strings,
-       .get_ethtool_stats      = qca8k_get_ethtool_stats,
-       .get_sset_count         = qca8k_get_sset_count,
-+      .set_ageing_time        = qca8k_set_ageing_time,
-       .get_mac_eee            = qca8k_get_mac_eee,
-       .set_mac_eee            = qca8k_set_mac_eee,
-       .port_enable            = qca8k_port_enable,
---- a/drivers/net/dsa/qca8k.h
-+++ b/drivers/net/dsa/qca8k.h
-@@ -175,6 +175,9 @@
- #define   QCA8K_VTU_FUNC1_BUSY                                BIT(31)
- #define   QCA8K_VTU_FUNC1_VID_MASK                    GENMASK(27, 16)
- #define   QCA8K_VTU_FUNC1_FULL                                BIT(4)
-+#define QCA8K_REG_ATU_CTRL                            0x618
-+#define   QCA8K_ATU_AGE_TIME_MASK                     GENMASK(15, 0)
-+#define   QCA8K_ATU_AGE_TIME(x)                               FIELD_PREP(QCA8K_ATU_AGE_TIME_MASK, (x))
- #define QCA8K_REG_GLOBAL_FW_CTRL0                     0x620
- #define   QCA8K_GLOBAL_FW_CTRL0_CPU_PORT_EN           BIT(10)
- #define QCA8K_REG_GLOBAL_FW_CTRL1                     0x624
diff --git a/target/linux/generic/backport-5.15/764-11-v5.17-net-next-net-dsa-qca8k-add-support-for-mdb_add-del.patch b/target/linux/generic/backport-5.15/764-11-v5.17-net-next-net-dsa-qca8k-add-support-for-mdb_add-del.patch
deleted file mode 100644 (file)
index 8b97939..0000000
+++ /dev/null
@@ -1,142 +0,0 @@
-From ba8f870dfa635113ce6e8095a5eb1835ecde2e9e Mon Sep 17 00:00:00 2001
-From: Ansuel Smith <[email protected]>
-Date: Mon, 22 Nov 2021 16:23:48 +0100
-Subject: net: dsa: qca8k: add support for mdb_add/del
-
-Add support for mdb add/del function. The ARL table is used to insert
-the rule. The rule will be searched, deleted and reinserted with the
-port mask updated. The function will check if the rule has to be updated
-or insert directly with no deletion of the old rule.
-If every port is removed from the port mask, the rule is removed.
-The rule is set STATIC in the ARL table (aka it doesn't age) to not be
-flushed by fast age function.
-
-Signed-off-by: Ansuel Smith <[email protected]>
-Reviewed-by: Vladimir Oltean <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/dsa/qca8k.c | 99 +++++++++++++++++++++++++++++++++++++++++++++++++
- 1 file changed, 99 insertions(+)
-
---- a/drivers/net/dsa/qca8k.c
-+++ b/drivers/net/dsa/qca8k.c
-@@ -436,6 +436,81 @@ qca8k_fdb_flush(struct qca8k_priv *priv)
- }
- static int
-+qca8k_fdb_search_and_insert(struct qca8k_priv *priv, u8 port_mask,
-+                          const u8 *mac, u16 vid)
-+{
-+      struct qca8k_fdb fdb = { 0 };
-+      int ret;
-+
-+      mutex_lock(&priv->reg_mutex);
-+
-+      qca8k_fdb_write(priv, vid, 0, mac, 0);
-+      ret = qca8k_fdb_access(priv, QCA8K_FDB_SEARCH, -1);
-+      if (ret < 0)
-+              goto exit;
-+
-+      ret = qca8k_fdb_read(priv, &fdb);
-+      if (ret < 0)
-+              goto exit;
-+
-+      /* Rule exist. Delete first */
-+      if (!fdb.aging) {
-+              ret = qca8k_fdb_access(priv, QCA8K_FDB_PURGE, -1);
-+              if (ret)
-+                      goto exit;
-+      }
-+
-+      /* Add port to fdb portmask */
-+      fdb.port_mask |= port_mask;
-+
-+      qca8k_fdb_write(priv, vid, fdb.port_mask, mac, fdb.aging);
-+      ret = qca8k_fdb_access(priv, QCA8K_FDB_LOAD, -1);
-+
-+exit:
-+      mutex_unlock(&priv->reg_mutex);
-+      return ret;
-+}
-+
-+static int
-+qca8k_fdb_search_and_del(struct qca8k_priv *priv, u8 port_mask,
-+                       const u8 *mac, u16 vid)
-+{
-+      struct qca8k_fdb fdb = { 0 };
-+      int ret;
-+
-+      mutex_lock(&priv->reg_mutex);
-+
-+      qca8k_fdb_write(priv, vid, 0, mac, 0);
-+      ret = qca8k_fdb_access(priv, QCA8K_FDB_SEARCH, -1);
-+      if (ret < 0)
-+              goto exit;
-+
-+      /* Rule doesn't exist. Why delete? */
-+      if (!fdb.aging) {
-+              ret = -EINVAL;
-+              goto exit;
-+      }
-+
-+      ret = qca8k_fdb_access(priv, QCA8K_FDB_PURGE, -1);
-+      if (ret)
-+              goto exit;
-+
-+      /* Only port in the rule is this port. Don't re insert */
-+      if (fdb.port_mask == port_mask)
-+              goto exit;
-+
-+      /* Remove port from port mask */
-+      fdb.port_mask &= ~port_mask;
-+
-+      qca8k_fdb_write(priv, vid, fdb.port_mask, mac, fdb.aging);
-+      ret = qca8k_fdb_access(priv, QCA8K_FDB_LOAD, -1);
-+
-+exit:
-+      mutex_unlock(&priv->reg_mutex);
-+      return ret;
-+}
-+
-+static int
- qca8k_vlan_access(struct qca8k_priv *priv, enum qca8k_vlan_cmd cmd, u16 vid)
- {
-       u32 reg;
-@@ -1949,6 +2024,28 @@ qca8k_port_fdb_dump(struct dsa_switch *d
- }
- static int
-+qca8k_port_mdb_add(struct dsa_switch *ds, int port,
-+                 const struct switchdev_obj_port_mdb *mdb)
-+{
-+      struct qca8k_priv *priv = ds->priv;
-+      const u8 *addr = mdb->addr;
-+      u16 vid = mdb->vid;
-+
-+      return qca8k_fdb_search_and_insert(priv, BIT(port), addr, vid);
-+}
-+
-+static int
-+qca8k_port_mdb_del(struct dsa_switch *ds, int port,
-+                 const struct switchdev_obj_port_mdb *mdb)
-+{
-+      struct qca8k_priv *priv = ds->priv;
-+      const u8 *addr = mdb->addr;
-+      u16 vid = mdb->vid;
-+
-+      return qca8k_fdb_search_and_del(priv, BIT(port), addr, vid);
-+}
-+
-+static int
- qca8k_port_vlan_filtering(struct dsa_switch *ds, int port, bool vlan_filtering,
-                         struct netlink_ext_ack *extack)
- {
-@@ -2056,6 +2153,8 @@ static const struct dsa_switch_ops qca8k
-       .port_fdb_add           = qca8k_port_fdb_add,
-       .port_fdb_del           = qca8k_port_fdb_del,
-       .port_fdb_dump          = qca8k_port_fdb_dump,
-+      .port_mdb_add           = qca8k_port_mdb_add,
-+      .port_mdb_del           = qca8k_port_mdb_del,
-       .port_vlan_filtering    = qca8k_port_vlan_filtering,
-       .port_vlan_add          = qca8k_port_vlan_add,
-       .port_vlan_del          = qca8k_port_vlan_del,
diff --git a/target/linux/generic/backport-5.15/764-12-v5.17-net-next-net-dsa-qca8k-add-support-for-mirror-mode.patch b/target/linux/generic/backport-5.15/764-12-v5.17-net-next-net-dsa-qca8k-add-support-for-mirror-mode.patch
deleted file mode 100644 (file)
index dc5a229..0000000
+++ /dev/null
@@ -1,155 +0,0 @@
-From 2c1bdbc7e7560d7de754cad277d968d56bb1899e Mon Sep 17 00:00:00 2001
-From: Ansuel Smith <[email protected]>
-Date: Tue, 23 Nov 2021 03:59:10 +0100
-Subject: net: dsa: qca8k: add support for mirror mode
-
-The switch supports mirror mode. Only one port can set as mirror port and
-every other port can set to both ingress and egress mode. The mirror
-port is disabled and reverted to normal operation once every port is
-removed from sending packet to it.
-
-Signed-off-by: Ansuel Smith <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/dsa/qca8k.c | 95 +++++++++++++++++++++++++++++++++++++++++++++++++
- drivers/net/dsa/qca8k.h |  4 +++
- 2 files changed, 99 insertions(+)
-
---- a/drivers/net/dsa/qca8k.c
-+++ b/drivers/net/dsa/qca8k.c
-@@ -2046,6 +2046,99 @@ qca8k_port_mdb_del(struct dsa_switch *ds
- }
- static int
-+qca8k_port_mirror_add(struct dsa_switch *ds, int port,
-+                    struct dsa_mall_mirror_tc_entry *mirror,
-+                    bool ingress)
-+{
-+      struct qca8k_priv *priv = ds->priv;
-+      int monitor_port, ret;
-+      u32 reg, val;
-+
-+      /* Check for existent entry */
-+      if ((ingress ? priv->mirror_rx : priv->mirror_tx) & BIT(port))
-+              return -EEXIST;
-+
-+      ret = regmap_read(priv->regmap, QCA8K_REG_GLOBAL_FW_CTRL0, &val);
-+      if (ret)
-+              return ret;
-+
-+      /* QCA83xx can have only one port set to mirror mode.
-+       * Check that the correct port is requested and return error otherwise.
-+       * When no mirror port is set, the values is set to 0xF
-+       */
-+      monitor_port = FIELD_GET(QCA8K_GLOBAL_FW_CTRL0_MIRROR_PORT_NUM, val);
-+      if (monitor_port != 0xF && monitor_port != mirror->to_local_port)
-+              return -EEXIST;
-+
-+      /* Set the monitor port */
-+      val = FIELD_PREP(QCA8K_GLOBAL_FW_CTRL0_MIRROR_PORT_NUM,
-+                       mirror->to_local_port);
-+      ret = regmap_update_bits(priv->regmap, QCA8K_REG_GLOBAL_FW_CTRL0,
-+                               QCA8K_GLOBAL_FW_CTRL0_MIRROR_PORT_NUM, val);
-+      if (ret)
-+              return ret;
-+
-+      if (ingress) {
-+              reg = QCA8K_PORT_LOOKUP_CTRL(port);
-+              val = QCA8K_PORT_LOOKUP_ING_MIRROR_EN;
-+      } else {
-+              reg = QCA8K_REG_PORT_HOL_CTRL1(port);
-+              val = QCA8K_PORT_HOL_CTRL1_EG_MIRROR_EN;
-+      }
-+
-+      ret = regmap_update_bits(priv->regmap, reg, val, val);
-+      if (ret)
-+              return ret;
-+
-+      /* Track mirror port for tx and rx to decide when the
-+       * mirror port has to be disabled.
-+       */
-+      if (ingress)
-+              priv->mirror_rx |= BIT(port);
-+      else
-+              priv->mirror_tx |= BIT(port);
-+
-+      return 0;
-+}
-+
-+static void
-+qca8k_port_mirror_del(struct dsa_switch *ds, int port,
-+                    struct dsa_mall_mirror_tc_entry *mirror)
-+{
-+      struct qca8k_priv *priv = ds->priv;
-+      u32 reg, val;
-+      int ret;
-+
-+      if (mirror->ingress) {
-+              reg = QCA8K_PORT_LOOKUP_CTRL(port);
-+              val = QCA8K_PORT_LOOKUP_ING_MIRROR_EN;
-+      } else {
-+              reg = QCA8K_REG_PORT_HOL_CTRL1(port);
-+              val = QCA8K_PORT_HOL_CTRL1_EG_MIRROR_EN;
-+      }
-+
-+      ret = regmap_clear_bits(priv->regmap, reg, val);
-+      if (ret)
-+              goto err;
-+
-+      if (mirror->ingress)
-+              priv->mirror_rx &= ~BIT(port);
-+      else
-+              priv->mirror_tx &= ~BIT(port);
-+
-+      /* No port set to send packet to mirror port. Disable mirror port */
-+      if (!priv->mirror_rx && !priv->mirror_tx) {
-+              val = FIELD_PREP(QCA8K_GLOBAL_FW_CTRL0_MIRROR_PORT_NUM, 0xF);
-+              ret = regmap_update_bits(priv->regmap, QCA8K_REG_GLOBAL_FW_CTRL0,
-+                                       QCA8K_GLOBAL_FW_CTRL0_MIRROR_PORT_NUM, val);
-+              if (ret)
-+                      goto err;
-+      }
-+err:
-+      dev_err(priv->dev, "Failed to del mirror port from %d", port);
-+}
-+
-+static int
- qca8k_port_vlan_filtering(struct dsa_switch *ds, int port, bool vlan_filtering,
-                         struct netlink_ext_ack *extack)
- {
-@@ -2155,6 +2248,8 @@ static const struct dsa_switch_ops qca8k
-       .port_fdb_dump          = qca8k_port_fdb_dump,
-       .port_mdb_add           = qca8k_port_mdb_add,
-       .port_mdb_del           = qca8k_port_mdb_del,
-+      .port_mirror_add        = qca8k_port_mirror_add,
-+      .port_mirror_del        = qca8k_port_mirror_del,
-       .port_vlan_filtering    = qca8k_port_vlan_filtering,
-       .port_vlan_add          = qca8k_port_vlan_add,
-       .port_vlan_del          = qca8k_port_vlan_del,
---- a/drivers/net/dsa/qca8k.h
-+++ b/drivers/net/dsa/qca8k.h
-@@ -180,6 +180,7 @@
- #define   QCA8K_ATU_AGE_TIME(x)                               FIELD_PREP(QCA8K_ATU_AGE_TIME_MASK, (x))
- #define QCA8K_REG_GLOBAL_FW_CTRL0                     0x620
- #define   QCA8K_GLOBAL_FW_CTRL0_CPU_PORT_EN           BIT(10)
-+#define   QCA8K_GLOBAL_FW_CTRL0_MIRROR_PORT_NUM               GENMASK(7, 4)
- #define QCA8K_REG_GLOBAL_FW_CTRL1                     0x624
- #define   QCA8K_GLOBAL_FW_CTRL1_IGMP_DP_MASK          GENMASK(30, 24)
- #define   QCA8K_GLOBAL_FW_CTRL1_BC_DP_MASK            GENMASK(22, 16)
-@@ -201,6 +202,7 @@
- #define   QCA8K_PORT_LOOKUP_STATE_LEARNING            QCA8K_PORT_LOOKUP_STATE(0x3)
- #define   QCA8K_PORT_LOOKUP_STATE_FORWARD             QCA8K_PORT_LOOKUP_STATE(0x4)
- #define   QCA8K_PORT_LOOKUP_LEARN                     BIT(20)
-+#define   QCA8K_PORT_LOOKUP_ING_MIRROR_EN             BIT(25)
- #define QCA8K_REG_GLOBAL_FC_THRESH                    0x800
- #define   QCA8K_GLOBAL_FC_GOL_XON_THRES_MASK          GENMASK(24, 16)
-@@ -305,6 +307,8 @@ struct qca8k_ports_config {
- struct qca8k_priv {
-       u8 switch_id;
-       u8 switch_revision;
-+      u8 mirror_rx;
-+      u8 mirror_tx;
-       bool legacy_phy_port_mapping;
-       struct qca8k_ports_config ports_config;
-       struct regmap *regmap;
diff --git a/target/linux/generic/backport-5.15/764-13-v5.17-net-next-net-dsa-qca8k-add-LAG-support.patch b/target/linux/generic/backport-5.15/764-13-v5.17-net-next-net-dsa-qca8k-add-LAG-support.patch
deleted file mode 100644 (file)
index b53f128..0000000
+++ /dev/null
@@ -1,288 +0,0 @@
-From def975307c01191b6f0170048c3724b0ed3348af Mon Sep 17 00:00:00 2001
-From: Ansuel Smith <[email protected]>
-Date: Tue, 23 Nov 2021 03:59:11 +0100
-Subject: net: dsa: qca8k: add LAG support
-
-Add LAG support to this switch. In Documentation this is described as
-trunk mode. A max of 4 LAGs are supported and each can support up to 4
-port. The current tx mode supported is Hash mode with both L2 and L2+3
-mode.
-When no port are present in the trunk, the trunk is disabled in the
-switch.
-When a port is disconnected, the traffic is redirected to the other
-available port.
-The hash mode is global and each LAG require to have the same hash mode
-set. To change the hash mode when multiple LAG are configured, it's
-required to remove each LAG and set the desired hash mode to the last.
-An error is printed when it's asked to set a not supported hadh mode.
-
-Signed-off-by: Ansuel Smith <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/dsa/qca8k.c | 177 ++++++++++++++++++++++++++++++++++++++++++++++++
- drivers/net/dsa/qca8k.h |  33 +++++++++
- 2 files changed, 210 insertions(+)
-
---- a/drivers/net/dsa/qca8k.c
-+++ b/drivers/net/dsa/qca8k.c
-@@ -1340,6 +1340,9 @@ qca8k_setup(struct dsa_switch *ds)
-       ds->ageing_time_min = 7000;
-       ds->ageing_time_max = 458745000;
-+      /* Set max number of LAGs supported */
-+      ds->num_lag_ids = QCA8K_NUM_LAGS;
-+
-       return 0;
- }
-@@ -2226,6 +2229,178 @@ qca8k_get_tag_protocol(struct dsa_switch
-       return DSA_TAG_PROTO_QCA;
- }
-+static bool
-+qca8k_lag_can_offload(struct dsa_switch *ds,
-+                    struct net_device *lag,
-+                    struct netdev_lag_upper_info *info)
-+{
-+      struct dsa_port *dp;
-+      int id, members = 0;
-+
-+      id = dsa_lag_id(ds->dst, lag);
-+      if (id < 0 || id >= ds->num_lag_ids)
-+              return false;
-+
-+      dsa_lag_foreach_port(dp, ds->dst, lag)
-+              /* Includes the port joining the LAG */
-+              members++;
-+
-+      if (members > QCA8K_NUM_PORTS_FOR_LAG)
-+              return false;
-+
-+      if (info->tx_type != NETDEV_LAG_TX_TYPE_HASH)
-+              return false;
-+
-+      if (info->hash_type != NETDEV_LAG_HASH_L2 ||
-+          info->hash_type != NETDEV_LAG_HASH_L23)
-+              return false;
-+
-+      return true;
-+}
-+
-+static int
-+qca8k_lag_setup_hash(struct dsa_switch *ds,
-+                   struct net_device *lag,
-+                   struct netdev_lag_upper_info *info)
-+{
-+      struct qca8k_priv *priv = ds->priv;
-+      bool unique_lag = true;
-+      int i, id;
-+      u32 hash;
-+
-+      id = dsa_lag_id(ds->dst, lag);
-+
-+      switch (info->hash_type) {
-+      case NETDEV_LAG_HASH_L23:
-+              hash |= QCA8K_TRUNK_HASH_SIP_EN;
-+              hash |= QCA8K_TRUNK_HASH_DIP_EN;
-+              fallthrough;
-+      case NETDEV_LAG_HASH_L2:
-+              hash |= QCA8K_TRUNK_HASH_SA_EN;
-+              hash |= QCA8K_TRUNK_HASH_DA_EN;
-+              break;
-+      default: /* We should NEVER reach this */
-+              return -EOPNOTSUPP;
-+      }
-+
-+      /* Check if we are the unique configured LAG */
-+      dsa_lags_foreach_id(i, ds->dst)
-+              if (i != id && dsa_lag_dev(ds->dst, i)) {
-+                      unique_lag = false;
-+                      break;
-+              }
-+
-+      /* Hash Mode is global. Make sure the same Hash Mode
-+       * is set to all the 4 possible lag.
-+       * If we are the unique LAG we can set whatever hash
-+       * mode we want.
-+       * To change hash mode it's needed to remove all LAG
-+       * and change the mode with the latest.
-+       */
-+      if (unique_lag) {
-+              priv->lag_hash_mode = hash;
-+      } else if (priv->lag_hash_mode != hash) {
-+              netdev_err(lag, "Error: Mismateched Hash Mode across different lag is not supported\n");
-+              return -EOPNOTSUPP;
-+      }
-+
-+      return regmap_update_bits(priv->regmap, QCA8K_TRUNK_HASH_EN_CTRL,
-+                                QCA8K_TRUNK_HASH_MASK, hash);
-+}
-+
-+static int
-+qca8k_lag_refresh_portmap(struct dsa_switch *ds, int port,
-+                        struct net_device *lag, bool delete)
-+{
-+      struct qca8k_priv *priv = ds->priv;
-+      int ret, id, i;
-+      u32 val;
-+
-+      id = dsa_lag_id(ds->dst, lag);
-+
-+      /* Read current port member */
-+      ret = regmap_read(priv->regmap, QCA8K_REG_GOL_TRUNK_CTRL0, &val);
-+      if (ret)
-+              return ret;
-+
-+      /* Shift val to the correct trunk */
-+      val >>= QCA8K_REG_GOL_TRUNK_SHIFT(id);
-+      val &= QCA8K_REG_GOL_TRUNK_MEMBER_MASK;
-+      if (delete)
-+              val &= ~BIT(port);
-+      else
-+              val |= BIT(port);
-+
-+      /* Update port member. With empty portmap disable trunk */
-+      ret = regmap_update_bits(priv->regmap, QCA8K_REG_GOL_TRUNK_CTRL0,
-+                               QCA8K_REG_GOL_TRUNK_MEMBER(id) |
-+                               QCA8K_REG_GOL_TRUNK_EN(id),
-+                               !val << QCA8K_REG_GOL_TRUNK_SHIFT(id) |
-+                               val << QCA8K_REG_GOL_TRUNK_SHIFT(id));
-+
-+      /* Search empty member if adding or port on deleting */
-+      for (i = 0; i < QCA8K_NUM_PORTS_FOR_LAG; i++) {
-+              ret = regmap_read(priv->regmap, QCA8K_REG_GOL_TRUNK_CTRL(id), &val);
-+              if (ret)
-+                      return ret;
-+
-+              val >>= QCA8K_REG_GOL_TRUNK_ID_MEM_ID_SHIFT(id, i);
-+              val &= QCA8K_REG_GOL_TRUNK_ID_MEM_ID_MASK;
-+
-+              if (delete) {
-+                      /* If port flagged to be disabled assume this member is
-+                       * empty
-+                       */
-+                      if (val != QCA8K_REG_GOL_TRUNK_ID_MEM_ID_EN_MASK)
-+                              continue;
-+
-+                      val &= QCA8K_REG_GOL_TRUNK_ID_MEM_ID_PORT_MASK;
-+                      if (val != port)
-+                              continue;
-+              } else {
-+                      /* If port flagged to be enabled assume this member is
-+                       * already set
-+                       */
-+                      if (val == QCA8K_REG_GOL_TRUNK_ID_MEM_ID_EN_MASK)
-+                              continue;
-+              }
-+
-+              /* We have found the member to add/remove */
-+              break;
-+      }
-+
-+      /* Set port in the correct port mask or disable port if in delete mode */
-+      return regmap_update_bits(priv->regmap, QCA8K_REG_GOL_TRUNK_CTRL(id),
-+                                QCA8K_REG_GOL_TRUNK_ID_MEM_ID_EN(id, i) |
-+                                QCA8K_REG_GOL_TRUNK_ID_MEM_ID_PORT(id, i),
-+                                !delete << QCA8K_REG_GOL_TRUNK_ID_MEM_ID_SHIFT(id, i) |
-+                                port << QCA8K_REG_GOL_TRUNK_ID_MEM_ID_SHIFT(id, i));
-+}
-+
-+static int
-+qca8k_port_lag_join(struct dsa_switch *ds, int port,
-+                  struct net_device *lag,
-+                  struct netdev_lag_upper_info *info)
-+{
-+      int ret;
-+
-+      if (!qca8k_lag_can_offload(ds, lag, info))
-+              return -EOPNOTSUPP;
-+
-+      ret = qca8k_lag_setup_hash(ds, lag, info);
-+      if (ret)
-+              return ret;
-+
-+      return qca8k_lag_refresh_portmap(ds, port, lag, false);
-+}
-+
-+static int
-+qca8k_port_lag_leave(struct dsa_switch *ds, int port,
-+                   struct net_device *lag)
-+{
-+      return qca8k_lag_refresh_portmap(ds, port, lag, true);
-+}
-+
- static const struct dsa_switch_ops qca8k_switch_ops = {
-       .get_tag_protocol       = qca8k_get_tag_protocol,
-       .setup                  = qca8k_setup,
-@@ -2259,6 +2434,8 @@ static const struct dsa_switch_ops qca8k
-       .phylink_mac_link_down  = qca8k_phylink_mac_link_down,
-       .phylink_mac_link_up    = qca8k_phylink_mac_link_up,
-       .get_phy_flags          = qca8k_get_phy_flags,
-+      .port_lag_join          = qca8k_port_lag_join,
-+      .port_lag_leave         = qca8k_port_lag_leave,
- };
- static int qca8k_read_switch_id(struct qca8k_priv *priv)
---- a/drivers/net/dsa/qca8k.h
-+++ b/drivers/net/dsa/qca8k.h
-@@ -15,6 +15,8 @@
- #define QCA8K_NUM_PORTS                                       7
- #define QCA8K_NUM_CPU_PORTS                           2
- #define QCA8K_MAX_MTU                                 9000
-+#define QCA8K_NUM_LAGS                                        4
-+#define QCA8K_NUM_PORTS_FOR_LAG                               4
- #define PHY_ID_QCA8327                                        0x004dd034
- #define QCA8K_ID_QCA8327                              0x12
-@@ -122,6 +124,14 @@
- #define QCA8K_REG_EEE_CTRL                            0x100
- #define  QCA8K_REG_EEE_CTRL_LPI_EN(_i)                        ((_i + 1) * 2)
-+/* TRUNK_HASH_EN registers */
-+#define QCA8K_TRUNK_HASH_EN_CTRL                      0x270
-+#define   QCA8K_TRUNK_HASH_SIP_EN                     BIT(3)
-+#define   QCA8K_TRUNK_HASH_DIP_EN                     BIT(2)
-+#define   QCA8K_TRUNK_HASH_SA_EN                      BIT(1)
-+#define   QCA8K_TRUNK_HASH_DA_EN                      BIT(0)
-+#define   QCA8K_TRUNK_HASH_MASK                               GENMASK(3, 0)
-+
- /* ACL registers */
- #define QCA8K_REG_PORT_VLAN_CTRL0(_i)                 (0x420 + (_i * 8))
- #define   QCA8K_PORT_VLAN_CVID_MASK                   GENMASK(27, 16)
-@@ -204,6 +214,28 @@
- #define   QCA8K_PORT_LOOKUP_LEARN                     BIT(20)
- #define   QCA8K_PORT_LOOKUP_ING_MIRROR_EN             BIT(25)
-+#define QCA8K_REG_GOL_TRUNK_CTRL0                     0x700
-+/* 4 max trunk first
-+ * first 6 bit for member bitmap
-+ * 7th bit is to enable trunk port
-+ */
-+#define QCA8K_REG_GOL_TRUNK_SHIFT(_i)                 ((_i) * 8)
-+#define QCA8K_REG_GOL_TRUNK_EN_MASK                   BIT(7)
-+#define QCA8K_REG_GOL_TRUNK_EN(_i)                    (QCA8K_REG_GOL_TRUNK_EN_MASK << QCA8K_REG_GOL_TRUNK_SHIFT(_i))
-+#define QCA8K_REG_GOL_TRUNK_MEMBER_MASK                       GENMASK(6, 0)
-+#define QCA8K_REG_GOL_TRUNK_MEMBER(_i)                        (QCA8K_REG_GOL_TRUNK_MEMBER_MASK << QCA8K_REG_GOL_TRUNK_SHIFT(_i))
-+/* 0x704 for TRUNK 0-1 --- 0x708 for TRUNK 2-3 */
-+#define QCA8K_REG_GOL_TRUNK_CTRL(_i)                  (0x704 + (((_i) / 2) * 4))
-+#define QCA8K_REG_GOL_TRUNK_ID_MEM_ID_MASK            GENMASK(3, 0)
-+#define QCA8K_REG_GOL_TRUNK_ID_MEM_ID_EN_MASK         BIT(3)
-+#define QCA8K_REG_GOL_TRUNK_ID_MEM_ID_PORT_MASK               GENMASK(2, 0)
-+#define QCA8K_REG_GOL_TRUNK_ID_SHIFT(_i)              (((_i) / 2) * 16)
-+#define QCA8K_REG_GOL_MEM_ID_SHIFT(_i)                        ((_i) * 4)
-+/* Complex shift: FIRST shift for port THEN shift for trunk */
-+#define QCA8K_REG_GOL_TRUNK_ID_MEM_ID_SHIFT(_i, _j)   (QCA8K_REG_GOL_MEM_ID_SHIFT(_j) + QCA8K_REG_GOL_TRUNK_ID_SHIFT(_i))
-+#define QCA8K_REG_GOL_TRUNK_ID_MEM_ID_EN(_i, _j)      (QCA8K_REG_GOL_TRUNK_ID_MEM_ID_EN_MASK << QCA8K_REG_GOL_TRUNK_ID_MEM_ID_SHIFT(_i, _j))
-+#define QCA8K_REG_GOL_TRUNK_ID_MEM_ID_PORT(_i, _j)    (QCA8K_REG_GOL_TRUNK_ID_MEM_ID_PORT_MASK << QCA8K_REG_GOL_TRUNK_ID_MEM_ID_SHIFT(_i, _j))
-+
- #define QCA8K_REG_GLOBAL_FC_THRESH                    0x800
- #define   QCA8K_GLOBAL_FC_GOL_XON_THRES_MASK          GENMASK(24, 16)
- #define   QCA8K_GLOBAL_FC_GOL_XON_THRES(x)            FIELD_PREP(QCA8K_GLOBAL_FC_GOL_XON_THRES_MASK, x)
-@@ -309,6 +341,7 @@ struct qca8k_priv {
-       u8 switch_revision;
-       u8 mirror_rx;
-       u8 mirror_tx;
-+      u8 lag_hash_mode;
-       bool legacy_phy_port_mapping;
-       struct qca8k_ports_config ports_config;
-       struct regmap *regmap;
diff --git a/target/linux/generic/backport-5.15/764-14-v5.17-net-next-net-dsa-qca8k-fix-warning-in-LAG-feature.patch b/target/linux/generic/backport-5.15/764-14-v5.17-net-next-net-dsa-qca8k-fix-warning-in-LAG-feature.patch
deleted file mode 100644 (file)
index 7d811be..0000000
+++ /dev/null
@@ -1,40 +0,0 @@
-From 0898ca67b86e14207d4feb3f3fea8b87cec5aab1 Mon Sep 17 00:00:00 2001
-From: Ansuel Smith <[email protected]>
-Date: Tue, 23 Nov 2021 16:44:46 +0100
-Subject: net: dsa: qca8k: fix warning in LAG feature
-
-Fix warning reported by bot.
-Make sure hash is init to 0 and fix wrong logic for hash_type in
-qca8k_lag_can_offload.
-
-Reported-by: kernel test robot <[email protected]>
-Fixes: def975307c01 ("net: dsa: qca8k: add LAG support")
-Signed-off-by: Ansuel Smith <[email protected]>
-Reviewed-by: Florian Fainelli <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- drivers/net/dsa/qca8k.c | 4 ++--
- 1 file changed, 2 insertions(+), 2 deletions(-)
-
---- a/drivers/net/dsa/qca8k.c
-+++ b/drivers/net/dsa/qca8k.c
-@@ -2251,7 +2251,7 @@ qca8k_lag_can_offload(struct dsa_switch
-       if (info->tx_type != NETDEV_LAG_TX_TYPE_HASH)
-               return false;
--      if (info->hash_type != NETDEV_LAG_HASH_L2 ||
-+      if (info->hash_type != NETDEV_LAG_HASH_L2 &&
-           info->hash_type != NETDEV_LAG_HASH_L23)
-               return false;
-@@ -2265,8 +2265,8 @@ qca8k_lag_setup_hash(struct dsa_switch *
- {
-       struct qca8k_priv *priv = ds->priv;
-       bool unique_lag = true;
-+      u32 hash = 0;
-       int i, id;
--      u32 hash;
-       id = dsa_lag_id(ds->dst, lag);
diff --git a/target/linux/generic/backport-5.15/765-v5.17-01-net-next-net-dsa-reorder-PHY-initialization-with-MTU-setup-in.patch b/target/linux/generic/backport-5.15/765-v5.17-01-net-next-net-dsa-reorder-PHY-initialization-with-MTU-setup-in.patch
deleted file mode 100644 (file)
index 77cf63b..0000000
+++ /dev/null
@@ -1,52 +0,0 @@
-From 904e112ad431492b34f235f59738e8312802bbf9 Mon Sep 17 00:00:00 2001
-From: Vladimir Oltean <[email protected]>
-Date: Thu, 6 Jan 2022 01:11:12 +0200
-Subject: [PATCH 1/6] net: dsa: reorder PHY initialization with MTU setup in
- slave.c
-
-In dsa_slave_create() there are 2 sections that take rtnl_lock():
-MTU change and netdev registration. They are separated by PHY
-initialization.
-
-There isn't any strict ordering requirement except for the fact that
-netdev registration should be last. Therefore, we can perform the MTU
-change a bit later, after the PHY setup. A future change will then be
-able to merge the two rtnl_lock sections into one.
-
-Signed-off-by: Vladimir Oltean <[email protected]>
-Reviewed-by: Florian Fainelli <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- net/dsa/slave.c | 14 +++++++-------
- 1 file changed, 7 insertions(+), 7 deletions(-)
-
---- a/net/dsa/slave.c
-+++ b/net/dsa/slave.c
-@@ -1977,13 +1977,6 @@ int dsa_slave_create(struct dsa_port *po
-       port->slave = slave_dev;
-       dsa_slave_setup_tagger(slave_dev);
--      rtnl_lock();
--      ret = dsa_slave_change_mtu(slave_dev, ETH_DATA_LEN);
--      rtnl_unlock();
--      if (ret && ret != -EOPNOTSUPP)
--              dev_warn(ds->dev, "nonfatal error %d setting MTU to %d on port %d\n",
--                       ret, ETH_DATA_LEN, port->index);
--
-       netif_carrier_off(slave_dev);
-       ret = dsa_slave_phy_setup(slave_dev);
-@@ -1995,6 +1988,13 @@ int dsa_slave_create(struct dsa_port *po
-       }
-       rtnl_lock();
-+      ret = dsa_slave_change_mtu(slave_dev, ETH_DATA_LEN);
-+      rtnl_unlock();
-+      if (ret && ret != -EOPNOTSUPP)
-+              dev_warn(ds->dev, "nonfatal error %d setting MTU to %d on port %d\n",
-+                       ret, ETH_DATA_LEN, port->index);
-+
-+      rtnl_lock();
-       ret = register_netdevice(slave_dev);
-       if (ret) {
diff --git a/target/linux/generic/backport-5.15/765-v5.17-02-net-next-net-dsa-merge-rtnl_lock-sections-in-dsa_slave_create.patch b/target/linux/generic/backport-5.15/765-v5.17-02-net-next-net-dsa-merge-rtnl_lock-sections-in-dsa_slave_create.patch
deleted file mode 100644 (file)
index 50aa5d8..0000000
+++ /dev/null
@@ -1,34 +0,0 @@
-From e31dbd3b6aba585231cd84a87adeb22e7c6a8c19 Mon Sep 17 00:00:00 2001
-From: Vladimir Oltean <[email protected]>
-Date: Thu, 6 Jan 2022 01:11:13 +0200
-Subject: [PATCH 2/6] net: dsa: merge rtnl_lock sections in dsa_slave_create
-
-Currently dsa_slave_create() has two sequences of rtnl_lock/rtnl_unlock
-in a row. Remove the rtnl_unlock() and rtnl_lock() in between, such that
-the operation can execute slighly faster.
-
-Signed-off-by: Vladimir Oltean <[email protected]>
-Reviewed-by: Florian Fainelli <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- net/dsa/slave.c | 4 +---
- 1 file changed, 1 insertion(+), 3 deletions(-)
-
---- a/net/dsa/slave.c
-+++ b/net/dsa/slave.c
-@@ -1988,14 +1988,12 @@ int dsa_slave_create(struct dsa_port *po
-       }
-       rtnl_lock();
-+
-       ret = dsa_slave_change_mtu(slave_dev, ETH_DATA_LEN);
--      rtnl_unlock();
-       if (ret && ret != -EOPNOTSUPP)
-               dev_warn(ds->dev, "nonfatal error %d setting MTU to %d on port %d\n",
-                        ret, ETH_DATA_LEN, port->index);
--      rtnl_lock();
--
-       ret = register_netdevice(slave_dev);
-       if (ret) {
-               netdev_err(master, "error %d registering interface %s\n",
diff --git a/target/linux/generic/backport-5.15/765-v5.17-03-net-next-net-dsa-stop-updating-master-MTU-from-master.c.patch b/target/linux/generic/backport-5.15/765-v5.17-03-net-next-net-dsa-stop-updating-master-MTU-from-master.c.patch
deleted file mode 100644 (file)
index 6c7aad6..0000000
+++ /dev/null
@@ -1,91 +0,0 @@
-From a1ff94c2973c43bc1e2677ac63ebb15b1d1ff846 Mon Sep 17 00:00:00 2001
-From: Vladimir Oltean <[email protected]>
-Date: Thu, 6 Jan 2022 01:11:14 +0200
-Subject: [PATCH 3/6] net: dsa: stop updating master MTU from master.c
-
-At present there are two paths for changing the MTU of the DSA master.
-
-The first is:
-
-dsa_tree_setup
--> dsa_tree_setup_ports
-   -> dsa_port_setup
-      -> dsa_slave_create
-         -> dsa_slave_change_mtu
-            -> dev_set_mtu(master)
-
-The second is:
-
-dsa_tree_setup
--> dsa_tree_setup_master
-   -> dsa_master_setup
-      -> dev_set_mtu(dev)
-
-So the dev_set_mtu() call from dsa_master_setup() has been effectively
-superseded by the dsa_slave_change_mtu(slave_dev, ETH_DATA_LEN) that is
-done from dsa_slave_create() for each user port. The later function also
-updates the master MTU according to the largest user port MTU from the
-tree. Therefore, updating the master MTU through a separate code path
-isn't needed.
-
-Signed-off-by: Vladimir Oltean <[email protected]>
-Reviewed-by: Florian Fainelli <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- net/dsa/master.c | 25 +------------------------
- 1 file changed, 1 insertion(+), 24 deletions(-)
-
---- a/net/dsa/master.c
-+++ b/net/dsa/master.c
-@@ -329,28 +329,13 @@ static const struct attribute_group dsa_
-       .attrs  = dsa_slave_attrs,
- };
--static void dsa_master_reset_mtu(struct net_device *dev)
--{
--      int err;
--
--      rtnl_lock();
--      err = dev_set_mtu(dev, ETH_DATA_LEN);
--      if (err)
--              netdev_dbg(dev,
--                         "Unable to reset MTU to exclude DSA overheads\n");
--      rtnl_unlock();
--}
--
- static struct lock_class_key dsa_master_addr_list_lock_key;
- int dsa_master_setup(struct net_device *dev, struct dsa_port *cpu_dp)
- {
--      const struct dsa_device_ops *tag_ops = cpu_dp->tag_ops;
-       struct dsa_switch *ds = cpu_dp->ds;
-       struct device_link *consumer_link;
--      int mtu, ret;
--
--      mtu = ETH_DATA_LEN + dsa_tag_protocol_overhead(tag_ops);
-+      int ret;
-       /* The DSA master must use SET_NETDEV_DEV for this to work. */
-       consumer_link = device_link_add(ds->dev, dev->dev.parent,
-@@ -360,13 +345,6 @@ int dsa_master_setup(struct net_device *
-                          "Failed to create a device link to DSA switch %s\n",
-                          dev_name(ds->dev));
--      rtnl_lock();
--      ret = dev_set_mtu(dev, mtu);
--      rtnl_unlock();
--      if (ret)
--              netdev_warn(dev, "error %d setting MTU to %d to include DSA overhead\n",
--                          ret, mtu);
--
-       /* If we use a tagging format that doesn't have an ethertype
-        * field, make sure that all packets from this point on get
-        * sent to the tag format's receive function.
-@@ -404,7 +382,6 @@ void dsa_master_teardown(struct net_devi
-       sysfs_remove_group(&dev->dev.kobj, &dsa_group);
-       dsa_netdev_ops_set(dev, NULL);
-       dsa_master_ethtool_teardown(dev);
--      dsa_master_reset_mtu(dev);
-       dsa_master_set_promiscuity(dev, -1);
-       dev->dsa_ptr = NULL;
diff --git a/target/linux/generic/backport-5.15/765-v5.17-04-net-next-net-dsa-hold-rtnl_mutex-when-calling-dsa_master_-set.patch b/target/linux/generic/backport-5.15/765-v5.17-04-net-next-net-dsa-hold-rtnl_mutex-when-calling-dsa_master_-set.patch
deleted file mode 100644 (file)
index dbc28ef..0000000
+++ /dev/null
@@ -1,78 +0,0 @@
-From c146f9bc195a9dc3ad7fd000a14540e7c9df952d Mon Sep 17 00:00:00 2001
-From: Vladimir Oltean <[email protected]>
-Date: Thu, 6 Jan 2022 01:11:15 +0200
-Subject: [PATCH 4/6] net: dsa: hold rtnl_mutex when calling
- dsa_master_{setup,teardown}
-
-DSA needs to simulate master tracking events when a binding is first
-with a DSA master established and torn down, in order to give drivers
-the simplifying guarantee that ->master_state_change calls are made
-only when the master's readiness state to pass traffic changes.
-master_state_change() provide a operational bool that DSA driver can use
-to understand if DSA master is operational or not.
-To avoid races, we need to block the reception of
-NETDEV_UP/NETDEV_CHANGE/NETDEV_GOING_DOWN events in the netdev notifier
-chain while we are changing the master's dev->dsa_ptr (this changes what
-netdev_uses_dsa(dev) reports).
-
-The dsa_master_setup() and dsa_master_teardown() functions optionally
-require the rtnl_mutex to be held, if the tagger needs the master to be
-promiscuous, these functions call dev_set_promiscuity(). Move the
-rtnl_lock() from that function and make it top-level.
-
-Signed-off-by: Vladimir Oltean <[email protected]>
-Reviewed-by: Florian Fainelli <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- net/dsa/dsa2.c   | 8 ++++++++
- net/dsa/master.c | 4 ++--
- 2 files changed, 10 insertions(+), 2 deletions(-)
-
---- a/net/dsa/dsa2.c
-+++ b/net/dsa/dsa2.c
-@@ -1056,6 +1056,8 @@ static int dsa_tree_setup_master(struct
-       struct dsa_port *dp;
-       int err;
-+      rtnl_lock();
-+
-       list_for_each_entry(dp, &dst->ports, list) {
-               if (dsa_port_is_cpu(dp)) {
-                       err = dsa_master_setup(dp->master, dp);
-@@ -1064,6 +1066,8 @@ static int dsa_tree_setup_master(struct
-               }
-       }
-+      rtnl_unlock();
-+
-       return 0;
- }
-@@ -1071,9 +1075,13 @@ static void dsa_tree_teardown_master(str
- {
-       struct dsa_port *dp;
-+      rtnl_lock();
-+
-       list_for_each_entry(dp, &dst->ports, list)
-               if (dsa_port_is_cpu(dp))
-                       dsa_master_teardown(dp->master);
-+
-+      rtnl_unlock();
- }
- static int dsa_tree_setup_lags(struct dsa_switch_tree *dst)
---- a/net/dsa/master.c
-+++ b/net/dsa/master.c
-@@ -266,9 +266,9 @@ static void dsa_master_set_promiscuity(s
-       if (!ops->promisc_on_master)
-               return;
--      rtnl_lock();
-+      ASSERT_RTNL();
-+
-       dev_set_promiscuity(dev, inc);
--      rtnl_unlock();
- }
- static ssize_t tagging_show(struct device *d, struct device_attribute *attr,
diff --git a/target/linux/generic/backport-5.15/765-v5.17-05-net-next-net-dsa-first-set-up-shared-ports-then-non-shared-po.patch b/target/linux/generic/backport-5.15/765-v5.17-05-net-next-net-dsa-first-set-up-shared-ports-then-non-shared-po.patch
deleted file mode 100644 (file)
index fbb9c94..0000000
+++ /dev/null
@@ -1,118 +0,0 @@
-From 1e3f407f3cacc5dcfe27166c412ed9bc263d82bf Mon Sep 17 00:00:00 2001
-From: Vladimir Oltean <[email protected]>
-Date: Thu, 6 Jan 2022 01:11:16 +0200
-Subject: [PATCH 5/6] net: dsa: first set up shared ports, then non-shared
- ports
-
-After commit a57d8c217aad ("net: dsa: flush switchdev workqueue before
-tearing down CPU/DSA ports"), the port setup and teardown procedure
-became asymmetric.
-
-The fact of the matter is that user ports need the shared ports to be up
-before they can be used for CPU-initiated termination. And since we
-register net devices for the user ports, those won't be functional until
-we also call the setup for the shared (CPU, DSA) ports. But we may do
-that later, depending on the port numbering scheme of the hardware we
-are dealing with.
-
-It just makes sense that all shared ports are brought up before any user
-port is. I can't pinpoint any issue due to the current behavior, but
-let's change it nonetheless, for consistency's sake.
-
-Signed-off-by: Vladimir Oltean <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- net/dsa/dsa2.c | 50 +++++++++++++++++++++++++++++++++++++-------------
- 1 file changed, 37 insertions(+), 13 deletions(-)
-
---- a/net/dsa/dsa2.c
-+++ b/net/dsa/dsa2.c
-@@ -1021,23 +1021,28 @@ static void dsa_tree_teardown_switches(s
-               dsa_switch_teardown(dp->ds);
- }
--static int dsa_tree_setup_switches(struct dsa_switch_tree *dst)
-+/* Bring shared ports up first, then non-shared ports */
-+static int dsa_tree_setup_ports(struct dsa_switch_tree *dst)
- {
-       struct dsa_port *dp;
--      int err;
-+      int err = 0;
-       list_for_each_entry(dp, &dst->ports, list) {
--              err = dsa_switch_setup(dp->ds);
--              if (err)
--                      goto teardown;
-+              if (dsa_port_is_dsa(dp) || dsa_port_is_cpu(dp)) {
-+                      err = dsa_port_setup(dp);
-+                      if (err)
-+                              goto teardown;
-+              }
-       }
-       list_for_each_entry(dp, &dst->ports, list) {
--              err = dsa_port_setup(dp);
--              if (err) {
--                      err = dsa_port_reinit_as_unused(dp);
--                      if (err)
--                              goto teardown;
-+              if (dsa_port_is_user(dp) || dsa_port_is_unused(dp)) {
-+                      err = dsa_port_setup(dp);
-+                      if (err) {
-+                              err = dsa_port_reinit_as_unused(dp);
-+                              if (err)
-+                                      goto teardown;
-+                      }
-               }
-       }
-@@ -1046,7 +1051,21 @@ static int dsa_tree_setup_switches(struc
- teardown:
-       dsa_tree_teardown_ports(dst);
--      dsa_tree_teardown_switches(dst);
-+      return err;
-+}
-+
-+static int dsa_tree_setup_switches(struct dsa_switch_tree *dst)
-+{
-+      struct dsa_port *dp;
-+      int err = 0;
-+
-+      list_for_each_entry(dp, &dst->ports, list) {
-+              err = dsa_switch_setup(dp->ds);
-+              if (err) {
-+                      dsa_tree_teardown_switches(dst);
-+                      break;
-+              }
-+      }
-       return err;
- }
-@@ -1133,10 +1152,14 @@ static int dsa_tree_setup(struct dsa_swi
-       if (err)
-               goto teardown_cpu_ports;
--      err = dsa_tree_setup_master(dst);
-+      err = dsa_tree_setup_ports(dst);
-       if (err)
-               goto teardown_switches;
-+      err = dsa_tree_setup_master(dst);
-+      if (err)
-+              goto teardown_ports;
-+
-       err = dsa_tree_setup_lags(dst);
-       if (err)
-               goto teardown_master;
-@@ -1149,8 +1172,9 @@ static int dsa_tree_setup(struct dsa_swi
- teardown_master:
-       dsa_tree_teardown_master(dst);
--teardown_switches:
-+teardown_ports:
-       dsa_tree_teardown_ports(dst);
-+teardown_switches:
-       dsa_tree_teardown_switches(dst);
- teardown_cpu_ports:
-       dsa_tree_teardown_cpu_ports(dst);
diff --git a/target/linux/generic/backport-5.15/765-v5.17-06-net-next-net-dsa-setup-master-before-ports.patch b/target/linux/generic/backport-5.15/765-v5.17-06-net-next-net-dsa-setup-master-before-ports.patch
deleted file mode 100644 (file)
index a46e06e..0000000
+++ /dev/null
@@ -1,115 +0,0 @@
-From 11fd667dac315ea3f2469961f6d2869271a46cae Mon Sep 17 00:00:00 2001
-From: Vladimir Oltean <[email protected]>
-Date: Thu, 6 Jan 2022 01:11:17 +0200
-Subject: [PATCH 6/6] net: dsa: setup master before ports
-
-It is said that as soon as a network interface is registered, all its
-resources should have already been prepared, so that it is available for
-sending and receiving traffic. One of the resources needed by a DSA
-slave interface is the master.
-
-dsa_tree_setup
--> dsa_tree_setup_ports
-   -> dsa_port_setup
-      -> dsa_slave_create
-         -> register_netdevice
--> dsa_tree_setup_master
-   -> dsa_master_setup
-      -> sets up master->dsa_ptr, which enables reception
-
-Therefore, there is a short period of time after register_netdevice()
-during which the master isn't prepared to pass traffic to the DSA layer
-(master->dsa_ptr is checked by eth_type_trans). Same thing during
-unregistration, there is a time frame in which packets might be missed.
-
-Note that this change opens us to another race: dsa_master_find_slave()
-will get invoked potentially earlier than the slave creation, and later
-than the slave deletion. Since dp->slave starts off as a NULL pointer,
-the earlier calls aren't a problem, but the later calls are. To avoid
-use-after-free, we should zeroize dp->slave before calling
-dsa_slave_destroy().
-
-In practice I cannot really test real life improvements brought by this
-change, since in my systems, netdevice creation races with PHY autoneg
-which takes a few seconds to complete, and that masks quite a few races.
-Effects might be noticeable in a setup with fixed links all the way to
-an external system.
-
-Signed-off-by: Vladimir Oltean <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- net/dsa/dsa2.c | 23 +++++++++++++----------
- 1 file changed, 13 insertions(+), 10 deletions(-)
-
---- a/net/dsa/dsa2.c
-+++ b/net/dsa/dsa2.c
-@@ -567,6 +567,7 @@ static void dsa_port_teardown(struct dsa
-       struct devlink_port *dlp = &dp->devlink_port;
-       struct dsa_switch *ds = dp->ds;
-       struct dsa_mac_addr *a, *tmp;
-+      struct net_device *slave;
-       if (!dp->setup)
-               return;
-@@ -588,9 +589,11 @@ static void dsa_port_teardown(struct dsa
-               dsa_port_link_unregister_of(dp);
-               break;
-       case DSA_PORT_TYPE_USER:
--              if (dp->slave) {
--                      dsa_slave_destroy(dp->slave);
-+              slave = dp->slave;
-+
-+              if (slave) {
-                       dp->slave = NULL;
-+                      dsa_slave_destroy(slave);
-               }
-               break;
-       }
-@@ -1152,17 +1155,17 @@ static int dsa_tree_setup(struct dsa_swi
-       if (err)
-               goto teardown_cpu_ports;
--      err = dsa_tree_setup_ports(dst);
-+      err = dsa_tree_setup_master(dst);
-       if (err)
-               goto teardown_switches;
--      err = dsa_tree_setup_master(dst);
-+      err = dsa_tree_setup_ports(dst);
-       if (err)
--              goto teardown_ports;
-+              goto teardown_master;
-       err = dsa_tree_setup_lags(dst);
-       if (err)
--              goto teardown_master;
-+              goto teardown_ports;
-       dst->setup = true;
-@@ -1170,10 +1173,10 @@ static int dsa_tree_setup(struct dsa_swi
-       return 0;
--teardown_master:
--      dsa_tree_teardown_master(dst);
- teardown_ports:
-       dsa_tree_teardown_ports(dst);
-+teardown_master:
-+      dsa_tree_teardown_master(dst);
- teardown_switches:
-       dsa_tree_teardown_switches(dst);
- teardown_cpu_ports:
-@@ -1191,10 +1194,10 @@ static void dsa_tree_teardown(struct dsa
-       dsa_tree_teardown_lags(dst);
--      dsa_tree_teardown_master(dst);
--
-       dsa_tree_teardown_ports(dst);
-+      dsa_tree_teardown_master(dst);
-+
-       dsa_tree_teardown_switches(dst);
-       dsa_tree_teardown_cpu_ports(dst);
diff --git a/target/linux/generic/backport-5.15/766-v5.18-01-net-dsa-provide-switch-operations-for-tracking-the-m.patch b/target/linux/generic/backport-5.15/766-v5.18-01-net-dsa-provide-switch-operations-for-tracking-the-m.patch
deleted file mode 100644 (file)
index 1512295..0000000
+++ /dev/null
@@ -1,254 +0,0 @@
-From 295ab96f478d0fa56393e85406f19a867e26ce22 Mon Sep 17 00:00:00 2001
-From: Vladimir Oltean <[email protected]>
-Date: Wed, 2 Feb 2022 01:03:20 +0100
-Subject: [PATCH 01/16] net: dsa: provide switch operations for tracking the
- master state
-
-Certain drivers may need to send management traffic to the switch for
-things like register access, FDB dump, etc, to accelerate what their
-slow bus (SPI, I2C, MDIO) can already do.
-
-Ethernet is faster (especially in bulk transactions) but is also more
-unreliable, since the user may decide to bring the DSA master down (or
-not bring it up), therefore severing the link between the host and the
-attached switch.
-
-Drivers needing Ethernet-based register access already should have
-fallback logic to the slow bus if the Ethernet method fails, but that
-fallback may be based on a timeout, and the I/O to the switch may slow
-down to a halt if the master is down, because every Ethernet packet will
-have to time out. The driver also doesn't have the option to turn off
-Ethernet-based I/O momentarily, because it wouldn't know when to turn it
-back on.
-
-Which is where this change comes in. By tracking NETDEV_CHANGE,
-NETDEV_UP and NETDEV_GOING_DOWN events on the DSA master, we should know
-the exact interval of time during which this interface is reliably
-available for traffic. Provide this information to switches so they can
-use it as they wish.
-
-An helper is added dsa_port_master_is_operational() to check if a master
-port is operational.
-
-Signed-off-by: Vladimir Oltean <[email protected]>
-Signed-off-by: Ansuel Smith <[email protected]>
-Reviewed-by: Florian Fainelli <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- include/net/dsa.h  | 17 +++++++++++++++++
- net/dsa/dsa2.c     | 46 ++++++++++++++++++++++++++++++++++++++++++++++
- net/dsa/dsa_priv.h | 13 +++++++++++++
- net/dsa/slave.c    | 32 ++++++++++++++++++++++++++++++++
- net/dsa/switch.c   | 15 +++++++++++++++
- 5 files changed, 123 insertions(+)
-
---- a/include/net/dsa.h
-+++ b/include/net/dsa.h
-@@ -291,6 +291,10 @@ struct dsa_port {
-       struct list_head        mdbs;
-       bool setup;
-+      /* Master state bits, valid only on CPU ports */
-+      u8                      master_admin_up:1;
-+      u8                      master_oper_up:1;
-+
- };
- /* TODO: ideally DSA ports would have a single dp->link_dp member,
-@@ -456,6 +460,12 @@ static inline bool dsa_port_is_unused(st
-       return dp->type == DSA_PORT_TYPE_UNUSED;
- }
-+static inline bool dsa_port_master_is_operational(struct dsa_port *dp)
-+{
-+      return dsa_port_is_cpu(dp) && dp->master_admin_up &&
-+             dp->master_oper_up;
-+}
-+
- static inline bool dsa_is_unused_port(struct dsa_switch *ds, int p)
- {
-       return dsa_to_port(ds, p)->type == DSA_PORT_TYPE_UNUSED;
-@@ -957,6 +967,13 @@ struct dsa_switch_ops {
-       int     (*tag_8021q_vlan_add)(struct dsa_switch *ds, int port, u16 vid,
-                                     u16 flags);
-       int     (*tag_8021q_vlan_del)(struct dsa_switch *ds, int port, u16 vid);
-+
-+      /*
-+       * DSA master tracking operations
-+       */
-+      void    (*master_state_change)(struct dsa_switch *ds,
-+                                     const struct net_device *master,
-+                                     bool operational);
- };
- #define DSA_DEVLINK_PARAM_DRIVER(_id, _name, _type, _cmodes)          \
---- a/net/dsa/dsa2.c
-+++ b/net/dsa/dsa2.c
-@@ -1297,6 +1297,52 @@ out_unlock:
-       return err;
- }
-+static void dsa_tree_master_state_change(struct dsa_switch_tree *dst,
-+                                       struct net_device *master)
-+{
-+      struct dsa_notifier_master_state_info info;
-+      struct dsa_port *cpu_dp = master->dsa_ptr;
-+
-+      info.master = master;
-+      info.operational = dsa_port_master_is_operational(cpu_dp);
-+
-+      dsa_tree_notify(dst, DSA_NOTIFIER_MASTER_STATE_CHANGE, &info);
-+}
-+
-+void dsa_tree_master_admin_state_change(struct dsa_switch_tree *dst,
-+                                      struct net_device *master,
-+                                      bool up)
-+{
-+      struct dsa_port *cpu_dp = master->dsa_ptr;
-+      bool notify = false;
-+
-+      if ((dsa_port_master_is_operational(cpu_dp)) !=
-+          (up && cpu_dp->master_oper_up))
-+              notify = true;
-+
-+      cpu_dp->master_admin_up = up;
-+
-+      if (notify)
-+              dsa_tree_master_state_change(dst, master);
-+}
-+
-+void dsa_tree_master_oper_state_change(struct dsa_switch_tree *dst,
-+                                     struct net_device *master,
-+                                     bool up)
-+{
-+      struct dsa_port *cpu_dp = master->dsa_ptr;
-+      bool notify = false;
-+
-+      if ((dsa_port_master_is_operational(cpu_dp)) !=
-+          (cpu_dp->master_admin_up && up))
-+              notify = true;
-+
-+      cpu_dp->master_oper_up = up;
-+
-+      if (notify)
-+              dsa_tree_master_state_change(dst, master);
-+}
-+
- static struct dsa_port *dsa_port_touch(struct dsa_switch *ds, int index)
- {
-       struct dsa_switch_tree *dst = ds->dst;
---- a/net/dsa/dsa_priv.h
-+++ b/net/dsa/dsa_priv.h
-@@ -45,6 +45,7 @@ enum {
-       DSA_NOTIFIER_MRP_DEL_RING_ROLE,
-       DSA_NOTIFIER_TAG_8021Q_VLAN_ADD,
-       DSA_NOTIFIER_TAG_8021Q_VLAN_DEL,
-+      DSA_NOTIFIER_MASTER_STATE_CHANGE,
- };
- /* DSA_NOTIFIER_AGEING_TIME */
-@@ -127,6 +128,12 @@ struct dsa_notifier_tag_8021q_vlan_info
-       u16 vid;
- };
-+/* DSA_NOTIFIER_MASTER_STATE_CHANGE */
-+struct dsa_notifier_master_state_info {
-+      const struct net_device *master;
-+      bool operational;
-+};
-+
- struct dsa_switchdev_event_work {
-       struct dsa_switch *ds;
-       int port;
-@@ -549,6 +556,12 @@ int dsa_tree_change_tag_proto(struct dsa
-                             struct net_device *master,
-                             const struct dsa_device_ops *tag_ops,
-                             const struct dsa_device_ops *old_tag_ops);
-+void dsa_tree_master_admin_state_change(struct dsa_switch_tree *dst,
-+                                      struct net_device *master,
-+                                      bool up);
-+void dsa_tree_master_oper_state_change(struct dsa_switch_tree *dst,
-+                                     struct net_device *master,
-+                                     bool up);
- int dsa_bridge_num_get(const struct net_device *bridge_dev, int max);
- void dsa_bridge_num_put(const struct net_device *bridge_dev, int bridge_num);
---- a/net/dsa/slave.c
-+++ b/net/dsa/slave.c
-@@ -2311,6 +2311,36 @@ static int dsa_slave_netdevice_event(str
-               err = dsa_port_lag_change(dp, info->lower_state_info);
-               return notifier_from_errno(err);
-       }
-+      case NETDEV_CHANGE:
-+      case NETDEV_UP: {
-+              /* Track state of master port.
-+               * DSA driver may require the master port (and indirectly
-+               * the tagger) to be available for some special operation.
-+               */
-+              if (netdev_uses_dsa(dev)) {
-+                      struct dsa_port *cpu_dp = dev->dsa_ptr;
-+                      struct dsa_switch_tree *dst = cpu_dp->ds->dst;
-+
-+                      /* Track when the master port is UP */
-+                      dsa_tree_master_oper_state_change(dst, dev,
-+                                                        netif_oper_up(dev));
-+
-+                      /* Track when the master port is ready and can accept
-+                       * packet.
-+                       * NETDEV_UP event is not enough to flag a port as ready.
-+                       * We also have to wait for linkwatch_do_dev to dev_activate
-+                       * and emit a NETDEV_CHANGE event.
-+                       * We check if a master port is ready by checking if the dev
-+                       * have a qdisc assigned and is not noop.
-+                       */
-+                      dsa_tree_master_admin_state_change(dst, dev,
-+                                                         !qdisc_tx_is_noop(dev));
-+
-+                      return NOTIFY_OK;
-+              }
-+
-+              return NOTIFY_DONE;
-+      }
-       case NETDEV_GOING_DOWN: {
-               struct dsa_port *dp, *cpu_dp;
-               struct dsa_switch_tree *dst;
-@@ -2322,6 +2352,8 @@ static int dsa_slave_netdevice_event(str
-               cpu_dp = dev->dsa_ptr;
-               dst = cpu_dp->ds->dst;
-+              dsa_tree_master_admin_state_change(dst, dev, false);
-+
-               list_for_each_entry(dp, &dst->ports, list) {
-                       if (!dsa_is_user_port(dp->ds, dp->index))
-                               continue;
---- a/net/dsa/switch.c
-+++ b/net/dsa/switch.c
-@@ -722,6 +722,18 @@ dsa_switch_mrp_del_ring_role(struct dsa_
-       return 0;
- }
-+static int
-+dsa_switch_master_state_change(struct dsa_switch *ds,
-+                             struct dsa_notifier_master_state_info *info)
-+{
-+      if (!ds->ops->master_state_change)
-+              return 0;
-+
-+      ds->ops->master_state_change(ds, info->master, info->operational);
-+
-+      return 0;
-+}
-+
- static int dsa_switch_event(struct notifier_block *nb,
-                           unsigned long event, void *info)
- {
-@@ -813,6 +825,9 @@ static int dsa_switch_event(struct notif
-       case DSA_NOTIFIER_TAG_8021Q_VLAN_DEL:
-               err = dsa_switch_tag_8021q_vlan_del(ds, info);
-               break;
-+      case DSA_NOTIFIER_MASTER_STATE_CHANGE:
-+              err = dsa_switch_master_state_change(ds, info);
-+              break;
-       default:
-               err = -EOPNOTSUPP;
-               break;
diff --git a/target/linux/generic/backport-5.15/766-v5.18-02-net-dsa-replay-master-state-events-in-dsa_tree_-setu.patch b/target/linux/generic/backport-5.15/766-v5.18-02-net-dsa-replay-master-state-events-in-dsa_tree_-setu.patch
deleted file mode 100644 (file)
index c55c527..0000000
+++ /dev/null
@@ -1,89 +0,0 @@
-From e83d56537859849f2223b90749e554831b1f3c27 Mon Sep 17 00:00:00 2001
-From: Vladimir Oltean <[email protected]>
-Date: Wed, 2 Feb 2022 01:03:21 +0100
-Subject: [PATCH 02/16] net: dsa: replay master state events in
- dsa_tree_{setup,teardown}_master
-
-In order for switch driver to be able to make simple and reliable use of
-the master tracking operations, they must also be notified of the
-initial state of the DSA master, not just of the changes. This is
-because they might enable certain features only during the time when
-they know that the DSA master is up and running.
-
-Therefore, this change explicitly checks the state of the DSA master
-under the same rtnl_mutex as we were holding during the
-dsa_master_setup() and dsa_master_teardown() call. The idea being that
-if the DSA master became operational in between the moment in which it
-became a DSA master (dsa_master_setup set dev->dsa_ptr) and the moment
-when we checked for the master being up, there is a chance that we
-would emit a ->master_state_change() call with no actual state change.
-We need to avoid that by serializing the concurrent netdevice event with
-us. If the netdevice event started before, we force it to finish before
-we begin, because we take rtnl_lock before making netdev_uses_dsa()
-return true. So we also handle that early event and do nothing on it.
-Similarly, if the dev_open() attempt is concurrent with us, it will
-attempt to take the rtnl_mutex, but we're holding it. We'll see that
-the master flag IFF_UP isn't set, then when we release the rtnl_mutex
-we'll process the NETDEV_UP notifier.
-
-Signed-off-by: Vladimir Oltean <[email protected]>
-Signed-off-by: Ansuel Smith <[email protected]>
-Reviewed-by: Florian Fainelli <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- net/dsa/dsa2.c | 28 ++++++++++++++++++++++++----
- 1 file changed, 24 insertions(+), 4 deletions(-)
-
---- a/net/dsa/dsa2.c
-+++ b/net/dsa/dsa2.c
-@@ -15,6 +15,7 @@
- #include <linux/of.h>
- #include <linux/of_net.h>
- #include <net/devlink.h>
-+#include <net/sch_generic.h>
- #include "dsa_priv.h"
-@@ -1082,9 +1083,18 @@ static int dsa_tree_setup_master(struct
-       list_for_each_entry(dp, &dst->ports, list) {
-               if (dsa_port_is_cpu(dp)) {
--                      err = dsa_master_setup(dp->master, dp);
-+                      struct net_device *master = dp->master;
-+                      bool admin_up = (master->flags & IFF_UP) &&
-+                                      !qdisc_tx_is_noop(master);
-+
-+                      err = dsa_master_setup(master, dp);
-                       if (err)
-                               return err;
-+
-+                      /* Replay master state event */
-+                      dsa_tree_master_admin_state_change(dst, master, admin_up);
-+                      dsa_tree_master_oper_state_change(dst, master,
-+                                                        netif_oper_up(master));
-               }
-       }
-@@ -1099,9 +1109,19 @@ static void dsa_tree_teardown_master(str
-       rtnl_lock();
--      list_for_each_entry(dp, &dst->ports, list)
--              if (dsa_port_is_cpu(dp))
--                      dsa_master_teardown(dp->master);
-+      list_for_each_entry(dp, &dst->ports, list) {
-+              if (dsa_port_is_cpu(dp)) {
-+                      struct net_device *master = dp->master;
-+
-+                      /* Synthesizing an "admin down" state is sufficient for
-+                       * the switches to get a notification if the master is
-+                       * currently up and running.
-+                       */
-+                      dsa_tree_master_admin_state_change(dst, master, false);
-+
-+                      dsa_master_teardown(master);
-+              }
-+      }
-       rtnl_unlock();
- }
diff --git a/target/linux/generic/backport-5.15/766-v5.18-03-net-dsa-tag_qca-convert-to-FIELD-macro.patch b/target/linux/generic/backport-5.15/766-v5.18-03-net-dsa-tag_qca-convert-to-FIELD-macro.patch
deleted file mode 100644 (file)
index 82c94b3..0000000
+++ /dev/null
@@ -1,86 +0,0 @@
-From 6b0458299297ca4ab6fb295800e29a4e501d50c1 Mon Sep 17 00:00:00 2001
-From: Ansuel Smith <[email protected]>
-Date: Wed, 2 Feb 2022 01:03:22 +0100
-Subject: [PATCH 03/16] net: dsa: tag_qca: convert to FIELD macro
-
-Convert driver to FIELD macro to drop redundant define.
-
-Signed-off-by: Ansuel Smith <[email protected]>
-Reviewed-by: Vladimir Oltean <[email protected]>
-Reviewed-by: Florian Fainelli <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- net/dsa/tag_qca.c | 34 +++++++++++++++-------------------
- 1 file changed, 15 insertions(+), 19 deletions(-)
-
---- a/net/dsa/tag_qca.c
-+++ b/net/dsa/tag_qca.c
-@@ -4,29 +4,24 @@
-  */
- #include <linux/etherdevice.h>
-+#include <linux/bitfield.h>
- #include "dsa_priv.h"
- #define QCA_HDR_LEN   2
- #define QCA_HDR_VERSION       0x2
--#define QCA_HDR_RECV_VERSION_MASK     GENMASK(15, 14)
--#define QCA_HDR_RECV_VERSION_S                14
--#define QCA_HDR_RECV_PRIORITY_MASK    GENMASK(13, 11)
--#define QCA_HDR_RECV_PRIORITY_S               11
--#define QCA_HDR_RECV_TYPE_MASK                GENMASK(10, 6)
--#define QCA_HDR_RECV_TYPE_S           6
-+#define QCA_HDR_RECV_VERSION          GENMASK(15, 14)
-+#define QCA_HDR_RECV_PRIORITY         GENMASK(13, 11)
-+#define QCA_HDR_RECV_TYPE             GENMASK(10, 6)
- #define QCA_HDR_RECV_FRAME_IS_TAGGED  BIT(3)
--#define QCA_HDR_RECV_SOURCE_PORT_MASK GENMASK(2, 0)
-+#define QCA_HDR_RECV_SOURCE_PORT      GENMASK(2, 0)
--#define QCA_HDR_XMIT_VERSION_MASK     GENMASK(15, 14)
--#define QCA_HDR_XMIT_VERSION_S                14
--#define QCA_HDR_XMIT_PRIORITY_MASK    GENMASK(13, 11)
--#define QCA_HDR_XMIT_PRIORITY_S               11
--#define QCA_HDR_XMIT_CONTROL_MASK     GENMASK(10, 8)
--#define QCA_HDR_XMIT_CONTROL_S                8
-+#define QCA_HDR_XMIT_VERSION          GENMASK(15, 14)
-+#define QCA_HDR_XMIT_PRIORITY         GENMASK(13, 11)
-+#define QCA_HDR_XMIT_CONTROL          GENMASK(10, 8)
- #define QCA_HDR_XMIT_FROM_CPU         BIT(7)
--#define QCA_HDR_XMIT_DP_BIT_MASK      GENMASK(6, 0)
-+#define QCA_HDR_XMIT_DP_BIT           GENMASK(6, 0)
- static struct sk_buff *qca_tag_xmit(struct sk_buff *skb, struct net_device *dev)
- {
-@@ -40,8 +35,9 @@ static struct sk_buff *qca_tag_xmit(stru
-       phdr = dsa_etype_header_pos_tx(skb);
-       /* Set the version field, and set destination port information */
--      hdr = QCA_HDR_VERSION << QCA_HDR_XMIT_VERSION_S |
--              QCA_HDR_XMIT_FROM_CPU | BIT(dp->index);
-+      hdr = FIELD_PREP(QCA_HDR_XMIT_VERSION, QCA_HDR_VERSION);
-+      hdr |= QCA_HDR_XMIT_FROM_CPU;
-+      hdr |= FIELD_PREP(QCA_HDR_XMIT_DP_BIT, BIT(dp->index));
-       *phdr = htons(hdr);
-@@ -62,7 +58,7 @@ static struct sk_buff *qca_tag_rcv(struc
-       hdr = ntohs(*phdr);
-       /* Make sure the version is correct */
--      ver = (hdr & QCA_HDR_RECV_VERSION_MASK) >> QCA_HDR_RECV_VERSION_S;
-+      ver = FIELD_GET(QCA_HDR_RECV_VERSION, hdr);
-       if (unlikely(ver != QCA_HDR_VERSION))
-               return NULL;
-@@ -71,7 +67,7 @@ static struct sk_buff *qca_tag_rcv(struc
-       dsa_strip_etype_header(skb, QCA_HDR_LEN);
-       /* Get source port information */
--      port = (hdr & QCA_HDR_RECV_SOURCE_PORT_MASK);
-+      port = FIELD_GET(QCA_HDR_RECV_SOURCE_PORT, hdr);
-       skb->dev = dsa_master_find_slave(dev, 0, port);
-       if (!skb->dev)
diff --git a/target/linux/generic/backport-5.15/766-v5.18-04-net-dsa-tag_qca-move-define-to-include-linux-dsa.patch b/target/linux/generic/backport-5.15/766-v5.18-04-net-dsa-tag_qca-move-define-to-include-linux-dsa.patch
deleted file mode 100644 (file)
index c1e74ce..0000000
+++ /dev/null
@@ -1,71 +0,0 @@
-From 3ec762fb13c7e7273800b94c80db1c2cc37590d1 Mon Sep 17 00:00:00 2001
-From: Ansuel Smith <[email protected]>
-Date: Wed, 2 Feb 2022 01:03:23 +0100
-Subject: [PATCH 04/16] net: dsa: tag_qca: move define to include linux/dsa
-
-Move tag_qca define to include dir linux/dsa as the qca8k require access
-to the tagger define to support in-band mdio read/write using ethernet
-packet.
-
-Signed-off-by: Ansuel Smith <[email protected]>
-Reviewed-by: Vladimir Oltean <[email protected]>
-Reviewed-by: Florian Fainelli <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- include/linux/dsa/tag_qca.h | 21 +++++++++++++++++++++
- net/dsa/tag_qca.c           | 16 +---------------
- 2 files changed, 22 insertions(+), 15 deletions(-)
- create mode 100644 include/linux/dsa/tag_qca.h
-
---- /dev/null
-+++ b/include/linux/dsa/tag_qca.h
-@@ -0,0 +1,21 @@
-+/* SPDX-License-Identifier: GPL-2.0 */
-+
-+#ifndef __TAG_QCA_H
-+#define __TAG_QCA_H
-+
-+#define QCA_HDR_LEN   2
-+#define QCA_HDR_VERSION       0x2
-+
-+#define QCA_HDR_RECV_VERSION          GENMASK(15, 14)
-+#define QCA_HDR_RECV_PRIORITY         GENMASK(13, 11)
-+#define QCA_HDR_RECV_TYPE             GENMASK(10, 6)
-+#define QCA_HDR_RECV_FRAME_IS_TAGGED  BIT(3)
-+#define QCA_HDR_RECV_SOURCE_PORT      GENMASK(2, 0)
-+
-+#define QCA_HDR_XMIT_VERSION          GENMASK(15, 14)
-+#define QCA_HDR_XMIT_PRIORITY         GENMASK(13, 11)
-+#define QCA_HDR_XMIT_CONTROL          GENMASK(10, 8)
-+#define QCA_HDR_XMIT_FROM_CPU         BIT(7)
-+#define QCA_HDR_XMIT_DP_BIT           GENMASK(6, 0)
-+
-+#endif /* __TAG_QCA_H */
---- a/net/dsa/tag_qca.c
-+++ b/net/dsa/tag_qca.c
-@@ -5,24 +5,10 @@
- #include <linux/etherdevice.h>
- #include <linux/bitfield.h>
-+#include <linux/dsa/tag_qca.h>
- #include "dsa_priv.h"
--#define QCA_HDR_LEN   2
--#define QCA_HDR_VERSION       0x2
--
--#define QCA_HDR_RECV_VERSION          GENMASK(15, 14)
--#define QCA_HDR_RECV_PRIORITY         GENMASK(13, 11)
--#define QCA_HDR_RECV_TYPE             GENMASK(10, 6)
--#define QCA_HDR_RECV_FRAME_IS_TAGGED  BIT(3)
--#define QCA_HDR_RECV_SOURCE_PORT      GENMASK(2, 0)
--
--#define QCA_HDR_XMIT_VERSION          GENMASK(15, 14)
--#define QCA_HDR_XMIT_PRIORITY         GENMASK(13, 11)
--#define QCA_HDR_XMIT_CONTROL          GENMASK(10, 8)
--#define QCA_HDR_XMIT_FROM_CPU         BIT(7)
--#define QCA_HDR_XMIT_DP_BIT           GENMASK(6, 0)
--
- static struct sk_buff *qca_tag_xmit(struct sk_buff *skb, struct net_device *dev)
- {
-       struct dsa_port *dp = dsa_slave_to_port(dev);
diff --git a/target/linux/generic/backport-5.15/766-v5.18-05-net-dsa-tag_qca-enable-promisc_on_master-flag.patch b/target/linux/generic/backport-5.15/766-v5.18-05-net-dsa-tag_qca-enable-promisc_on_master-flag.patch
deleted file mode 100644 (file)
index 9394a0d..0000000
+++ /dev/null
@@ -1,27 +0,0 @@
-From 101c04c3463b87061e6a3d4f72c1bc57670685a6 Mon Sep 17 00:00:00 2001
-From: Ansuel Smith <[email protected]>
-Date: Wed, 2 Feb 2022 01:03:24 +0100
-Subject: [PATCH 05/16] net: dsa: tag_qca: enable promisc_on_master flag
-
-Ethernet MDIO packets are non-standard and DSA master expects the first
-6 octets to be the MAC DA. To address these kind of packet, enable
-promisc_on_master flag for the tagger.
-
-Signed-off-by: Ansuel Smith <[email protected]>
-Reviewed-by: Vladimir Oltean <[email protected]>
-Reviewed-by: Florian Fainelli <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- net/dsa/tag_qca.c | 1 +
- 1 file changed, 1 insertion(+)
-
---- a/net/dsa/tag_qca.c
-+++ b/net/dsa/tag_qca.c
-@@ -68,6 +68,7 @@ static const struct dsa_device_ops qca_n
-       .xmit   = qca_tag_xmit,
-       .rcv    = qca_tag_rcv,
-       .needed_headroom = QCA_HDR_LEN,
-+      .promisc_on_master = true,
- };
- MODULE_LICENSE("GPL");
diff --git a/target/linux/generic/backport-5.15/766-v5.18-06-net-dsa-tag_qca-add-define-for-handling-mgmt-Etherne.patch b/target/linux/generic/backport-5.15/766-v5.18-06-net-dsa-tag_qca-add-define-for-handling-mgmt-Etherne.patch
deleted file mode 100644 (file)
index 459454e..0000000
+++ /dev/null
@@ -1,110 +0,0 @@
-From c2ee8181fddb293d296477f60b3eb4fa3ce4e1a6 Mon Sep 17 00:00:00 2001
-From: Ansuel Smith <[email protected]>
-Date: Wed, 2 Feb 2022 01:03:25 +0100
-Subject: [PATCH 06/16] net: dsa: tag_qca: add define for handling mgmt
- Ethernet packet
-
-Add all the required define to prepare support for mgmt read/write in
-Ethernet packet. Any packet of this type has to be dropped as the only
-use of these special packet is receive ack for an mgmt write request or
-receive data for an mgmt read request.
-A struct is used that emulates the Ethernet header but is used for a
-different purpose.
-
-Signed-off-by: Ansuel Smith <[email protected]>
-Reviewed-by: Florian Fainelli <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- include/linux/dsa/tag_qca.h | 44 +++++++++++++++++++++++++++++++++++++
- net/dsa/tag_qca.c           | 15 ++++++++++---
- 2 files changed, 56 insertions(+), 3 deletions(-)
-
---- a/include/linux/dsa/tag_qca.h
-+++ b/include/linux/dsa/tag_qca.h
-@@ -12,10 +12,54 @@
- #define QCA_HDR_RECV_FRAME_IS_TAGGED  BIT(3)
- #define QCA_HDR_RECV_SOURCE_PORT      GENMASK(2, 0)
-+/* Packet type for recv */
-+#define QCA_HDR_RECV_TYPE_NORMAL      0x0
-+#define QCA_HDR_RECV_TYPE_MIB         0x1
-+#define QCA_HDR_RECV_TYPE_RW_REG_ACK  0x2
-+
- #define QCA_HDR_XMIT_VERSION          GENMASK(15, 14)
- #define QCA_HDR_XMIT_PRIORITY         GENMASK(13, 11)
- #define QCA_HDR_XMIT_CONTROL          GENMASK(10, 8)
- #define QCA_HDR_XMIT_FROM_CPU         BIT(7)
- #define QCA_HDR_XMIT_DP_BIT           GENMASK(6, 0)
-+/* Packet type for xmit */
-+#define QCA_HDR_XMIT_TYPE_NORMAL      0x0
-+#define QCA_HDR_XMIT_TYPE_RW_REG      0x1
-+
-+/* Check code for a valid mgmt packet. Switch will ignore the packet
-+ * with this wrong.
-+ */
-+#define QCA_HDR_MGMT_CHECK_CODE_VAL   0x5
-+
-+/* Specific define for in-band MDIO read/write with Ethernet packet */
-+#define QCA_HDR_MGMT_SEQ_LEN          4 /* 4 byte for the seq */
-+#define QCA_HDR_MGMT_COMMAND_LEN      4 /* 4 byte for the command */
-+#define QCA_HDR_MGMT_DATA1_LEN                4 /* First 4 byte for the mdio data */
-+#define QCA_HDR_MGMT_HEADER_LEN               (QCA_HDR_MGMT_SEQ_LEN + \
-+                                      QCA_HDR_MGMT_COMMAND_LEN + \
-+                                      QCA_HDR_MGMT_DATA1_LEN)
-+
-+#define QCA_HDR_MGMT_DATA2_LEN                12 /* Other 12 byte for the mdio data */
-+#define QCA_HDR_MGMT_PADDING_LEN      34 /* Padding to reach the min Ethernet packet */
-+
-+#define QCA_HDR_MGMT_PKT_LEN          (QCA_HDR_MGMT_HEADER_LEN + \
-+                                      QCA_HDR_LEN + \
-+                                      QCA_HDR_MGMT_DATA2_LEN + \
-+                                      QCA_HDR_MGMT_PADDING_LEN)
-+
-+#define QCA_HDR_MGMT_SEQ_NUM          GENMASK(31, 0)  /* 63, 32 */
-+#define QCA_HDR_MGMT_CHECK_CODE               GENMASK(31, 29) /* 31, 29 */
-+#define QCA_HDR_MGMT_CMD              BIT(28)         /* 28 */
-+#define QCA_HDR_MGMT_LENGTH           GENMASK(23, 20) /* 23, 20 */
-+#define QCA_HDR_MGMT_ADDR             GENMASK(18, 0)  /* 18, 0 */
-+
-+/* Special struct emulating a Ethernet header */
-+struct qca_mgmt_ethhdr {
-+      u32 command;            /* command bit 31:0 */
-+      u32 seq;                /* seq 63:32 */
-+      u32 mdio_data;          /* first 4byte mdio */
-+      __be16 hdr;             /* qca hdr */
-+} __packed;
-+
- #endif /* __TAG_QCA_H */
---- a/net/dsa/tag_qca.c
-+++ b/net/dsa/tag_qca.c
-@@ -32,10 +32,12 @@ static struct sk_buff *qca_tag_xmit(stru
- static struct sk_buff *qca_tag_rcv(struct sk_buff *skb, struct net_device *dev)
- {
--      u8 ver;
--      u16  hdr;
--      int port;
-+      u8 ver, pk_type;
-       __be16 *phdr;
-+      int port;
-+      u16 hdr;
-+
-+      BUILD_BUG_ON(sizeof(struct qca_mgmt_ethhdr) != QCA_HDR_MGMT_HEADER_LEN + QCA_HDR_LEN);
-       if (unlikely(!pskb_may_pull(skb, QCA_HDR_LEN)))
-               return NULL;
-@@ -48,6 +50,13 @@ static struct sk_buff *qca_tag_rcv(struc
-       if (unlikely(ver != QCA_HDR_VERSION))
-               return NULL;
-+      /* Get pk type */
-+      pk_type = FIELD_GET(QCA_HDR_RECV_TYPE, hdr);
-+
-+      /* Ethernet MDIO read/write packet */
-+      if (pk_type == QCA_HDR_RECV_TYPE_RW_REG_ACK)
-+              return NULL;
-+
-       /* Remove QCA tag and recalculate checksum */
-       skb_pull_rcsum(skb, QCA_HDR_LEN);
-       dsa_strip_etype_header(skb, QCA_HDR_LEN);
diff --git a/target/linux/generic/backport-5.15/766-v5.18-07-net-dsa-tag_qca-add-define-for-handling-MIB-packet.patch b/target/linux/generic/backport-5.15/766-v5.18-07-net-dsa-tag_qca-add-define-for-handling-MIB-packet.patch
deleted file mode 100644 (file)
index 7e5dc65..0000000
+++ /dev/null
@@ -1,45 +0,0 @@
-From 18be654a4345f7d937b4bfbad74bea8093e3a93c Mon Sep 17 00:00:00 2001
-From: Ansuel Smith <[email protected]>
-Date: Wed, 2 Feb 2022 01:03:26 +0100
-Subject: [PATCH 07/16] net: dsa: tag_qca: add define for handling MIB packet
-
-Add struct to correctly parse a mib Ethernet packet.
-
-Signed-off-by: Ansuel Smith <[email protected]>
-Reviewed-by: Florian Fainelli <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- include/linux/dsa/tag_qca.h | 10 ++++++++++
- net/dsa/tag_qca.c           |  4 ++++
- 2 files changed, 14 insertions(+)
-
---- a/include/linux/dsa/tag_qca.h
-+++ b/include/linux/dsa/tag_qca.h
-@@ -62,4 +62,14 @@ struct qca_mgmt_ethhdr {
-       __be16 hdr;             /* qca hdr */
- } __packed;
-+enum mdio_cmd {
-+      MDIO_WRITE = 0x0,
-+      MDIO_READ
-+};
-+
-+struct mib_ethhdr {
-+      u32 data[3];            /* first 3 mib counter */
-+      __be16 hdr;             /* qca hdr */
-+} __packed;
-+
- #endif /* __TAG_QCA_H */
---- a/net/dsa/tag_qca.c
-+++ b/net/dsa/tag_qca.c
-@@ -57,6 +57,10 @@ static struct sk_buff *qca_tag_rcv(struc
-       if (pk_type == QCA_HDR_RECV_TYPE_RW_REG_ACK)
-               return NULL;
-+      /* Ethernet MIB counter packet */
-+      if (pk_type == QCA_HDR_RECV_TYPE_MIB)
-+              return NULL;
-+
-       /* Remove QCA tag and recalculate checksum */
-       skb_pull_rcsum(skb, QCA_HDR_LEN);
-       dsa_strip_etype_header(skb, QCA_HDR_LEN);
diff --git a/target/linux/generic/backport-5.15/766-v5.18-08-net-dsa-tag_qca-add-support-for-handling-mgmt-and-MI.patch b/target/linux/generic/backport-5.15/766-v5.18-08-net-dsa-tag_qca-add-support-for-handling-mgmt-and-MI.patch
deleted file mode 100644 (file)
index ad25da3..0000000
+++ /dev/null
@@ -1,116 +0,0 @@
-From 31eb6b4386ad91930417e3f5c8157a4b5e31cbd5 Mon Sep 17 00:00:00 2001
-From: Ansuel Smith <[email protected]>
-Date: Wed, 2 Feb 2022 01:03:27 +0100
-Subject: [PATCH 08/16] net: dsa: tag_qca: add support for handling mgmt and
- MIB Ethernet packet
-
-Add connect/disconnect helper to assign private struct to the DSA switch.
-Add support for Ethernet mgmt and MIB if the DSA driver provide an handler
-to correctly parse and elaborate the data.
-
-Signed-off-by: Ansuel Smith <[email protected]>
-Reviewed-by: Vladimir Oltean <[email protected]>
-Reviewed-by: Florian Fainelli <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- include/linux/dsa/tag_qca.h |  7 +++++++
- net/dsa/tag_qca.c           | 39 ++++++++++++++++++++++++++++++++++---
- 2 files changed, 43 insertions(+), 3 deletions(-)
-
---- a/include/linux/dsa/tag_qca.h
-+++ b/include/linux/dsa/tag_qca.h
-@@ -72,4 +72,11 @@ struct mib_ethhdr {
-       __be16 hdr;             /* qca hdr */
- } __packed;
-+struct qca_tagger_data {
-+      void (*rw_reg_ack_handler)(struct dsa_switch *ds,
-+                                 struct sk_buff *skb);
-+      void (*mib_autocast_handler)(struct dsa_switch *ds,
-+                                   struct sk_buff *skb);
-+};
-+
- #endif /* __TAG_QCA_H */
---- a/net/dsa/tag_qca.c
-+++ b/net/dsa/tag_qca.c
-@@ -5,6 +5,7 @@
- #include <linux/etherdevice.h>
- #include <linux/bitfield.h>
-+#include <net/dsa.h>
- #include <linux/dsa/tag_qca.h>
- #include "dsa_priv.h"
-@@ -32,6 +33,9 @@ static struct sk_buff *qca_tag_xmit(stru
- static struct sk_buff *qca_tag_rcv(struct sk_buff *skb, struct net_device *dev)
- {
-+      struct qca_tagger_data *tagger_data;
-+      struct dsa_port *dp = dev->dsa_ptr;
-+      struct dsa_switch *ds = dp->ds;
-       u8 ver, pk_type;
-       __be16 *phdr;
-       int port;
-@@ -39,6 +43,8 @@ static struct sk_buff *qca_tag_rcv(struc
-       BUILD_BUG_ON(sizeof(struct qca_mgmt_ethhdr) != QCA_HDR_MGMT_HEADER_LEN + QCA_HDR_LEN);
-+      tagger_data = ds->tagger_data;
-+
-       if (unlikely(!pskb_may_pull(skb, QCA_HDR_LEN)))
-               return NULL;
-@@ -53,13 +59,19 @@ static struct sk_buff *qca_tag_rcv(struc
-       /* Get pk type */
-       pk_type = FIELD_GET(QCA_HDR_RECV_TYPE, hdr);
--      /* Ethernet MDIO read/write packet */
--      if (pk_type == QCA_HDR_RECV_TYPE_RW_REG_ACK)
-+      /* Ethernet mgmt read/write packet */
-+      if (pk_type == QCA_HDR_RECV_TYPE_RW_REG_ACK) {
-+              if (likely(tagger_data->rw_reg_ack_handler))
-+                      tagger_data->rw_reg_ack_handler(ds, skb);
-               return NULL;
-+      }
-       /* Ethernet MIB counter packet */
--      if (pk_type == QCA_HDR_RECV_TYPE_MIB)
-+      if (pk_type == QCA_HDR_RECV_TYPE_MIB) {
-+              if (likely(tagger_data->mib_autocast_handler))
-+                      tagger_data->mib_autocast_handler(ds, skb);
-               return NULL;
-+      }
-       /* Remove QCA tag and recalculate checksum */
-       skb_pull_rcsum(skb, QCA_HDR_LEN);
-@@ -75,9 +87,30 @@ static struct sk_buff *qca_tag_rcv(struc
-       return skb;
- }
-+static int qca_tag_connect(struct dsa_switch *ds)
-+{
-+      struct qca_tagger_data *tagger_data;
-+
-+      tagger_data = kzalloc(sizeof(*tagger_data), GFP_KERNEL);
-+      if (!tagger_data)
-+              return -ENOMEM;
-+
-+      ds->tagger_data = tagger_data;
-+
-+      return 0;
-+}
-+
-+static void qca_tag_disconnect(struct dsa_switch *ds)
-+{
-+      kfree(ds->tagger_data);
-+      ds->tagger_data = NULL;
-+}
-+
- static const struct dsa_device_ops qca_netdev_ops = {
-       .name   = "qca",
-       .proto  = DSA_TAG_PROTO_QCA,
-+      .connect = qca_tag_connect,
-+      .disconnect = qca_tag_disconnect,
-       .xmit   = qca_tag_xmit,
-       .rcv    = qca_tag_rcv,
-       .needed_headroom = QCA_HDR_LEN,
diff --git a/target/linux/generic/backport-5.15/766-v5.18-09-net-dsa-qca8k-add-tracking-state-of-master-port.patch b/target/linux/generic/backport-5.15/766-v5.18-09-net-dsa-qca8k-add-tracking-state-of-master-port.patch
deleted file mode 100644 (file)
index eb21cc3..0000000
+++ /dev/null
@@ -1,67 +0,0 @@
-From cddbec19466a1dfb4d45ddd507d9f09f991d54ae Mon Sep 17 00:00:00 2001
-From: Ansuel Smith <[email protected]>
-Date: Wed, 2 Feb 2022 01:03:28 +0100
-Subject: [PATCH 09/16] net: dsa: qca8k: add tracking state of master port
-
-MDIO/MIB Ethernet require the master port and the tagger availabale to
-correctly work. Use the new api master_state_change to track when master
-is operational or not and set a bool in qca8k_priv.
-We cache the first cached master available and we check if other cpu
-port are operational when the cached one goes down.
-This cached master will later be used by mdio read/write and mib request to
-correctly use the working function.
-
-qca8k implementation for MDIO/MIB Ethernet is bad. CPU port0 is the only
-one that answers with the ack packet or sends MIB Ethernet packets. For
-this reason the master_state_change ignore CPU port6 and only checks
-CPU port0 if it's operational and enables this mode.
-
-Signed-off-by: Ansuel Smith <[email protected]>
-Reviewed-by: Florian Fainelli <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/dsa/qca8k.c | 15 +++++++++++++++
- drivers/net/dsa/qca8k.h |  1 +
- 2 files changed, 16 insertions(+)
-
---- a/drivers/net/dsa/qca8k.c
-+++ b/drivers/net/dsa/qca8k.c
-@@ -2401,6 +2401,20 @@ qca8k_port_lag_leave(struct dsa_switch *
-       return qca8k_lag_refresh_portmap(ds, port, lag, true);
- }
-+static void
-+qca8k_master_change(struct dsa_switch *ds, const struct net_device *master,
-+                  bool operational)
-+{
-+      struct dsa_port *dp = master->dsa_ptr;
-+      struct qca8k_priv *priv = ds->priv;
-+
-+      /* Ethernet MIB/MDIO is only supported for CPU port 0 */
-+      if (dp->index != 0)
-+              return;
-+
-+      priv->mgmt_master = operational ? (struct net_device *)master : NULL;
-+}
-+
- static const struct dsa_switch_ops qca8k_switch_ops = {
-       .get_tag_protocol       = qca8k_get_tag_protocol,
-       .setup                  = qca8k_setup,
-@@ -2436,6 +2450,7 @@ static const struct dsa_switch_ops qca8k
-       .get_phy_flags          = qca8k_get_phy_flags,
-       .port_lag_join          = qca8k_port_lag_join,
-       .port_lag_leave         = qca8k_port_lag_leave,
-+      .master_state_change    = qca8k_master_change,
- };
- static int qca8k_read_switch_id(struct qca8k_priv *priv)
---- a/drivers/net/dsa/qca8k.h
-+++ b/drivers/net/dsa/qca8k.h
-@@ -353,6 +353,7 @@ struct qca8k_priv {
-       struct dsa_switch_ops ops;
-       struct gpio_desc *reset_gpio;
-       unsigned int port_mtu[QCA8K_NUM_PORTS];
-+      struct net_device *mgmt_master; /* Track if mdio/mib Ethernet is available */
- };
- struct qca8k_mib_desc {
diff --git a/target/linux/generic/backport-5.15/766-v5.18-10-net-dsa-qca8k-add-support-for-mgmt-read-write-in-Eth.patch b/target/linux/generic/backport-5.15/766-v5.18-10-net-dsa-qca8k-add-support-for-mgmt-read-write-in-Eth.patch
deleted file mode 100644 (file)
index 07c5ba4..0000000
+++ /dev/null
@@ -1,363 +0,0 @@
-From 5950c7c0a68c915b336c70f79388626e2d576ab7 Mon Sep 17 00:00:00 2001
-From: Ansuel Smith <[email protected]>
-Date: Wed, 2 Feb 2022 01:03:29 +0100
-Subject: [PATCH 10/16] net: dsa: qca8k: add support for mgmt read/write in
- Ethernet packet
-
-Add qca8k side support for mgmt read/write in Ethernet packet.
-qca8k supports some specially crafted Ethernet packet that can be used
-for mgmt read/write instead of the legacy method uart/internal mdio.
-This add support for the qca8k side to craft the packet and enqueue it.
-Each port and the qca8k_priv have a special struct to put data in it.
-The completion API is used to wait for the packet to be received back
-with the requested data.
-
-The various steps are:
-1. Craft the special packet with the qca hdr set to mgmt read/write
-   mode.
-2. Set the lock in the dedicated mgmt struct.
-3. Increment the seq number and set it in the mgmt pkt
-4. Reinit the completion.
-5. Enqueue the packet.
-6. Wait the packet to be received.
-7. Use the data set by the tagger to complete the mdio operation.
-
-If the completion timeouts or the ack value is not true, the legacy
-mdio way is used.
-
-It has to be considered that in the initial setup mdio is still used and
-mdio is still used until DSA is ready to accept and tag packet.
-
-tag_proto_connect() is used to fill the required handler for the tagger
-to correctly parse and elaborate the special Ethernet mdio packet.
-
-Locking is added to qca8k_master_change() to make sure no mgmt Ethernet
-are in progress.
-
-Signed-off-by: Ansuel Smith <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/dsa/qca8k.c | 225 ++++++++++++++++++++++++++++++++++++++++
- drivers/net/dsa/qca8k.h |  13 +++
- 2 files changed, 238 insertions(+)
-
---- a/drivers/net/dsa/qca8k.c
-+++ b/drivers/net/dsa/qca8k.c
-@@ -20,6 +20,7 @@
- #include <linux/phylink.h>
- #include <linux/gpio/consumer.h>
- #include <linux/etherdevice.h>
-+#include <linux/dsa/tag_qca.h>
- #include "qca8k.h"
-@@ -170,6 +171,194 @@ qca8k_rmw(struct qca8k_priv *priv, u32 r
-       return regmap_update_bits(priv->regmap, reg, mask, write_val);
- }
-+static void qca8k_rw_reg_ack_handler(struct dsa_switch *ds, struct sk_buff *skb)
-+{
-+      struct qca8k_mgmt_eth_data *mgmt_eth_data;
-+      struct qca8k_priv *priv = ds->priv;
-+      struct qca_mgmt_ethhdr *mgmt_ethhdr;
-+      u8 len, cmd;
-+
-+      mgmt_ethhdr = (struct qca_mgmt_ethhdr *)skb_mac_header(skb);
-+      mgmt_eth_data = &priv->mgmt_eth_data;
-+
-+      cmd = FIELD_GET(QCA_HDR_MGMT_CMD, mgmt_ethhdr->command);
-+      len = FIELD_GET(QCA_HDR_MGMT_LENGTH, mgmt_ethhdr->command);
-+
-+      /* Make sure the seq match the requested packet */
-+      if (mgmt_ethhdr->seq == mgmt_eth_data->seq)
-+              mgmt_eth_data->ack = true;
-+
-+      if (cmd == MDIO_READ) {
-+              mgmt_eth_data->data[0] = mgmt_ethhdr->mdio_data;
-+
-+              /* Get the rest of the 12 byte of data */
-+              if (len > QCA_HDR_MGMT_DATA1_LEN)
-+                      memcpy(mgmt_eth_data->data + 1, skb->data,
-+                             QCA_HDR_MGMT_DATA2_LEN);
-+      }
-+
-+      complete(&mgmt_eth_data->rw_done);
-+}
-+
-+static struct sk_buff *qca8k_alloc_mdio_header(enum mdio_cmd cmd, u32 reg, u32 *val,
-+                                             int priority)
-+{
-+      struct qca_mgmt_ethhdr *mgmt_ethhdr;
-+      struct sk_buff *skb;
-+      u16 hdr;
-+
-+      skb = dev_alloc_skb(QCA_HDR_MGMT_PKT_LEN);
-+      if (!skb)
-+              return NULL;
-+
-+      skb_reset_mac_header(skb);
-+      skb_set_network_header(skb, skb->len);
-+
-+      mgmt_ethhdr = skb_push(skb, QCA_HDR_MGMT_HEADER_LEN + QCA_HDR_LEN);
-+
-+      hdr = FIELD_PREP(QCA_HDR_XMIT_VERSION, QCA_HDR_VERSION);
-+      hdr |= FIELD_PREP(QCA_HDR_XMIT_PRIORITY, priority);
-+      hdr |= QCA_HDR_XMIT_FROM_CPU;
-+      hdr |= FIELD_PREP(QCA_HDR_XMIT_DP_BIT, BIT(0));
-+      hdr |= FIELD_PREP(QCA_HDR_XMIT_CONTROL, QCA_HDR_XMIT_TYPE_RW_REG);
-+
-+      mgmt_ethhdr->command = FIELD_PREP(QCA_HDR_MGMT_ADDR, reg);
-+      mgmt_ethhdr->command |= FIELD_PREP(QCA_HDR_MGMT_LENGTH, 4);
-+      mgmt_ethhdr->command |= FIELD_PREP(QCA_HDR_MGMT_CMD, cmd);
-+      mgmt_ethhdr->command |= FIELD_PREP(QCA_HDR_MGMT_CHECK_CODE,
-+                                         QCA_HDR_MGMT_CHECK_CODE_VAL);
-+
-+      if (cmd == MDIO_WRITE)
-+              mgmt_ethhdr->mdio_data = *val;
-+
-+      mgmt_ethhdr->hdr = htons(hdr);
-+
-+      skb_put_zero(skb, QCA_HDR_MGMT_DATA2_LEN + QCA_HDR_MGMT_PADDING_LEN);
-+
-+      return skb;
-+}
-+
-+static void qca8k_mdio_header_fill_seq_num(struct sk_buff *skb, u32 seq_num)
-+{
-+      struct qca_mgmt_ethhdr *mgmt_ethhdr;
-+
-+      mgmt_ethhdr = (struct qca_mgmt_ethhdr *)skb->data;
-+      mgmt_ethhdr->seq = FIELD_PREP(QCA_HDR_MGMT_SEQ_NUM, seq_num);
-+}
-+
-+static int qca8k_read_eth(struct qca8k_priv *priv, u32 reg, u32 *val)
-+{
-+      struct qca8k_mgmt_eth_data *mgmt_eth_data = &priv->mgmt_eth_data;
-+      struct sk_buff *skb;
-+      bool ack;
-+      int ret;
-+
-+      skb = qca8k_alloc_mdio_header(MDIO_READ, reg, NULL,
-+                                    QCA8K_ETHERNET_MDIO_PRIORITY);
-+      if (!skb)
-+              return -ENOMEM;
-+
-+      mutex_lock(&mgmt_eth_data->mutex);
-+
-+      /* Check mgmt_master if is operational */
-+      if (!priv->mgmt_master) {
-+              kfree_skb(skb);
-+              mutex_unlock(&mgmt_eth_data->mutex);
-+              return -EINVAL;
-+      }
-+
-+      skb->dev = priv->mgmt_master;
-+
-+      reinit_completion(&mgmt_eth_data->rw_done);
-+
-+      /* Increment seq_num and set it in the mdio pkt */
-+      mgmt_eth_data->seq++;
-+      qca8k_mdio_header_fill_seq_num(skb, mgmt_eth_data->seq);
-+      mgmt_eth_data->ack = false;
-+
-+      dev_queue_xmit(skb);
-+
-+      ret = wait_for_completion_timeout(&mgmt_eth_data->rw_done,
-+                                        msecs_to_jiffies(QCA8K_ETHERNET_TIMEOUT));
-+
-+      *val = mgmt_eth_data->data[0];
-+      ack = mgmt_eth_data->ack;
-+
-+      mutex_unlock(&mgmt_eth_data->mutex);
-+
-+      if (ret <= 0)
-+              return -ETIMEDOUT;
-+
-+      if (!ack)
-+              return -EINVAL;
-+
-+      return 0;
-+}
-+
-+static int qca8k_write_eth(struct qca8k_priv *priv, u32 reg, u32 val)
-+{
-+      struct qca8k_mgmt_eth_data *mgmt_eth_data = &priv->mgmt_eth_data;
-+      struct sk_buff *skb;
-+      bool ack;
-+      int ret;
-+
-+      skb = qca8k_alloc_mdio_header(MDIO_WRITE, reg, &val,
-+                                    QCA8K_ETHERNET_MDIO_PRIORITY);
-+      if (!skb)
-+              return -ENOMEM;
-+
-+      mutex_lock(&mgmt_eth_data->mutex);
-+
-+      /* Check mgmt_master if is operational */
-+      if (!priv->mgmt_master) {
-+              kfree_skb(skb);
-+              mutex_unlock(&mgmt_eth_data->mutex);
-+              return -EINVAL;
-+      }
-+
-+      skb->dev = priv->mgmt_master;
-+
-+      reinit_completion(&mgmt_eth_data->rw_done);
-+
-+      /* Increment seq_num and set it in the mdio pkt */
-+      mgmt_eth_data->seq++;
-+      qca8k_mdio_header_fill_seq_num(skb, mgmt_eth_data->seq);
-+      mgmt_eth_data->ack = false;
-+
-+      dev_queue_xmit(skb);
-+
-+      ret = wait_for_completion_timeout(&mgmt_eth_data->rw_done,
-+                                        msecs_to_jiffies(QCA8K_ETHERNET_TIMEOUT));
-+
-+      ack = mgmt_eth_data->ack;
-+
-+      mutex_unlock(&mgmt_eth_data->mutex);
-+
-+      if (ret <= 0)
-+              return -ETIMEDOUT;
-+
-+      if (!ack)
-+              return -EINVAL;
-+
-+      return 0;
-+}
-+
-+static int
-+qca8k_regmap_update_bits_eth(struct qca8k_priv *priv, u32 reg, u32 mask, u32 write_val)
-+{
-+      u32 val = 0;
-+      int ret;
-+
-+      ret = qca8k_read_eth(priv, reg, &val);
-+      if (ret)
-+              return ret;
-+
-+      val &= ~mask;
-+      val |= write_val;
-+
-+      return qca8k_write_eth(priv, reg, val);
-+}
-+
- static int
- qca8k_regmap_read(void *ctx, uint32_t reg, uint32_t *val)
- {
-@@ -178,6 +367,9 @@ qca8k_regmap_read(void *ctx, uint32_t re
-       u16 r1, r2, page;
-       int ret;
-+      if (!qca8k_read_eth(priv, reg, val))
-+              return 0;
-+
-       qca8k_split_addr(reg, &r1, &r2, &page);
-       mutex_lock_nested(&bus->mdio_lock, MDIO_MUTEX_NESTED);
-@@ -201,6 +393,9 @@ qca8k_regmap_write(void *ctx, uint32_t r
-       u16 r1, r2, page;
-       int ret;
-+      if (!qca8k_write_eth(priv, reg, val))
-+              return 0;
-+
-       qca8k_split_addr(reg, &r1, &r2, &page);
-       mutex_lock_nested(&bus->mdio_lock, MDIO_MUTEX_NESTED);
-@@ -225,6 +420,9 @@ qca8k_regmap_update_bits(void *ctx, uint
-       u32 val;
-       int ret;
-+      if (!qca8k_regmap_update_bits_eth(priv, reg, mask, write_val))
-+              return 0;
-+
-       qca8k_split_addr(reg, &r1, &r2, &page);
-       mutex_lock_nested(&bus->mdio_lock, MDIO_MUTEX_NESTED);
-@@ -2412,7 +2610,30 @@ qca8k_master_change(struct dsa_switch *d
-       if (dp->index != 0)
-               return;
-+      mutex_lock(&priv->mgmt_eth_data.mutex);
-+
-       priv->mgmt_master = operational ? (struct net_device *)master : NULL;
-+
-+      mutex_unlock(&priv->mgmt_eth_data.mutex);
-+}
-+
-+static int qca8k_connect_tag_protocol(struct dsa_switch *ds,
-+                                    enum dsa_tag_protocol proto)
-+{
-+      struct qca_tagger_data *tagger_data;
-+
-+      switch (proto) {
-+      case DSA_TAG_PROTO_QCA:
-+              tagger_data = ds->tagger_data;
-+
-+              tagger_data->rw_reg_ack_handler = qca8k_rw_reg_ack_handler;
-+
-+              break;
-+      default:
-+              return -EOPNOTSUPP;
-+      }
-+
-+      return 0;
- }
- static const struct dsa_switch_ops qca8k_switch_ops = {
-@@ -2451,6 +2672,7 @@ static const struct dsa_switch_ops qca8k
-       .port_lag_join          = qca8k_port_lag_join,
-       .port_lag_leave         = qca8k_port_lag_leave,
-       .master_state_change    = qca8k_master_change,
-+      .connect_tag_protocol   = qca8k_connect_tag_protocol,
- };
- static int qca8k_read_switch_id(struct qca8k_priv *priv)
-@@ -2530,6 +2752,9 @@ qca8k_sw_probe(struct mdio_device *mdiod
-       if (!priv->ds)
-               return -ENOMEM;
-+      mutex_init(&priv->mgmt_eth_data.mutex);
-+      init_completion(&priv->mgmt_eth_data.rw_done);
-+
-       priv->ds->dev = &mdiodev->dev;
-       priv->ds->num_ports = QCA8K_NUM_PORTS;
-       priv->ds->priv = priv;
---- a/drivers/net/dsa/qca8k.h
-+++ b/drivers/net/dsa/qca8k.h
-@@ -11,6 +11,10 @@
- #include <linux/delay.h>
- #include <linux/regmap.h>
- #include <linux/gpio.h>
-+#include <linux/dsa/tag_qca.h>
-+
-+#define QCA8K_ETHERNET_MDIO_PRIORITY                  7
-+#define QCA8K_ETHERNET_TIMEOUT                                100
- #define QCA8K_NUM_PORTS                                       7
- #define QCA8K_NUM_CPU_PORTS                           2
-@@ -328,6 +332,14 @@ enum {
-       QCA8K_CPU_PORT6,
- };
-+struct qca8k_mgmt_eth_data {
-+      struct completion rw_done;
-+      struct mutex mutex; /* Enforce one mdio read/write at time */
-+      bool ack;
-+      u32 seq;
-+      u32 data[4];
-+};
-+
- struct qca8k_ports_config {
-       bool sgmii_rx_clk_falling_edge;
-       bool sgmii_tx_clk_falling_edge;
-@@ -354,6 +366,7 @@ struct qca8k_priv {
-       struct gpio_desc *reset_gpio;
-       unsigned int port_mtu[QCA8K_NUM_PORTS];
-       struct net_device *mgmt_master; /* Track if mdio/mib Ethernet is available */
-+      struct qca8k_mgmt_eth_data mgmt_eth_data;
- };
- struct qca8k_mib_desc {
diff --git a/target/linux/generic/backport-5.15/766-v5.18-11-net-dsa-qca8k-add-support-for-mib-autocast-in-Ethern.patch b/target/linux/generic/backport-5.15/766-v5.18-11-net-dsa-qca8k-add-support-for-mib-autocast-in-Ethern.patch
deleted file mode 100644 (file)
index 0dcf279..0000000
+++ /dev/null
@@ -1,226 +0,0 @@
-From 5c957c7ca78cce5e4b96866722b0115bd758d945 Mon Sep 17 00:00:00 2001
-From: Ansuel Smith <[email protected]>
-Date: Wed, 2 Feb 2022 01:03:30 +0100
-Subject: [PATCH 11/16] net: dsa: qca8k: add support for mib autocast in
- Ethernet packet
-
-The switch can autocast MIB counter using Ethernet packet.
-Add support for this and provide a handler for the tagger.
-The switch will send packet with MIB counter for each port, the switch
-will use completion API to wait for the correct packet to be received
-and will complete the task only when each packet is received.
-Although the handler will drop all the other packet, we still have to
-consume each MIB packet to complete the request. This is done to prevent
-mixed data with concurrent ethtool request.
-
-connect_tag_protocol() is used to add the handler to the tag_qca tagger,
-master_state_change() use the MIB lock to make sure no MIB Ethernet is
-in progress.
-
-Signed-off-by: Ansuel Smith <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/dsa/qca8k.c | 106 +++++++++++++++++++++++++++++++++++++++-
- drivers/net/dsa/qca8k.h |  17 ++++++-
- 2 files changed, 121 insertions(+), 2 deletions(-)
-
---- a/drivers/net/dsa/qca8k.c
-+++ b/drivers/net/dsa/qca8k.c
-@@ -830,7 +830,10 @@ qca8k_mib_init(struct qca8k_priv *priv)
-       int ret;
-       mutex_lock(&priv->reg_mutex);
--      ret = regmap_set_bits(priv->regmap, QCA8K_REG_MIB, QCA8K_MIB_FLUSH | QCA8K_MIB_BUSY);
-+      ret = regmap_update_bits(priv->regmap, QCA8K_REG_MIB,
-+                               QCA8K_MIB_FUNC | QCA8K_MIB_BUSY,
-+                               FIELD_PREP(QCA8K_MIB_FUNC, QCA8K_MIB_FLUSH) |
-+                               QCA8K_MIB_BUSY);
-       if (ret)
-               goto exit;
-@@ -1901,6 +1904,97 @@ qca8k_get_strings(struct dsa_switch *ds,
-                       ETH_GSTRING_LEN);
- }
-+static void qca8k_mib_autocast_handler(struct dsa_switch *ds, struct sk_buff *skb)
-+{
-+      const struct qca8k_match_data *match_data;
-+      struct qca8k_mib_eth_data *mib_eth_data;
-+      struct qca8k_priv *priv = ds->priv;
-+      const struct qca8k_mib_desc *mib;
-+      struct mib_ethhdr *mib_ethhdr;
-+      int i, mib_len, offset = 0;
-+      u64 *data;
-+      u8 port;
-+
-+      mib_ethhdr = (struct mib_ethhdr *)skb_mac_header(skb);
-+      mib_eth_data = &priv->mib_eth_data;
-+
-+      /* The switch autocast every port. Ignore other packet and
-+       * parse only the requested one.
-+       */
-+      port = FIELD_GET(QCA_HDR_RECV_SOURCE_PORT, ntohs(mib_ethhdr->hdr));
-+      if (port != mib_eth_data->req_port)
-+              goto exit;
-+
-+      match_data = device_get_match_data(priv->dev);
-+      data = mib_eth_data->data;
-+
-+      for (i = 0; i < match_data->mib_count; i++) {
-+              mib = &ar8327_mib[i];
-+
-+              /* First 3 mib are present in the skb head */
-+              if (i < 3) {
-+                      data[i] = mib_ethhdr->data[i];
-+                      continue;
-+              }
-+
-+              mib_len = sizeof(uint32_t);
-+
-+              /* Some mib are 64 bit wide */
-+              if (mib->size == 2)
-+                      mib_len = sizeof(uint64_t);
-+
-+              /* Copy the mib value from packet to the */
-+              memcpy(data + i, skb->data + offset, mib_len);
-+
-+              /* Set the offset for the next mib */
-+              offset += mib_len;
-+      }
-+
-+exit:
-+      /* Complete on receiving all the mib packet */
-+      if (refcount_dec_and_test(&mib_eth_data->port_parsed))
-+              complete(&mib_eth_data->rw_done);
-+}
-+
-+static int
-+qca8k_get_ethtool_stats_eth(struct dsa_switch *ds, int port, u64 *data)
-+{
-+      struct dsa_port *dp = dsa_to_port(ds, port);
-+      struct qca8k_mib_eth_data *mib_eth_data;
-+      struct qca8k_priv *priv = ds->priv;
-+      int ret;
-+
-+      mib_eth_data = &priv->mib_eth_data;
-+
-+      mutex_lock(&mib_eth_data->mutex);
-+
-+      reinit_completion(&mib_eth_data->rw_done);
-+
-+      mib_eth_data->req_port = dp->index;
-+      mib_eth_data->data = data;
-+      refcount_set(&mib_eth_data->port_parsed, QCA8K_NUM_PORTS);
-+
-+      mutex_lock(&priv->reg_mutex);
-+
-+      /* Send mib autocast request */
-+      ret = regmap_update_bits(priv->regmap, QCA8K_REG_MIB,
-+                               QCA8K_MIB_FUNC | QCA8K_MIB_BUSY,
-+                               FIELD_PREP(QCA8K_MIB_FUNC, QCA8K_MIB_CAST) |
-+                               QCA8K_MIB_BUSY);
-+
-+      mutex_unlock(&priv->reg_mutex);
-+
-+      if (ret)
-+              goto exit;
-+
-+      ret = wait_for_completion_timeout(&mib_eth_data->rw_done, QCA8K_ETHERNET_TIMEOUT);
-+
-+exit:
-+      mutex_unlock(&mib_eth_data->mutex);
-+
-+      return ret;
-+}
-+
- static void
- qca8k_get_ethtool_stats(struct dsa_switch *ds, int port,
-                       uint64_t *data)
-@@ -1912,6 +2006,10 @@ qca8k_get_ethtool_stats(struct dsa_switc
-       u32 hi = 0;
-       int ret;
-+      if (priv->mgmt_master &&
-+          qca8k_get_ethtool_stats_eth(ds, port, data) > 0)
-+              return;
-+
-       match_data = of_device_get_match_data(priv->dev);
-       for (i = 0; i < match_data->mib_count; i++) {
-@@ -2611,9 +2709,11 @@ qca8k_master_change(struct dsa_switch *d
-               return;
-       mutex_lock(&priv->mgmt_eth_data.mutex);
-+      mutex_lock(&priv->mib_eth_data.mutex);
-       priv->mgmt_master = operational ? (struct net_device *)master : NULL;
-+      mutex_unlock(&priv->mib_eth_data.mutex);
-       mutex_unlock(&priv->mgmt_eth_data.mutex);
- }
-@@ -2627,6 +2727,7 @@ static int qca8k_connect_tag_protocol(st
-               tagger_data = ds->tagger_data;
-               tagger_data->rw_reg_ack_handler = qca8k_rw_reg_ack_handler;
-+              tagger_data->mib_autocast_handler = qca8k_mib_autocast_handler;
-               break;
-       default:
-@@ -2755,6 +2856,9 @@ qca8k_sw_probe(struct mdio_device *mdiod
-       mutex_init(&priv->mgmt_eth_data.mutex);
-       init_completion(&priv->mgmt_eth_data.rw_done);
-+      mutex_init(&priv->mib_eth_data.mutex);
-+      init_completion(&priv->mib_eth_data.rw_done);
-+
-       priv->ds->dev = &mdiodev->dev;
-       priv->ds->num_ports = QCA8K_NUM_PORTS;
-       priv->ds->priv = priv;
---- a/drivers/net/dsa/qca8k.h
-+++ b/drivers/net/dsa/qca8k.h
-@@ -67,7 +67,7 @@
- #define QCA8K_REG_MODULE_EN                           0x030
- #define   QCA8K_MODULE_EN_MIB                         BIT(0)
- #define QCA8K_REG_MIB                                 0x034
--#define   QCA8K_MIB_FLUSH                             BIT(24)
-+#define   QCA8K_MIB_FUNC                              GENMASK(26, 24)
- #define   QCA8K_MIB_CPU_KEEP                          BIT(20)
- #define   QCA8K_MIB_BUSY                              BIT(17)
- #define QCA8K_MDIO_MASTER_CTRL                                0x3c
-@@ -317,6 +317,12 @@ enum qca8k_vlan_cmd {
-       QCA8K_VLAN_READ = 6,
- };
-+enum qca8k_mid_cmd {
-+      QCA8K_MIB_FLUSH = 1,
-+      QCA8K_MIB_FLUSH_PORT = 2,
-+      QCA8K_MIB_CAST = 3,
-+};
-+
- struct ar8xxx_port_status {
-       int enabled;
- };
-@@ -340,6 +346,14 @@ struct qca8k_mgmt_eth_data {
-       u32 data[4];
- };
-+struct qca8k_mib_eth_data {
-+      struct completion rw_done;
-+      struct mutex mutex; /* Process one command at time */
-+      refcount_t port_parsed; /* Counter to track parsed port */
-+      u8 req_port;
-+      u64 *data; /* pointer to ethtool data */
-+};
-+
- struct qca8k_ports_config {
-       bool sgmii_rx_clk_falling_edge;
-       bool sgmii_tx_clk_falling_edge;
-@@ -367,6 +381,7 @@ struct qca8k_priv {
-       unsigned int port_mtu[QCA8K_NUM_PORTS];
-       struct net_device *mgmt_master; /* Track if mdio/mib Ethernet is available */
-       struct qca8k_mgmt_eth_data mgmt_eth_data;
-+      struct qca8k_mib_eth_data mib_eth_data;
- };
- struct qca8k_mib_desc {
diff --git a/target/linux/generic/backport-5.15/766-v5.18-12-net-dsa-qca8k-add-support-for-phy-read-write-with-mg.patch b/target/linux/generic/backport-5.15/766-v5.18-12-net-dsa-qca8k-add-support-for-phy-read-write-with-mg.patch
deleted file mode 100644 (file)
index f5899eb..0000000
+++ /dev/null
@@ -1,287 +0,0 @@
-From 2cd5485663847d468dc207b3ff85fb1fab44d97f Mon Sep 17 00:00:00 2001
-From: Ansuel Smith <[email protected]>
-Date: Wed, 2 Feb 2022 01:03:31 +0100
-Subject: [PATCH 12/16] net: dsa: qca8k: add support for phy read/write with
- mgmt Ethernet
-
-Use mgmt Ethernet also for phy read/write if availabale. Use a different
-seq number to make sure we receive the correct packet.
-On any error, we fallback to the legacy mdio read/write.
-
-Signed-off-by: Ansuel Smith <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/dsa/qca8k.c | 216 ++++++++++++++++++++++++++++++++++++++++
- drivers/net/dsa/qca8k.h |   1 +
- 2 files changed, 217 insertions(+)
-
---- a/drivers/net/dsa/qca8k.c
-+++ b/drivers/net/dsa/qca8k.c
-@@ -867,6 +867,199 @@ qca8k_port_set_status(struct qca8k_priv
-               regmap_clear_bits(priv->regmap, QCA8K_REG_PORT_STATUS(port), mask);
- }
-+static int
-+qca8k_phy_eth_busy_wait(struct qca8k_mgmt_eth_data *mgmt_eth_data,
-+                      struct sk_buff *read_skb, u32 *val)
-+{
-+      struct sk_buff *skb = skb_copy(read_skb, GFP_KERNEL);
-+      bool ack;
-+      int ret;
-+
-+      reinit_completion(&mgmt_eth_data->rw_done);
-+
-+      /* Increment seq_num and set it in the copy pkt */
-+      mgmt_eth_data->seq++;
-+      qca8k_mdio_header_fill_seq_num(skb, mgmt_eth_data->seq);
-+      mgmt_eth_data->ack = false;
-+
-+      dev_queue_xmit(skb);
-+
-+      ret = wait_for_completion_timeout(&mgmt_eth_data->rw_done,
-+                                        QCA8K_ETHERNET_TIMEOUT);
-+
-+      ack = mgmt_eth_data->ack;
-+
-+      if (ret <= 0)
-+              return -ETIMEDOUT;
-+
-+      if (!ack)
-+              return -EINVAL;
-+
-+      *val = mgmt_eth_data->data[0];
-+
-+      return 0;
-+}
-+
-+static int
-+qca8k_phy_eth_command(struct qca8k_priv *priv, bool read, int phy,
-+                    int regnum, u16 data)
-+{
-+      struct sk_buff *write_skb, *clear_skb, *read_skb;
-+      struct qca8k_mgmt_eth_data *mgmt_eth_data;
-+      u32 write_val, clear_val = 0, val;
-+      struct net_device *mgmt_master;
-+      int ret, ret1;
-+      bool ack;
-+
-+      if (regnum >= QCA8K_MDIO_MASTER_MAX_REG)
-+              return -EINVAL;
-+
-+      mgmt_eth_data = &priv->mgmt_eth_data;
-+
-+      write_val = QCA8K_MDIO_MASTER_BUSY | QCA8K_MDIO_MASTER_EN |
-+                  QCA8K_MDIO_MASTER_PHY_ADDR(phy) |
-+                  QCA8K_MDIO_MASTER_REG_ADDR(regnum);
-+
-+      if (read) {
-+              write_val |= QCA8K_MDIO_MASTER_READ;
-+      } else {
-+              write_val |= QCA8K_MDIO_MASTER_WRITE;
-+              write_val |= QCA8K_MDIO_MASTER_DATA(data);
-+      }
-+
-+      /* Prealloc all the needed skb before the lock */
-+      write_skb = qca8k_alloc_mdio_header(MDIO_WRITE, QCA8K_MDIO_MASTER_CTRL,
-+                                          &write_val, QCA8K_ETHERNET_PHY_PRIORITY);
-+      if (!write_skb)
-+              return -ENOMEM;
-+
-+      clear_skb = qca8k_alloc_mdio_header(MDIO_WRITE, QCA8K_MDIO_MASTER_CTRL,
-+                                          &clear_val, QCA8K_ETHERNET_PHY_PRIORITY);
-+      if (!write_skb) {
-+              ret = -ENOMEM;
-+              goto err_clear_skb;
-+      }
-+
-+      read_skb = qca8k_alloc_mdio_header(MDIO_READ, QCA8K_MDIO_MASTER_CTRL,
-+                                         &clear_val, QCA8K_ETHERNET_PHY_PRIORITY);
-+      if (!write_skb) {
-+              ret = -ENOMEM;
-+              goto err_read_skb;
-+      }
-+
-+      /* Actually start the request:
-+       * 1. Send mdio master packet
-+       * 2. Busy Wait for mdio master command
-+       * 3. Get the data if we are reading
-+       * 4. Reset the mdio master (even with error)
-+       */
-+      mutex_lock(&mgmt_eth_data->mutex);
-+
-+      /* Check if mgmt_master is operational */
-+      mgmt_master = priv->mgmt_master;
-+      if (!mgmt_master) {
-+              mutex_unlock(&mgmt_eth_data->mutex);
-+              ret = -EINVAL;
-+              goto err_mgmt_master;
-+      }
-+
-+      read_skb->dev = mgmt_master;
-+      clear_skb->dev = mgmt_master;
-+      write_skb->dev = mgmt_master;
-+
-+      reinit_completion(&mgmt_eth_data->rw_done);
-+
-+      /* Increment seq_num and set it in the write pkt */
-+      mgmt_eth_data->seq++;
-+      qca8k_mdio_header_fill_seq_num(write_skb, mgmt_eth_data->seq);
-+      mgmt_eth_data->ack = false;
-+
-+      dev_queue_xmit(write_skb);
-+
-+      ret = wait_for_completion_timeout(&mgmt_eth_data->rw_done,
-+                                        QCA8K_ETHERNET_TIMEOUT);
-+
-+      ack = mgmt_eth_data->ack;
-+
-+      if (ret <= 0) {
-+              ret = -ETIMEDOUT;
-+              kfree_skb(read_skb);
-+              goto exit;
-+      }
-+
-+      if (!ack) {
-+              ret = -EINVAL;
-+              kfree_skb(read_skb);
-+              goto exit;
-+      }
-+
-+      ret = read_poll_timeout(qca8k_phy_eth_busy_wait, ret1,
-+                              !(val & QCA8K_MDIO_MASTER_BUSY), 0,
-+                              QCA8K_BUSY_WAIT_TIMEOUT * USEC_PER_MSEC, false,
-+                              mgmt_eth_data, read_skb, &val);
-+
-+      if (ret < 0 && ret1 < 0) {
-+              ret = ret1;
-+              goto exit;
-+      }
-+
-+      if (read) {
-+              reinit_completion(&mgmt_eth_data->rw_done);
-+
-+              /* Increment seq_num and set it in the read pkt */
-+              mgmt_eth_data->seq++;
-+              qca8k_mdio_header_fill_seq_num(read_skb, mgmt_eth_data->seq);
-+              mgmt_eth_data->ack = false;
-+
-+              dev_queue_xmit(read_skb);
-+
-+              ret = wait_for_completion_timeout(&mgmt_eth_data->rw_done,
-+                                                QCA8K_ETHERNET_TIMEOUT);
-+
-+              ack = mgmt_eth_data->ack;
-+
-+              if (ret <= 0) {
-+                      ret = -ETIMEDOUT;
-+                      goto exit;
-+              }
-+
-+              if (!ack) {
-+                      ret = -EINVAL;
-+                      goto exit;
-+              }
-+
-+              ret = mgmt_eth_data->data[0] & QCA8K_MDIO_MASTER_DATA_MASK;
-+      } else {
-+              kfree_skb(read_skb);
-+      }
-+exit:
-+      reinit_completion(&mgmt_eth_data->rw_done);
-+
-+      /* Increment seq_num and set it in the clear pkt */
-+      mgmt_eth_data->seq++;
-+      qca8k_mdio_header_fill_seq_num(clear_skb, mgmt_eth_data->seq);
-+      mgmt_eth_data->ack = false;
-+
-+      dev_queue_xmit(clear_skb);
-+
-+      wait_for_completion_timeout(&mgmt_eth_data->rw_done,
-+                                  QCA8K_ETHERNET_TIMEOUT);
-+
-+      mutex_unlock(&mgmt_eth_data->mutex);
-+
-+      return ret;
-+
-+      /* Error handling before lock */
-+err_mgmt_master:
-+      kfree_skb(read_skb);
-+err_read_skb:
-+      kfree_skb(clear_skb);
-+err_clear_skb:
-+      kfree_skb(write_skb);
-+
-+      return ret;
-+}
-+
- static u32
- qca8k_port_to_phy(int port)
- {
-@@ -989,6 +1182,12 @@ qca8k_internal_mdio_write(struct mii_bus
- {
-       struct qca8k_priv *priv = slave_bus->priv;
-       struct mii_bus *bus = priv->bus;
-+      int ret;
-+
-+      /* Use mdio Ethernet when available, fallback to legacy one on error */
-+      ret = qca8k_phy_eth_command(priv, false, phy, regnum, data);
-+      if (!ret)
-+              return 0;
-       return qca8k_mdio_write(bus, phy, regnum, data);
- }
-@@ -998,6 +1197,12 @@ qca8k_internal_mdio_read(struct mii_bus
- {
-       struct qca8k_priv *priv = slave_bus->priv;
-       struct mii_bus *bus = priv->bus;
-+      int ret;
-+
-+      /* Use mdio Ethernet when available, fallback to legacy one on error */
-+      ret = qca8k_phy_eth_command(priv, true, phy, regnum, 0);
-+      if (ret >= 0)
-+              return ret;
-       return qca8k_mdio_read(bus, phy, regnum);
- }
-@@ -1006,6 +1211,7 @@ static int
- qca8k_phy_write(struct dsa_switch *ds, int port, int regnum, u16 data)
- {
-       struct qca8k_priv *priv = ds->priv;
-+      int ret;
-       /* Check if the legacy mapping should be used and the
-        * port is not correctly mapped to the right PHY in the
-@@ -1014,6 +1220,11 @@ qca8k_phy_write(struct dsa_switch *ds, i
-       if (priv->legacy_phy_port_mapping)
-               port = qca8k_port_to_phy(port) % PHY_MAX_ADDR;
-+      /* Use mdio Ethernet when available, fallback to legacy one on error */
-+      ret = qca8k_phy_eth_command(priv, false, port, regnum, 0);
-+      if (!ret)
-+              return ret;
-+
-       return qca8k_mdio_write(priv->bus, port, regnum, data);
- }
-@@ -1030,6 +1241,11 @@ qca8k_phy_read(struct dsa_switch *ds, in
-       if (priv->legacy_phy_port_mapping)
-               port = qca8k_port_to_phy(port) % PHY_MAX_ADDR;
-+      /* Use mdio Ethernet when available, fallback to legacy one on error */
-+      ret = qca8k_phy_eth_command(priv, true, port, regnum, 0);
-+      if (ret >= 0)
-+              return ret;
-+
-       ret = qca8k_mdio_read(priv->bus, port, regnum);
-       if (ret < 0)
---- a/drivers/net/dsa/qca8k.h
-+++ b/drivers/net/dsa/qca8k.h
-@@ -14,6 +14,7 @@
- #include <linux/dsa/tag_qca.h>
- #define QCA8K_ETHERNET_MDIO_PRIORITY                  7
-+#define QCA8K_ETHERNET_PHY_PRIORITY                   6
- #define QCA8K_ETHERNET_TIMEOUT                                100
- #define QCA8K_NUM_PORTS                                       7
diff --git a/target/linux/generic/backport-5.15/766-v5.18-13-net-dsa-qca8k-move-page-cache-to-driver-priv.patch b/target/linux/generic/backport-5.15/766-v5.18-13-net-dsa-qca8k-move-page-cache-to-driver-priv.patch
deleted file mode 100644 (file)
index 4ac0bc3..0000000
+++ /dev/null
@@ -1,208 +0,0 @@
-From 4264350acb75430d5021a1d7de56a33faf69a097 Mon Sep 17 00:00:00 2001
-From: Ansuel Smith <[email protected]>
-Date: Wed, 2 Feb 2022 01:03:32 +0100
-Subject: [PATCH 13/16] net: dsa: qca8k: move page cache to driver priv
-
-There can be multiple qca8k switch on the same system. Move the static
-qca8k_current_page to qca8k_priv and make it specific for each switch.
-
-Signed-off-by: Ansuel Smith <[email protected]>
-Reviewed-by: Florian Fainelli <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/dsa/qca8k.c | 42 ++++++++++++++++++++---------------------
- drivers/net/dsa/qca8k.h |  9 +++++++++
- 2 files changed, 29 insertions(+), 22 deletions(-)
-
---- a/drivers/net/dsa/qca8k.c
-+++ b/drivers/net/dsa/qca8k.c
-@@ -75,12 +75,6 @@ static const struct qca8k_mib_desc ar832
-       MIB_DESC(1, 0xac, "TXUnicast"),
- };
--/* The 32bit switch registers are accessed indirectly. To achieve this we need
-- * to set the page of the register. Track the last page that was set to reduce
-- * mdio writes
-- */
--static u16 qca8k_current_page = 0xffff;
--
- static void
- qca8k_split_addr(u32 regaddr, u16 *r1, u16 *r2, u16 *page)
- {
-@@ -134,11 +128,13 @@ qca8k_mii_write32(struct mii_bus *bus, i
- }
- static int
--qca8k_set_page(struct mii_bus *bus, u16 page)
-+qca8k_set_page(struct qca8k_priv *priv, u16 page)
- {
-+      u16 *cached_page = &priv->mdio_cache.page;
-+      struct mii_bus *bus = priv->bus;
-       int ret;
--      if (page == qca8k_current_page)
-+      if (page == *cached_page)
-               return 0;
-       ret = bus->write(bus, 0x18, 0, page);
-@@ -148,7 +144,7 @@ qca8k_set_page(struct mii_bus *bus, u16
-               return ret;
-       }
--      qca8k_current_page = page;
-+      *cached_page = page;
-       usleep_range(1000, 2000);
-       return 0;
- }
-@@ -374,7 +370,7 @@ qca8k_regmap_read(void *ctx, uint32_t re
-       mutex_lock_nested(&bus->mdio_lock, MDIO_MUTEX_NESTED);
--      ret = qca8k_set_page(bus, page);
-+      ret = qca8k_set_page(priv, page);
-       if (ret < 0)
-               goto exit;
-@@ -400,7 +396,7 @@ qca8k_regmap_write(void *ctx, uint32_t r
-       mutex_lock_nested(&bus->mdio_lock, MDIO_MUTEX_NESTED);
--      ret = qca8k_set_page(bus, page);
-+      ret = qca8k_set_page(priv, page);
-       if (ret < 0)
-               goto exit;
-@@ -427,7 +423,7 @@ qca8k_regmap_update_bits(void *ctx, uint
-       mutex_lock_nested(&bus->mdio_lock, MDIO_MUTEX_NESTED);
--      ret = qca8k_set_page(bus, page);
-+      ret = qca8k_set_page(priv, page);
-       if (ret < 0)
-               goto exit;
-@@ -1098,8 +1094,9 @@ qca8k_mdio_busy_wait(struct mii_bus *bus
- }
- static int
--qca8k_mdio_write(struct mii_bus *bus, int phy, int regnum, u16 data)
-+qca8k_mdio_write(struct qca8k_priv *priv, int phy, int regnum, u16 data)
- {
-+      struct mii_bus *bus = priv->bus;
-       u16 r1, r2, page;
-       u32 val;
-       int ret;
-@@ -1116,7 +1113,7 @@ qca8k_mdio_write(struct mii_bus *bus, in
-       mutex_lock_nested(&bus->mdio_lock, MDIO_MUTEX_NESTED);
--      ret = qca8k_set_page(bus, page);
-+      ret = qca8k_set_page(priv, page);
-       if (ret)
-               goto exit;
-@@ -1135,8 +1132,9 @@ exit:
- }
- static int
--qca8k_mdio_read(struct mii_bus *bus, int phy, int regnum)
-+qca8k_mdio_read(struct qca8k_priv *priv, int phy, int regnum)
- {
-+      struct mii_bus *bus = priv->bus;
-       u16 r1, r2, page;
-       u32 val;
-       int ret;
-@@ -1152,7 +1150,7 @@ qca8k_mdio_read(struct mii_bus *bus, int
-       mutex_lock_nested(&bus->mdio_lock, MDIO_MUTEX_NESTED);
--      ret = qca8k_set_page(bus, page);
-+      ret = qca8k_set_page(priv, page);
-       if (ret)
-               goto exit;
-@@ -1181,7 +1179,6 @@ static int
- qca8k_internal_mdio_write(struct mii_bus *slave_bus, int phy, int regnum, u16 data)
- {
-       struct qca8k_priv *priv = slave_bus->priv;
--      struct mii_bus *bus = priv->bus;
-       int ret;
-       /* Use mdio Ethernet when available, fallback to legacy one on error */
-@@ -1189,14 +1186,13 @@ qca8k_internal_mdio_write(struct mii_bus
-       if (!ret)
-               return 0;
--      return qca8k_mdio_write(bus, phy, regnum, data);
-+      return qca8k_mdio_write(priv, phy, regnum, data);
- }
- static int
- qca8k_internal_mdio_read(struct mii_bus *slave_bus, int phy, int regnum)
- {
-       struct qca8k_priv *priv = slave_bus->priv;
--      struct mii_bus *bus = priv->bus;
-       int ret;
-       /* Use mdio Ethernet when available, fallback to legacy one on error */
-@@ -1204,7 +1200,7 @@ qca8k_internal_mdio_read(struct mii_bus
-       if (ret >= 0)
-               return ret;
--      return qca8k_mdio_read(bus, phy, regnum);
-+      return qca8k_mdio_read(priv, phy, regnum);
- }
- static int
-@@ -1225,7 +1221,7 @@ qca8k_phy_write(struct dsa_switch *ds, i
-       if (!ret)
-               return ret;
--      return qca8k_mdio_write(priv->bus, port, regnum, data);
-+      return qca8k_mdio_write(priv, port, regnum, data);
- }
- static int
-@@ -1246,7 +1242,7 @@ qca8k_phy_read(struct dsa_switch *ds, in
-       if (ret >= 0)
-               return ret;
--      ret = qca8k_mdio_read(priv->bus, port, regnum);
-+      ret = qca8k_mdio_read(priv, port, regnum);
-       if (ret < 0)
-               return 0xffff;
-@@ -3060,6 +3056,8 @@ qca8k_sw_probe(struct mdio_device *mdiod
-               return PTR_ERR(priv->regmap);
-       }
-+      priv->mdio_cache.page = 0xffff;
-+
-       /* Check the detected switch id */
-       ret = qca8k_read_switch_id(priv);
-       if (ret)
---- a/drivers/net/dsa/qca8k.h
-+++ b/drivers/net/dsa/qca8k.h
-@@ -363,6 +363,14 @@ struct qca8k_ports_config {
-       u8 rgmii_tx_delay[QCA8K_NUM_CPU_PORTS]; /* 0: CPU port0, 1: CPU port6 */
- };
-+struct qca8k_mdio_cache {
-+/* The 32bit switch registers are accessed indirectly. To achieve this we need
-+ * to set the page of the register. Track the last page that was set to reduce
-+ * mdio writes
-+ */
-+      u16 page;
-+};
-+
- struct qca8k_priv {
-       u8 switch_id;
-       u8 switch_revision;
-@@ -383,6 +391,7 @@ struct qca8k_priv {
-       struct net_device *mgmt_master; /* Track if mdio/mib Ethernet is available */
-       struct qca8k_mgmt_eth_data mgmt_eth_data;
-       struct qca8k_mib_eth_data mib_eth_data;
-+      struct qca8k_mdio_cache mdio_cache;
- };
- struct qca8k_mib_desc {
diff --git a/target/linux/generic/backport-5.15/766-v5.18-14-net-dsa-qca8k-cache-lo-and-hi-for-mdio-write.patch b/target/linux/generic/backport-5.15/766-v5.18-14-net-dsa-qca8k-cache-lo-and-hi-for-mdio-write.patch
deleted file mode 100644 (file)
index e2cb272..0000000
+++ /dev/null
@@ -1,164 +0,0 @@
-From 2481d206fae7884cd07014fd1318e63af35e99eb Mon Sep 17 00:00:00 2001
-From: Ansuel Smith <[email protected]>
-Date: Wed, 2 Feb 2022 01:03:33 +0100
-Subject: [PATCH 14/16] net: dsa: qca8k: cache lo and hi for mdio write
-
-From Documentation, we can cache lo and hi the same way we do with the
-page. This massively reduce the mdio write as 3/4 of the time as we only
-require to write the lo or hi part for a mdio write.
-
-Signed-off-by: Ansuel Smith <[email protected]>
-Reviewed-by: Florian Fainelli <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/dsa/qca8k.c | 61 +++++++++++++++++++++++++++++++++--------
- drivers/net/dsa/qca8k.h |  5 ++++
- 2 files changed, 54 insertions(+), 12 deletions(-)
-
---- a/drivers/net/dsa/qca8k.c
-+++ b/drivers/net/dsa/qca8k.c
-@@ -89,6 +89,44 @@ qca8k_split_addr(u32 regaddr, u16 *r1, u
- }
- static int
-+qca8k_set_lo(struct qca8k_priv *priv, int phy_id, u32 regnum, u16 lo)
-+{
-+      u16 *cached_lo = &priv->mdio_cache.lo;
-+      struct mii_bus *bus = priv->bus;
-+      int ret;
-+
-+      if (lo == *cached_lo)
-+              return 0;
-+
-+      ret = bus->write(bus, phy_id, regnum, lo);
-+      if (ret < 0)
-+              dev_err_ratelimited(&bus->dev,
-+                                  "failed to write qca8k 32bit lo register\n");
-+
-+      *cached_lo = lo;
-+      return 0;
-+}
-+
-+static int
-+qca8k_set_hi(struct qca8k_priv *priv, int phy_id, u32 regnum, u16 hi)
-+{
-+      u16 *cached_hi = &priv->mdio_cache.hi;
-+      struct mii_bus *bus = priv->bus;
-+      int ret;
-+
-+      if (hi == *cached_hi)
-+              return 0;
-+
-+      ret = bus->write(bus, phy_id, regnum, hi);
-+      if (ret < 0)
-+              dev_err_ratelimited(&bus->dev,
-+                                  "failed to write qca8k 32bit hi register\n");
-+
-+      *cached_hi = hi;
-+      return 0;
-+}
-+
-+static int
- qca8k_mii_read32(struct mii_bus *bus, int phy_id, u32 regnum, u32 *val)
- {
-       int ret;
-@@ -111,7 +149,7 @@ qca8k_mii_read32(struct mii_bus *bus, in
- }
- static void
--qca8k_mii_write32(struct mii_bus *bus, int phy_id, u32 regnum, u32 val)
-+qca8k_mii_write32(struct qca8k_priv *priv, int phy_id, u32 regnum, u32 val)
- {
-       u16 lo, hi;
-       int ret;
-@@ -119,12 +157,9 @@ qca8k_mii_write32(struct mii_bus *bus, i
-       lo = val & 0xffff;
-       hi = (u16)(val >> 16);
--      ret = bus->write(bus, phy_id, regnum, lo);
-+      ret = qca8k_set_lo(priv, phy_id, regnum, lo);
-       if (ret >= 0)
--              ret = bus->write(bus, phy_id, regnum + 1, hi);
--      if (ret < 0)
--              dev_err_ratelimited(&bus->dev,
--                                  "failed to write qca8k 32bit register\n");
-+              ret = qca8k_set_hi(priv, phy_id, regnum + 1, hi);
- }
- static int
-@@ -400,7 +435,7 @@ qca8k_regmap_write(void *ctx, uint32_t r
-       if (ret < 0)
-               goto exit;
--      qca8k_mii_write32(bus, 0x10 | r2, r1, val);
-+      qca8k_mii_write32(priv, 0x10 | r2, r1, val);
- exit:
-       mutex_unlock(&bus->mdio_lock);
-@@ -433,7 +468,7 @@ qca8k_regmap_update_bits(void *ctx, uint
-       val &= ~mask;
-       val |= write_val;
--      qca8k_mii_write32(bus, 0x10 | r2, r1, val);
-+      qca8k_mii_write32(priv, 0x10 | r2, r1, val);
- exit:
-       mutex_unlock(&bus->mdio_lock);
-@@ -1117,14 +1152,14 @@ qca8k_mdio_write(struct qca8k_priv *priv
-       if (ret)
-               goto exit;
--      qca8k_mii_write32(bus, 0x10 | r2, r1, val);
-+      qca8k_mii_write32(priv, 0x10 | r2, r1, val);
-       ret = qca8k_mdio_busy_wait(bus, QCA8K_MDIO_MASTER_CTRL,
-                                  QCA8K_MDIO_MASTER_BUSY);
- exit:
-       /* even if the busy_wait timeouts try to clear the MASTER_EN */
--      qca8k_mii_write32(bus, 0x10 | r2, r1, 0);
-+      qca8k_mii_write32(priv, 0x10 | r2, r1, 0);
-       mutex_unlock(&bus->mdio_lock);
-@@ -1154,7 +1189,7 @@ qca8k_mdio_read(struct qca8k_priv *priv,
-       if (ret)
-               goto exit;
--      qca8k_mii_write32(bus, 0x10 | r2, r1, val);
-+      qca8k_mii_write32(priv, 0x10 | r2, r1, val);
-       ret = qca8k_mdio_busy_wait(bus, QCA8K_MDIO_MASTER_CTRL,
-                                  QCA8K_MDIO_MASTER_BUSY);
-@@ -1165,7 +1200,7 @@ qca8k_mdio_read(struct qca8k_priv *priv,
- exit:
-       /* even if the busy_wait timeouts try to clear the MASTER_EN */
--      qca8k_mii_write32(bus, 0x10 | r2, r1, 0);
-+      qca8k_mii_write32(priv, 0x10 | r2, r1, 0);
-       mutex_unlock(&bus->mdio_lock);
-@@ -3057,6 +3092,8 @@ qca8k_sw_probe(struct mdio_device *mdiod
-       }
-       priv->mdio_cache.page = 0xffff;
-+      priv->mdio_cache.lo = 0xffff;
-+      priv->mdio_cache.hi = 0xffff;
-       /* Check the detected switch id */
-       ret = qca8k_read_switch_id(priv);
---- a/drivers/net/dsa/qca8k.h
-+++ b/drivers/net/dsa/qca8k.h
-@@ -369,6 +369,11 @@ struct qca8k_mdio_cache {
-  * mdio writes
-  */
-       u16 page;
-+/* lo and hi can also be cached and from Documentation we can skip one
-+ * extra mdio write if lo or hi is didn't change.
-+ */
-+      u16 lo;
-+      u16 hi;
- };
- struct qca8k_priv {
diff --git a/target/linux/generic/backport-5.15/766-v5.18-15-net-dsa-qca8k-add-support-for-larger-read-write-size.patch b/target/linux/generic/backport-5.15/766-v5.18-15-net-dsa-qca8k-add-support-for-larger-read-write-size.patch
deleted file mode 100644 (file)
index 5acd13d..0000000
+++ /dev/null
@@ -1,206 +0,0 @@
-From 90386223f44e2a751d7e9e9ac8f78ea33358a891 Mon Sep 17 00:00:00 2001
-From: Ansuel Smith <[email protected]>
-Date: Wed, 2 Feb 2022 01:03:34 +0100
-Subject: [PATCH 15/16] net: dsa: qca8k: add support for larger read/write size
- with mgmt Ethernet
-
-mgmt Ethernet packet can read/write up to 16byte at times. The len reg
-is limited to 15 (0xf). The switch actually sends and accepts data in 4
-different steps of len values.
-Len steps:
-- 0: nothing
-- 1-4: first 4 byte
-- 5-6: first 12 byte
-- 7-15: all 16 byte
-
-In the alloc skb function we check if the len is 16 and we fix it to a
-len of 15. It the read/write function interest to extract the real asked
-data. The tagger handler will always copy the fully 16byte with a READ
-command. This is useful for some big regs like the fdb reg that are
-more than 4byte of data. This permits to introduce a bulk function that
-will send and request the entire entry in one go.
-Write function is changed and it does now require to pass the pointer to
-val to also handle array val.
-
-Signed-off-by: Ansuel Smith <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/dsa/qca8k.c | 61 +++++++++++++++++++++++++++--------------
- 1 file changed, 41 insertions(+), 20 deletions(-)
-
---- a/drivers/net/dsa/qca8k.c
-+++ b/drivers/net/dsa/qca8k.c
-@@ -222,7 +222,9 @@ static void qca8k_rw_reg_ack_handler(str
-       if (cmd == MDIO_READ) {
-               mgmt_eth_data->data[0] = mgmt_ethhdr->mdio_data;
--              /* Get the rest of the 12 byte of data */
-+              /* Get the rest of the 12 byte of data.
-+               * The read/write function will extract the requested data.
-+               */
-               if (len > QCA_HDR_MGMT_DATA1_LEN)
-                       memcpy(mgmt_eth_data->data + 1, skb->data,
-                              QCA_HDR_MGMT_DATA2_LEN);
-@@ -232,16 +234,30 @@ static void qca8k_rw_reg_ack_handler(str
- }
- static struct sk_buff *qca8k_alloc_mdio_header(enum mdio_cmd cmd, u32 reg, u32 *val,
--                                             int priority)
-+                                             int priority, unsigned int len)
- {
-       struct qca_mgmt_ethhdr *mgmt_ethhdr;
-+      unsigned int real_len;
-       struct sk_buff *skb;
-+      u32 *data2;
-       u16 hdr;
-       skb = dev_alloc_skb(QCA_HDR_MGMT_PKT_LEN);
-       if (!skb)
-               return NULL;
-+      /* Max value for len reg is 15 (0xf) but the switch actually return 16 byte
-+       * Actually for some reason the steps are:
-+       * 0: nothing
-+       * 1-4: first 4 byte
-+       * 5-6: first 12 byte
-+       * 7-15: all 16 byte
-+       */
-+      if (len == 16)
-+              real_len = 15;
-+      else
-+              real_len = len;
-+
-       skb_reset_mac_header(skb);
-       skb_set_network_header(skb, skb->len);
-@@ -254,7 +270,7 @@ static struct sk_buff *qca8k_alloc_mdio_
-       hdr |= FIELD_PREP(QCA_HDR_XMIT_CONTROL, QCA_HDR_XMIT_TYPE_RW_REG);
-       mgmt_ethhdr->command = FIELD_PREP(QCA_HDR_MGMT_ADDR, reg);
--      mgmt_ethhdr->command |= FIELD_PREP(QCA_HDR_MGMT_LENGTH, 4);
-+      mgmt_ethhdr->command |= FIELD_PREP(QCA_HDR_MGMT_LENGTH, real_len);
-       mgmt_ethhdr->command |= FIELD_PREP(QCA_HDR_MGMT_CMD, cmd);
-       mgmt_ethhdr->command |= FIELD_PREP(QCA_HDR_MGMT_CHECK_CODE,
-                                          QCA_HDR_MGMT_CHECK_CODE_VAL);
-@@ -264,7 +280,9 @@ static struct sk_buff *qca8k_alloc_mdio_
-       mgmt_ethhdr->hdr = htons(hdr);
--      skb_put_zero(skb, QCA_HDR_MGMT_DATA2_LEN + QCA_HDR_MGMT_PADDING_LEN);
-+      data2 = skb_put_zero(skb, QCA_HDR_MGMT_DATA2_LEN + QCA_HDR_MGMT_PADDING_LEN);
-+      if (cmd == MDIO_WRITE && len > QCA_HDR_MGMT_DATA1_LEN)
-+              memcpy(data2, val + 1, len - QCA_HDR_MGMT_DATA1_LEN);
-       return skb;
- }
-@@ -277,7 +295,7 @@ static void qca8k_mdio_header_fill_seq_n
-       mgmt_ethhdr->seq = FIELD_PREP(QCA_HDR_MGMT_SEQ_NUM, seq_num);
- }
--static int qca8k_read_eth(struct qca8k_priv *priv, u32 reg, u32 *val)
-+static int qca8k_read_eth(struct qca8k_priv *priv, u32 reg, u32 *val, int len)
- {
-       struct qca8k_mgmt_eth_data *mgmt_eth_data = &priv->mgmt_eth_data;
-       struct sk_buff *skb;
-@@ -285,7 +303,7 @@ static int qca8k_read_eth(struct qca8k_p
-       int ret;
-       skb = qca8k_alloc_mdio_header(MDIO_READ, reg, NULL,
--                                    QCA8K_ETHERNET_MDIO_PRIORITY);
-+                                    QCA8K_ETHERNET_MDIO_PRIORITY, len);
-       if (!skb)
-               return -ENOMEM;
-@@ -313,6 +331,9 @@ static int qca8k_read_eth(struct qca8k_p
-                                         msecs_to_jiffies(QCA8K_ETHERNET_TIMEOUT));
-       *val = mgmt_eth_data->data[0];
-+      if (len > QCA_HDR_MGMT_DATA1_LEN)
-+              memcpy(val + 1, mgmt_eth_data->data + 1, len - QCA_HDR_MGMT_DATA1_LEN);
-+
-       ack = mgmt_eth_data->ack;
-       mutex_unlock(&mgmt_eth_data->mutex);
-@@ -326,15 +347,15 @@ static int qca8k_read_eth(struct qca8k_p
-       return 0;
- }
--static int qca8k_write_eth(struct qca8k_priv *priv, u32 reg, u32 val)
-+static int qca8k_write_eth(struct qca8k_priv *priv, u32 reg, u32 *val, int len)
- {
-       struct qca8k_mgmt_eth_data *mgmt_eth_data = &priv->mgmt_eth_data;
-       struct sk_buff *skb;
-       bool ack;
-       int ret;
--      skb = qca8k_alloc_mdio_header(MDIO_WRITE, reg, &val,
--                                    QCA8K_ETHERNET_MDIO_PRIORITY);
-+      skb = qca8k_alloc_mdio_header(MDIO_WRITE, reg, val,
-+                                    QCA8K_ETHERNET_MDIO_PRIORITY, len);
-       if (!skb)
-               return -ENOMEM;
-@@ -380,14 +401,14 @@ qca8k_regmap_update_bits_eth(struct qca8
-       u32 val = 0;
-       int ret;
--      ret = qca8k_read_eth(priv, reg, &val);
-+      ret = qca8k_read_eth(priv, reg, &val, sizeof(val));
-       if (ret)
-               return ret;
-       val &= ~mask;
-       val |= write_val;
--      return qca8k_write_eth(priv, reg, val);
-+      return qca8k_write_eth(priv, reg, &val, sizeof(val));
- }
- static int
-@@ -398,7 +419,7 @@ qca8k_regmap_read(void *ctx, uint32_t re
-       u16 r1, r2, page;
-       int ret;
--      if (!qca8k_read_eth(priv, reg, val))
-+      if (!qca8k_read_eth(priv, reg, val, sizeof(val)))
-               return 0;
-       qca8k_split_addr(reg, &r1, &r2, &page);
-@@ -424,7 +445,7 @@ qca8k_regmap_write(void *ctx, uint32_t r
-       u16 r1, r2, page;
-       int ret;
--      if (!qca8k_write_eth(priv, reg, val))
-+      if (!qca8k_write_eth(priv, reg, &val, sizeof(val)))
-               return 0;
-       qca8k_split_addr(reg, &r1, &r2, &page);
-@@ -959,21 +980,21 @@ qca8k_phy_eth_command(struct qca8k_priv
-       }
-       /* Prealloc all the needed skb before the lock */
--      write_skb = qca8k_alloc_mdio_header(MDIO_WRITE, QCA8K_MDIO_MASTER_CTRL,
--                                          &write_val, QCA8K_ETHERNET_PHY_PRIORITY);
-+      write_skb = qca8k_alloc_mdio_header(MDIO_WRITE, QCA8K_MDIO_MASTER_CTRL, &write_val,
-+                                          QCA8K_ETHERNET_PHY_PRIORITY, sizeof(write_val));
-       if (!write_skb)
-               return -ENOMEM;
--      clear_skb = qca8k_alloc_mdio_header(MDIO_WRITE, QCA8K_MDIO_MASTER_CTRL,
--                                          &clear_val, QCA8K_ETHERNET_PHY_PRIORITY);
-+      clear_skb = qca8k_alloc_mdio_header(MDIO_WRITE, QCA8K_MDIO_MASTER_CTRL, &clear_val,
-+                                          QCA8K_ETHERNET_PHY_PRIORITY, sizeof(clear_val));
-       if (!write_skb) {
-               ret = -ENOMEM;
-               goto err_clear_skb;
-       }
--      read_skb = qca8k_alloc_mdio_header(MDIO_READ, QCA8K_MDIO_MASTER_CTRL,
--                                         &clear_val, QCA8K_ETHERNET_PHY_PRIORITY);
--      if (!write_skb) {
-+      read_skb = qca8k_alloc_mdio_header(MDIO_READ, QCA8K_MDIO_MASTER_CTRL, &clear_val,
-+                                         QCA8K_ETHERNET_PHY_PRIORITY, sizeof(clear_val));
-+      if (!read_skb) {
-               ret = -ENOMEM;
-               goto err_read_skb;
-       }
diff --git a/target/linux/generic/backport-5.15/766-v5.18-16-net-dsa-qca8k-introduce-qca8k_bulk_read-write-functi.patch b/target/linux/generic/backport-5.15/766-v5.18-16-net-dsa-qca8k-introduce-qca8k_bulk_read-write-functi.patch
deleted file mode 100644 (file)
index f26c6b9..0000000
+++ /dev/null
@@ -1,104 +0,0 @@
-From 4f3701fc599820568ba4395070d34e4248800fc0 Mon Sep 17 00:00:00 2001
-From: Ansuel Smith <[email protected]>
-Date: Wed, 2 Feb 2022 01:03:35 +0100
-Subject: [PATCH 16/16] net: dsa: qca8k: introduce qca8k_bulk_read/write
- function
-
-Introduce qca8k_bulk_read/write() function to use mgmt Ethernet way to
-read/write packet in bulk. Make use of this new function in the fdb
-function and while at it reduce the reg for fdb_read from 4 to 3 as the
-max bit for the ARL(fdb) table is 83 bits.
-
-Signed-off-by: Ansuel Smith <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/dsa/qca8k.c | 55 ++++++++++++++++++++++++++++++++---------
- 1 file changed, 43 insertions(+), 12 deletions(-)
-
---- a/drivers/net/dsa/qca8k.c
-+++ b/drivers/net/dsa/qca8k.c
-@@ -412,6 +412,43 @@ qca8k_regmap_update_bits_eth(struct qca8
- }
- static int
-+qca8k_bulk_read(struct qca8k_priv *priv, u32 reg, u32 *val, int len)
-+{
-+      int i, count = len / sizeof(u32), ret;
-+
-+      if (priv->mgmt_master && !qca8k_read_eth(priv, reg, val, len))
-+              return 0;
-+
-+      for (i = 0; i < count; i++) {
-+              ret = regmap_read(priv->regmap, reg + (i * 4), val + i);
-+              if (ret < 0)
-+                      return ret;
-+      }
-+
-+      return 0;
-+}
-+
-+static int
-+qca8k_bulk_write(struct qca8k_priv *priv, u32 reg, u32 *val, int len)
-+{
-+      int i, count = len / sizeof(u32), ret;
-+      u32 tmp;
-+
-+      if (priv->mgmt_master && !qca8k_write_eth(priv, reg, val, len))
-+              return 0;
-+
-+      for (i = 0; i < count; i++) {
-+              tmp = val[i];
-+
-+              ret = regmap_write(priv->regmap, reg + (i * 4), tmp);
-+              if (ret < 0)
-+                      return ret;
-+      }
-+
-+      return 0;
-+}
-+
-+static int
- qca8k_regmap_read(void *ctx, uint32_t reg, uint32_t *val)
- {
-       struct qca8k_priv *priv = (struct qca8k_priv *)ctx;
-@@ -546,17 +583,13 @@ qca8k_busy_wait(struct qca8k_priv *priv,
- static int
- qca8k_fdb_read(struct qca8k_priv *priv, struct qca8k_fdb *fdb)
- {
--      u32 reg[4], val;
--      int i, ret;
-+      u32 reg[3];
-+      int ret;
-       /* load the ARL table into an array */
--      for (i = 0; i < 4; i++) {
--              ret = qca8k_read(priv, QCA8K_REG_ATU_DATA0 + (i * 4), &val);
--              if (ret < 0)
--                      return ret;
--
--              reg[i] = val;
--      }
-+      ret = qca8k_bulk_read(priv, QCA8K_REG_ATU_DATA0, reg, sizeof(reg));
-+      if (ret)
-+              return ret;
-       /* vid - 83:72 */
-       fdb->vid = FIELD_GET(QCA8K_ATU_VID_MASK, reg[2]);
-@@ -580,7 +613,6 @@ qca8k_fdb_write(struct qca8k_priv *priv,
-               u8 aging)
- {
-       u32 reg[3] = { 0 };
--      int i;
-       /* vid - 83:72 */
-       reg[2] = FIELD_PREP(QCA8K_ATU_VID_MASK, vid);
-@@ -597,8 +629,7 @@ qca8k_fdb_write(struct qca8k_priv *priv,
-       reg[0] |= FIELD_PREP(QCA8K_ATU_ADDR5_MASK, mac[5]);
-       /* load the array into the ARL table */
--      for (i = 0; i < 3; i++)
--              qca8k_write(priv, QCA8K_REG_ATU_DATA0 + (i * 4), reg[i]);
-+      qca8k_bulk_write(priv, QCA8K_REG_ATU_DATA0, reg, sizeof(reg));
- }
- static int
diff --git a/target/linux/generic/backport-5.15/767-v5.18-net-dsa-qca8k-check-correct-variable-in-qca8k_phy_et.patch b/target/linux/generic/backport-5.15/767-v5.18-net-dsa-qca8k-check-correct-variable-in-qca8k_phy_et.patch
deleted file mode 100644 (file)
index 34607c2..0000000
+++ /dev/null
@@ -1,28 +0,0 @@
-From c3664d913dc115cab4a5fdb5634df4887048000e Mon Sep 17 00:00:00 2001
-From: Dan Carpenter <[email protected]>
-Date: Fri, 4 Feb 2022 13:03:36 +0300
-Subject: [PATCH 1/1] net: dsa: qca8k: check correct variable in
- qca8k_phy_eth_command()
-
-This is a copy and paste bug.  It was supposed to check "clear_skb"
-instead of "write_skb".
-
-Fixes: 2cd548566384 ("net: dsa: qca8k: add support for phy read/write with mgmt Ethernet")
-Signed-off-by: Dan Carpenter <[email protected]>
-Reviewed-by: Florian Fainelli <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/dsa/qca8k.c | 2 +-
- 1 file changed, 1 insertion(+), 1 deletion(-)
-
---- a/drivers/net/dsa/qca8k.c
-+++ b/drivers/net/dsa/qca8k.c
-@@ -1018,7 +1018,7 @@ qca8k_phy_eth_command(struct qca8k_priv
-       clear_skb = qca8k_alloc_mdio_header(MDIO_WRITE, QCA8K_MDIO_MASTER_CTRL, &clear_val,
-                                           QCA8K_ETHERNET_PHY_PRIORITY, sizeof(clear_val));
--      if (!write_skb) {
-+      if (!clear_skb) {
-               ret = -ENOMEM;
-               goto err_clear_skb;
-       }
diff --git a/target/linux/generic/backport-5.15/768-v5.18-net-dsa-qca8k-fix-noderef.cocci-warnings.patch b/target/linux/generic/backport-5.15/768-v5.18-net-dsa-qca8k-fix-noderef.cocci-warnings.patch
deleted file mode 100644 (file)
index d8cf266..0000000
+++ /dev/null
@@ -1,34 +0,0 @@
-From 4f5e483b8c7a644733db941a1ae00173baa7b463 Mon Sep 17 00:00:00 2001
-From: kernel test robot <[email protected]>
-Date: Thu, 10 Feb 2022 06:13:04 +0800
-Subject: [PATCH 1/1] net: dsa: qca8k: fix noderef.cocci warnings
-
-drivers/net/dsa/qca8k.c:422:37-43: ERROR: application of sizeof to pointer
-
- sizeof when applied to a pointer typed expression gives the size of
- the pointer
-
-Generated by: scripts/coccinelle/misc/noderef.cocci
-
-Fixes: 90386223f44e ("net: dsa: qca8k: add support for larger read/write size with mgmt Ethernet")
-CC: Ansuel Smith <[email protected]>
-Reported-by: kernel test robot <[email protected]>
-Signed-off-by: kernel test robot <[email protected]>
-Reviewed-by: Florian Fainelli <[email protected]>
-Link: https://lore.kernel.org/r/20220209221304.GA17529@d2214a582157
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- drivers/net/dsa/qca8k.c | 2 +-
- 1 file changed, 1 insertion(+), 1 deletion(-)
-
---- a/drivers/net/dsa/qca8k.c
-+++ b/drivers/net/dsa/qca8k.c
-@@ -456,7 +456,7 @@ qca8k_regmap_read(void *ctx, uint32_t re
-       u16 r1, r2, page;
-       int ret;
--      if (!qca8k_read_eth(priv, reg, val, sizeof(val)))
-+      if (!qca8k_read_eth(priv, reg, val, sizeof(*val)))
-               return 0;
-       qca8k_split_addr(reg, &r1, &r2, &page);
diff --git a/target/linux/generic/backport-5.15/769-v5.19-01-net-dsa-qca8k-drop-MTU-tracking-from-qca8k_priv.patch b/target/linux/generic/backport-5.15/769-v5.19-01-net-dsa-qca8k-drop-MTU-tracking-from-qca8k_priv.patch
deleted file mode 100644 (file)
index 57df4c1..0000000
+++ /dev/null
@@ -1,79 +0,0 @@
-From 69fd055957a02309ffdc23d887a01988b6e5bab1 Mon Sep 17 00:00:00 2001
-From: Ansuel Smith <[email protected]>
-Date: Sat, 16 Apr 2022 01:30:12 +0200
-Subject: [PATCH 1/6] net: dsa: qca8k: drop MTU tracking from qca8k_priv
-
-DSA set the CPU port based on the largest MTU of all the slave ports.
-Based on this we can drop the MTU array from qca8k_priv and set the
-port_change_mtu logic on DSA changing MTU of the CPU port as the switch
-have a global MTU settingfor each port.
-
-Signed-off-by: Ansuel Smith <[email protected]>
-Reviewed-by: Vladimir Oltean <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/dsa/qca8k.c | 26 +++++++++-----------------
- drivers/net/dsa/qca8k.h |  1 -
- 2 files changed, 9 insertions(+), 18 deletions(-)
-
---- a/drivers/net/dsa/qca8k.c
-+++ b/drivers/net/dsa/qca8k.c
-@@ -1803,16 +1803,6 @@ qca8k_setup(struct dsa_switch *ds)
-                                 QCA8K_PORT_HOL_CTRL1_WRED_EN,
-                                 mask);
-               }
--
--              /* Set initial MTU for every port.
--               * We have only have a general MTU setting. So track
--               * every port and set the max across all port.
--               * Set per port MTU to 1500 as the MTU change function
--               * will add the overhead and if its set to 1518 then it
--               * will apply the overhead again and we will end up with
--               * MTU of 1536 instead of 1518
--               */
--              priv->port_mtu[i] = ETH_DATA_LEN;
-       }
-       /* Special GLOBAL_FC_THRESH value are needed for ar8327 switch */
-@@ -2525,13 +2515,16 @@ static int
- qca8k_port_change_mtu(struct dsa_switch *ds, int port, int new_mtu)
- {
-       struct qca8k_priv *priv = ds->priv;
--      int ret, i, mtu = 0;
--
--      priv->port_mtu[port] = new_mtu;
-+      int ret;
--      for (i = 0; i < QCA8K_NUM_PORTS; i++)
--              if (priv->port_mtu[i] > mtu)
--                      mtu = priv->port_mtu[i];
-+      /* We have only have a general MTU setting.
-+       * DSA always set the CPU port's MTU to the largest MTU of the slave
-+       * ports.
-+       * Setting MTU just for the CPU port is sufficient to correctly set a
-+       * value for every port.
-+       */
-+      if (!dsa_is_cpu_port(ds, port))
-+              return 0;
-       /* To change the MAX_FRAME_SIZE the cpu ports must be off or
-        * the switch panics.
-@@ -2545,7 +2538,7 @@ qca8k_port_change_mtu(struct dsa_switch
-               qca8k_port_set_status(priv, 6, 0);
-       /* Include L2 header / FCS length */
--      ret = qca8k_write(priv, QCA8K_MAX_FRAME_SIZE, mtu + ETH_HLEN + ETH_FCS_LEN);
-+      ret = qca8k_write(priv, QCA8K_MAX_FRAME_SIZE, new_mtu + ETH_HLEN + ETH_FCS_LEN);
-       if (priv->port_sts[0].enabled)
-               qca8k_port_set_status(priv, 0, 1);
---- a/drivers/net/dsa/qca8k.h
-+++ b/drivers/net/dsa/qca8k.h
-@@ -392,7 +392,6 @@ struct qca8k_priv {
-       struct device *dev;
-       struct dsa_switch_ops ops;
-       struct gpio_desc *reset_gpio;
--      unsigned int port_mtu[QCA8K_NUM_PORTS];
-       struct net_device *mgmt_master; /* Track if mdio/mib Ethernet is available */
-       struct qca8k_mgmt_eth_data mgmt_eth_data;
-       struct qca8k_mib_eth_data mib_eth_data;
diff --git a/target/linux/generic/backport-5.15/769-v5.19-02-net-dsa-qca8k-drop-port_sts-from-qca8k_priv.patch b/target/linux/generic/backport-5.15/769-v5.19-02-net-dsa-qca8k-drop-port_sts-from-qca8k_priv.patch
deleted file mode 100644 (file)
index 3cacd7e..0000000
+++ /dev/null
@@ -1,116 +0,0 @@
-From 2b8fd87af7f156942971789abac8ee2bb60c03bc Mon Sep 17 00:00:00 2001
-From: Ansuel Smith <[email protected]>
-Date: Sat, 16 Apr 2022 01:30:13 +0200
-Subject: [PATCH 2/6] net: dsa: qca8k: drop port_sts from qca8k_priv
-
-Port_sts is a thing of the past for this driver. It was something
-present on the initial implementation of this driver and parts of the
-original struct were dropped over time. Using an array of int to store if
-a port is enabled or not to handle PM operation seems overkill. Switch
-and use a simple u8 to store the port status where each bit correspond
-to a port. (bit is set port is enabled, bit is not set, port is disabled)
-Also add some comments to better describe why we need to track port
-status.
-
-Signed-off-by: Ansuel Smith <[email protected]>
-Reviewed-by: Vladimir Oltean <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/dsa/qca8k.c | 15 +++++++++------
- drivers/net/dsa/qca8k.h |  9 ++++-----
- 2 files changed, 13 insertions(+), 11 deletions(-)
-
---- a/drivers/net/dsa/qca8k.c
-+++ b/drivers/net/dsa/qca8k.c
-@@ -2494,7 +2494,7 @@ qca8k_port_enable(struct dsa_switch *ds,
-       struct qca8k_priv *priv = (struct qca8k_priv *)ds->priv;
-       qca8k_port_set_status(priv, port, 1);
--      priv->port_sts[port].enabled = 1;
-+      priv->port_enabled_map |= BIT(port);
-       if (dsa_is_user_port(ds, port))
-               phy_support_asym_pause(phy);
-@@ -2508,7 +2508,7 @@ qca8k_port_disable(struct dsa_switch *ds
-       struct qca8k_priv *priv = (struct qca8k_priv *)ds->priv;
-       qca8k_port_set_status(priv, port, 0);
--      priv->port_sts[port].enabled = 0;
-+      priv->port_enabled_map &= ~BIT(port);
- }
- static int
-@@ -2531,19 +2531,19 @@ qca8k_port_change_mtu(struct dsa_switch
-        * Turn off both cpu ports before applying the new value to prevent
-        * this.
-        */
--      if (priv->port_sts[0].enabled)
-+      if (priv->port_enabled_map & BIT(0))
-               qca8k_port_set_status(priv, 0, 0);
--      if (priv->port_sts[6].enabled)
-+      if (priv->port_enabled_map & BIT(6))
-               qca8k_port_set_status(priv, 6, 0);
-       /* Include L2 header / FCS length */
-       ret = qca8k_write(priv, QCA8K_MAX_FRAME_SIZE, new_mtu + ETH_HLEN + ETH_FCS_LEN);
--      if (priv->port_sts[0].enabled)
-+      if (priv->port_enabled_map & BIT(0))
-               qca8k_port_set_status(priv, 0, 1);
--      if (priv->port_sts[6].enabled)
-+      if (priv->port_enabled_map & BIT(6))
-               qca8k_port_set_status(priv, 6, 1);
-       return ret;
-@@ -3199,13 +3199,16 @@ static void qca8k_sw_shutdown(struct mdi
- static void
- qca8k_set_pm(struct qca8k_priv *priv, int enable)
- {
--      int i;
-+      int port;
--      for (i = 0; i < QCA8K_NUM_PORTS; i++) {
--              if (!priv->port_sts[i].enabled)
-+      for (port = 0; port < QCA8K_NUM_PORTS; port++) {
-+              /* Do not enable on resume if the port was
-+               * disabled before.
-+               */
-+              if (!(priv->port_enabled_map & BIT(port)))
-                       continue;
--              qca8k_port_set_status(priv, i, enable);
-+              qca8k_port_set_status(priv, port, enable);
-       }
- }
---- a/drivers/net/dsa/qca8k.h
-+++ b/drivers/net/dsa/qca8k.h
-@@ -324,10 +324,6 @@ enum qca8k_mid_cmd {
-       QCA8K_MIB_CAST = 3,
- };
--struct ar8xxx_port_status {
--      int enabled;
--};
--
- struct qca8k_match_data {
-       u8 id;
-       bool reduced_package;
-@@ -382,11 +378,14 @@ struct qca8k_priv {
-       u8 mirror_rx;
-       u8 mirror_tx;
-       u8 lag_hash_mode;
-+      /* Each bit correspond to a port. This switch can support a max of 7 port.
-+       * Bit 1: port enabled. Bit 0: port disabled.
-+       */
-+      u8 port_enabled_map;
-       bool legacy_phy_port_mapping;
-       struct qca8k_ports_config ports_config;
-       struct regmap *regmap;
-       struct mii_bus *bus;
--      struct ar8xxx_port_status port_sts[QCA8K_NUM_PORTS];
-       struct dsa_switch *ds;
-       struct mutex reg_mutex;
-       struct device *dev;
diff --git a/target/linux/generic/backport-5.15/769-v5.19-03-net-dsa-qca8k-rework-and-simplify-mdiobus-logic.patch b/target/linux/generic/backport-5.15/769-v5.19-03-net-dsa-qca8k-rework-and-simplify-mdiobus-logic.patch
deleted file mode 100644 (file)
index 12c3221..0000000
+++ /dev/null
@@ -1,173 +0,0 @@
-From 8255212e4130bd2dc1463286a3dddb74797bbdc1 Mon Sep 17 00:00:00 2001
-From: Ansuel Smith <[email protected]>
-Date: Sat, 16 Apr 2022 01:30:14 +0200
-Subject: [PATCH 3/6] net: dsa: qca8k: rework and simplify mdiobus logic
-
-In an attempt to reduce qca8k_priv space, rework and simplify mdiobus
-logic.
-We now declare a mdiobus instead of relying on DSA phy_read/write even
-if a mdio node is not present. This is all to make the qca8k ops static
-and not switch specific. With a legacy implementation where port doesn't
-have a phy map declared in the dts with a mdio node, we declare a
-'qca8k-legacy' mdiobus. The conversion logic is used as legacy read and
-write ops are used instead of the internal one.
-Also drop the legacy_phy_port_mapping as we now declare mdiobus with ops
-that already address the workaround.
-
-Signed-off-by: Ansuel Smith <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/dsa/qca8k.c | 95 +++++++++++++----------------------------
- drivers/net/dsa/qca8k.h |  1 -
- 2 files changed, 29 insertions(+), 67 deletions(-)
-
---- a/drivers/net/dsa/qca8k.c
-+++ b/drivers/net/dsa/qca8k.c
-@@ -1291,83 +1291,63 @@ qca8k_internal_mdio_read(struct mii_bus
- }
- static int
--qca8k_phy_write(struct dsa_switch *ds, int port, int regnum, u16 data)
-+qca8k_legacy_mdio_write(struct mii_bus *slave_bus, int port, int regnum, u16 data)
- {
--      struct qca8k_priv *priv = ds->priv;
--      int ret;
-+      port = qca8k_port_to_phy(port) % PHY_MAX_ADDR;
--      /* Check if the legacy mapping should be used and the
--       * port is not correctly mapped to the right PHY in the
--       * devicetree
--       */
--      if (priv->legacy_phy_port_mapping)
--              port = qca8k_port_to_phy(port) % PHY_MAX_ADDR;
--
--      /* Use mdio Ethernet when available, fallback to legacy one on error */
--      ret = qca8k_phy_eth_command(priv, false, port, regnum, 0);
--      if (!ret)
--              return ret;
--
--      return qca8k_mdio_write(priv, port, regnum, data);
-+      return qca8k_internal_mdio_write(slave_bus, port, regnum, data);
- }
- static int
--qca8k_phy_read(struct dsa_switch *ds, int port, int regnum)
-+qca8k_legacy_mdio_read(struct mii_bus *slave_bus, int port, int regnum)
- {
--      struct qca8k_priv *priv = ds->priv;
--      int ret;
--
--      /* Check if the legacy mapping should be used and the
--       * port is not correctly mapped to the right PHY in the
--       * devicetree
--       */
--      if (priv->legacy_phy_port_mapping)
--              port = qca8k_port_to_phy(port) % PHY_MAX_ADDR;
--
--      /* Use mdio Ethernet when available, fallback to legacy one on error */
--      ret = qca8k_phy_eth_command(priv, true, port, regnum, 0);
--      if (ret >= 0)
--              return ret;
--
--      ret = qca8k_mdio_read(priv, port, regnum);
--
--      if (ret < 0)
--              return 0xffff;
-+      port = qca8k_port_to_phy(port) % PHY_MAX_ADDR;
--      return ret;
-+      return qca8k_internal_mdio_read(slave_bus, port, regnum);
- }
- static int
--qca8k_mdio_register(struct qca8k_priv *priv, struct device_node *mdio)
-+qca8k_mdio_register(struct qca8k_priv *priv)
- {
-       struct dsa_switch *ds = priv->ds;
-+      struct device_node *mdio;
-       struct mii_bus *bus;
-       bus = devm_mdiobus_alloc(ds->dev);
--
-       if (!bus)
-               return -ENOMEM;
-       bus->priv = (void *)priv;
--      bus->name = "qca8k slave mii";
--      bus->read = qca8k_internal_mdio_read;
--      bus->write = qca8k_internal_mdio_write;
--      snprintf(bus->id, MII_BUS_ID_SIZE, "qca8k-%d",
--               ds->index);
--
-       bus->parent = ds->dev;
-       bus->phy_mask = ~ds->phys_mii_mask;
--
-       ds->slave_mii_bus = bus;
--      return devm_of_mdiobus_register(priv->dev, bus, mdio);
-+      /* Check if the devicetree declare the port:phy mapping */
-+      mdio = of_get_child_by_name(priv->dev->of_node, "mdio");
-+      if (of_device_is_available(mdio)) {
-+              snprintf(bus->id, MII_BUS_ID_SIZE, "qca8k-%d", ds->index);
-+              bus->name = "qca8k slave mii";
-+              bus->read = qca8k_internal_mdio_read;
-+              bus->write = qca8k_internal_mdio_write;
-+              return devm_of_mdiobus_register(priv->dev, bus, mdio);
-+      }
-+
-+      /* If a mapping can't be found the legacy mapping is used,
-+       * using the qca8k_port_to_phy function
-+       */
-+      snprintf(bus->id, MII_BUS_ID_SIZE, "qca8k-%d.%d",
-+               ds->dst->index, ds->index);
-+      bus->name = "qca8k-legacy slave mii";
-+      bus->read = qca8k_legacy_mdio_read;
-+      bus->write = qca8k_legacy_mdio_write;
-+      return devm_mdiobus_register(priv->dev, bus);
- }
- static int
- qca8k_setup_mdio_bus(struct qca8k_priv *priv)
- {
-       u32 internal_mdio_mask = 0, external_mdio_mask = 0, reg;
--      struct device_node *ports, *port, *mdio;
-+      struct device_node *ports, *port;
-       phy_interface_t mode;
-       int err;
-@@ -1429,24 +1409,7 @@ qca8k_setup_mdio_bus(struct qca8k_priv *
-                                        QCA8K_MDIO_MASTER_EN);
-       }
--      /* Check if the devicetree declare the port:phy mapping */
--      mdio = of_get_child_by_name(priv->dev->of_node, "mdio");
--      if (of_device_is_available(mdio)) {
--              err = qca8k_mdio_register(priv, mdio);
--              if (err)
--                      of_node_put(mdio);
--
--              return err;
--      }
--
--      /* If a mapping can't be found the legacy mapping is used,
--       * using the qca8k_port_to_phy function
--       */
--      priv->legacy_phy_port_mapping = true;
--      priv->ops.phy_read = qca8k_phy_read;
--      priv->ops.phy_write = qca8k_phy_write;
--
--      return 0;
-+      return qca8k_mdio_register(priv);
- }
- static int
---- a/drivers/net/dsa/qca8k.h
-+++ b/drivers/net/dsa/qca8k.h
-@@ -382,7 +382,6 @@ struct qca8k_priv {
-        * Bit 1: port enabled. Bit 0: port disabled.
-        */
-       u8 port_enabled_map;
--      bool legacy_phy_port_mapping;
-       struct qca8k_ports_config ports_config;
-       struct regmap *regmap;
-       struct mii_bus *bus;
diff --git a/target/linux/generic/backport-5.15/769-v5.19-04-net-dsa-qca8k-drop-dsa_switch_ops-from-qca8k_priv.patch b/target/linux/generic/backport-5.15/769-v5.19-04-net-dsa-qca8k-drop-dsa_switch_ops-from-qca8k_priv.patch
deleted file mode 100644 (file)
index 8641000..0000000
+++ /dev/null
@@ -1,39 +0,0 @@
-From 2349b83a2486c55b9dd225326f0172a84a43c5e4 Mon Sep 17 00:00:00 2001
-From: Ansuel Smith <[email protected]>
-Date: Sat, 16 Apr 2022 01:30:15 +0200
-Subject: [PATCH 4/6] net: dsa: qca8k: drop dsa_switch_ops from qca8k_priv
-
-Now that dsa_switch_ops is not switch specific anymore, we can drop it
-from qca8k_priv and use the static ops directly for the dsa_switch
-pointer.
-
-Signed-off-by: Ansuel Smith <[email protected]>
-Reviewed-by: Vladimir Oltean <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/dsa/qca8k.c | 3 +--
- drivers/net/dsa/qca8k.h | 1 -
- 2 files changed, 1 insertion(+), 3 deletions(-)
-
---- a/drivers/net/dsa/qca8k.c
-+++ b/drivers/net/dsa/qca8k.c
-@@ -3121,8 +3121,7 @@ qca8k_sw_probe(struct mdio_device *mdiod
-       priv->ds->dev = &mdiodev->dev;
-       priv->ds->num_ports = QCA8K_NUM_PORTS;
-       priv->ds->priv = priv;
--      priv->ops = qca8k_switch_ops;
--      priv->ds->ops = &priv->ops;
-+      priv->ds->ops = &qca8k_switch_ops;
-       mutex_init(&priv->reg_mutex);
-       dev_set_drvdata(&mdiodev->dev, priv);
---- a/drivers/net/dsa/qca8k.h
-+++ b/drivers/net/dsa/qca8k.h
-@@ -388,7 +388,6 @@ struct qca8k_priv {
-       struct dsa_switch *ds;
-       struct mutex reg_mutex;
-       struct device *dev;
--      struct dsa_switch_ops ops;
-       struct gpio_desc *reset_gpio;
-       struct net_device *mgmt_master; /* Track if mdio/mib Ethernet is available */
-       struct qca8k_mgmt_eth_data mgmt_eth_data;
diff --git a/target/linux/generic/backport-5.15/769-v5.19-05-net-dsa-qca8k-correctly-handle-mdio-read-error.patch b/target/linux/generic/backport-5.15/769-v5.19-05-net-dsa-qca8k-correctly-handle-mdio-read-error.patch
deleted file mode 100644 (file)
index b14b220..0000000
+++ /dev/null
@@ -1,33 +0,0 @@
-From 6cfc03b602200c5cbbd8d906fd905547814e83df Mon Sep 17 00:00:00 2001
-From: Ansuel Smith <[email protected]>
-Date: Sat, 16 Apr 2022 01:30:16 +0200
-Subject: [PATCH 5/6] net: dsa: qca8k: correctly handle mdio read error
-
-Restore original way to handle mdio read error by returning 0xffff.
-This was wrongly changed when the internal_mdio_read was introduced,
-now that both legacy and internal use the same function, make sure that
-they behave the same way.
-
-Fixes: ce062a0adbfe ("net: dsa: qca8k: fix kernel panic with legacy mdio mapping")
-Signed-off-by: Ansuel Smith <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/dsa/qca8k.c | 7 ++++++-
- 1 file changed, 6 insertions(+), 1 deletion(-)
-
---- a/drivers/net/dsa/qca8k.c
-+++ b/drivers/net/dsa/qca8k.c
-@@ -1287,7 +1287,12 @@ qca8k_internal_mdio_read(struct mii_bus
-       if (ret >= 0)
-               return ret;
--      return qca8k_mdio_read(priv, phy, regnum);
-+      ret = qca8k_mdio_read(priv, phy, regnum);
-+
-+      if (ret < 0)
-+              return 0xffff;
-+
-+      return ret;
- }
- static int
diff --git a/target/linux/generic/backport-5.15/769-v5.19-06-net-dsa-qca8k-unify-bus-id-naming-with-legacy-and-OF.patch b/target/linux/generic/backport-5.15/769-v5.19-06-net-dsa-qca8k-unify-bus-id-naming-with-legacy-and-OF.patch
deleted file mode 100644 (file)
index 094686f..0000000
+++ /dev/null
@@ -1,44 +0,0 @@
-From 8d1af50842bf2774f4edc57054206e909117469b Mon Sep 17 00:00:00 2001
-From: Ansuel Smith <[email protected]>
-Date: Sat, 16 Apr 2022 01:30:17 +0200
-Subject: [PATCH 6/6] net: dsa: qca8k: unify bus id naming with legacy and OF
- mdio bus
-
-Add support for multiple switch with OF mdio bus declaration.
-Unify the bus id naming and use the same logic for both legacy and OF
-mdio bus.
-
-Signed-off-by: Ansuel Smith <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/dsa/qca8k.c | 5 ++---
- 1 file changed, 2 insertions(+), 3 deletions(-)
-
---- a/drivers/net/dsa/qca8k.c
-+++ b/drivers/net/dsa/qca8k.c
-@@ -1323,6 +1323,8 @@ qca8k_mdio_register(struct qca8k_priv *p
-               return -ENOMEM;
-       bus->priv = (void *)priv;
-+      snprintf(bus->id, MII_BUS_ID_SIZE, "qca8k-%d.%d",
-+               ds->dst->index, ds->index);
-       bus->parent = ds->dev;
-       bus->phy_mask = ~ds->phys_mii_mask;
-       ds->slave_mii_bus = bus;
-@@ -1330,7 +1332,6 @@ qca8k_mdio_register(struct qca8k_priv *p
-       /* Check if the devicetree declare the port:phy mapping */
-       mdio = of_get_child_by_name(priv->dev->of_node, "mdio");
-       if (of_device_is_available(mdio)) {
--              snprintf(bus->id, MII_BUS_ID_SIZE, "qca8k-%d", ds->index);
-               bus->name = "qca8k slave mii";
-               bus->read = qca8k_internal_mdio_read;
-               bus->write = qca8k_internal_mdio_write;
-@@ -1340,8 +1341,6 @@ qca8k_mdio_register(struct qca8k_priv *p
-       /* If a mapping can't be found the legacy mapping is used,
-        * using the qca8k_port_to_phy function
-        */
--      snprintf(bus->id, MII_BUS_ID_SIZE, "qca8k-%d.%d",
--               ds->dst->index, ds->index);
-       bus->name = "qca8k-legacy slave mii";
-       bus->read = qca8k_legacy_mdio_read;
-       bus->write = qca8k_legacy_mdio_write;
diff --git a/target/linux/generic/backport-5.15/770-v6.0-net-dsa-qca8k-move-driver-to-qca-dir.patch b/target/linux/generic/backport-5.15/770-v6.0-net-dsa-qca8k-move-driver-to-qca-dir.patch
deleted file mode 100644 (file)
index 1534113..0000000
+++ /dev/null
@@ -1,7389 +0,0 @@
-From 4bbaf764e1e1786eb937fdb62172f656f512e116 Mon Sep 17 00:00:00 2001
-From: Christian Marangi <[email protected]>
-Date: Wed, 13 Jul 2022 22:53:50 +0200
-Subject: [PATCH 1/1] net: dsa: qca8k: move driver to qca dir
-
-Move qca8k driver to qca dir in preparation for code split and
-introduction of ipq4019 switch based on qca8k.
-
-Signed-off-by: Christian Marangi <[email protected]>
-Reviewed-by: Florian Fainelli <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/dsa/Kconfig           | 8 --------
- drivers/net/dsa/Makefile          | 1 -
- drivers/net/dsa/qca/Kconfig       | 8 ++++++++
- drivers/net/dsa/qca/Makefile      | 1 +
- drivers/net/dsa/{ => qca}/qca8k.c | 0
- drivers/net/dsa/{ => qca}/qca8k.h | 0
- 6 files changed, 9 insertions(+), 9 deletions(-)
- rename drivers/net/dsa/{ => qca}/qca8k.c (100%)
- rename drivers/net/dsa/{ => qca}/qca8k.h (100%)
-
---- a/drivers/net/dsa/Kconfig
-+++ b/drivers/net/dsa/Kconfig
-@@ -60,14 +60,6 @@ source "drivers/net/dsa/sja1105/Kconfig"
- source "drivers/net/dsa/xrs700x/Kconfig"
--config NET_DSA_QCA8K
--      tristate "Qualcomm Atheros QCA8K Ethernet switch family support"
--      select NET_DSA_TAG_QCA
--      select REGMAP
--      help
--        This enables support for the Qualcomm Atheros QCA8K Ethernet
--        switch chips.
--
- config NET_DSA_REALTEK_SMI
-       tristate "Realtek SMI Ethernet switch family support"
-       select NET_DSA_TAG_RTL4_A
---- a/drivers/net/dsa/Makefile
-+++ b/drivers/net/dsa/Makefile
-@@ -8,7 +8,6 @@ endif
- obj-$(CONFIG_NET_DSA_LANTIQ_GSWIP) += lantiq_gswip.o
- obj-$(CONFIG_NET_DSA_MT7530)  += mt7530.o
- obj-$(CONFIG_NET_DSA_MV88E6060) += mv88e6060.o
--obj-$(CONFIG_NET_DSA_QCA8K)   += qca8k.o
- obj-$(CONFIG_NET_DSA_REALTEK_SMI) += realtek-smi.o
- realtek-smi-objs              := realtek-smi-core.o rtl8366.o rtl8366rb.o
- obj-$(CONFIG_NET_DSA_SMSC_LAN9303) += lan9303-core.o
---- a/drivers/net/dsa/qca/Kconfig
-+++ b/drivers/net/dsa/qca/Kconfig
-@@ -7,3 +7,11 @@ config NET_DSA_AR9331
-       help
-         This enables support for the Qualcomm Atheros AR9331 built-in Ethernet
-         switch.
-+
-+config NET_DSA_QCA8K
-+      tristate "Qualcomm Atheros QCA8K Ethernet switch family support"
-+      select NET_DSA_TAG_QCA
-+      select REGMAP
-+      help
-+        This enables support for the Qualcomm Atheros QCA8K Ethernet
-+        switch chips.
---- a/drivers/net/dsa/qca/Makefile
-+++ b/drivers/net/dsa/qca/Makefile
-@@ -1,2 +1,3 @@
- # SPDX-License-Identifier: GPL-2.0-only
- obj-$(CONFIG_NET_DSA_AR9331)  += ar9331.o
-+obj-$(CONFIG_NET_DSA_QCA8K)   += qca8k.o
---- /dev/null
-+++ b/drivers/net/dsa/qca/qca8k.c
-@@ -0,0 +1,3243 @@
-+// SPDX-License-Identifier: GPL-2.0
-+/*
-+ * Copyright (C) 2009 Felix Fietkau <[email protected]>
-+ * Copyright (C) 2011-2012 Gabor Juhos <[email protected]>
-+ * Copyright (c) 2015, 2019, The Linux Foundation. All rights reserved.
-+ * Copyright (c) 2016 John Crispin <[email protected]>
-+ */
-+
-+#include <linux/module.h>
-+#include <linux/phy.h>
-+#include <linux/netdevice.h>
-+#include <linux/bitfield.h>
-+#include <linux/regmap.h>
-+#include <net/dsa.h>
-+#include <linux/of_net.h>
-+#include <linux/of_mdio.h>
-+#include <linux/of_platform.h>
-+#include <linux/if_bridge.h>
-+#include <linux/mdio.h>
-+#include <linux/phylink.h>
-+#include <linux/gpio/consumer.h>
-+#include <linux/etherdevice.h>
-+#include <linux/dsa/tag_qca.h>
-+
-+#include "qca8k.h"
-+
-+#define MIB_DESC(_s, _o, _n)  \
-+      {                       \
-+              .size = (_s),   \
-+              .offset = (_o), \
-+              .name = (_n),   \
-+      }
-+
-+static const struct qca8k_mib_desc ar8327_mib[] = {
-+      MIB_DESC(1, 0x00, "RxBroad"),
-+      MIB_DESC(1, 0x04, "RxPause"),
-+      MIB_DESC(1, 0x08, "RxMulti"),
-+      MIB_DESC(1, 0x0c, "RxFcsErr"),
-+      MIB_DESC(1, 0x10, "RxAlignErr"),
-+      MIB_DESC(1, 0x14, "RxRunt"),
-+      MIB_DESC(1, 0x18, "RxFragment"),
-+      MIB_DESC(1, 0x1c, "Rx64Byte"),
-+      MIB_DESC(1, 0x20, "Rx128Byte"),
-+      MIB_DESC(1, 0x24, "Rx256Byte"),
-+      MIB_DESC(1, 0x28, "Rx512Byte"),
-+      MIB_DESC(1, 0x2c, "Rx1024Byte"),
-+      MIB_DESC(1, 0x30, "Rx1518Byte"),
-+      MIB_DESC(1, 0x34, "RxMaxByte"),
-+      MIB_DESC(1, 0x38, "RxTooLong"),
-+      MIB_DESC(2, 0x3c, "RxGoodByte"),
-+      MIB_DESC(2, 0x44, "RxBadByte"),
-+      MIB_DESC(1, 0x4c, "RxOverFlow"),
-+      MIB_DESC(1, 0x50, "Filtered"),
-+      MIB_DESC(1, 0x54, "TxBroad"),
-+      MIB_DESC(1, 0x58, "TxPause"),
-+      MIB_DESC(1, 0x5c, "TxMulti"),
-+      MIB_DESC(1, 0x60, "TxUnderRun"),
-+      MIB_DESC(1, 0x64, "Tx64Byte"),
-+      MIB_DESC(1, 0x68, "Tx128Byte"),
-+      MIB_DESC(1, 0x6c, "Tx256Byte"),
-+      MIB_DESC(1, 0x70, "Tx512Byte"),
-+      MIB_DESC(1, 0x74, "Tx1024Byte"),
-+      MIB_DESC(1, 0x78, "Tx1518Byte"),
-+      MIB_DESC(1, 0x7c, "TxMaxByte"),
-+      MIB_DESC(1, 0x80, "TxOverSize"),
-+      MIB_DESC(2, 0x84, "TxByte"),
-+      MIB_DESC(1, 0x8c, "TxCollision"),
-+      MIB_DESC(1, 0x90, "TxAbortCol"),
-+      MIB_DESC(1, 0x94, "TxMultiCol"),
-+      MIB_DESC(1, 0x98, "TxSingleCol"),
-+      MIB_DESC(1, 0x9c, "TxExcDefer"),
-+      MIB_DESC(1, 0xa0, "TxDefer"),
-+      MIB_DESC(1, 0xa4, "TxLateCol"),
-+      MIB_DESC(1, 0xa8, "RXUnicast"),
-+      MIB_DESC(1, 0xac, "TXUnicast"),
-+};
-+
-+static void
-+qca8k_split_addr(u32 regaddr, u16 *r1, u16 *r2, u16 *page)
-+{
-+      regaddr >>= 1;
-+      *r1 = regaddr & 0x1e;
-+
-+      regaddr >>= 5;
-+      *r2 = regaddr & 0x7;
-+
-+      regaddr >>= 3;
-+      *page = regaddr & 0x3ff;
-+}
-+
-+static int
-+qca8k_set_lo(struct qca8k_priv *priv, int phy_id, u32 regnum, u16 lo)
-+{
-+      u16 *cached_lo = &priv->mdio_cache.lo;
-+      struct mii_bus *bus = priv->bus;
-+      int ret;
-+
-+      if (lo == *cached_lo)
-+              return 0;
-+
-+      ret = bus->write(bus, phy_id, regnum, lo);
-+      if (ret < 0)
-+              dev_err_ratelimited(&bus->dev,
-+                                  "failed to write qca8k 32bit lo register\n");
-+
-+      *cached_lo = lo;
-+      return 0;
-+}
-+
-+static int
-+qca8k_set_hi(struct qca8k_priv *priv, int phy_id, u32 regnum, u16 hi)
-+{
-+      u16 *cached_hi = &priv->mdio_cache.hi;
-+      struct mii_bus *bus = priv->bus;
-+      int ret;
-+
-+      if (hi == *cached_hi)
-+              return 0;
-+
-+      ret = bus->write(bus, phy_id, regnum, hi);
-+      if (ret < 0)
-+              dev_err_ratelimited(&bus->dev,
-+                                  "failed to write qca8k 32bit hi register\n");
-+
-+      *cached_hi = hi;
-+      return 0;
-+}
-+
-+static int
-+qca8k_mii_read32(struct mii_bus *bus, int phy_id, u32 regnum, u32 *val)
-+{
-+      int ret;
-+
-+      ret = bus->read(bus, phy_id, regnum);
-+      if (ret >= 0) {
-+              *val = ret;
-+              ret = bus->read(bus, phy_id, regnum + 1);
-+              *val |= ret << 16;
-+      }
-+
-+      if (ret < 0) {
-+              dev_err_ratelimited(&bus->dev,
-+                                  "failed to read qca8k 32bit register\n");
-+              *val = 0;
-+              return ret;
-+      }
-+
-+      return 0;
-+}
-+
-+static void
-+qca8k_mii_write32(struct qca8k_priv *priv, int phy_id, u32 regnum, u32 val)
-+{
-+      u16 lo, hi;
-+      int ret;
-+
-+      lo = val & 0xffff;
-+      hi = (u16)(val >> 16);
-+
-+      ret = qca8k_set_lo(priv, phy_id, regnum, lo);
-+      if (ret >= 0)
-+              ret = qca8k_set_hi(priv, phy_id, regnum + 1, hi);
-+}
-+
-+static int
-+qca8k_set_page(struct qca8k_priv *priv, u16 page)
-+{
-+      u16 *cached_page = &priv->mdio_cache.page;
-+      struct mii_bus *bus = priv->bus;
-+      int ret;
-+
-+      if (page == *cached_page)
-+              return 0;
-+
-+      ret = bus->write(bus, 0x18, 0, page);
-+      if (ret < 0) {
-+              dev_err_ratelimited(&bus->dev,
-+                                  "failed to set qca8k page\n");
-+              return ret;
-+      }
-+
-+      *cached_page = page;
-+      usleep_range(1000, 2000);
-+      return 0;
-+}
-+
-+static int
-+qca8k_read(struct qca8k_priv *priv, u32 reg, u32 *val)
-+{
-+      return regmap_read(priv->regmap, reg, val);
-+}
-+
-+static int
-+qca8k_write(struct qca8k_priv *priv, u32 reg, u32 val)
-+{
-+      return regmap_write(priv->regmap, reg, val);
-+}
-+
-+static int
-+qca8k_rmw(struct qca8k_priv *priv, u32 reg, u32 mask, u32 write_val)
-+{
-+      return regmap_update_bits(priv->regmap, reg, mask, write_val);
-+}
-+
-+static void qca8k_rw_reg_ack_handler(struct dsa_switch *ds, struct sk_buff *skb)
-+{
-+      struct qca8k_mgmt_eth_data *mgmt_eth_data;
-+      struct qca8k_priv *priv = ds->priv;
-+      struct qca_mgmt_ethhdr *mgmt_ethhdr;
-+      u8 len, cmd;
-+
-+      mgmt_ethhdr = (struct qca_mgmt_ethhdr *)skb_mac_header(skb);
-+      mgmt_eth_data = &priv->mgmt_eth_data;
-+
-+      cmd = FIELD_GET(QCA_HDR_MGMT_CMD, mgmt_ethhdr->command);
-+      len = FIELD_GET(QCA_HDR_MGMT_LENGTH, mgmt_ethhdr->command);
-+
-+      /* Make sure the seq match the requested packet */
-+      if (mgmt_ethhdr->seq == mgmt_eth_data->seq)
-+              mgmt_eth_data->ack = true;
-+
-+      if (cmd == MDIO_READ) {
-+              mgmt_eth_data->data[0] = mgmt_ethhdr->mdio_data;
-+
-+              /* Get the rest of the 12 byte of data.
-+               * The read/write function will extract the requested data.
-+               */
-+              if (len > QCA_HDR_MGMT_DATA1_LEN)
-+                      memcpy(mgmt_eth_data->data + 1, skb->data,
-+                             QCA_HDR_MGMT_DATA2_LEN);
-+      }
-+
-+      complete(&mgmt_eth_data->rw_done);
-+}
-+
-+static struct sk_buff *qca8k_alloc_mdio_header(enum mdio_cmd cmd, u32 reg, u32 *val,
-+                                             int priority, unsigned int len)
-+{
-+      struct qca_mgmt_ethhdr *mgmt_ethhdr;
-+      unsigned int real_len;
-+      struct sk_buff *skb;
-+      u32 *data2;
-+      u16 hdr;
-+
-+      skb = dev_alloc_skb(QCA_HDR_MGMT_PKT_LEN);
-+      if (!skb)
-+              return NULL;
-+
-+      /* Max value for len reg is 15 (0xf) but the switch actually return 16 byte
-+       * Actually for some reason the steps are:
-+       * 0: nothing
-+       * 1-4: first 4 byte
-+       * 5-6: first 12 byte
-+       * 7-15: all 16 byte
-+       */
-+      if (len == 16)
-+              real_len = 15;
-+      else
-+              real_len = len;
-+
-+      skb_reset_mac_header(skb);
-+      skb_set_network_header(skb, skb->len);
-+
-+      mgmt_ethhdr = skb_push(skb, QCA_HDR_MGMT_HEADER_LEN + QCA_HDR_LEN);
-+
-+      hdr = FIELD_PREP(QCA_HDR_XMIT_VERSION, QCA_HDR_VERSION);
-+      hdr |= FIELD_PREP(QCA_HDR_XMIT_PRIORITY, priority);
-+      hdr |= QCA_HDR_XMIT_FROM_CPU;
-+      hdr |= FIELD_PREP(QCA_HDR_XMIT_DP_BIT, BIT(0));
-+      hdr |= FIELD_PREP(QCA_HDR_XMIT_CONTROL, QCA_HDR_XMIT_TYPE_RW_REG);
-+
-+      mgmt_ethhdr->command = FIELD_PREP(QCA_HDR_MGMT_ADDR, reg);
-+      mgmt_ethhdr->command |= FIELD_PREP(QCA_HDR_MGMT_LENGTH, real_len);
-+      mgmt_ethhdr->command |= FIELD_PREP(QCA_HDR_MGMT_CMD, cmd);
-+      mgmt_ethhdr->command |= FIELD_PREP(QCA_HDR_MGMT_CHECK_CODE,
-+                                         QCA_HDR_MGMT_CHECK_CODE_VAL);
-+
-+      if (cmd == MDIO_WRITE)
-+              mgmt_ethhdr->mdio_data = *val;
-+
-+      mgmt_ethhdr->hdr = htons(hdr);
-+
-+      data2 = skb_put_zero(skb, QCA_HDR_MGMT_DATA2_LEN + QCA_HDR_MGMT_PADDING_LEN);
-+      if (cmd == MDIO_WRITE && len > QCA_HDR_MGMT_DATA1_LEN)
-+              memcpy(data2, val + 1, len - QCA_HDR_MGMT_DATA1_LEN);
-+
-+      return skb;
-+}
-+
-+static void qca8k_mdio_header_fill_seq_num(struct sk_buff *skb, u32 seq_num)
-+{
-+      struct qca_mgmt_ethhdr *mgmt_ethhdr;
-+
-+      mgmt_ethhdr = (struct qca_mgmt_ethhdr *)skb->data;
-+      mgmt_ethhdr->seq = FIELD_PREP(QCA_HDR_MGMT_SEQ_NUM, seq_num);
-+}
-+
-+static int qca8k_read_eth(struct qca8k_priv *priv, u32 reg, u32 *val, int len)
-+{
-+      struct qca8k_mgmt_eth_data *mgmt_eth_data = &priv->mgmt_eth_data;
-+      struct sk_buff *skb;
-+      bool ack;
-+      int ret;
-+
-+      skb = qca8k_alloc_mdio_header(MDIO_READ, reg, NULL,
-+                                    QCA8K_ETHERNET_MDIO_PRIORITY, len);
-+      if (!skb)
-+              return -ENOMEM;
-+
-+      mutex_lock(&mgmt_eth_data->mutex);
-+
-+      /* Check mgmt_master if is operational */
-+      if (!priv->mgmt_master) {
-+              kfree_skb(skb);
-+              mutex_unlock(&mgmt_eth_data->mutex);
-+              return -EINVAL;
-+      }
-+
-+      skb->dev = priv->mgmt_master;
-+
-+      reinit_completion(&mgmt_eth_data->rw_done);
-+
-+      /* Increment seq_num and set it in the mdio pkt */
-+      mgmt_eth_data->seq++;
-+      qca8k_mdio_header_fill_seq_num(skb, mgmt_eth_data->seq);
-+      mgmt_eth_data->ack = false;
-+
-+      dev_queue_xmit(skb);
-+
-+      ret = wait_for_completion_timeout(&mgmt_eth_data->rw_done,
-+                                        msecs_to_jiffies(QCA8K_ETHERNET_TIMEOUT));
-+
-+      *val = mgmt_eth_data->data[0];
-+      if (len > QCA_HDR_MGMT_DATA1_LEN)
-+              memcpy(val + 1, mgmt_eth_data->data + 1, len - QCA_HDR_MGMT_DATA1_LEN);
-+
-+      ack = mgmt_eth_data->ack;
-+
-+      mutex_unlock(&mgmt_eth_data->mutex);
-+
-+      if (ret <= 0)
-+              return -ETIMEDOUT;
-+
-+      if (!ack)
-+              return -EINVAL;
-+
-+      return 0;
-+}
-+
-+static int qca8k_write_eth(struct qca8k_priv *priv, u32 reg, u32 *val, int len)
-+{
-+      struct qca8k_mgmt_eth_data *mgmt_eth_data = &priv->mgmt_eth_data;
-+      struct sk_buff *skb;
-+      bool ack;
-+      int ret;
-+
-+      skb = qca8k_alloc_mdio_header(MDIO_WRITE, reg, val,
-+                                    QCA8K_ETHERNET_MDIO_PRIORITY, len);
-+      if (!skb)
-+              return -ENOMEM;
-+
-+      mutex_lock(&mgmt_eth_data->mutex);
-+
-+      /* Check mgmt_master if is operational */
-+      if (!priv->mgmt_master) {
-+              kfree_skb(skb);
-+              mutex_unlock(&mgmt_eth_data->mutex);
-+              return -EINVAL;
-+      }
-+
-+      skb->dev = priv->mgmt_master;
-+
-+      reinit_completion(&mgmt_eth_data->rw_done);
-+
-+      /* Increment seq_num and set it in the mdio pkt */
-+      mgmt_eth_data->seq++;
-+      qca8k_mdio_header_fill_seq_num(skb, mgmt_eth_data->seq);
-+      mgmt_eth_data->ack = false;
-+
-+      dev_queue_xmit(skb);
-+
-+      ret = wait_for_completion_timeout(&mgmt_eth_data->rw_done,
-+                                        msecs_to_jiffies(QCA8K_ETHERNET_TIMEOUT));
-+
-+      ack = mgmt_eth_data->ack;
-+
-+      mutex_unlock(&mgmt_eth_data->mutex);
-+
-+      if (ret <= 0)
-+              return -ETIMEDOUT;
-+
-+      if (!ack)
-+              return -EINVAL;
-+
-+      return 0;
-+}
-+
-+static int
-+qca8k_regmap_update_bits_eth(struct qca8k_priv *priv, u32 reg, u32 mask, u32 write_val)
-+{
-+      u32 val = 0;
-+      int ret;
-+
-+      ret = qca8k_read_eth(priv, reg, &val, sizeof(val));
-+      if (ret)
-+              return ret;
-+
-+      val &= ~mask;
-+      val |= write_val;
-+
-+      return qca8k_write_eth(priv, reg, &val, sizeof(val));
-+}
-+
-+static int
-+qca8k_bulk_read(struct qca8k_priv *priv, u32 reg, u32 *val, int len)
-+{
-+      int i, count = len / sizeof(u32), ret;
-+
-+      if (priv->mgmt_master && !qca8k_read_eth(priv, reg, val, len))
-+              return 0;
-+
-+      for (i = 0; i < count; i++) {
-+              ret = regmap_read(priv->regmap, reg + (i * 4), val + i);
-+              if (ret < 0)
-+                      return ret;
-+      }
-+
-+      return 0;
-+}
-+
-+static int
-+qca8k_bulk_write(struct qca8k_priv *priv, u32 reg, u32 *val, int len)
-+{
-+      int i, count = len / sizeof(u32), ret;
-+      u32 tmp;
-+
-+      if (priv->mgmt_master && !qca8k_write_eth(priv, reg, val, len))
-+              return 0;
-+
-+      for (i = 0; i < count; i++) {
-+              tmp = val[i];
-+
-+              ret = regmap_write(priv->regmap, reg + (i * 4), tmp);
-+              if (ret < 0)
-+                      return ret;
-+      }
-+
-+      return 0;
-+}
-+
-+static int
-+qca8k_regmap_read(void *ctx, uint32_t reg, uint32_t *val)
-+{
-+      struct qca8k_priv *priv = (struct qca8k_priv *)ctx;
-+      struct mii_bus *bus = priv->bus;
-+      u16 r1, r2, page;
-+      int ret;
-+
-+      if (!qca8k_read_eth(priv, reg, val, sizeof(*val)))
-+              return 0;
-+
-+      qca8k_split_addr(reg, &r1, &r2, &page);
-+
-+      mutex_lock_nested(&bus->mdio_lock, MDIO_MUTEX_NESTED);
-+
-+      ret = qca8k_set_page(priv, page);
-+      if (ret < 0)
-+              goto exit;
-+
-+      ret = qca8k_mii_read32(bus, 0x10 | r2, r1, val);
-+
-+exit:
-+      mutex_unlock(&bus->mdio_lock);
-+      return ret;
-+}
-+
-+static int
-+qca8k_regmap_write(void *ctx, uint32_t reg, uint32_t val)
-+{
-+      struct qca8k_priv *priv = (struct qca8k_priv *)ctx;
-+      struct mii_bus *bus = priv->bus;
-+      u16 r1, r2, page;
-+      int ret;
-+
-+      if (!qca8k_write_eth(priv, reg, &val, sizeof(val)))
-+              return 0;
-+
-+      qca8k_split_addr(reg, &r1, &r2, &page);
-+
-+      mutex_lock_nested(&bus->mdio_lock, MDIO_MUTEX_NESTED);
-+
-+      ret = qca8k_set_page(priv, page);
-+      if (ret < 0)
-+              goto exit;
-+
-+      qca8k_mii_write32(priv, 0x10 | r2, r1, val);
-+
-+exit:
-+      mutex_unlock(&bus->mdio_lock);
-+      return ret;
-+}
-+
-+static int
-+qca8k_regmap_update_bits(void *ctx, uint32_t reg, uint32_t mask, uint32_t write_val)
-+{
-+      struct qca8k_priv *priv = (struct qca8k_priv *)ctx;
-+      struct mii_bus *bus = priv->bus;
-+      u16 r1, r2, page;
-+      u32 val;
-+      int ret;
-+
-+      if (!qca8k_regmap_update_bits_eth(priv, reg, mask, write_val))
-+              return 0;
-+
-+      qca8k_split_addr(reg, &r1, &r2, &page);
-+
-+      mutex_lock_nested(&bus->mdio_lock, MDIO_MUTEX_NESTED);
-+
-+      ret = qca8k_set_page(priv, page);
-+      if (ret < 0)
-+              goto exit;
-+
-+      ret = qca8k_mii_read32(bus, 0x10 | r2, r1, &val);
-+      if (ret < 0)
-+              goto exit;
-+
-+      val &= ~mask;
-+      val |= write_val;
-+      qca8k_mii_write32(priv, 0x10 | r2, r1, val);
-+
-+exit:
-+      mutex_unlock(&bus->mdio_lock);
-+
-+      return ret;
-+}
-+
-+static const struct regmap_range qca8k_readable_ranges[] = {
-+      regmap_reg_range(0x0000, 0x00e4), /* Global control */
-+      regmap_reg_range(0x0100, 0x0168), /* EEE control */
-+      regmap_reg_range(0x0200, 0x0270), /* Parser control */
-+      regmap_reg_range(0x0400, 0x0454), /* ACL */
-+      regmap_reg_range(0x0600, 0x0718), /* Lookup */
-+      regmap_reg_range(0x0800, 0x0b70), /* QM */
-+      regmap_reg_range(0x0c00, 0x0c80), /* PKT */
-+      regmap_reg_range(0x0e00, 0x0e98), /* L3 */
-+      regmap_reg_range(0x1000, 0x10ac), /* MIB - Port0 */
-+      regmap_reg_range(0x1100, 0x11ac), /* MIB - Port1 */
-+      regmap_reg_range(0x1200, 0x12ac), /* MIB - Port2 */
-+      regmap_reg_range(0x1300, 0x13ac), /* MIB - Port3 */
-+      regmap_reg_range(0x1400, 0x14ac), /* MIB - Port4 */
-+      regmap_reg_range(0x1500, 0x15ac), /* MIB - Port5 */
-+      regmap_reg_range(0x1600, 0x16ac), /* MIB - Port6 */
-+
-+};
-+
-+static const struct regmap_access_table qca8k_readable_table = {
-+      .yes_ranges = qca8k_readable_ranges,
-+      .n_yes_ranges = ARRAY_SIZE(qca8k_readable_ranges),
-+};
-+
-+static struct regmap_config qca8k_regmap_config = {
-+      .reg_bits = 16,
-+      .val_bits = 32,
-+      .reg_stride = 4,
-+      .max_register = 0x16ac, /* end MIB - Port6 range */
-+      .reg_read = qca8k_regmap_read,
-+      .reg_write = qca8k_regmap_write,
-+      .reg_update_bits = qca8k_regmap_update_bits,
-+      .rd_table = &qca8k_readable_table,
-+      .disable_locking = true, /* Locking is handled by qca8k read/write */
-+      .cache_type = REGCACHE_NONE, /* Explicitly disable CACHE */
-+};
-+
-+static int
-+qca8k_busy_wait(struct qca8k_priv *priv, u32 reg, u32 mask)
-+{
-+      u32 val;
-+
-+      return regmap_read_poll_timeout(priv->regmap, reg, val, !(val & mask), 0,
-+                                     QCA8K_BUSY_WAIT_TIMEOUT * USEC_PER_MSEC);
-+}
-+
-+static int
-+qca8k_fdb_read(struct qca8k_priv *priv, struct qca8k_fdb *fdb)
-+{
-+      u32 reg[3];
-+      int ret;
-+
-+      /* load the ARL table into an array */
-+      ret = qca8k_bulk_read(priv, QCA8K_REG_ATU_DATA0, reg, sizeof(reg));
-+      if (ret)
-+              return ret;
-+
-+      /* vid - 83:72 */
-+      fdb->vid = FIELD_GET(QCA8K_ATU_VID_MASK, reg[2]);
-+      /* aging - 67:64 */
-+      fdb->aging = FIELD_GET(QCA8K_ATU_STATUS_MASK, reg[2]);
-+      /* portmask - 54:48 */
-+      fdb->port_mask = FIELD_GET(QCA8K_ATU_PORT_MASK, reg[1]);
-+      /* mac - 47:0 */
-+      fdb->mac[0] = FIELD_GET(QCA8K_ATU_ADDR0_MASK, reg[1]);
-+      fdb->mac[1] = FIELD_GET(QCA8K_ATU_ADDR1_MASK, reg[1]);
-+      fdb->mac[2] = FIELD_GET(QCA8K_ATU_ADDR2_MASK, reg[0]);
-+      fdb->mac[3] = FIELD_GET(QCA8K_ATU_ADDR3_MASK, reg[0]);
-+      fdb->mac[4] = FIELD_GET(QCA8K_ATU_ADDR4_MASK, reg[0]);
-+      fdb->mac[5] = FIELD_GET(QCA8K_ATU_ADDR5_MASK, reg[0]);
-+
-+      return 0;
-+}
-+
-+static void
-+qca8k_fdb_write(struct qca8k_priv *priv, u16 vid, u8 port_mask, const u8 *mac,
-+              u8 aging)
-+{
-+      u32 reg[3] = { 0 };
-+
-+      /* vid - 83:72 */
-+      reg[2] = FIELD_PREP(QCA8K_ATU_VID_MASK, vid);
-+      /* aging - 67:64 */
-+      reg[2] |= FIELD_PREP(QCA8K_ATU_STATUS_MASK, aging);
-+      /* portmask - 54:48 */
-+      reg[1] = FIELD_PREP(QCA8K_ATU_PORT_MASK, port_mask);
-+      /* mac - 47:0 */
-+      reg[1] |= FIELD_PREP(QCA8K_ATU_ADDR0_MASK, mac[0]);
-+      reg[1] |= FIELD_PREP(QCA8K_ATU_ADDR1_MASK, mac[1]);
-+      reg[0] |= FIELD_PREP(QCA8K_ATU_ADDR2_MASK, mac[2]);
-+      reg[0] |= FIELD_PREP(QCA8K_ATU_ADDR3_MASK, mac[3]);
-+      reg[0] |= FIELD_PREP(QCA8K_ATU_ADDR4_MASK, mac[4]);
-+      reg[0] |= FIELD_PREP(QCA8K_ATU_ADDR5_MASK, mac[5]);
-+
-+      /* load the array into the ARL table */
-+      qca8k_bulk_write(priv, QCA8K_REG_ATU_DATA0, reg, sizeof(reg));
-+}
-+
-+static int
-+qca8k_fdb_access(struct qca8k_priv *priv, enum qca8k_fdb_cmd cmd, int port)
-+{
-+      u32 reg;
-+      int ret;
-+
-+      /* Set the command and FDB index */
-+      reg = QCA8K_ATU_FUNC_BUSY;
-+      reg |= cmd;
-+      if (port >= 0) {
-+              reg |= QCA8K_ATU_FUNC_PORT_EN;
-+              reg |= FIELD_PREP(QCA8K_ATU_FUNC_PORT_MASK, port);
-+      }
-+
-+      /* Write the function register triggering the table access */
-+      ret = qca8k_write(priv, QCA8K_REG_ATU_FUNC, reg);
-+      if (ret)
-+              return ret;
-+
-+      /* wait for completion */
-+      ret = qca8k_busy_wait(priv, QCA8K_REG_ATU_FUNC, QCA8K_ATU_FUNC_BUSY);
-+      if (ret)
-+              return ret;
-+
-+      /* Check for table full violation when adding an entry */
-+      if (cmd == QCA8K_FDB_LOAD) {
-+              ret = qca8k_read(priv, QCA8K_REG_ATU_FUNC, &reg);
-+              if (ret < 0)
-+                      return ret;
-+              if (reg & QCA8K_ATU_FUNC_FULL)
-+                      return -1;
-+      }
-+
-+      return 0;
-+}
-+
-+static int
-+qca8k_fdb_next(struct qca8k_priv *priv, struct qca8k_fdb *fdb, int port)
-+{
-+      int ret;
-+
-+      qca8k_fdb_write(priv, fdb->vid, fdb->port_mask, fdb->mac, fdb->aging);
-+      ret = qca8k_fdb_access(priv, QCA8K_FDB_NEXT, port);
-+      if (ret < 0)
-+              return ret;
-+
-+      return qca8k_fdb_read(priv, fdb);
-+}
-+
-+static int
-+qca8k_fdb_add(struct qca8k_priv *priv, const u8 *mac, u16 port_mask,
-+            u16 vid, u8 aging)
-+{
-+      int ret;
-+
-+      mutex_lock(&priv->reg_mutex);
-+      qca8k_fdb_write(priv, vid, port_mask, mac, aging);
-+      ret = qca8k_fdb_access(priv, QCA8K_FDB_LOAD, -1);
-+      mutex_unlock(&priv->reg_mutex);
-+
-+      return ret;
-+}
-+
-+static int
-+qca8k_fdb_del(struct qca8k_priv *priv, const u8 *mac, u16 port_mask, u16 vid)
-+{
-+      int ret;
-+
-+      mutex_lock(&priv->reg_mutex);
-+      qca8k_fdb_write(priv, vid, port_mask, mac, 0);
-+      ret = qca8k_fdb_access(priv, QCA8K_FDB_PURGE, -1);
-+      mutex_unlock(&priv->reg_mutex);
-+
-+      return ret;
-+}
-+
-+static void
-+qca8k_fdb_flush(struct qca8k_priv *priv)
-+{
-+      mutex_lock(&priv->reg_mutex);
-+      qca8k_fdb_access(priv, QCA8K_FDB_FLUSH, -1);
-+      mutex_unlock(&priv->reg_mutex);
-+}
-+
-+static int
-+qca8k_fdb_search_and_insert(struct qca8k_priv *priv, u8 port_mask,
-+                          const u8 *mac, u16 vid)
-+{
-+      struct qca8k_fdb fdb = { 0 };
-+      int ret;
-+
-+      mutex_lock(&priv->reg_mutex);
-+
-+      qca8k_fdb_write(priv, vid, 0, mac, 0);
-+      ret = qca8k_fdb_access(priv, QCA8K_FDB_SEARCH, -1);
-+      if (ret < 0)
-+              goto exit;
-+
-+      ret = qca8k_fdb_read(priv, &fdb);
-+      if (ret < 0)
-+              goto exit;
-+
-+      /* Rule exist. Delete first */
-+      if (!fdb.aging) {
-+              ret = qca8k_fdb_access(priv, QCA8K_FDB_PURGE, -1);
-+              if (ret)
-+                      goto exit;
-+      }
-+
-+      /* Add port to fdb portmask */
-+      fdb.port_mask |= port_mask;
-+
-+      qca8k_fdb_write(priv, vid, fdb.port_mask, mac, fdb.aging);
-+      ret = qca8k_fdb_access(priv, QCA8K_FDB_LOAD, -1);
-+
-+exit:
-+      mutex_unlock(&priv->reg_mutex);
-+      return ret;
-+}
-+
-+static int
-+qca8k_fdb_search_and_del(struct qca8k_priv *priv, u8 port_mask,
-+                       const u8 *mac, u16 vid)
-+{
-+      struct qca8k_fdb fdb = { 0 };
-+      int ret;
-+
-+      mutex_lock(&priv->reg_mutex);
-+
-+      qca8k_fdb_write(priv, vid, 0, mac, 0);
-+      ret = qca8k_fdb_access(priv, QCA8K_FDB_SEARCH, -1);
-+      if (ret < 0)
-+              goto exit;
-+
-+      /* Rule doesn't exist. Why delete? */
-+      if (!fdb.aging) {
-+              ret = -EINVAL;
-+              goto exit;
-+      }
-+
-+      ret = qca8k_fdb_access(priv, QCA8K_FDB_PURGE, -1);
-+      if (ret)
-+              goto exit;
-+
-+      /* Only port in the rule is this port. Don't re insert */
-+      if (fdb.port_mask == port_mask)
-+              goto exit;
-+
-+      /* Remove port from port mask */
-+      fdb.port_mask &= ~port_mask;
-+
-+      qca8k_fdb_write(priv, vid, fdb.port_mask, mac, fdb.aging);
-+      ret = qca8k_fdb_access(priv, QCA8K_FDB_LOAD, -1);
-+
-+exit:
-+      mutex_unlock(&priv->reg_mutex);
-+      return ret;
-+}
-+
-+static int
-+qca8k_vlan_access(struct qca8k_priv *priv, enum qca8k_vlan_cmd cmd, u16 vid)
-+{
-+      u32 reg;
-+      int ret;
-+
-+      /* Set the command and VLAN index */
-+      reg = QCA8K_VTU_FUNC1_BUSY;
-+      reg |= cmd;
-+      reg |= FIELD_PREP(QCA8K_VTU_FUNC1_VID_MASK, vid);
-+
-+      /* Write the function register triggering the table access */
-+      ret = qca8k_write(priv, QCA8K_REG_VTU_FUNC1, reg);
-+      if (ret)
-+              return ret;
-+
-+      /* wait for completion */
-+      ret = qca8k_busy_wait(priv, QCA8K_REG_VTU_FUNC1, QCA8K_VTU_FUNC1_BUSY);
-+      if (ret)
-+              return ret;
-+
-+      /* Check for table full violation when adding an entry */
-+      if (cmd == QCA8K_VLAN_LOAD) {
-+              ret = qca8k_read(priv, QCA8K_REG_VTU_FUNC1, &reg);
-+              if (ret < 0)
-+                      return ret;
-+              if (reg & QCA8K_VTU_FUNC1_FULL)
-+                      return -ENOMEM;
-+      }
-+
-+      return 0;
-+}
-+
-+static int
-+qca8k_vlan_add(struct qca8k_priv *priv, u8 port, u16 vid, bool untagged)
-+{
-+      u32 reg;
-+      int ret;
-+
-+      /*
-+         We do the right thing with VLAN 0 and treat it as untagged while
-+         preserving the tag on egress.
-+       */
-+      if (vid == 0)
-+              return 0;
-+
-+      mutex_lock(&priv->reg_mutex);
-+      ret = qca8k_vlan_access(priv, QCA8K_VLAN_READ, vid);
-+      if (ret < 0)
-+              goto out;
-+
-+      ret = qca8k_read(priv, QCA8K_REG_VTU_FUNC0, &reg);
-+      if (ret < 0)
-+              goto out;
-+      reg |= QCA8K_VTU_FUNC0_VALID | QCA8K_VTU_FUNC0_IVL_EN;
-+      reg &= ~QCA8K_VTU_FUNC0_EG_MODE_PORT_MASK(port);
-+      if (untagged)
-+              reg |= QCA8K_VTU_FUNC0_EG_MODE_PORT_UNTAG(port);
-+      else
-+              reg |= QCA8K_VTU_FUNC0_EG_MODE_PORT_TAG(port);
-+
-+      ret = qca8k_write(priv, QCA8K_REG_VTU_FUNC0, reg);
-+      if (ret)
-+              goto out;
-+      ret = qca8k_vlan_access(priv, QCA8K_VLAN_LOAD, vid);
-+
-+out:
-+      mutex_unlock(&priv->reg_mutex);
-+
-+      return ret;
-+}
-+
-+static int
-+qca8k_vlan_del(struct qca8k_priv *priv, u8 port, u16 vid)
-+{
-+      u32 reg, mask;
-+      int ret, i;
-+      bool del;
-+
-+      mutex_lock(&priv->reg_mutex);
-+      ret = qca8k_vlan_access(priv, QCA8K_VLAN_READ, vid);
-+      if (ret < 0)
-+              goto out;
-+
-+      ret = qca8k_read(priv, QCA8K_REG_VTU_FUNC0, &reg);
-+      if (ret < 0)
-+              goto out;
-+      reg &= ~QCA8K_VTU_FUNC0_EG_MODE_PORT_MASK(port);
-+      reg |= QCA8K_VTU_FUNC0_EG_MODE_PORT_NOT(port);
-+
-+      /* Check if we're the last member to be removed */
-+      del = true;
-+      for (i = 0; i < QCA8K_NUM_PORTS; i++) {
-+              mask = QCA8K_VTU_FUNC0_EG_MODE_PORT_NOT(i);
-+
-+              if ((reg & mask) != mask) {
-+                      del = false;
-+                      break;
-+              }
-+      }
-+
-+      if (del) {
-+              ret = qca8k_vlan_access(priv, QCA8K_VLAN_PURGE, vid);
-+      } else {
-+              ret = qca8k_write(priv, QCA8K_REG_VTU_FUNC0, reg);
-+              if (ret)
-+                      goto out;
-+              ret = qca8k_vlan_access(priv, QCA8K_VLAN_LOAD, vid);
-+      }
-+
-+out:
-+      mutex_unlock(&priv->reg_mutex);
-+
-+      return ret;
-+}
-+
-+static int
-+qca8k_mib_init(struct qca8k_priv *priv)
-+{
-+      int ret;
-+
-+      mutex_lock(&priv->reg_mutex);
-+      ret = regmap_update_bits(priv->regmap, QCA8K_REG_MIB,
-+                               QCA8K_MIB_FUNC | QCA8K_MIB_BUSY,
-+                               FIELD_PREP(QCA8K_MIB_FUNC, QCA8K_MIB_FLUSH) |
-+                               QCA8K_MIB_BUSY);
-+      if (ret)
-+              goto exit;
-+
-+      ret = qca8k_busy_wait(priv, QCA8K_REG_MIB, QCA8K_MIB_BUSY);
-+      if (ret)
-+              goto exit;
-+
-+      ret = regmap_set_bits(priv->regmap, QCA8K_REG_MIB, QCA8K_MIB_CPU_KEEP);
-+      if (ret)
-+              goto exit;
-+
-+      ret = qca8k_write(priv, QCA8K_REG_MODULE_EN, QCA8K_MODULE_EN_MIB);
-+
-+exit:
-+      mutex_unlock(&priv->reg_mutex);
-+      return ret;
-+}
-+
-+static void
-+qca8k_port_set_status(struct qca8k_priv *priv, int port, int enable)
-+{
-+      u32 mask = QCA8K_PORT_STATUS_TXMAC | QCA8K_PORT_STATUS_RXMAC;
-+
-+      /* Port 0 and 6 have no internal PHY */
-+      if (port > 0 && port < 6)
-+              mask |= QCA8K_PORT_STATUS_LINK_AUTO;
-+
-+      if (enable)
-+              regmap_set_bits(priv->regmap, QCA8K_REG_PORT_STATUS(port), mask);
-+      else
-+              regmap_clear_bits(priv->regmap, QCA8K_REG_PORT_STATUS(port), mask);
-+}
-+
-+static int
-+qca8k_phy_eth_busy_wait(struct qca8k_mgmt_eth_data *mgmt_eth_data,
-+                      struct sk_buff *read_skb, u32 *val)
-+{
-+      struct sk_buff *skb = skb_copy(read_skb, GFP_KERNEL);
-+      bool ack;
-+      int ret;
-+
-+      reinit_completion(&mgmt_eth_data->rw_done);
-+
-+      /* Increment seq_num and set it in the copy pkt */
-+      mgmt_eth_data->seq++;
-+      qca8k_mdio_header_fill_seq_num(skb, mgmt_eth_data->seq);
-+      mgmt_eth_data->ack = false;
-+
-+      dev_queue_xmit(skb);
-+
-+      ret = wait_for_completion_timeout(&mgmt_eth_data->rw_done,
-+                                        QCA8K_ETHERNET_TIMEOUT);
-+
-+      ack = mgmt_eth_data->ack;
-+
-+      if (ret <= 0)
-+              return -ETIMEDOUT;
-+
-+      if (!ack)
-+              return -EINVAL;
-+
-+      *val = mgmt_eth_data->data[0];
-+
-+      return 0;
-+}
-+
-+static int
-+qca8k_phy_eth_command(struct qca8k_priv *priv, bool read, int phy,
-+                    int regnum, u16 data)
-+{
-+      struct sk_buff *write_skb, *clear_skb, *read_skb;
-+      struct qca8k_mgmt_eth_data *mgmt_eth_data;
-+      u32 write_val, clear_val = 0, val;
-+      struct net_device *mgmt_master;
-+      int ret, ret1;
-+      bool ack;
-+
-+      if (regnum >= QCA8K_MDIO_MASTER_MAX_REG)
-+              return -EINVAL;
-+
-+      mgmt_eth_data = &priv->mgmt_eth_data;
-+
-+      write_val = QCA8K_MDIO_MASTER_BUSY | QCA8K_MDIO_MASTER_EN |
-+                  QCA8K_MDIO_MASTER_PHY_ADDR(phy) |
-+                  QCA8K_MDIO_MASTER_REG_ADDR(regnum);
-+
-+      if (read) {
-+              write_val |= QCA8K_MDIO_MASTER_READ;
-+      } else {
-+              write_val |= QCA8K_MDIO_MASTER_WRITE;
-+              write_val |= QCA8K_MDIO_MASTER_DATA(data);
-+      }
-+
-+      /* Prealloc all the needed skb before the lock */
-+      write_skb = qca8k_alloc_mdio_header(MDIO_WRITE, QCA8K_MDIO_MASTER_CTRL, &write_val,
-+                                          QCA8K_ETHERNET_PHY_PRIORITY, sizeof(write_val));
-+      if (!write_skb)
-+              return -ENOMEM;
-+
-+      clear_skb = qca8k_alloc_mdio_header(MDIO_WRITE, QCA8K_MDIO_MASTER_CTRL, &clear_val,
-+                                          QCA8K_ETHERNET_PHY_PRIORITY, sizeof(clear_val));
-+      if (!clear_skb) {
-+              ret = -ENOMEM;
-+              goto err_clear_skb;
-+      }
-+
-+      read_skb = qca8k_alloc_mdio_header(MDIO_READ, QCA8K_MDIO_MASTER_CTRL, &clear_val,
-+                                         QCA8K_ETHERNET_PHY_PRIORITY, sizeof(clear_val));
-+      if (!read_skb) {
-+              ret = -ENOMEM;
-+              goto err_read_skb;
-+      }
-+
-+      /* Actually start the request:
-+       * 1. Send mdio master packet
-+       * 2. Busy Wait for mdio master command
-+       * 3. Get the data if we are reading
-+       * 4. Reset the mdio master (even with error)
-+       */
-+      mutex_lock(&mgmt_eth_data->mutex);
-+
-+      /* Check if mgmt_master is operational */
-+      mgmt_master = priv->mgmt_master;
-+      if (!mgmt_master) {
-+              mutex_unlock(&mgmt_eth_data->mutex);
-+              ret = -EINVAL;
-+              goto err_mgmt_master;
-+      }
-+
-+      read_skb->dev = mgmt_master;
-+      clear_skb->dev = mgmt_master;
-+      write_skb->dev = mgmt_master;
-+
-+      reinit_completion(&mgmt_eth_data->rw_done);
-+
-+      /* Increment seq_num and set it in the write pkt */
-+      mgmt_eth_data->seq++;
-+      qca8k_mdio_header_fill_seq_num(write_skb, mgmt_eth_data->seq);
-+      mgmt_eth_data->ack = false;
-+
-+      dev_queue_xmit(write_skb);
-+
-+      ret = wait_for_completion_timeout(&mgmt_eth_data->rw_done,
-+                                        QCA8K_ETHERNET_TIMEOUT);
-+
-+      ack = mgmt_eth_data->ack;
-+
-+      if (ret <= 0) {
-+              ret = -ETIMEDOUT;
-+              kfree_skb(read_skb);
-+              goto exit;
-+      }
-+
-+      if (!ack) {
-+              ret = -EINVAL;
-+              kfree_skb(read_skb);
-+              goto exit;
-+      }
-+
-+      ret = read_poll_timeout(qca8k_phy_eth_busy_wait, ret1,
-+                              !(val & QCA8K_MDIO_MASTER_BUSY), 0,
-+                              QCA8K_BUSY_WAIT_TIMEOUT * USEC_PER_MSEC, false,
-+                              mgmt_eth_data, read_skb, &val);
-+
-+      if (ret < 0 && ret1 < 0) {
-+              ret = ret1;
-+              goto exit;
-+      }
-+
-+      if (read) {
-+              reinit_completion(&mgmt_eth_data->rw_done);
-+
-+              /* Increment seq_num and set it in the read pkt */
-+              mgmt_eth_data->seq++;
-+              qca8k_mdio_header_fill_seq_num(read_skb, mgmt_eth_data->seq);
-+              mgmt_eth_data->ack = false;
-+
-+              dev_queue_xmit(read_skb);
-+
-+              ret = wait_for_completion_timeout(&mgmt_eth_data->rw_done,
-+                                                QCA8K_ETHERNET_TIMEOUT);
-+
-+              ack = mgmt_eth_data->ack;
-+
-+              if (ret <= 0) {
-+                      ret = -ETIMEDOUT;
-+                      goto exit;
-+              }
-+
-+              if (!ack) {
-+                      ret = -EINVAL;
-+                      goto exit;
-+              }
-+
-+              ret = mgmt_eth_data->data[0] & QCA8K_MDIO_MASTER_DATA_MASK;
-+      } else {
-+              kfree_skb(read_skb);
-+      }
-+exit:
-+      reinit_completion(&mgmt_eth_data->rw_done);
-+
-+      /* Increment seq_num and set it in the clear pkt */
-+      mgmt_eth_data->seq++;
-+      qca8k_mdio_header_fill_seq_num(clear_skb, mgmt_eth_data->seq);
-+      mgmt_eth_data->ack = false;
-+
-+      dev_queue_xmit(clear_skb);
-+
-+      wait_for_completion_timeout(&mgmt_eth_data->rw_done,
-+                                  QCA8K_ETHERNET_TIMEOUT);
-+
-+      mutex_unlock(&mgmt_eth_data->mutex);
-+
-+      return ret;
-+
-+      /* Error handling before lock */
-+err_mgmt_master:
-+      kfree_skb(read_skb);
-+err_read_skb:
-+      kfree_skb(clear_skb);
-+err_clear_skb:
-+      kfree_skb(write_skb);
-+
-+      return ret;
-+}
-+
-+static u32
-+qca8k_port_to_phy(int port)
-+{
-+      /* From Andrew Lunn:
-+       * Port 0 has no internal phy.
-+       * Port 1 has an internal PHY at MDIO address 0.
-+       * Port 2 has an internal PHY at MDIO address 1.
-+       * ...
-+       * Port 5 has an internal PHY at MDIO address 4.
-+       * Port 6 has no internal PHY.
-+       */
-+
-+      return port - 1;
-+}
-+
-+static int
-+qca8k_mdio_busy_wait(struct mii_bus *bus, u32 reg, u32 mask)
-+{
-+      u16 r1, r2, page;
-+      u32 val;
-+      int ret, ret1;
-+
-+      qca8k_split_addr(reg, &r1, &r2, &page);
-+
-+      ret = read_poll_timeout(qca8k_mii_read32, ret1, !(val & mask), 0,
-+                              QCA8K_BUSY_WAIT_TIMEOUT * USEC_PER_MSEC, false,
-+                              bus, 0x10 | r2, r1, &val);
-+
-+      /* Check if qca8k_read has failed for a different reason
-+       * before returnting -ETIMEDOUT
-+       */
-+      if (ret < 0 && ret1 < 0)
-+              return ret1;
-+
-+      return ret;
-+}
-+
-+static int
-+qca8k_mdio_write(struct qca8k_priv *priv, int phy, int regnum, u16 data)
-+{
-+      struct mii_bus *bus = priv->bus;
-+      u16 r1, r2, page;
-+      u32 val;
-+      int ret;
-+
-+      if (regnum >= QCA8K_MDIO_MASTER_MAX_REG)
-+              return -EINVAL;
-+
-+      val = QCA8K_MDIO_MASTER_BUSY | QCA8K_MDIO_MASTER_EN |
-+            QCA8K_MDIO_MASTER_WRITE | QCA8K_MDIO_MASTER_PHY_ADDR(phy) |
-+            QCA8K_MDIO_MASTER_REG_ADDR(regnum) |
-+            QCA8K_MDIO_MASTER_DATA(data);
-+
-+      qca8k_split_addr(QCA8K_MDIO_MASTER_CTRL, &r1, &r2, &page);
-+
-+      mutex_lock_nested(&bus->mdio_lock, MDIO_MUTEX_NESTED);
-+
-+      ret = qca8k_set_page(priv, page);
-+      if (ret)
-+              goto exit;
-+
-+      qca8k_mii_write32(priv, 0x10 | r2, r1, val);
-+
-+      ret = qca8k_mdio_busy_wait(bus, QCA8K_MDIO_MASTER_CTRL,
-+                                 QCA8K_MDIO_MASTER_BUSY);
-+
-+exit:
-+      /* even if the busy_wait timeouts try to clear the MASTER_EN */
-+      qca8k_mii_write32(priv, 0x10 | r2, r1, 0);
-+
-+      mutex_unlock(&bus->mdio_lock);
-+
-+      return ret;
-+}
-+
-+static int
-+qca8k_mdio_read(struct qca8k_priv *priv, int phy, int regnum)
-+{
-+      struct mii_bus *bus = priv->bus;
-+      u16 r1, r2, page;
-+      u32 val;
-+      int ret;
-+
-+      if (regnum >= QCA8K_MDIO_MASTER_MAX_REG)
-+              return -EINVAL;
-+
-+      val = QCA8K_MDIO_MASTER_BUSY | QCA8K_MDIO_MASTER_EN |
-+            QCA8K_MDIO_MASTER_READ | QCA8K_MDIO_MASTER_PHY_ADDR(phy) |
-+            QCA8K_MDIO_MASTER_REG_ADDR(regnum);
-+
-+      qca8k_split_addr(QCA8K_MDIO_MASTER_CTRL, &r1, &r2, &page);
-+
-+      mutex_lock_nested(&bus->mdio_lock, MDIO_MUTEX_NESTED);
-+
-+      ret = qca8k_set_page(priv, page);
-+      if (ret)
-+              goto exit;
-+
-+      qca8k_mii_write32(priv, 0x10 | r2, r1, val);
-+
-+      ret = qca8k_mdio_busy_wait(bus, QCA8K_MDIO_MASTER_CTRL,
-+                                 QCA8K_MDIO_MASTER_BUSY);
-+      if (ret)
-+              goto exit;
-+
-+      ret = qca8k_mii_read32(bus, 0x10 | r2, r1, &val);
-+
-+exit:
-+      /* even if the busy_wait timeouts try to clear the MASTER_EN */
-+      qca8k_mii_write32(priv, 0x10 | r2, r1, 0);
-+
-+      mutex_unlock(&bus->mdio_lock);
-+
-+      if (ret >= 0)
-+              ret = val & QCA8K_MDIO_MASTER_DATA_MASK;
-+
-+      return ret;
-+}
-+
-+static int
-+qca8k_internal_mdio_write(struct mii_bus *slave_bus, int phy, int regnum, u16 data)
-+{
-+      struct qca8k_priv *priv = slave_bus->priv;
-+      int ret;
-+
-+      /* Use mdio Ethernet when available, fallback to legacy one on error */
-+      ret = qca8k_phy_eth_command(priv, false, phy, regnum, data);
-+      if (!ret)
-+              return 0;
-+
-+      return qca8k_mdio_write(priv, phy, regnum, data);
-+}
-+
-+static int
-+qca8k_internal_mdio_read(struct mii_bus *slave_bus, int phy, int regnum)
-+{
-+      struct qca8k_priv *priv = slave_bus->priv;
-+      int ret;
-+
-+      /* Use mdio Ethernet when available, fallback to legacy one on error */
-+      ret = qca8k_phy_eth_command(priv, true, phy, regnum, 0);
-+      if (ret >= 0)
-+              return ret;
-+
-+      ret = qca8k_mdio_read(priv, phy, regnum);
-+
-+      if (ret < 0)
-+              return 0xffff;
-+
-+      return ret;
-+}
-+
-+static int
-+qca8k_legacy_mdio_write(struct mii_bus *slave_bus, int port, int regnum, u16 data)
-+{
-+      port = qca8k_port_to_phy(port) % PHY_MAX_ADDR;
-+
-+      return qca8k_internal_mdio_write(slave_bus, port, regnum, data);
-+}
-+
-+static int
-+qca8k_legacy_mdio_read(struct mii_bus *slave_bus, int port, int regnum)
-+{
-+      port = qca8k_port_to_phy(port) % PHY_MAX_ADDR;
-+
-+      return qca8k_internal_mdio_read(slave_bus, port, regnum);
-+}
-+
-+static int
-+qca8k_mdio_register(struct qca8k_priv *priv)
-+{
-+      struct dsa_switch *ds = priv->ds;
-+      struct device_node *mdio;
-+      struct mii_bus *bus;
-+
-+      bus = devm_mdiobus_alloc(ds->dev);
-+      if (!bus)
-+              return -ENOMEM;
-+
-+      bus->priv = (void *)priv;
-+      snprintf(bus->id, MII_BUS_ID_SIZE, "qca8k-%d.%d",
-+               ds->dst->index, ds->index);
-+      bus->parent = ds->dev;
-+      bus->phy_mask = ~ds->phys_mii_mask;
-+      ds->slave_mii_bus = bus;
-+
-+      /* Check if the devicetree declare the port:phy mapping */
-+      mdio = of_get_child_by_name(priv->dev->of_node, "mdio");
-+      if (of_device_is_available(mdio)) {
-+              bus->name = "qca8k slave mii";
-+              bus->read = qca8k_internal_mdio_read;
-+              bus->write = qca8k_internal_mdio_write;
-+              return devm_of_mdiobus_register(priv->dev, bus, mdio);
-+      }
-+
-+      /* If a mapping can't be found the legacy mapping is used,
-+       * using the qca8k_port_to_phy function
-+       */
-+      bus->name = "qca8k-legacy slave mii";
-+      bus->read = qca8k_legacy_mdio_read;
-+      bus->write = qca8k_legacy_mdio_write;
-+      return devm_mdiobus_register(priv->dev, bus);
-+}
-+
-+static int
-+qca8k_setup_mdio_bus(struct qca8k_priv *priv)
-+{
-+      u32 internal_mdio_mask = 0, external_mdio_mask = 0, reg;
-+      struct device_node *ports, *port;
-+      phy_interface_t mode;
-+      int err;
-+
-+      ports = of_get_child_by_name(priv->dev->of_node, "ports");
-+      if (!ports)
-+              ports = of_get_child_by_name(priv->dev->of_node, "ethernet-ports");
-+
-+      if (!ports)
-+              return -EINVAL;
-+
-+      for_each_available_child_of_node(ports, port) {
-+              err = of_property_read_u32(port, "reg", &reg);
-+              if (err) {
-+                      of_node_put(port);
-+                      of_node_put(ports);
-+                      return err;
-+              }
-+
-+              if (!dsa_is_user_port(priv->ds, reg))
-+                      continue;
-+
-+              of_get_phy_mode(port, &mode);
-+
-+              if (of_property_read_bool(port, "phy-handle") &&
-+                  mode != PHY_INTERFACE_MODE_INTERNAL)
-+                      external_mdio_mask |= BIT(reg);
-+              else
-+                      internal_mdio_mask |= BIT(reg);
-+      }
-+
-+      of_node_put(ports);
-+      if (!external_mdio_mask && !internal_mdio_mask) {
-+              dev_err(priv->dev, "no PHYs are defined.\n");
-+              return -EINVAL;
-+      }
-+
-+      /* The QCA8K_MDIO_MASTER_EN Bit, which grants access to PHYs through
-+       * the MDIO_MASTER register also _disconnects_ the external MDC
-+       * passthrough to the internal PHYs. It's not possible to use both
-+       * configurations at the same time!
-+       *
-+       * Because this came up during the review process:
-+       * If the external mdio-bus driver is capable magically disabling
-+       * the QCA8K_MDIO_MASTER_EN and mutex/spin-locking out the qca8k's
-+       * accessors for the time being, it would be possible to pull this
-+       * off.
-+       */
-+      if (!!external_mdio_mask && !!internal_mdio_mask) {
-+              dev_err(priv->dev, "either internal or external mdio bus configuration is supported.\n");
-+              return -EINVAL;
-+      }
-+
-+      if (external_mdio_mask) {
-+              /* Make sure to disable the internal mdio bus in cases
-+               * a dt-overlay and driver reload changed the configuration
-+               */
-+
-+              return regmap_clear_bits(priv->regmap, QCA8K_MDIO_MASTER_CTRL,
-+                                       QCA8K_MDIO_MASTER_EN);
-+      }
-+
-+      return qca8k_mdio_register(priv);
-+}
-+
-+static int
-+qca8k_setup_mac_pwr_sel(struct qca8k_priv *priv)
-+{
-+      u32 mask = 0;
-+      int ret = 0;
-+
-+      /* SoC specific settings for ipq8064.
-+       * If more device require this consider adding
-+       * a dedicated binding.
-+       */
-+      if (of_machine_is_compatible("qcom,ipq8064"))
-+              mask |= QCA8K_MAC_PWR_RGMII0_1_8V;
-+
-+      /* SoC specific settings for ipq8065 */
-+      if (of_machine_is_compatible("qcom,ipq8065"))
-+              mask |= QCA8K_MAC_PWR_RGMII1_1_8V;
-+
-+      if (mask) {
-+              ret = qca8k_rmw(priv, QCA8K_REG_MAC_PWR_SEL,
-+                              QCA8K_MAC_PWR_RGMII0_1_8V |
-+                              QCA8K_MAC_PWR_RGMII1_1_8V,
-+                              mask);
-+      }
-+
-+      return ret;
-+}
-+
-+static int qca8k_find_cpu_port(struct dsa_switch *ds)
-+{
-+      struct qca8k_priv *priv = ds->priv;
-+
-+      /* Find the connected cpu port. Valid port are 0 or 6 */
-+      if (dsa_is_cpu_port(ds, 0))
-+              return 0;
-+
-+      dev_dbg(priv->dev, "port 0 is not the CPU port. Checking port 6");
-+
-+      if (dsa_is_cpu_port(ds, 6))
-+              return 6;
-+
-+      return -EINVAL;
-+}
-+
-+static int
-+qca8k_setup_of_pws_reg(struct qca8k_priv *priv)
-+{
-+      struct device_node *node = priv->dev->of_node;
-+      const struct qca8k_match_data *data;
-+      u32 val = 0;
-+      int ret;
-+
-+      /* QCA8327 require to set to the correct mode.
-+       * His bigger brother QCA8328 have the 172 pin layout.
-+       * Should be applied by default but we set this just to make sure.
-+       */
-+      if (priv->switch_id == QCA8K_ID_QCA8327) {
-+              data = of_device_get_match_data(priv->dev);
-+
-+              /* Set the correct package of 148 pin for QCA8327 */
-+              if (data->reduced_package)
-+                      val |= QCA8327_PWS_PACKAGE148_EN;
-+
-+              ret = qca8k_rmw(priv, QCA8K_REG_PWS, QCA8327_PWS_PACKAGE148_EN,
-+                              val);
-+              if (ret)
-+                      return ret;
-+      }
-+
-+      if (of_property_read_bool(node, "qca,ignore-power-on-sel"))
-+              val |= QCA8K_PWS_POWER_ON_SEL;
-+
-+      if (of_property_read_bool(node, "qca,led-open-drain")) {
-+              if (!(val & QCA8K_PWS_POWER_ON_SEL)) {
-+                      dev_err(priv->dev, "qca,led-open-drain require qca,ignore-power-on-sel to be set.");
-+                      return -EINVAL;
-+              }
-+
-+              val |= QCA8K_PWS_LED_OPEN_EN_CSR;
-+      }
-+
-+      return qca8k_rmw(priv, QCA8K_REG_PWS,
-+                      QCA8K_PWS_LED_OPEN_EN_CSR | QCA8K_PWS_POWER_ON_SEL,
-+                      val);
-+}
-+
-+static int
-+qca8k_parse_port_config(struct qca8k_priv *priv)
-+{
-+      int port, cpu_port_index = -1, ret;
-+      struct device_node *port_dn;
-+      phy_interface_t mode;
-+      struct dsa_port *dp;
-+      u32 delay;
-+
-+      /* We have 2 CPU port. Check them */
-+      for (port = 0; port < QCA8K_NUM_PORTS; port++) {
-+              /* Skip every other port */
-+              if (port != 0 && port != 6)
-+                      continue;
-+
-+              dp = dsa_to_port(priv->ds, port);
-+              port_dn = dp->dn;
-+              cpu_port_index++;
-+
-+              if (!of_device_is_available(port_dn))
-+                      continue;
-+
-+              ret = of_get_phy_mode(port_dn, &mode);
-+              if (ret)
-+                      continue;
-+
-+              switch (mode) {
-+              case PHY_INTERFACE_MODE_RGMII:
-+              case PHY_INTERFACE_MODE_RGMII_ID:
-+              case PHY_INTERFACE_MODE_RGMII_TXID:
-+              case PHY_INTERFACE_MODE_RGMII_RXID:
-+              case PHY_INTERFACE_MODE_SGMII:
-+                      delay = 0;
-+
-+                      if (!of_property_read_u32(port_dn, "tx-internal-delay-ps", &delay))
-+                              /* Switch regs accept value in ns, convert ps to ns */
-+                              delay = delay / 1000;
-+                      else if (mode == PHY_INTERFACE_MODE_RGMII_ID ||
-+                               mode == PHY_INTERFACE_MODE_RGMII_TXID)
-+                              delay = 1;
-+
-+                      if (!FIELD_FIT(QCA8K_PORT_PAD_RGMII_TX_DELAY_MASK, delay)) {
-+                              dev_err(priv->dev, "rgmii tx delay is limited to a max value of 3ns, setting to the max value");
-+                              delay = 3;
-+                      }
-+
-+                      priv->ports_config.rgmii_tx_delay[cpu_port_index] = delay;
-+
-+                      delay = 0;
-+
-+                      if (!of_property_read_u32(port_dn, "rx-internal-delay-ps", &delay))
-+                              /* Switch regs accept value in ns, convert ps to ns */
-+                              delay = delay / 1000;
-+                      else if (mode == PHY_INTERFACE_MODE_RGMII_ID ||
-+                               mode == PHY_INTERFACE_MODE_RGMII_RXID)
-+                              delay = 2;
-+
-+                      if (!FIELD_FIT(QCA8K_PORT_PAD_RGMII_RX_DELAY_MASK, delay)) {
-+                              dev_err(priv->dev, "rgmii rx delay is limited to a max value of 3ns, setting to the max value");
-+                              delay = 3;
-+                      }
-+
-+                      priv->ports_config.rgmii_rx_delay[cpu_port_index] = delay;
-+
-+                      /* Skip sgmii parsing for rgmii* mode */
-+                      if (mode == PHY_INTERFACE_MODE_RGMII ||
-+                          mode == PHY_INTERFACE_MODE_RGMII_ID ||
-+                          mode == PHY_INTERFACE_MODE_RGMII_TXID ||
-+                          mode == PHY_INTERFACE_MODE_RGMII_RXID)
-+                              break;
-+
-+                      if (of_property_read_bool(port_dn, "qca,sgmii-txclk-falling-edge"))
-+                              priv->ports_config.sgmii_tx_clk_falling_edge = true;
-+
-+                      if (of_property_read_bool(port_dn, "qca,sgmii-rxclk-falling-edge"))
-+                              priv->ports_config.sgmii_rx_clk_falling_edge = true;
-+
-+                      if (of_property_read_bool(port_dn, "qca,sgmii-enable-pll")) {
-+                              priv->ports_config.sgmii_enable_pll = true;
-+
-+                              if (priv->switch_id == QCA8K_ID_QCA8327) {
-+                                      dev_err(priv->dev, "SGMII PLL should NOT be enabled for qca8327. Aborting enabling");
-+                                      priv->ports_config.sgmii_enable_pll = false;
-+                              }
-+
-+                              if (priv->switch_revision < 2)
-+                                      dev_warn(priv->dev, "SGMII PLL should NOT be enabled for qca8337 with revision 2 or more.");
-+                      }
-+
-+                      break;
-+              default:
-+                      continue;
-+              }
-+      }
-+
-+      return 0;
-+}
-+
-+static int
-+qca8k_setup(struct dsa_switch *ds)
-+{
-+      struct qca8k_priv *priv = (struct qca8k_priv *)ds->priv;
-+      int cpu_port, ret, i;
-+      u32 mask;
-+
-+      cpu_port = qca8k_find_cpu_port(ds);
-+      if (cpu_port < 0) {
-+              dev_err(priv->dev, "No cpu port configured in both cpu port0 and port6");
-+              return cpu_port;
-+      }
-+
-+      /* Parse CPU port config to be later used in phy_link mac_config */
-+      ret = qca8k_parse_port_config(priv);
-+      if (ret)
-+              return ret;
-+
-+      ret = qca8k_setup_mdio_bus(priv);
-+      if (ret)
-+              return ret;
-+
-+      ret = qca8k_setup_of_pws_reg(priv);
-+      if (ret)
-+              return ret;
-+
-+      ret = qca8k_setup_mac_pwr_sel(priv);
-+      if (ret)
-+              return ret;
-+
-+      /* Make sure MAC06 is disabled */
-+      ret = regmap_clear_bits(priv->regmap, QCA8K_REG_PORT0_PAD_CTRL,
-+                              QCA8K_PORT0_PAD_MAC06_EXCHANGE_EN);
-+      if (ret) {
-+              dev_err(priv->dev, "failed disabling MAC06 exchange");
-+              return ret;
-+      }
-+
-+      /* Enable CPU Port */
-+      ret = regmap_set_bits(priv->regmap, QCA8K_REG_GLOBAL_FW_CTRL0,
-+                            QCA8K_GLOBAL_FW_CTRL0_CPU_PORT_EN);
-+      if (ret) {
-+              dev_err(priv->dev, "failed enabling CPU port");
-+              return ret;
-+      }
-+
-+      /* Enable MIB counters */
-+      ret = qca8k_mib_init(priv);
-+      if (ret)
-+              dev_warn(priv->dev, "mib init failed");
-+
-+      /* Initial setup of all ports */
-+      for (i = 0; i < QCA8K_NUM_PORTS; i++) {
-+              /* Disable forwarding by default on all ports */
-+              ret = qca8k_rmw(priv, QCA8K_PORT_LOOKUP_CTRL(i),
-+                              QCA8K_PORT_LOOKUP_MEMBER, 0);
-+              if (ret)
-+                      return ret;
-+
-+              /* Enable QCA header mode on all cpu ports */
-+              if (dsa_is_cpu_port(ds, i)) {
-+                      ret = qca8k_write(priv, QCA8K_REG_PORT_HDR_CTRL(i),
-+                                        FIELD_PREP(QCA8K_PORT_HDR_CTRL_TX_MASK, QCA8K_PORT_HDR_CTRL_ALL) |
-+                                        FIELD_PREP(QCA8K_PORT_HDR_CTRL_RX_MASK, QCA8K_PORT_HDR_CTRL_ALL));
-+                      if (ret) {
-+                              dev_err(priv->dev, "failed enabling QCA header mode");
-+                              return ret;
-+                      }
-+              }
-+
-+              /* Disable MAC by default on all user ports */
-+              if (dsa_is_user_port(ds, i))
-+                      qca8k_port_set_status(priv, i, 0);
-+      }
-+
-+      /* Forward all unknown frames to CPU port for Linux processing
-+       * Notice that in multi-cpu config only one port should be set
-+       * for igmp, unknown, multicast and broadcast packet
-+       */
-+      ret = qca8k_write(priv, QCA8K_REG_GLOBAL_FW_CTRL1,
-+                        FIELD_PREP(QCA8K_GLOBAL_FW_CTRL1_IGMP_DP_MASK, BIT(cpu_port)) |
-+                        FIELD_PREP(QCA8K_GLOBAL_FW_CTRL1_BC_DP_MASK, BIT(cpu_port)) |
-+                        FIELD_PREP(QCA8K_GLOBAL_FW_CTRL1_MC_DP_MASK, BIT(cpu_port)) |
-+                        FIELD_PREP(QCA8K_GLOBAL_FW_CTRL1_UC_DP_MASK, BIT(cpu_port)));
-+      if (ret)
-+              return ret;
-+
-+      /* Setup connection between CPU port & user ports
-+       * Configure specific switch configuration for ports
-+       */
-+      for (i = 0; i < QCA8K_NUM_PORTS; i++) {
-+              /* CPU port gets connected to all user ports of the switch */
-+              if (dsa_is_cpu_port(ds, i)) {
-+                      ret = qca8k_rmw(priv, QCA8K_PORT_LOOKUP_CTRL(i),
-+                                      QCA8K_PORT_LOOKUP_MEMBER, dsa_user_ports(ds));
-+                      if (ret)
-+                              return ret;
-+              }
-+
-+              /* Individual user ports get connected to CPU port only */
-+              if (dsa_is_user_port(ds, i)) {
-+                      ret = qca8k_rmw(priv, QCA8K_PORT_LOOKUP_CTRL(i),
-+                                      QCA8K_PORT_LOOKUP_MEMBER,
-+                                      BIT(cpu_port));
-+                      if (ret)
-+                              return ret;
-+
-+                      /* Enable ARP Auto-learning by default */
-+                      ret = regmap_set_bits(priv->regmap, QCA8K_PORT_LOOKUP_CTRL(i),
-+                                            QCA8K_PORT_LOOKUP_LEARN);
-+                      if (ret)
-+                              return ret;
-+
-+                      /* For port based vlans to work we need to set the
-+                       * default egress vid
-+                       */
-+                      ret = qca8k_rmw(priv, QCA8K_EGRESS_VLAN(i),
-+                                      QCA8K_EGREES_VLAN_PORT_MASK(i),
-+                                      QCA8K_EGREES_VLAN_PORT(i, QCA8K_PORT_VID_DEF));
-+                      if (ret)
-+                              return ret;
-+
-+                      ret = qca8k_write(priv, QCA8K_REG_PORT_VLAN_CTRL0(i),
-+                                        QCA8K_PORT_VLAN_CVID(QCA8K_PORT_VID_DEF) |
-+                                        QCA8K_PORT_VLAN_SVID(QCA8K_PORT_VID_DEF));
-+                      if (ret)
-+                              return ret;
-+              }
-+
-+              /* The port 5 of the qca8337 have some problem in flood condition. The
-+               * original legacy driver had some specific buffer and priority settings
-+               * for the different port suggested by the QCA switch team. Add this
-+               * missing settings to improve switch stability under load condition.
-+               * This problem is limited to qca8337 and other qca8k switch are not affected.
-+               */
-+              if (priv->switch_id == QCA8K_ID_QCA8337) {
-+                      switch (i) {
-+                      /* The 2 CPU port and port 5 requires some different
-+                       * priority than any other ports.
-+                       */
-+                      case 0:
-+                      case 5:
-+                      case 6:
-+                              mask = QCA8K_PORT_HOL_CTRL0_EG_PRI0(0x3) |
-+                                      QCA8K_PORT_HOL_CTRL0_EG_PRI1(0x4) |
-+                                      QCA8K_PORT_HOL_CTRL0_EG_PRI2(0x4) |
-+                                      QCA8K_PORT_HOL_CTRL0_EG_PRI3(0x4) |
-+                                      QCA8K_PORT_HOL_CTRL0_EG_PRI4(0x6) |
-+                                      QCA8K_PORT_HOL_CTRL0_EG_PRI5(0x8) |
-+                                      QCA8K_PORT_HOL_CTRL0_EG_PORT(0x1e);
-+                              break;
-+                      default:
-+                              mask = QCA8K_PORT_HOL_CTRL0_EG_PRI0(0x3) |
-+                                      QCA8K_PORT_HOL_CTRL0_EG_PRI1(0x4) |
-+                                      QCA8K_PORT_HOL_CTRL0_EG_PRI2(0x6) |
-+                                      QCA8K_PORT_HOL_CTRL0_EG_PRI3(0x8) |
-+                                      QCA8K_PORT_HOL_CTRL0_EG_PORT(0x19);
-+                      }
-+                      qca8k_write(priv, QCA8K_REG_PORT_HOL_CTRL0(i), mask);
-+
-+                      mask = QCA8K_PORT_HOL_CTRL1_ING(0x6) |
-+                      QCA8K_PORT_HOL_CTRL1_EG_PRI_BUF_EN |
-+                      QCA8K_PORT_HOL_CTRL1_EG_PORT_BUF_EN |
-+                      QCA8K_PORT_HOL_CTRL1_WRED_EN;
-+                      qca8k_rmw(priv, QCA8K_REG_PORT_HOL_CTRL1(i),
-+                                QCA8K_PORT_HOL_CTRL1_ING_BUF_MASK |
-+                                QCA8K_PORT_HOL_CTRL1_EG_PRI_BUF_EN |
-+                                QCA8K_PORT_HOL_CTRL1_EG_PORT_BUF_EN |
-+                                QCA8K_PORT_HOL_CTRL1_WRED_EN,
-+                                mask);
-+              }
-+      }
-+
-+      /* Special GLOBAL_FC_THRESH value are needed for ar8327 switch */
-+      if (priv->switch_id == QCA8K_ID_QCA8327) {
-+              mask = QCA8K_GLOBAL_FC_GOL_XON_THRES(288) |
-+                     QCA8K_GLOBAL_FC_GOL_XOFF_THRES(496);
-+              qca8k_rmw(priv, QCA8K_REG_GLOBAL_FC_THRESH,
-+                        QCA8K_GLOBAL_FC_GOL_XON_THRES_MASK |
-+                        QCA8K_GLOBAL_FC_GOL_XOFF_THRES_MASK,
-+                        mask);
-+      }
-+
-+      /* Setup our port MTUs to match power on defaults */
-+      ret = qca8k_write(priv, QCA8K_MAX_FRAME_SIZE, ETH_FRAME_LEN + ETH_FCS_LEN);
-+      if (ret)
-+              dev_warn(priv->dev, "failed setting MTU settings");
-+
-+      /* Flush the FDB table */
-+      qca8k_fdb_flush(priv);
-+
-+      /* We don't have interrupts for link changes, so we need to poll */
-+      ds->pcs_poll = true;
-+
-+      /* Set min a max ageing value supported */
-+      ds->ageing_time_min = 7000;
-+      ds->ageing_time_max = 458745000;
-+
-+      /* Set max number of LAGs supported */
-+      ds->num_lag_ids = QCA8K_NUM_LAGS;
-+
-+      return 0;
-+}
-+
-+static void
-+qca8k_mac_config_setup_internal_delay(struct qca8k_priv *priv, int cpu_port_index,
-+                                    u32 reg)
-+{
-+      u32 delay, val = 0;
-+      int ret;
-+
-+      /* Delay can be declared in 3 different way.
-+       * Mode to rgmii and internal-delay standard binding defined
-+       * rgmii-id or rgmii-tx/rx phy mode set.
-+       * The parse logic set a delay different than 0 only when one
-+       * of the 3 different way is used. In all other case delay is
-+       * not enabled. With ID or TX/RXID delay is enabled and set
-+       * to the default and recommended value.
-+       */
-+      if (priv->ports_config.rgmii_tx_delay[cpu_port_index]) {
-+              delay = priv->ports_config.rgmii_tx_delay[cpu_port_index];
-+
-+              val |= QCA8K_PORT_PAD_RGMII_TX_DELAY(delay) |
-+                      QCA8K_PORT_PAD_RGMII_TX_DELAY_EN;
-+      }
-+
-+      if (priv->ports_config.rgmii_rx_delay[cpu_port_index]) {
-+              delay = priv->ports_config.rgmii_rx_delay[cpu_port_index];
-+
-+              val |= QCA8K_PORT_PAD_RGMII_RX_DELAY(delay) |
-+                      QCA8K_PORT_PAD_RGMII_RX_DELAY_EN;
-+      }
-+
-+      /* Set RGMII delay based on the selected values */
-+      ret = qca8k_rmw(priv, reg,
-+                      QCA8K_PORT_PAD_RGMII_TX_DELAY_MASK |
-+                      QCA8K_PORT_PAD_RGMII_RX_DELAY_MASK |
-+                      QCA8K_PORT_PAD_RGMII_TX_DELAY_EN |
-+                      QCA8K_PORT_PAD_RGMII_RX_DELAY_EN,
-+                      val);
-+      if (ret)
-+              dev_err(priv->dev, "Failed to set internal delay for CPU port%d",
-+                      cpu_port_index == QCA8K_CPU_PORT0 ? 0 : 6);
-+}
-+
-+static void
-+qca8k_phylink_mac_config(struct dsa_switch *ds, int port, unsigned int mode,
-+                       const struct phylink_link_state *state)
-+{
-+      struct qca8k_priv *priv = ds->priv;
-+      int cpu_port_index, ret;
-+      u32 reg, val;
-+
-+      switch (port) {
-+      case 0: /* 1st CPU port */
-+              if (state->interface != PHY_INTERFACE_MODE_RGMII &&
-+                  state->interface != PHY_INTERFACE_MODE_RGMII_ID &&
-+                  state->interface != PHY_INTERFACE_MODE_RGMII_TXID &&
-+                  state->interface != PHY_INTERFACE_MODE_RGMII_RXID &&
-+                  state->interface != PHY_INTERFACE_MODE_SGMII)
-+                      return;
-+
-+              reg = QCA8K_REG_PORT0_PAD_CTRL;
-+              cpu_port_index = QCA8K_CPU_PORT0;
-+              break;
-+      case 1:
-+      case 2:
-+      case 3:
-+      case 4:
-+      case 5:
-+              /* Internal PHY, nothing to do */
-+              return;
-+      case 6: /* 2nd CPU port / external PHY */
-+              if (state->interface != PHY_INTERFACE_MODE_RGMII &&
-+                  state->interface != PHY_INTERFACE_MODE_RGMII_ID &&
-+                  state->interface != PHY_INTERFACE_MODE_RGMII_TXID &&
-+                  state->interface != PHY_INTERFACE_MODE_RGMII_RXID &&
-+                  state->interface != PHY_INTERFACE_MODE_SGMII &&
-+                  state->interface != PHY_INTERFACE_MODE_1000BASEX)
-+                      return;
-+
-+              reg = QCA8K_REG_PORT6_PAD_CTRL;
-+              cpu_port_index = QCA8K_CPU_PORT6;
-+              break;
-+      default:
-+              dev_err(ds->dev, "%s: unsupported port: %i\n", __func__, port);
-+              return;
-+      }
-+
-+      if (port != 6 && phylink_autoneg_inband(mode)) {
-+              dev_err(ds->dev, "%s: in-band negotiation unsupported\n",
-+                      __func__);
-+              return;
-+      }
-+
-+      switch (state->interface) {
-+      case PHY_INTERFACE_MODE_RGMII:
-+      case PHY_INTERFACE_MODE_RGMII_ID:
-+      case PHY_INTERFACE_MODE_RGMII_TXID:
-+      case PHY_INTERFACE_MODE_RGMII_RXID:
-+              qca8k_write(priv, reg, QCA8K_PORT_PAD_RGMII_EN);
-+
-+              /* Configure rgmii delay */
-+              qca8k_mac_config_setup_internal_delay(priv, cpu_port_index, reg);
-+
-+              /* QCA8337 requires to set rgmii rx delay for all ports.
-+               * This is enabled through PORT5_PAD_CTRL for all ports,
-+               * rather than individual port registers.
-+               */
-+              if (priv->switch_id == QCA8K_ID_QCA8337)
-+                      qca8k_write(priv, QCA8K_REG_PORT5_PAD_CTRL,
-+                                  QCA8K_PORT_PAD_RGMII_RX_DELAY_EN);
-+              break;
-+      case PHY_INTERFACE_MODE_SGMII:
-+      case PHY_INTERFACE_MODE_1000BASEX:
-+              /* Enable SGMII on the port */
-+              qca8k_write(priv, reg, QCA8K_PORT_PAD_SGMII_EN);
-+
-+              /* Enable/disable SerDes auto-negotiation as necessary */
-+              ret = qca8k_read(priv, QCA8K_REG_PWS, &val);
-+              if (ret)
-+                      return;
-+              if (phylink_autoneg_inband(mode))
-+                      val &= ~QCA8K_PWS_SERDES_AEN_DIS;
-+              else
-+                      val |= QCA8K_PWS_SERDES_AEN_DIS;
-+              qca8k_write(priv, QCA8K_REG_PWS, val);
-+
-+              /* Configure the SGMII parameters */
-+              ret = qca8k_read(priv, QCA8K_REG_SGMII_CTRL, &val);
-+              if (ret)
-+                      return;
-+
-+              val |= QCA8K_SGMII_EN_SD;
-+
-+              if (priv->ports_config.sgmii_enable_pll)
-+                      val |= QCA8K_SGMII_EN_PLL | QCA8K_SGMII_EN_RX |
-+                             QCA8K_SGMII_EN_TX;
-+
-+              if (dsa_is_cpu_port(ds, port)) {
-+                      /* CPU port, we're talking to the CPU MAC, be a PHY */
-+                      val &= ~QCA8K_SGMII_MODE_CTRL_MASK;
-+                      val |= QCA8K_SGMII_MODE_CTRL_PHY;
-+              } else if (state->interface == PHY_INTERFACE_MODE_SGMII) {
-+                      val &= ~QCA8K_SGMII_MODE_CTRL_MASK;
-+                      val |= QCA8K_SGMII_MODE_CTRL_MAC;
-+              } else if (state->interface == PHY_INTERFACE_MODE_1000BASEX) {
-+                      val &= ~QCA8K_SGMII_MODE_CTRL_MASK;
-+                      val |= QCA8K_SGMII_MODE_CTRL_BASEX;
-+              }
-+
-+              qca8k_write(priv, QCA8K_REG_SGMII_CTRL, val);
-+
-+              /* From original code is reported port instability as SGMII also
-+               * require delay set. Apply advised values here or take them from DT.
-+               */
-+              if (state->interface == PHY_INTERFACE_MODE_SGMII)
-+                      qca8k_mac_config_setup_internal_delay(priv, cpu_port_index, reg);
-+
-+              /* For qca8327/qca8328/qca8334/qca8338 sgmii is unique and
-+               * falling edge is set writing in the PORT0 PAD reg
-+               */
-+              if (priv->switch_id == QCA8K_ID_QCA8327 ||
-+                  priv->switch_id == QCA8K_ID_QCA8337)
-+                      reg = QCA8K_REG_PORT0_PAD_CTRL;
-+
-+              val = 0;
-+
-+              /* SGMII Clock phase configuration */
-+              if (priv->ports_config.sgmii_rx_clk_falling_edge)
-+                      val |= QCA8K_PORT0_PAD_SGMII_RXCLK_FALLING_EDGE;
-+
-+              if (priv->ports_config.sgmii_tx_clk_falling_edge)
-+                      val |= QCA8K_PORT0_PAD_SGMII_TXCLK_FALLING_EDGE;
-+
-+              if (val)
-+                      ret = qca8k_rmw(priv, reg,
-+                                      QCA8K_PORT0_PAD_SGMII_RXCLK_FALLING_EDGE |
-+                                      QCA8K_PORT0_PAD_SGMII_TXCLK_FALLING_EDGE,
-+                                      val);
-+
-+              break;
-+      default:
-+              dev_err(ds->dev, "xMII mode %s not supported for port %d\n",
-+                      phy_modes(state->interface), port);
-+              return;
-+      }
-+}
-+
-+static void
-+qca8k_phylink_validate(struct dsa_switch *ds, int port,
-+                     unsigned long *supported,
-+                     struct phylink_link_state *state)
-+{
-+      __ETHTOOL_DECLARE_LINK_MODE_MASK(mask) = { 0, };
-+
-+      switch (port) {
-+      case 0: /* 1st CPU port */
-+              if (state->interface != PHY_INTERFACE_MODE_NA &&
-+                  state->interface != PHY_INTERFACE_MODE_RGMII &&
-+                  state->interface != PHY_INTERFACE_MODE_RGMII_ID &&
-+                  state->interface != PHY_INTERFACE_MODE_RGMII_TXID &&
-+                  state->interface != PHY_INTERFACE_MODE_RGMII_RXID &&
-+                  state->interface != PHY_INTERFACE_MODE_SGMII)
-+                      goto unsupported;
-+              break;
-+      case 1:
-+      case 2:
-+      case 3:
-+      case 4:
-+      case 5:
-+              /* Internal PHY */
-+              if (state->interface != PHY_INTERFACE_MODE_NA &&
-+                  state->interface != PHY_INTERFACE_MODE_GMII &&
-+                  state->interface != PHY_INTERFACE_MODE_INTERNAL)
-+                      goto unsupported;
-+              break;
-+      case 6: /* 2nd CPU port / external PHY */
-+              if (state->interface != PHY_INTERFACE_MODE_NA &&
-+                  state->interface != PHY_INTERFACE_MODE_RGMII &&
-+                  state->interface != PHY_INTERFACE_MODE_RGMII_ID &&
-+                  state->interface != PHY_INTERFACE_MODE_RGMII_TXID &&
-+                  state->interface != PHY_INTERFACE_MODE_RGMII_RXID &&
-+                  state->interface != PHY_INTERFACE_MODE_SGMII &&
-+                  state->interface != PHY_INTERFACE_MODE_1000BASEX)
-+                      goto unsupported;
-+              break;
-+      default:
-+unsupported:
-+              linkmode_zero(supported);
-+              return;
-+      }
-+
-+      phylink_set_port_modes(mask);
-+      phylink_set(mask, Autoneg);
-+
-+      phylink_set(mask, 1000baseT_Full);
-+      phylink_set(mask, 10baseT_Half);
-+      phylink_set(mask, 10baseT_Full);
-+      phylink_set(mask, 100baseT_Half);
-+      phylink_set(mask, 100baseT_Full);
-+
-+      if (state->interface == PHY_INTERFACE_MODE_1000BASEX)
-+              phylink_set(mask, 1000baseX_Full);
-+
-+      phylink_set(mask, Pause);
-+      phylink_set(mask, Asym_Pause);
-+
-+      linkmode_and(supported, supported, mask);
-+      linkmode_and(state->advertising, state->advertising, mask);
-+}
-+
-+static int
-+qca8k_phylink_mac_link_state(struct dsa_switch *ds, int port,
-+                           struct phylink_link_state *state)
-+{
-+      struct qca8k_priv *priv = ds->priv;
-+      u32 reg;
-+      int ret;
-+
-+      ret = qca8k_read(priv, QCA8K_REG_PORT_STATUS(port), &reg);
-+      if (ret < 0)
-+              return ret;
-+
-+      state->link = !!(reg & QCA8K_PORT_STATUS_LINK_UP);
-+      state->an_complete = state->link;
-+      state->an_enabled = !!(reg & QCA8K_PORT_STATUS_LINK_AUTO);
-+      state->duplex = (reg & QCA8K_PORT_STATUS_DUPLEX) ? DUPLEX_FULL :
-+                                                         DUPLEX_HALF;
-+
-+      switch (reg & QCA8K_PORT_STATUS_SPEED) {
-+      case QCA8K_PORT_STATUS_SPEED_10:
-+              state->speed = SPEED_10;
-+              break;
-+      case QCA8K_PORT_STATUS_SPEED_100:
-+              state->speed = SPEED_100;
-+              break;
-+      case QCA8K_PORT_STATUS_SPEED_1000:
-+              state->speed = SPEED_1000;
-+              break;
-+      default:
-+              state->speed = SPEED_UNKNOWN;
-+              break;
-+      }
-+
-+      state->pause = MLO_PAUSE_NONE;
-+      if (reg & QCA8K_PORT_STATUS_RXFLOW)
-+              state->pause |= MLO_PAUSE_RX;
-+      if (reg & QCA8K_PORT_STATUS_TXFLOW)
-+              state->pause |= MLO_PAUSE_TX;
-+
-+      return 1;
-+}
-+
-+static void
-+qca8k_phylink_mac_link_down(struct dsa_switch *ds, int port, unsigned int mode,
-+                          phy_interface_t interface)
-+{
-+      struct qca8k_priv *priv = ds->priv;
-+
-+      qca8k_port_set_status(priv, port, 0);
-+}
-+
-+static void
-+qca8k_phylink_mac_link_up(struct dsa_switch *ds, int port, unsigned int mode,
-+                        phy_interface_t interface, struct phy_device *phydev,
-+                        int speed, int duplex, bool tx_pause, bool rx_pause)
-+{
-+      struct qca8k_priv *priv = ds->priv;
-+      u32 reg;
-+
-+      if (phylink_autoneg_inband(mode)) {
-+              reg = QCA8K_PORT_STATUS_LINK_AUTO;
-+      } else {
-+              switch (speed) {
-+              case SPEED_10:
-+                      reg = QCA8K_PORT_STATUS_SPEED_10;
-+                      break;
-+              case SPEED_100:
-+                      reg = QCA8K_PORT_STATUS_SPEED_100;
-+                      break;
-+              case SPEED_1000:
-+                      reg = QCA8K_PORT_STATUS_SPEED_1000;
-+                      break;
-+              default:
-+                      reg = QCA8K_PORT_STATUS_LINK_AUTO;
-+                      break;
-+              }
-+
-+              if (duplex == DUPLEX_FULL)
-+                      reg |= QCA8K_PORT_STATUS_DUPLEX;
-+
-+              if (rx_pause || dsa_is_cpu_port(ds, port))
-+                      reg |= QCA8K_PORT_STATUS_RXFLOW;
-+
-+              if (tx_pause || dsa_is_cpu_port(ds, port))
-+                      reg |= QCA8K_PORT_STATUS_TXFLOW;
-+      }
-+
-+      reg |= QCA8K_PORT_STATUS_TXMAC | QCA8K_PORT_STATUS_RXMAC;
-+
-+      qca8k_write(priv, QCA8K_REG_PORT_STATUS(port), reg);
-+}
-+
-+static void
-+qca8k_get_strings(struct dsa_switch *ds, int port, u32 stringset, uint8_t *data)
-+{
-+      const struct qca8k_match_data *match_data;
-+      struct qca8k_priv *priv = ds->priv;
-+      int i;
-+
-+      if (stringset != ETH_SS_STATS)
-+              return;
-+
-+      match_data = of_device_get_match_data(priv->dev);
-+
-+      for (i = 0; i < match_data->mib_count; i++)
-+              strncpy(data + i * ETH_GSTRING_LEN, ar8327_mib[i].name,
-+                      ETH_GSTRING_LEN);
-+}
-+
-+static void qca8k_mib_autocast_handler(struct dsa_switch *ds, struct sk_buff *skb)
-+{
-+      const struct qca8k_match_data *match_data;
-+      struct qca8k_mib_eth_data *mib_eth_data;
-+      struct qca8k_priv *priv = ds->priv;
-+      const struct qca8k_mib_desc *mib;
-+      struct mib_ethhdr *mib_ethhdr;
-+      int i, mib_len, offset = 0;
-+      u64 *data;
-+      u8 port;
-+
-+      mib_ethhdr = (struct mib_ethhdr *)skb_mac_header(skb);
-+      mib_eth_data = &priv->mib_eth_data;
-+
-+      /* The switch autocast every port. Ignore other packet and
-+       * parse only the requested one.
-+       */
-+      port = FIELD_GET(QCA_HDR_RECV_SOURCE_PORT, ntohs(mib_ethhdr->hdr));
-+      if (port != mib_eth_data->req_port)
-+              goto exit;
-+
-+      match_data = device_get_match_data(priv->dev);
-+      data = mib_eth_data->data;
-+
-+      for (i = 0; i < match_data->mib_count; i++) {
-+              mib = &ar8327_mib[i];
-+
-+              /* First 3 mib are present in the skb head */
-+              if (i < 3) {
-+                      data[i] = mib_ethhdr->data[i];
-+                      continue;
-+              }
-+
-+              mib_len = sizeof(uint32_t);
-+
-+              /* Some mib are 64 bit wide */
-+              if (mib->size == 2)
-+                      mib_len = sizeof(uint64_t);
-+
-+              /* Copy the mib value from packet to the */
-+              memcpy(data + i, skb->data + offset, mib_len);
-+
-+              /* Set the offset for the next mib */
-+              offset += mib_len;
-+      }
-+
-+exit:
-+      /* Complete on receiving all the mib packet */
-+      if (refcount_dec_and_test(&mib_eth_data->port_parsed))
-+              complete(&mib_eth_data->rw_done);
-+}
-+
-+static int
-+qca8k_get_ethtool_stats_eth(struct dsa_switch *ds, int port, u64 *data)
-+{
-+      struct dsa_port *dp = dsa_to_port(ds, port);
-+      struct qca8k_mib_eth_data *mib_eth_data;
-+      struct qca8k_priv *priv = ds->priv;
-+      int ret;
-+
-+      mib_eth_data = &priv->mib_eth_data;
-+
-+      mutex_lock(&mib_eth_data->mutex);
-+
-+      reinit_completion(&mib_eth_data->rw_done);
-+
-+      mib_eth_data->req_port = dp->index;
-+      mib_eth_data->data = data;
-+      refcount_set(&mib_eth_data->port_parsed, QCA8K_NUM_PORTS);
-+
-+      mutex_lock(&priv->reg_mutex);
-+
-+      /* Send mib autocast request */
-+      ret = regmap_update_bits(priv->regmap, QCA8K_REG_MIB,
-+                               QCA8K_MIB_FUNC | QCA8K_MIB_BUSY,
-+                               FIELD_PREP(QCA8K_MIB_FUNC, QCA8K_MIB_CAST) |
-+                               QCA8K_MIB_BUSY);
-+
-+      mutex_unlock(&priv->reg_mutex);
-+
-+      if (ret)
-+              goto exit;
-+
-+      ret = wait_for_completion_timeout(&mib_eth_data->rw_done, QCA8K_ETHERNET_TIMEOUT);
-+
-+exit:
-+      mutex_unlock(&mib_eth_data->mutex);
-+
-+      return ret;
-+}
-+
-+static void
-+qca8k_get_ethtool_stats(struct dsa_switch *ds, int port,
-+                      uint64_t *data)
-+{
-+      struct qca8k_priv *priv = (struct qca8k_priv *)ds->priv;
-+      const struct qca8k_match_data *match_data;
-+      const struct qca8k_mib_desc *mib;
-+      u32 reg, i, val;
-+      u32 hi = 0;
-+      int ret;
-+
-+      if (priv->mgmt_master &&
-+          qca8k_get_ethtool_stats_eth(ds, port, data) > 0)
-+              return;
-+
-+      match_data = of_device_get_match_data(priv->dev);
-+
-+      for (i = 0; i < match_data->mib_count; i++) {
-+              mib = &ar8327_mib[i];
-+              reg = QCA8K_PORT_MIB_COUNTER(port) + mib->offset;
-+
-+              ret = qca8k_read(priv, reg, &val);
-+              if (ret < 0)
-+                      continue;
-+
-+              if (mib->size == 2) {
-+                      ret = qca8k_read(priv, reg + 4, &hi);
-+                      if (ret < 0)
-+                              continue;
-+              }
-+
-+              data[i] = val;
-+              if (mib->size == 2)
-+                      data[i] |= (u64)hi << 32;
-+      }
-+}
-+
-+static int
-+qca8k_get_sset_count(struct dsa_switch *ds, int port, int sset)
-+{
-+      const struct qca8k_match_data *match_data;
-+      struct qca8k_priv *priv = ds->priv;
-+
-+      if (sset != ETH_SS_STATS)
-+              return 0;
-+
-+      match_data = of_device_get_match_data(priv->dev);
-+
-+      return match_data->mib_count;
-+}
-+
-+static int
-+qca8k_set_mac_eee(struct dsa_switch *ds, int port, struct ethtool_eee *eee)
-+{
-+      struct qca8k_priv *priv = (struct qca8k_priv *)ds->priv;
-+      u32 lpi_en = QCA8K_REG_EEE_CTRL_LPI_EN(port);
-+      u32 reg;
-+      int ret;
-+
-+      mutex_lock(&priv->reg_mutex);
-+      ret = qca8k_read(priv, QCA8K_REG_EEE_CTRL, &reg);
-+      if (ret < 0)
-+              goto exit;
-+
-+      if (eee->eee_enabled)
-+              reg |= lpi_en;
-+      else
-+              reg &= ~lpi_en;
-+      ret = qca8k_write(priv, QCA8K_REG_EEE_CTRL, reg);
-+
-+exit:
-+      mutex_unlock(&priv->reg_mutex);
-+      return ret;
-+}
-+
-+static int
-+qca8k_get_mac_eee(struct dsa_switch *ds, int port, struct ethtool_eee *e)
-+{
-+      /* Nothing to do on the port's MAC */
-+      return 0;
-+}
-+
-+static void
-+qca8k_port_stp_state_set(struct dsa_switch *ds, int port, u8 state)
-+{
-+      struct qca8k_priv *priv = (struct qca8k_priv *)ds->priv;
-+      u32 stp_state;
-+
-+      switch (state) {
-+      case BR_STATE_DISABLED:
-+              stp_state = QCA8K_PORT_LOOKUP_STATE_DISABLED;
-+              break;
-+      case BR_STATE_BLOCKING:
-+              stp_state = QCA8K_PORT_LOOKUP_STATE_BLOCKING;
-+              break;
-+      case BR_STATE_LISTENING:
-+              stp_state = QCA8K_PORT_LOOKUP_STATE_LISTENING;
-+              break;
-+      case BR_STATE_LEARNING:
-+              stp_state = QCA8K_PORT_LOOKUP_STATE_LEARNING;
-+              break;
-+      case BR_STATE_FORWARDING:
-+      default:
-+              stp_state = QCA8K_PORT_LOOKUP_STATE_FORWARD;
-+              break;
-+      }
-+
-+      qca8k_rmw(priv, QCA8K_PORT_LOOKUP_CTRL(port),
-+                QCA8K_PORT_LOOKUP_STATE_MASK, stp_state);
-+}
-+
-+static int
-+qca8k_port_bridge_join(struct dsa_switch *ds, int port, struct net_device *br)
-+{
-+      struct qca8k_priv *priv = (struct qca8k_priv *)ds->priv;
-+      int port_mask, cpu_port;
-+      int i, ret;
-+
-+      cpu_port = dsa_to_port(ds, port)->cpu_dp->index;
-+      port_mask = BIT(cpu_port);
-+
-+      for (i = 0; i < QCA8K_NUM_PORTS; i++) {
-+              if (dsa_is_cpu_port(ds, i))
-+                      continue;
-+              if (dsa_to_port(ds, i)->bridge_dev != br)
-+                      continue;
-+              /* Add this port to the portvlan mask of the other ports
-+               * in the bridge
-+               */
-+              ret = regmap_set_bits(priv->regmap,
-+                                    QCA8K_PORT_LOOKUP_CTRL(i),
-+                                    BIT(port));
-+              if (ret)
-+                      return ret;
-+              if (i != port)
-+                      port_mask |= BIT(i);
-+      }
-+
-+      /* Add all other ports to this ports portvlan mask */
-+      ret = qca8k_rmw(priv, QCA8K_PORT_LOOKUP_CTRL(port),
-+                      QCA8K_PORT_LOOKUP_MEMBER, port_mask);
-+
-+      return ret;
-+}
-+
-+static void
-+qca8k_port_bridge_leave(struct dsa_switch *ds, int port, struct net_device *br)
-+{
-+      struct qca8k_priv *priv = (struct qca8k_priv *)ds->priv;
-+      int cpu_port, i;
-+
-+      cpu_port = dsa_to_port(ds, port)->cpu_dp->index;
-+
-+      for (i = 0; i < QCA8K_NUM_PORTS; i++) {
-+              if (dsa_is_cpu_port(ds, i))
-+                      continue;
-+              if (dsa_to_port(ds, i)->bridge_dev != br)
-+                      continue;
-+              /* Remove this port to the portvlan mask of the other ports
-+               * in the bridge
-+               */
-+              regmap_clear_bits(priv->regmap,
-+                                QCA8K_PORT_LOOKUP_CTRL(i),
-+                                BIT(port));
-+      }
-+
-+      /* Set the cpu port to be the only one in the portvlan mask of
-+       * this port
-+       */
-+      qca8k_rmw(priv, QCA8K_PORT_LOOKUP_CTRL(port),
-+                QCA8K_PORT_LOOKUP_MEMBER, BIT(cpu_port));
-+}
-+
-+static void
-+qca8k_port_fast_age(struct dsa_switch *ds, int port)
-+{
-+      struct qca8k_priv *priv = ds->priv;
-+
-+      mutex_lock(&priv->reg_mutex);
-+      qca8k_fdb_access(priv, QCA8K_FDB_FLUSH_PORT, port);
-+      mutex_unlock(&priv->reg_mutex);
-+}
-+
-+static int
-+qca8k_set_ageing_time(struct dsa_switch *ds, unsigned int msecs)
-+{
-+      struct qca8k_priv *priv = ds->priv;
-+      unsigned int secs = msecs / 1000;
-+      u32 val;
-+
-+      /* AGE_TIME reg is set in 7s step */
-+      val = secs / 7;
-+
-+      /* Handle case with 0 as val to NOT disable
-+       * learning
-+       */
-+      if (!val)
-+              val = 1;
-+
-+      return regmap_update_bits(priv->regmap, QCA8K_REG_ATU_CTRL, QCA8K_ATU_AGE_TIME_MASK,
-+                                QCA8K_ATU_AGE_TIME(val));
-+}
-+
-+static int
-+qca8k_port_enable(struct dsa_switch *ds, int port,
-+                struct phy_device *phy)
-+{
-+      struct qca8k_priv *priv = (struct qca8k_priv *)ds->priv;
-+
-+      qca8k_port_set_status(priv, port, 1);
-+      priv->port_enabled_map |= BIT(port);
-+
-+      if (dsa_is_user_port(ds, port))
-+              phy_support_asym_pause(phy);
-+
-+      return 0;
-+}
-+
-+static void
-+qca8k_port_disable(struct dsa_switch *ds, int port)
-+{
-+      struct qca8k_priv *priv = (struct qca8k_priv *)ds->priv;
-+
-+      qca8k_port_set_status(priv, port, 0);
-+      priv->port_enabled_map &= ~BIT(port);
-+}
-+
-+static int
-+qca8k_port_change_mtu(struct dsa_switch *ds, int port, int new_mtu)
-+{
-+      struct qca8k_priv *priv = ds->priv;
-+      int ret;
-+
-+      /* We have only have a general MTU setting.
-+       * DSA always set the CPU port's MTU to the largest MTU of the slave
-+       * ports.
-+       * Setting MTU just for the CPU port is sufficient to correctly set a
-+       * value for every port.
-+       */
-+      if (!dsa_is_cpu_port(ds, port))
-+              return 0;
-+
-+      /* To change the MAX_FRAME_SIZE the cpu ports must be off or
-+       * the switch panics.
-+       * Turn off both cpu ports before applying the new value to prevent
-+       * this.
-+       */
-+      if (priv->port_enabled_map & BIT(0))
-+              qca8k_port_set_status(priv, 0, 0);
-+
-+      if (priv->port_enabled_map & BIT(6))
-+              qca8k_port_set_status(priv, 6, 0);
-+
-+      /* Include L2 header / FCS length */
-+      ret = qca8k_write(priv, QCA8K_MAX_FRAME_SIZE, new_mtu + ETH_HLEN + ETH_FCS_LEN);
-+
-+      if (priv->port_enabled_map & BIT(0))
-+              qca8k_port_set_status(priv, 0, 1);
-+
-+      if (priv->port_enabled_map & BIT(6))
-+              qca8k_port_set_status(priv, 6, 1);
-+
-+      return ret;
-+}
-+
-+static int
-+qca8k_port_max_mtu(struct dsa_switch *ds, int port)
-+{
-+      return QCA8K_MAX_MTU;
-+}
-+
-+static int
-+qca8k_port_fdb_insert(struct qca8k_priv *priv, const u8 *addr,
-+                    u16 port_mask, u16 vid)
-+{
-+      /* Set the vid to the port vlan id if no vid is set */
-+      if (!vid)
-+              vid = QCA8K_PORT_VID_DEF;
-+
-+      return qca8k_fdb_add(priv, addr, port_mask, vid,
-+                           QCA8K_ATU_STATUS_STATIC);
-+}
-+
-+static int
-+qca8k_port_fdb_add(struct dsa_switch *ds, int port,
-+                 const unsigned char *addr, u16 vid)
-+{
-+      struct qca8k_priv *priv = (struct qca8k_priv *)ds->priv;
-+      u16 port_mask = BIT(port);
-+
-+      return qca8k_port_fdb_insert(priv, addr, port_mask, vid);
-+}
-+
-+static int
-+qca8k_port_fdb_del(struct dsa_switch *ds, int port,
-+                 const unsigned char *addr, u16 vid)
-+{
-+      struct qca8k_priv *priv = (struct qca8k_priv *)ds->priv;
-+      u16 port_mask = BIT(port);
-+
-+      if (!vid)
-+              vid = QCA8K_PORT_VID_DEF;
-+
-+      return qca8k_fdb_del(priv, addr, port_mask, vid);
-+}
-+
-+static int
-+qca8k_port_fdb_dump(struct dsa_switch *ds, int port,
-+                  dsa_fdb_dump_cb_t *cb, void *data)
-+{
-+      struct qca8k_priv *priv = (struct qca8k_priv *)ds->priv;
-+      struct qca8k_fdb _fdb = { 0 };
-+      int cnt = QCA8K_NUM_FDB_RECORDS;
-+      bool is_static;
-+      int ret = 0;
-+
-+      mutex_lock(&priv->reg_mutex);
-+      while (cnt-- && !qca8k_fdb_next(priv, &_fdb, port)) {
-+              if (!_fdb.aging)
-+                      break;
-+              is_static = (_fdb.aging == QCA8K_ATU_STATUS_STATIC);
-+              ret = cb(_fdb.mac, _fdb.vid, is_static, data);
-+              if (ret)
-+                      break;
-+      }
-+      mutex_unlock(&priv->reg_mutex);
-+
-+      return 0;
-+}
-+
-+static int
-+qca8k_port_mdb_add(struct dsa_switch *ds, int port,
-+                 const struct switchdev_obj_port_mdb *mdb)
-+{
-+      struct qca8k_priv *priv = ds->priv;
-+      const u8 *addr = mdb->addr;
-+      u16 vid = mdb->vid;
-+
-+      return qca8k_fdb_search_and_insert(priv, BIT(port), addr, vid);
-+}
-+
-+static int
-+qca8k_port_mdb_del(struct dsa_switch *ds, int port,
-+                 const struct switchdev_obj_port_mdb *mdb)
-+{
-+      struct qca8k_priv *priv = ds->priv;
-+      const u8 *addr = mdb->addr;
-+      u16 vid = mdb->vid;
-+
-+      return qca8k_fdb_search_and_del(priv, BIT(port), addr, vid);
-+}
-+
-+static int
-+qca8k_port_mirror_add(struct dsa_switch *ds, int port,
-+                    struct dsa_mall_mirror_tc_entry *mirror,
-+                    bool ingress)
-+{
-+      struct qca8k_priv *priv = ds->priv;
-+      int monitor_port, ret;
-+      u32 reg, val;
-+
-+      /* Check for existent entry */
-+      if ((ingress ? priv->mirror_rx : priv->mirror_tx) & BIT(port))
-+              return -EEXIST;
-+
-+      ret = regmap_read(priv->regmap, QCA8K_REG_GLOBAL_FW_CTRL0, &val);
-+      if (ret)
-+              return ret;
-+
-+      /* QCA83xx can have only one port set to mirror mode.
-+       * Check that the correct port is requested and return error otherwise.
-+       * When no mirror port is set, the values is set to 0xF
-+       */
-+      monitor_port = FIELD_GET(QCA8K_GLOBAL_FW_CTRL0_MIRROR_PORT_NUM, val);
-+      if (monitor_port != 0xF && monitor_port != mirror->to_local_port)
-+              return -EEXIST;
-+
-+      /* Set the monitor port */
-+      val = FIELD_PREP(QCA8K_GLOBAL_FW_CTRL0_MIRROR_PORT_NUM,
-+                       mirror->to_local_port);
-+      ret = regmap_update_bits(priv->regmap, QCA8K_REG_GLOBAL_FW_CTRL0,
-+                               QCA8K_GLOBAL_FW_CTRL0_MIRROR_PORT_NUM, val);
-+      if (ret)
-+              return ret;
-+
-+      if (ingress) {
-+              reg = QCA8K_PORT_LOOKUP_CTRL(port);
-+              val = QCA8K_PORT_LOOKUP_ING_MIRROR_EN;
-+      } else {
-+              reg = QCA8K_REG_PORT_HOL_CTRL1(port);
-+              val = QCA8K_PORT_HOL_CTRL1_EG_MIRROR_EN;
-+      }
-+
-+      ret = regmap_update_bits(priv->regmap, reg, val, val);
-+      if (ret)
-+              return ret;
-+
-+      /* Track mirror port for tx and rx to decide when the
-+       * mirror port has to be disabled.
-+       */
-+      if (ingress)
-+              priv->mirror_rx |= BIT(port);
-+      else
-+              priv->mirror_tx |= BIT(port);
-+
-+      return 0;
-+}
-+
-+static void
-+qca8k_port_mirror_del(struct dsa_switch *ds, int port,
-+                    struct dsa_mall_mirror_tc_entry *mirror)
-+{
-+      struct qca8k_priv *priv = ds->priv;
-+      u32 reg, val;
-+      int ret;
-+
-+      if (mirror->ingress) {
-+              reg = QCA8K_PORT_LOOKUP_CTRL(port);
-+              val = QCA8K_PORT_LOOKUP_ING_MIRROR_EN;
-+      } else {
-+              reg = QCA8K_REG_PORT_HOL_CTRL1(port);
-+              val = QCA8K_PORT_HOL_CTRL1_EG_MIRROR_EN;
-+      }
-+
-+      ret = regmap_clear_bits(priv->regmap, reg, val);
-+      if (ret)
-+              goto err;
-+
-+      if (mirror->ingress)
-+              priv->mirror_rx &= ~BIT(port);
-+      else
-+              priv->mirror_tx &= ~BIT(port);
-+
-+      /* No port set to send packet to mirror port. Disable mirror port */
-+      if (!priv->mirror_rx && !priv->mirror_tx) {
-+              val = FIELD_PREP(QCA8K_GLOBAL_FW_CTRL0_MIRROR_PORT_NUM, 0xF);
-+              ret = regmap_update_bits(priv->regmap, QCA8K_REG_GLOBAL_FW_CTRL0,
-+                                       QCA8K_GLOBAL_FW_CTRL0_MIRROR_PORT_NUM, val);
-+              if (ret)
-+                      goto err;
-+      }
-+err:
-+      dev_err(priv->dev, "Failed to del mirror port from %d", port);
-+}
-+
-+static int
-+qca8k_port_vlan_filtering(struct dsa_switch *ds, int port, bool vlan_filtering,
-+                        struct netlink_ext_ack *extack)
-+{
-+      struct qca8k_priv *priv = ds->priv;
-+      int ret;
-+
-+      if (vlan_filtering) {
-+              ret = qca8k_rmw(priv, QCA8K_PORT_LOOKUP_CTRL(port),
-+                              QCA8K_PORT_LOOKUP_VLAN_MODE_MASK,
-+                              QCA8K_PORT_LOOKUP_VLAN_MODE_SECURE);
-+      } else {
-+              ret = qca8k_rmw(priv, QCA8K_PORT_LOOKUP_CTRL(port),
-+                              QCA8K_PORT_LOOKUP_VLAN_MODE_MASK,
-+                              QCA8K_PORT_LOOKUP_VLAN_MODE_NONE);
-+      }
-+
-+      return ret;
-+}
-+
-+static int
-+qca8k_port_vlan_add(struct dsa_switch *ds, int port,
-+                  const struct switchdev_obj_port_vlan *vlan,
-+                  struct netlink_ext_ack *extack)
-+{
-+      bool untagged = vlan->flags & BRIDGE_VLAN_INFO_UNTAGGED;
-+      bool pvid = vlan->flags & BRIDGE_VLAN_INFO_PVID;
-+      struct qca8k_priv *priv = ds->priv;
-+      int ret;
-+
-+      ret = qca8k_vlan_add(priv, port, vlan->vid, untagged);
-+      if (ret) {
-+              dev_err(priv->dev, "Failed to add VLAN to port %d (%d)", port, ret);
-+              return ret;
-+      }
-+
-+      if (pvid) {
-+              ret = qca8k_rmw(priv, QCA8K_EGRESS_VLAN(port),
-+                              QCA8K_EGREES_VLAN_PORT_MASK(port),
-+                              QCA8K_EGREES_VLAN_PORT(port, vlan->vid));
-+              if (ret)
-+                      return ret;
-+
-+              ret = qca8k_write(priv, QCA8K_REG_PORT_VLAN_CTRL0(port),
-+                                QCA8K_PORT_VLAN_CVID(vlan->vid) |
-+                                QCA8K_PORT_VLAN_SVID(vlan->vid));
-+      }
-+
-+      return ret;
-+}
-+
-+static int
-+qca8k_port_vlan_del(struct dsa_switch *ds, int port,
-+                  const struct switchdev_obj_port_vlan *vlan)
-+{
-+      struct qca8k_priv *priv = ds->priv;
-+      int ret;
-+
-+      ret = qca8k_vlan_del(priv, port, vlan->vid);
-+      if (ret)
-+              dev_err(priv->dev, "Failed to delete VLAN from port %d (%d)", port, ret);
-+
-+      return ret;
-+}
-+
-+static u32 qca8k_get_phy_flags(struct dsa_switch *ds, int port)
-+{
-+      struct qca8k_priv *priv = ds->priv;
-+
-+      /* Communicate to the phy internal driver the switch revision.
-+       * Based on the switch revision different values needs to be
-+       * set to the dbg and mmd reg on the phy.
-+       * The first 2 bit are used to communicate the switch revision
-+       * to the phy driver.
-+       */
-+      if (port > 0 && port < 6)
-+              return priv->switch_revision;
-+
-+      return 0;
-+}
-+
-+static enum dsa_tag_protocol
-+qca8k_get_tag_protocol(struct dsa_switch *ds, int port,
-+                     enum dsa_tag_protocol mp)
-+{
-+      return DSA_TAG_PROTO_QCA;
-+}
-+
-+static bool
-+qca8k_lag_can_offload(struct dsa_switch *ds,
-+                    struct net_device *lag,
-+                    struct netdev_lag_upper_info *info)
-+{
-+      struct dsa_port *dp;
-+      int id, members = 0;
-+
-+      id = dsa_lag_id(ds->dst, lag);
-+      if (id < 0 || id >= ds->num_lag_ids)
-+              return false;
-+
-+      dsa_lag_foreach_port(dp, ds->dst, lag)
-+              /* Includes the port joining the LAG */
-+              members++;
-+
-+      if (members > QCA8K_NUM_PORTS_FOR_LAG)
-+              return false;
-+
-+      if (info->tx_type != NETDEV_LAG_TX_TYPE_HASH)
-+              return false;
-+
-+      if (info->hash_type != NETDEV_LAG_HASH_L2 &&
-+          info->hash_type != NETDEV_LAG_HASH_L23)
-+              return false;
-+
-+      return true;
-+}
-+
-+static int
-+qca8k_lag_setup_hash(struct dsa_switch *ds,
-+                   struct net_device *lag,
-+                   struct netdev_lag_upper_info *info)
-+{
-+      struct qca8k_priv *priv = ds->priv;
-+      bool unique_lag = true;
-+      u32 hash = 0;
-+      int i, id;
-+
-+      id = dsa_lag_id(ds->dst, lag);
-+
-+      switch (info->hash_type) {
-+      case NETDEV_LAG_HASH_L23:
-+              hash |= QCA8K_TRUNK_HASH_SIP_EN;
-+              hash |= QCA8K_TRUNK_HASH_DIP_EN;
-+              fallthrough;
-+      case NETDEV_LAG_HASH_L2:
-+              hash |= QCA8K_TRUNK_HASH_SA_EN;
-+              hash |= QCA8K_TRUNK_HASH_DA_EN;
-+              break;
-+      default: /* We should NEVER reach this */
-+              return -EOPNOTSUPP;
-+      }
-+
-+      /* Check if we are the unique configured LAG */
-+      dsa_lags_foreach_id(i, ds->dst)
-+              if (i != id && dsa_lag_dev(ds->dst, i)) {
-+                      unique_lag = false;
-+                      break;
-+              }
-+
-+      /* Hash Mode is global. Make sure the same Hash Mode
-+       * is set to all the 4 possible lag.
-+       * If we are the unique LAG we can set whatever hash
-+       * mode we want.
-+       * To change hash mode it's needed to remove all LAG
-+       * and change the mode with the latest.
-+       */
-+      if (unique_lag) {
-+              priv->lag_hash_mode = hash;
-+      } else if (priv->lag_hash_mode != hash) {
-+              netdev_err(lag, "Error: Mismateched Hash Mode across different lag is not supported\n");
-+              return -EOPNOTSUPP;
-+      }
-+
-+      return regmap_update_bits(priv->regmap, QCA8K_TRUNK_HASH_EN_CTRL,
-+                                QCA8K_TRUNK_HASH_MASK, hash);
-+}
-+
-+static int
-+qca8k_lag_refresh_portmap(struct dsa_switch *ds, int port,
-+                        struct net_device *lag, bool delete)
-+{
-+      struct qca8k_priv *priv = ds->priv;
-+      int ret, id, i;
-+      u32 val;
-+
-+      id = dsa_lag_id(ds->dst, lag);
-+
-+      /* Read current port member */
-+      ret = regmap_read(priv->regmap, QCA8K_REG_GOL_TRUNK_CTRL0, &val);
-+      if (ret)
-+              return ret;
-+
-+      /* Shift val to the correct trunk */
-+      val >>= QCA8K_REG_GOL_TRUNK_SHIFT(id);
-+      val &= QCA8K_REG_GOL_TRUNK_MEMBER_MASK;
-+      if (delete)
-+              val &= ~BIT(port);
-+      else
-+              val |= BIT(port);
-+
-+      /* Update port member. With empty portmap disable trunk */
-+      ret = regmap_update_bits(priv->regmap, QCA8K_REG_GOL_TRUNK_CTRL0,
-+                               QCA8K_REG_GOL_TRUNK_MEMBER(id) |
-+                               QCA8K_REG_GOL_TRUNK_EN(id),
-+                               !val << QCA8K_REG_GOL_TRUNK_SHIFT(id) |
-+                               val << QCA8K_REG_GOL_TRUNK_SHIFT(id));
-+
-+      /* Search empty member if adding or port on deleting */
-+      for (i = 0; i < QCA8K_NUM_PORTS_FOR_LAG; i++) {
-+              ret = regmap_read(priv->regmap, QCA8K_REG_GOL_TRUNK_CTRL(id), &val);
-+              if (ret)
-+                      return ret;
-+
-+              val >>= QCA8K_REG_GOL_TRUNK_ID_MEM_ID_SHIFT(id, i);
-+              val &= QCA8K_REG_GOL_TRUNK_ID_MEM_ID_MASK;
-+
-+              if (delete) {
-+                      /* If port flagged to be disabled assume this member is
-+                       * empty
-+                       */
-+                      if (val != QCA8K_REG_GOL_TRUNK_ID_MEM_ID_EN_MASK)
-+                              continue;
-+
-+                      val &= QCA8K_REG_GOL_TRUNK_ID_MEM_ID_PORT_MASK;
-+                      if (val != port)
-+                              continue;
-+              } else {
-+                      /* If port flagged to be enabled assume this member is
-+                       * already set
-+                       */
-+                      if (val == QCA8K_REG_GOL_TRUNK_ID_MEM_ID_EN_MASK)
-+                              continue;
-+              }
-+
-+              /* We have found the member to add/remove */
-+              break;
-+      }
-+
-+      /* Set port in the correct port mask or disable port if in delete mode */
-+      return regmap_update_bits(priv->regmap, QCA8K_REG_GOL_TRUNK_CTRL(id),
-+                                QCA8K_REG_GOL_TRUNK_ID_MEM_ID_EN(id, i) |
-+                                QCA8K_REG_GOL_TRUNK_ID_MEM_ID_PORT(id, i),
-+                                !delete << QCA8K_REG_GOL_TRUNK_ID_MEM_ID_SHIFT(id, i) |
-+                                port << QCA8K_REG_GOL_TRUNK_ID_MEM_ID_SHIFT(id, i));
-+}
-+
-+static int
-+qca8k_port_lag_join(struct dsa_switch *ds, int port,
-+                  struct net_device *lag,
-+                  struct netdev_lag_upper_info *info)
-+{
-+      int ret;
-+
-+      if (!qca8k_lag_can_offload(ds, lag, info))
-+              return -EOPNOTSUPP;
-+
-+      ret = qca8k_lag_setup_hash(ds, lag, info);
-+      if (ret)
-+              return ret;
-+
-+      return qca8k_lag_refresh_portmap(ds, port, lag, false);
-+}
-+
-+static int
-+qca8k_port_lag_leave(struct dsa_switch *ds, int port,
-+                   struct net_device *lag)
-+{
-+      return qca8k_lag_refresh_portmap(ds, port, lag, true);
-+}
-+
-+static void
-+qca8k_master_change(struct dsa_switch *ds, const struct net_device *master,
-+                  bool operational)
-+{
-+      struct dsa_port *dp = master->dsa_ptr;
-+      struct qca8k_priv *priv = ds->priv;
-+
-+      /* Ethernet MIB/MDIO is only supported for CPU port 0 */
-+      if (dp->index != 0)
-+              return;
-+
-+      mutex_lock(&priv->mgmt_eth_data.mutex);
-+      mutex_lock(&priv->mib_eth_data.mutex);
-+
-+      priv->mgmt_master = operational ? (struct net_device *)master : NULL;
-+
-+      mutex_unlock(&priv->mib_eth_data.mutex);
-+      mutex_unlock(&priv->mgmt_eth_data.mutex);
-+}
-+
-+static int qca8k_connect_tag_protocol(struct dsa_switch *ds,
-+                                    enum dsa_tag_protocol proto)
-+{
-+      struct qca_tagger_data *tagger_data;
-+
-+      switch (proto) {
-+      case DSA_TAG_PROTO_QCA:
-+              tagger_data = ds->tagger_data;
-+
-+              tagger_data->rw_reg_ack_handler = qca8k_rw_reg_ack_handler;
-+              tagger_data->mib_autocast_handler = qca8k_mib_autocast_handler;
-+
-+              break;
-+      default:
-+              return -EOPNOTSUPP;
-+      }
-+
-+      return 0;
-+}
-+
-+static const struct dsa_switch_ops qca8k_switch_ops = {
-+      .get_tag_protocol       = qca8k_get_tag_protocol,
-+      .setup                  = qca8k_setup,
-+      .get_strings            = qca8k_get_strings,
-+      .get_ethtool_stats      = qca8k_get_ethtool_stats,
-+      .get_sset_count         = qca8k_get_sset_count,
-+      .set_ageing_time        = qca8k_set_ageing_time,
-+      .get_mac_eee            = qca8k_get_mac_eee,
-+      .set_mac_eee            = qca8k_set_mac_eee,
-+      .port_enable            = qca8k_port_enable,
-+      .port_disable           = qca8k_port_disable,
-+      .port_change_mtu        = qca8k_port_change_mtu,
-+      .port_max_mtu           = qca8k_port_max_mtu,
-+      .port_stp_state_set     = qca8k_port_stp_state_set,
-+      .port_bridge_join       = qca8k_port_bridge_join,
-+      .port_bridge_leave      = qca8k_port_bridge_leave,
-+      .port_fast_age          = qca8k_port_fast_age,
-+      .port_fdb_add           = qca8k_port_fdb_add,
-+      .port_fdb_del           = qca8k_port_fdb_del,
-+      .port_fdb_dump          = qca8k_port_fdb_dump,
-+      .port_mdb_add           = qca8k_port_mdb_add,
-+      .port_mdb_del           = qca8k_port_mdb_del,
-+      .port_mirror_add        = qca8k_port_mirror_add,
-+      .port_mirror_del        = qca8k_port_mirror_del,
-+      .port_vlan_filtering    = qca8k_port_vlan_filtering,
-+      .port_vlan_add          = qca8k_port_vlan_add,
-+      .port_vlan_del          = qca8k_port_vlan_del,
-+      .phylink_validate       = qca8k_phylink_validate,
-+      .phylink_mac_link_state = qca8k_phylink_mac_link_state,
-+      .phylink_mac_config     = qca8k_phylink_mac_config,
-+      .phylink_mac_link_down  = qca8k_phylink_mac_link_down,
-+      .phylink_mac_link_up    = qca8k_phylink_mac_link_up,
-+      .get_phy_flags          = qca8k_get_phy_flags,
-+      .port_lag_join          = qca8k_port_lag_join,
-+      .port_lag_leave         = qca8k_port_lag_leave,
-+      .master_state_change    = qca8k_master_change,
-+      .connect_tag_protocol   = qca8k_connect_tag_protocol,
-+};
-+
-+static int qca8k_read_switch_id(struct qca8k_priv *priv)
-+{
-+      const struct qca8k_match_data *data;
-+      u32 val;
-+      u8 id;
-+      int ret;
-+
-+      /* get the switches ID from the compatible */
-+      data = of_device_get_match_data(priv->dev);
-+      if (!data)
-+              return -ENODEV;
-+
-+      ret = qca8k_read(priv, QCA8K_REG_MASK_CTRL, &val);
-+      if (ret < 0)
-+              return -ENODEV;
-+
-+      id = QCA8K_MASK_CTRL_DEVICE_ID(val);
-+      if (id != data->id) {
-+              dev_err(priv->dev, "Switch id detected %x but expected %x", id, data->id);
-+              return -ENODEV;
-+      }
-+
-+      priv->switch_id = id;
-+
-+      /* Save revision to communicate to the internal PHY driver */
-+      priv->switch_revision = QCA8K_MASK_CTRL_REV_ID(val);
-+
-+      return 0;
-+}
-+
-+static int
-+qca8k_sw_probe(struct mdio_device *mdiodev)
-+{
-+      struct qca8k_priv *priv;
-+      int ret;
-+
-+      /* allocate the private data struct so that we can probe the switches
-+       * ID register
-+       */
-+      priv = devm_kzalloc(&mdiodev->dev, sizeof(*priv), GFP_KERNEL);
-+      if (!priv)
-+              return -ENOMEM;
-+
-+      priv->bus = mdiodev->bus;
-+      priv->dev = &mdiodev->dev;
-+
-+      priv->reset_gpio = devm_gpiod_get_optional(priv->dev, "reset",
-+                                                 GPIOD_ASIS);
-+      if (IS_ERR(priv->reset_gpio))
-+              return PTR_ERR(priv->reset_gpio);
-+
-+      if (priv->reset_gpio) {
-+              gpiod_set_value_cansleep(priv->reset_gpio, 1);
-+              /* The active low duration must be greater than 10 ms
-+               * and checkpatch.pl wants 20 ms.
-+               */
-+              msleep(20);
-+              gpiod_set_value_cansleep(priv->reset_gpio, 0);
-+      }
-+
-+      /* Start by setting up the register mapping */
-+      priv->regmap = devm_regmap_init(&mdiodev->dev, NULL, priv,
-+                                      &qca8k_regmap_config);
-+      if (IS_ERR(priv->regmap)) {
-+              dev_err(priv->dev, "regmap initialization failed");
-+              return PTR_ERR(priv->regmap);
-+      }
-+
-+      priv->mdio_cache.page = 0xffff;
-+      priv->mdio_cache.lo = 0xffff;
-+      priv->mdio_cache.hi = 0xffff;
-+
-+      /* Check the detected switch id */
-+      ret = qca8k_read_switch_id(priv);
-+      if (ret)
-+              return ret;
-+
-+      priv->ds = devm_kzalloc(&mdiodev->dev, sizeof(*priv->ds), GFP_KERNEL);
-+      if (!priv->ds)
-+              return -ENOMEM;
-+
-+      mutex_init(&priv->mgmt_eth_data.mutex);
-+      init_completion(&priv->mgmt_eth_data.rw_done);
-+
-+      mutex_init(&priv->mib_eth_data.mutex);
-+      init_completion(&priv->mib_eth_data.rw_done);
-+
-+      priv->ds->dev = &mdiodev->dev;
-+      priv->ds->num_ports = QCA8K_NUM_PORTS;
-+      priv->ds->priv = priv;
-+      priv->ds->ops = &qca8k_switch_ops;
-+      mutex_init(&priv->reg_mutex);
-+      dev_set_drvdata(&mdiodev->dev, priv);
-+
-+      return dsa_register_switch(priv->ds);
-+}
-+
-+static void
-+qca8k_sw_remove(struct mdio_device *mdiodev)
-+{
-+      struct qca8k_priv *priv = dev_get_drvdata(&mdiodev->dev);
-+      int i;
-+
-+      if (!priv)
-+              return;
-+
-+      for (i = 0; i < QCA8K_NUM_PORTS; i++)
-+              qca8k_port_set_status(priv, i, 0);
-+
-+      dsa_unregister_switch(priv->ds);
-+
-+      dev_set_drvdata(&mdiodev->dev, NULL);
-+}
-+
-+static void qca8k_sw_shutdown(struct mdio_device *mdiodev)
-+{
-+      struct qca8k_priv *priv = dev_get_drvdata(&mdiodev->dev);
-+
-+      if (!priv)
-+              return;
-+
-+      dsa_switch_shutdown(priv->ds);
-+
-+      dev_set_drvdata(&mdiodev->dev, NULL);
-+}
-+
-+#ifdef CONFIG_PM_SLEEP
-+static void
-+qca8k_set_pm(struct qca8k_priv *priv, int enable)
-+{
-+      int port;
-+
-+      for (port = 0; port < QCA8K_NUM_PORTS; port++) {
-+              /* Do not enable on resume if the port was
-+               * disabled before.
-+               */
-+              if (!(priv->port_enabled_map & BIT(port)))
-+                      continue;
-+
-+              qca8k_port_set_status(priv, port, enable);
-+      }
-+}
-+
-+static int qca8k_suspend(struct device *dev)
-+{
-+      struct qca8k_priv *priv = dev_get_drvdata(dev);
-+
-+      qca8k_set_pm(priv, 0);
-+
-+      return dsa_switch_suspend(priv->ds);
-+}
-+
-+static int qca8k_resume(struct device *dev)
-+{
-+      struct qca8k_priv *priv = dev_get_drvdata(dev);
-+
-+      qca8k_set_pm(priv, 1);
-+
-+      return dsa_switch_resume(priv->ds);
-+}
-+#endif /* CONFIG_PM_SLEEP */
-+
-+static SIMPLE_DEV_PM_OPS(qca8k_pm_ops,
-+                       qca8k_suspend, qca8k_resume);
-+
-+static const struct qca8k_match_data qca8327 = {
-+      .id = QCA8K_ID_QCA8327,
-+      .reduced_package = true,
-+      .mib_count = QCA8K_QCA832X_MIB_COUNT,
-+};
-+
-+static const struct qca8k_match_data qca8328 = {
-+      .id = QCA8K_ID_QCA8327,
-+      .mib_count = QCA8K_QCA832X_MIB_COUNT,
-+};
-+
-+static const struct qca8k_match_data qca833x = {
-+      .id = QCA8K_ID_QCA8337,
-+      .mib_count = QCA8K_QCA833X_MIB_COUNT,
-+};
-+
-+static const struct of_device_id qca8k_of_match[] = {
-+      { .compatible = "qca,qca8327", .data = &qca8327 },
-+      { .compatible = "qca,qca8328", .data = &qca8328 },
-+      { .compatible = "qca,qca8334", .data = &qca833x },
-+      { .compatible = "qca,qca8337", .data = &qca833x },
-+      { /* sentinel */ },
-+};
-+
-+static struct mdio_driver qca8kmdio_driver = {
-+      .probe  = qca8k_sw_probe,
-+      .remove = qca8k_sw_remove,
-+      .shutdown = qca8k_sw_shutdown,
-+      .mdiodrv.driver = {
-+              .name = "qca8k",
-+              .of_match_table = qca8k_of_match,
-+              .pm = &qca8k_pm_ops,
-+      },
-+};
-+
-+mdio_module_driver(qca8kmdio_driver);
-+
-+MODULE_AUTHOR("Mathieu Olivari, John Crispin <[email protected]>");
-+MODULE_DESCRIPTION("Driver for QCA8K ethernet switch family");
-+MODULE_LICENSE("GPL v2");
-+MODULE_ALIAS("platform:qca8k");
---- /dev/null
-+++ b/drivers/net/dsa/qca/qca8k.h
-@@ -0,0 +1,411 @@
-+/* SPDX-License-Identifier: GPL-2.0-only */
-+/*
-+ * Copyright (C) 2009 Felix Fietkau <[email protected]>
-+ * Copyright (C) 2011-2012 Gabor Juhos <[email protected]>
-+ * Copyright (c) 2015, The Linux Foundation. All rights reserved.
-+ */
-+
-+#ifndef __QCA8K_H
-+#define __QCA8K_H
-+
-+#include <linux/delay.h>
-+#include <linux/regmap.h>
-+#include <linux/gpio.h>
-+#include <linux/dsa/tag_qca.h>
-+
-+#define QCA8K_ETHERNET_MDIO_PRIORITY                  7
-+#define QCA8K_ETHERNET_PHY_PRIORITY                   6
-+#define QCA8K_ETHERNET_TIMEOUT                                100
-+
-+#define QCA8K_NUM_PORTS                                       7
-+#define QCA8K_NUM_CPU_PORTS                           2
-+#define QCA8K_MAX_MTU                                 9000
-+#define QCA8K_NUM_LAGS                                        4
-+#define QCA8K_NUM_PORTS_FOR_LAG                               4
-+
-+#define PHY_ID_QCA8327                                        0x004dd034
-+#define QCA8K_ID_QCA8327                              0x12
-+#define PHY_ID_QCA8337                                        0x004dd036
-+#define QCA8K_ID_QCA8337                              0x13
-+
-+#define QCA8K_QCA832X_MIB_COUNT                               39
-+#define QCA8K_QCA833X_MIB_COUNT                               41
-+
-+#define QCA8K_BUSY_WAIT_TIMEOUT                               2000
-+
-+#define QCA8K_NUM_FDB_RECORDS                         2048
-+
-+#define QCA8K_PORT_VID_DEF                            1
-+
-+/* Global control registers */
-+#define QCA8K_REG_MASK_CTRL                           0x000
-+#define   QCA8K_MASK_CTRL_REV_ID_MASK                 GENMASK(7, 0)
-+#define   QCA8K_MASK_CTRL_REV_ID(x)                   FIELD_GET(QCA8K_MASK_CTRL_REV_ID_MASK, x)
-+#define   QCA8K_MASK_CTRL_DEVICE_ID_MASK              GENMASK(15, 8)
-+#define   QCA8K_MASK_CTRL_DEVICE_ID(x)                        FIELD_GET(QCA8K_MASK_CTRL_DEVICE_ID_MASK, x)
-+#define QCA8K_REG_PORT0_PAD_CTRL                      0x004
-+#define   QCA8K_PORT0_PAD_MAC06_EXCHANGE_EN           BIT(31)
-+#define   QCA8K_PORT0_PAD_SGMII_RXCLK_FALLING_EDGE    BIT(19)
-+#define   QCA8K_PORT0_PAD_SGMII_TXCLK_FALLING_EDGE    BIT(18)
-+#define QCA8K_REG_PORT5_PAD_CTRL                      0x008
-+#define QCA8K_REG_PORT6_PAD_CTRL                      0x00c
-+#define   QCA8K_PORT_PAD_RGMII_EN                     BIT(26)
-+#define   QCA8K_PORT_PAD_RGMII_TX_DELAY_MASK          GENMASK(23, 22)
-+#define   QCA8K_PORT_PAD_RGMII_TX_DELAY(x)            FIELD_PREP(QCA8K_PORT_PAD_RGMII_TX_DELAY_MASK, x)
-+#define   QCA8K_PORT_PAD_RGMII_RX_DELAY_MASK          GENMASK(21, 20)
-+#define   QCA8K_PORT_PAD_RGMII_RX_DELAY(x)            FIELD_PREP(QCA8K_PORT_PAD_RGMII_RX_DELAY_MASK, x)
-+#define         QCA8K_PORT_PAD_RGMII_TX_DELAY_EN              BIT(25)
-+#define   QCA8K_PORT_PAD_RGMII_RX_DELAY_EN            BIT(24)
-+#define   QCA8K_PORT_PAD_SGMII_EN                     BIT(7)
-+#define QCA8K_REG_PWS                                 0x010
-+#define   QCA8K_PWS_POWER_ON_SEL                      BIT(31)
-+/* This reg is only valid for QCA832x and toggle the package
-+ * type from 176 pin (by default) to 148 pin used on QCA8327
-+ */
-+#define   QCA8327_PWS_PACKAGE148_EN                   BIT(30)
-+#define   QCA8K_PWS_LED_OPEN_EN_CSR                   BIT(24)
-+#define   QCA8K_PWS_SERDES_AEN_DIS                    BIT(7)
-+#define QCA8K_REG_MODULE_EN                           0x030
-+#define   QCA8K_MODULE_EN_MIB                         BIT(0)
-+#define QCA8K_REG_MIB                                 0x034
-+#define   QCA8K_MIB_FUNC                              GENMASK(26, 24)
-+#define   QCA8K_MIB_CPU_KEEP                          BIT(20)
-+#define   QCA8K_MIB_BUSY                              BIT(17)
-+#define QCA8K_MDIO_MASTER_CTRL                                0x3c
-+#define   QCA8K_MDIO_MASTER_BUSY                      BIT(31)
-+#define   QCA8K_MDIO_MASTER_EN                                BIT(30)
-+#define   QCA8K_MDIO_MASTER_READ                      BIT(27)
-+#define   QCA8K_MDIO_MASTER_WRITE                     0
-+#define   QCA8K_MDIO_MASTER_SUP_PRE                   BIT(26)
-+#define   QCA8K_MDIO_MASTER_PHY_ADDR_MASK             GENMASK(25, 21)
-+#define   QCA8K_MDIO_MASTER_PHY_ADDR(x)                       FIELD_PREP(QCA8K_MDIO_MASTER_PHY_ADDR_MASK, x)
-+#define   QCA8K_MDIO_MASTER_REG_ADDR_MASK             GENMASK(20, 16)
-+#define   QCA8K_MDIO_MASTER_REG_ADDR(x)                       FIELD_PREP(QCA8K_MDIO_MASTER_REG_ADDR_MASK, x)
-+#define   QCA8K_MDIO_MASTER_DATA_MASK                 GENMASK(15, 0)
-+#define   QCA8K_MDIO_MASTER_DATA(x)                   FIELD_PREP(QCA8K_MDIO_MASTER_DATA_MASK, x)
-+#define   QCA8K_MDIO_MASTER_MAX_PORTS                 5
-+#define   QCA8K_MDIO_MASTER_MAX_REG                   32
-+#define QCA8K_GOL_MAC_ADDR0                           0x60
-+#define QCA8K_GOL_MAC_ADDR1                           0x64
-+#define QCA8K_MAX_FRAME_SIZE                          0x78
-+#define QCA8K_REG_PORT_STATUS(_i)                     (0x07c + (_i) * 4)
-+#define   QCA8K_PORT_STATUS_SPEED                     GENMASK(1, 0)
-+#define   QCA8K_PORT_STATUS_SPEED_10                  0
-+#define   QCA8K_PORT_STATUS_SPEED_100                 0x1
-+#define   QCA8K_PORT_STATUS_SPEED_1000                        0x2
-+#define   QCA8K_PORT_STATUS_TXMAC                     BIT(2)
-+#define   QCA8K_PORT_STATUS_RXMAC                     BIT(3)
-+#define   QCA8K_PORT_STATUS_TXFLOW                    BIT(4)
-+#define   QCA8K_PORT_STATUS_RXFLOW                    BIT(5)
-+#define   QCA8K_PORT_STATUS_DUPLEX                    BIT(6)
-+#define   QCA8K_PORT_STATUS_LINK_UP                   BIT(8)
-+#define   QCA8K_PORT_STATUS_LINK_AUTO                 BIT(9)
-+#define   QCA8K_PORT_STATUS_LINK_PAUSE                        BIT(10)
-+#define   QCA8K_PORT_STATUS_FLOW_AUTO                 BIT(12)
-+#define QCA8K_REG_PORT_HDR_CTRL(_i)                   (0x9c + (_i * 4))
-+#define   QCA8K_PORT_HDR_CTRL_RX_MASK                 GENMASK(3, 2)
-+#define   QCA8K_PORT_HDR_CTRL_TX_MASK                 GENMASK(1, 0)
-+#define   QCA8K_PORT_HDR_CTRL_ALL                     2
-+#define   QCA8K_PORT_HDR_CTRL_MGMT                    1
-+#define   QCA8K_PORT_HDR_CTRL_NONE                    0
-+#define QCA8K_REG_SGMII_CTRL                          0x0e0
-+#define   QCA8K_SGMII_EN_PLL                          BIT(1)
-+#define   QCA8K_SGMII_EN_RX                           BIT(2)
-+#define   QCA8K_SGMII_EN_TX                           BIT(3)
-+#define   QCA8K_SGMII_EN_SD                           BIT(4)
-+#define   QCA8K_SGMII_CLK125M_DELAY                   BIT(7)
-+#define   QCA8K_SGMII_MODE_CTRL_MASK                  GENMASK(23, 22)
-+#define   QCA8K_SGMII_MODE_CTRL(x)                    FIELD_PREP(QCA8K_SGMII_MODE_CTRL_MASK, x)
-+#define   QCA8K_SGMII_MODE_CTRL_BASEX                 QCA8K_SGMII_MODE_CTRL(0x0)
-+#define   QCA8K_SGMII_MODE_CTRL_PHY                   QCA8K_SGMII_MODE_CTRL(0x1)
-+#define   QCA8K_SGMII_MODE_CTRL_MAC                   QCA8K_SGMII_MODE_CTRL(0x2)
-+
-+/* MAC_PWR_SEL registers */
-+#define QCA8K_REG_MAC_PWR_SEL                         0x0e4
-+#define   QCA8K_MAC_PWR_RGMII1_1_8V                   BIT(18)
-+#define   QCA8K_MAC_PWR_RGMII0_1_8V                   BIT(19)
-+
-+/* EEE control registers */
-+#define QCA8K_REG_EEE_CTRL                            0x100
-+#define  QCA8K_REG_EEE_CTRL_LPI_EN(_i)                        ((_i + 1) * 2)
-+
-+/* TRUNK_HASH_EN registers */
-+#define QCA8K_TRUNK_HASH_EN_CTRL                      0x270
-+#define   QCA8K_TRUNK_HASH_SIP_EN                     BIT(3)
-+#define   QCA8K_TRUNK_HASH_DIP_EN                     BIT(2)
-+#define   QCA8K_TRUNK_HASH_SA_EN                      BIT(1)
-+#define   QCA8K_TRUNK_HASH_DA_EN                      BIT(0)
-+#define   QCA8K_TRUNK_HASH_MASK                               GENMASK(3, 0)
-+
-+/* ACL registers */
-+#define QCA8K_REG_PORT_VLAN_CTRL0(_i)                 (0x420 + (_i * 8))
-+#define   QCA8K_PORT_VLAN_CVID_MASK                   GENMASK(27, 16)
-+#define   QCA8K_PORT_VLAN_CVID(x)                     FIELD_PREP(QCA8K_PORT_VLAN_CVID_MASK, x)
-+#define   QCA8K_PORT_VLAN_SVID_MASK                   GENMASK(11, 0)
-+#define   QCA8K_PORT_VLAN_SVID(x)                     FIELD_PREP(QCA8K_PORT_VLAN_SVID_MASK, x)
-+#define QCA8K_REG_PORT_VLAN_CTRL1(_i)                 (0x424 + (_i * 8))
-+#define QCA8K_REG_IPV4_PRI_BASE_ADDR                  0x470
-+#define QCA8K_REG_IPV4_PRI_ADDR_MASK                  0x474
-+
-+/* Lookup registers */
-+#define QCA8K_REG_ATU_DATA0                           0x600
-+#define   QCA8K_ATU_ADDR2_MASK                                GENMASK(31, 24)
-+#define   QCA8K_ATU_ADDR3_MASK                                GENMASK(23, 16)
-+#define   QCA8K_ATU_ADDR4_MASK                                GENMASK(15, 8)
-+#define   QCA8K_ATU_ADDR5_MASK                                GENMASK(7, 0)
-+#define QCA8K_REG_ATU_DATA1                           0x604
-+#define   QCA8K_ATU_PORT_MASK                         GENMASK(22, 16)
-+#define   QCA8K_ATU_ADDR0_MASK                                GENMASK(15, 8)
-+#define   QCA8K_ATU_ADDR1_MASK                                GENMASK(7, 0)
-+#define QCA8K_REG_ATU_DATA2                           0x608
-+#define   QCA8K_ATU_VID_MASK                          GENMASK(19, 8)
-+#define   QCA8K_ATU_STATUS_MASK                               GENMASK(3, 0)
-+#define   QCA8K_ATU_STATUS_STATIC                     0xf
-+#define QCA8K_REG_ATU_FUNC                            0x60c
-+#define   QCA8K_ATU_FUNC_BUSY                         BIT(31)
-+#define   QCA8K_ATU_FUNC_PORT_EN                      BIT(14)
-+#define   QCA8K_ATU_FUNC_MULTI_EN                     BIT(13)
-+#define   QCA8K_ATU_FUNC_FULL                         BIT(12)
-+#define   QCA8K_ATU_FUNC_PORT_MASK                    GENMASK(11, 8)
-+#define QCA8K_REG_VTU_FUNC0                           0x610
-+#define   QCA8K_VTU_FUNC0_VALID                               BIT(20)
-+#define   QCA8K_VTU_FUNC0_IVL_EN                      BIT(19)
-+/*        QCA8K_VTU_FUNC0_EG_MODE_MASK                        GENMASK(17, 4)
-+ *          It does contain VLAN_MODE for each port [5:4] for port0,
-+ *          [7:6] for port1 ... [17:16] for port6. Use virtual port
-+ *          define to handle this.
-+ */
-+#define   QCA8K_VTU_FUNC0_EG_MODE_PORT_SHIFT(_i)      (4 + (_i) * 2)
-+#define   QCA8K_VTU_FUNC0_EG_MODE_MASK                        GENMASK(1, 0)
-+#define   QCA8K_VTU_FUNC0_EG_MODE_PORT_MASK(_i)               (GENMASK(1, 0) << QCA8K_VTU_FUNC0_EG_MODE_PORT_SHIFT(_i))
-+#define   QCA8K_VTU_FUNC0_EG_MODE_UNMOD                       FIELD_PREP(QCA8K_VTU_FUNC0_EG_MODE_MASK, 0x0)
-+#define   QCA8K_VTU_FUNC0_EG_MODE_PORT_UNMOD(_i)      (QCA8K_VTU_FUNC0_EG_MODE_UNMOD << QCA8K_VTU_FUNC0_EG_MODE_PORT_SHIFT(_i))
-+#define   QCA8K_VTU_FUNC0_EG_MODE_UNTAG                       FIELD_PREP(QCA8K_VTU_FUNC0_EG_MODE_MASK, 0x1)
-+#define   QCA8K_VTU_FUNC0_EG_MODE_PORT_UNTAG(_i)      (QCA8K_VTU_FUNC0_EG_MODE_UNTAG << QCA8K_VTU_FUNC0_EG_MODE_PORT_SHIFT(_i))
-+#define   QCA8K_VTU_FUNC0_EG_MODE_TAG                 FIELD_PREP(QCA8K_VTU_FUNC0_EG_MODE_MASK, 0x2)
-+#define   QCA8K_VTU_FUNC0_EG_MODE_PORT_TAG(_i)                (QCA8K_VTU_FUNC0_EG_MODE_TAG << QCA8K_VTU_FUNC0_EG_MODE_PORT_SHIFT(_i))
-+#define   QCA8K_VTU_FUNC0_EG_MODE_NOT                 FIELD_PREP(QCA8K_VTU_FUNC0_EG_MODE_MASK, 0x3)
-+#define   QCA8K_VTU_FUNC0_EG_MODE_PORT_NOT(_i)                (QCA8K_VTU_FUNC0_EG_MODE_NOT << QCA8K_VTU_FUNC0_EG_MODE_PORT_SHIFT(_i))
-+#define QCA8K_REG_VTU_FUNC1                           0x614
-+#define   QCA8K_VTU_FUNC1_BUSY                                BIT(31)
-+#define   QCA8K_VTU_FUNC1_VID_MASK                    GENMASK(27, 16)
-+#define   QCA8K_VTU_FUNC1_FULL                                BIT(4)
-+#define QCA8K_REG_ATU_CTRL                            0x618
-+#define   QCA8K_ATU_AGE_TIME_MASK                     GENMASK(15, 0)
-+#define   QCA8K_ATU_AGE_TIME(x)                               FIELD_PREP(QCA8K_ATU_AGE_TIME_MASK, (x))
-+#define QCA8K_REG_GLOBAL_FW_CTRL0                     0x620
-+#define   QCA8K_GLOBAL_FW_CTRL0_CPU_PORT_EN           BIT(10)
-+#define   QCA8K_GLOBAL_FW_CTRL0_MIRROR_PORT_NUM               GENMASK(7, 4)
-+#define QCA8K_REG_GLOBAL_FW_CTRL1                     0x624
-+#define   QCA8K_GLOBAL_FW_CTRL1_IGMP_DP_MASK          GENMASK(30, 24)
-+#define   QCA8K_GLOBAL_FW_CTRL1_BC_DP_MASK            GENMASK(22, 16)
-+#define   QCA8K_GLOBAL_FW_CTRL1_MC_DP_MASK            GENMASK(14, 8)
-+#define   QCA8K_GLOBAL_FW_CTRL1_UC_DP_MASK            GENMASK(6, 0)
-+#define QCA8K_PORT_LOOKUP_CTRL(_i)                    (0x660 + (_i) * 0xc)
-+#define   QCA8K_PORT_LOOKUP_MEMBER                    GENMASK(6, 0)
-+#define   QCA8K_PORT_LOOKUP_VLAN_MODE_MASK            GENMASK(9, 8)
-+#define   QCA8K_PORT_LOOKUP_VLAN_MODE(x)              FIELD_PREP(QCA8K_PORT_LOOKUP_VLAN_MODE_MASK, x)
-+#define   QCA8K_PORT_LOOKUP_VLAN_MODE_NONE            QCA8K_PORT_LOOKUP_VLAN_MODE(0x0)
-+#define   QCA8K_PORT_LOOKUP_VLAN_MODE_FALLBACK                QCA8K_PORT_LOOKUP_VLAN_MODE(0x1)
-+#define   QCA8K_PORT_LOOKUP_VLAN_MODE_CHECK           QCA8K_PORT_LOOKUP_VLAN_MODE(0x2)
-+#define   QCA8K_PORT_LOOKUP_VLAN_MODE_SECURE          QCA8K_PORT_LOOKUP_VLAN_MODE(0x3)
-+#define   QCA8K_PORT_LOOKUP_STATE_MASK                        GENMASK(18, 16)
-+#define   QCA8K_PORT_LOOKUP_STATE(x)                  FIELD_PREP(QCA8K_PORT_LOOKUP_STATE_MASK, x)
-+#define   QCA8K_PORT_LOOKUP_STATE_DISABLED            QCA8K_PORT_LOOKUP_STATE(0x0)
-+#define   QCA8K_PORT_LOOKUP_STATE_BLOCKING            QCA8K_PORT_LOOKUP_STATE(0x1)
-+#define   QCA8K_PORT_LOOKUP_STATE_LISTENING           QCA8K_PORT_LOOKUP_STATE(0x2)
-+#define   QCA8K_PORT_LOOKUP_STATE_LEARNING            QCA8K_PORT_LOOKUP_STATE(0x3)
-+#define   QCA8K_PORT_LOOKUP_STATE_FORWARD             QCA8K_PORT_LOOKUP_STATE(0x4)
-+#define   QCA8K_PORT_LOOKUP_LEARN                     BIT(20)
-+#define   QCA8K_PORT_LOOKUP_ING_MIRROR_EN             BIT(25)
-+
-+#define QCA8K_REG_GOL_TRUNK_CTRL0                     0x700
-+/* 4 max trunk first
-+ * first 6 bit for member bitmap
-+ * 7th bit is to enable trunk port
-+ */
-+#define QCA8K_REG_GOL_TRUNK_SHIFT(_i)                 ((_i) * 8)
-+#define QCA8K_REG_GOL_TRUNK_EN_MASK                   BIT(7)
-+#define QCA8K_REG_GOL_TRUNK_EN(_i)                    (QCA8K_REG_GOL_TRUNK_EN_MASK << QCA8K_REG_GOL_TRUNK_SHIFT(_i))
-+#define QCA8K_REG_GOL_TRUNK_MEMBER_MASK                       GENMASK(6, 0)
-+#define QCA8K_REG_GOL_TRUNK_MEMBER(_i)                        (QCA8K_REG_GOL_TRUNK_MEMBER_MASK << QCA8K_REG_GOL_TRUNK_SHIFT(_i))
-+/* 0x704 for TRUNK 0-1 --- 0x708 for TRUNK 2-3 */
-+#define QCA8K_REG_GOL_TRUNK_CTRL(_i)                  (0x704 + (((_i) / 2) * 4))
-+#define QCA8K_REG_GOL_TRUNK_ID_MEM_ID_MASK            GENMASK(3, 0)
-+#define QCA8K_REG_GOL_TRUNK_ID_MEM_ID_EN_MASK         BIT(3)
-+#define QCA8K_REG_GOL_TRUNK_ID_MEM_ID_PORT_MASK               GENMASK(2, 0)
-+#define QCA8K_REG_GOL_TRUNK_ID_SHIFT(_i)              (((_i) / 2) * 16)
-+#define QCA8K_REG_GOL_MEM_ID_SHIFT(_i)                        ((_i) * 4)
-+/* Complex shift: FIRST shift for port THEN shift for trunk */
-+#define QCA8K_REG_GOL_TRUNK_ID_MEM_ID_SHIFT(_i, _j)   (QCA8K_REG_GOL_MEM_ID_SHIFT(_j) + QCA8K_REG_GOL_TRUNK_ID_SHIFT(_i))
-+#define QCA8K_REG_GOL_TRUNK_ID_MEM_ID_EN(_i, _j)      (QCA8K_REG_GOL_TRUNK_ID_MEM_ID_EN_MASK << QCA8K_REG_GOL_TRUNK_ID_MEM_ID_SHIFT(_i, _j))
-+#define QCA8K_REG_GOL_TRUNK_ID_MEM_ID_PORT(_i, _j)    (QCA8K_REG_GOL_TRUNK_ID_MEM_ID_PORT_MASK << QCA8K_REG_GOL_TRUNK_ID_MEM_ID_SHIFT(_i, _j))
-+
-+#define QCA8K_REG_GLOBAL_FC_THRESH                    0x800
-+#define   QCA8K_GLOBAL_FC_GOL_XON_THRES_MASK          GENMASK(24, 16)
-+#define   QCA8K_GLOBAL_FC_GOL_XON_THRES(x)            FIELD_PREP(QCA8K_GLOBAL_FC_GOL_XON_THRES_MASK, x)
-+#define   QCA8K_GLOBAL_FC_GOL_XOFF_THRES_MASK         GENMASK(8, 0)
-+#define   QCA8K_GLOBAL_FC_GOL_XOFF_THRES(x)           FIELD_PREP(QCA8K_GLOBAL_FC_GOL_XOFF_THRES_MASK, x)
-+
-+#define QCA8K_REG_PORT_HOL_CTRL0(_i)                  (0x970 + (_i) * 0x8)
-+#define   QCA8K_PORT_HOL_CTRL0_EG_PRI0_BUF_MASK               GENMASK(3, 0)
-+#define   QCA8K_PORT_HOL_CTRL0_EG_PRI0(x)             FIELD_PREP(QCA8K_PORT_HOL_CTRL0_EG_PRI0_BUF_MASK, x)
-+#define   QCA8K_PORT_HOL_CTRL0_EG_PRI1_BUF_MASK               GENMASK(7, 4)
-+#define   QCA8K_PORT_HOL_CTRL0_EG_PRI1(x)             FIELD_PREP(QCA8K_PORT_HOL_CTRL0_EG_PRI1_BUF_MASK, x)
-+#define   QCA8K_PORT_HOL_CTRL0_EG_PRI2_BUF_MASK               GENMASK(11, 8)
-+#define   QCA8K_PORT_HOL_CTRL0_EG_PRI2(x)             FIELD_PREP(QCA8K_PORT_HOL_CTRL0_EG_PRI2_BUF_MASK, x)
-+#define   QCA8K_PORT_HOL_CTRL0_EG_PRI3_BUF_MASK               GENMASK(15, 12)
-+#define   QCA8K_PORT_HOL_CTRL0_EG_PRI3(x)             FIELD_PREP(QCA8K_PORT_HOL_CTRL0_EG_PRI3_BUF_MASK, x)
-+#define   QCA8K_PORT_HOL_CTRL0_EG_PRI4_BUF_MASK               GENMASK(19, 16)
-+#define   QCA8K_PORT_HOL_CTRL0_EG_PRI4(x)             FIELD_PREP(QCA8K_PORT_HOL_CTRL0_EG_PRI4_BUF_MASK, x)
-+#define   QCA8K_PORT_HOL_CTRL0_EG_PRI5_BUF_MASK               GENMASK(23, 20)
-+#define   QCA8K_PORT_HOL_CTRL0_EG_PRI5(x)             FIELD_PREP(QCA8K_PORT_HOL_CTRL0_EG_PRI5_BUF_MASK, x)
-+#define   QCA8K_PORT_HOL_CTRL0_EG_PORT_BUF_MASK               GENMASK(29, 24)
-+#define   QCA8K_PORT_HOL_CTRL0_EG_PORT(x)             FIELD_PREP(QCA8K_PORT_HOL_CTRL0_EG_PORT_BUF_MASK, x)
-+
-+#define QCA8K_REG_PORT_HOL_CTRL1(_i)                  (0x974 + (_i) * 0x8)
-+#define   QCA8K_PORT_HOL_CTRL1_ING_BUF_MASK           GENMASK(3, 0)
-+#define   QCA8K_PORT_HOL_CTRL1_ING(x)                 FIELD_PREP(QCA8K_PORT_HOL_CTRL1_ING_BUF_MASK, x)
-+#define   QCA8K_PORT_HOL_CTRL1_EG_PRI_BUF_EN          BIT(6)
-+#define   QCA8K_PORT_HOL_CTRL1_EG_PORT_BUF_EN         BIT(7)
-+#define   QCA8K_PORT_HOL_CTRL1_WRED_EN                        BIT(8)
-+#define   QCA8K_PORT_HOL_CTRL1_EG_MIRROR_EN           BIT(16)
-+
-+/* Pkt edit registers */
-+#define QCA8K_EGREES_VLAN_PORT_SHIFT(_i)              (16 * ((_i) % 2))
-+#define QCA8K_EGREES_VLAN_PORT_MASK(_i)                       (GENMASK(11, 0) << QCA8K_EGREES_VLAN_PORT_SHIFT(_i))
-+#define QCA8K_EGREES_VLAN_PORT(_i, x)                 ((x) << QCA8K_EGREES_VLAN_PORT_SHIFT(_i))
-+#define QCA8K_EGRESS_VLAN(x)                          (0x0c70 + (4 * (x / 2)))
-+
-+/* L3 registers */
-+#define QCA8K_HROUTER_CONTROL                         0xe00
-+#define   QCA8K_HROUTER_CONTROL_GLB_LOCKTIME_M                GENMASK(17, 16)
-+#define   QCA8K_HROUTER_CONTROL_GLB_LOCKTIME_S                16
-+#define   QCA8K_HROUTER_CONTROL_ARP_AGE_MODE          1
-+#define QCA8K_HROUTER_PBASED_CONTROL1                 0xe08
-+#define QCA8K_HROUTER_PBASED_CONTROL2                 0xe0c
-+#define QCA8K_HNAT_CONTROL                            0xe38
-+
-+/* MIB registers */
-+#define QCA8K_PORT_MIB_COUNTER(_i)                    (0x1000 + (_i) * 0x100)
-+
-+/* QCA specific MII registers */
-+#define MII_ATH_MMD_ADDR                              0x0d
-+#define MII_ATH_MMD_DATA                              0x0e
-+
-+enum {
-+      QCA8K_PORT_SPEED_10M = 0,
-+      QCA8K_PORT_SPEED_100M = 1,
-+      QCA8K_PORT_SPEED_1000M = 2,
-+      QCA8K_PORT_SPEED_ERR = 3,
-+};
-+
-+enum qca8k_fdb_cmd {
-+      QCA8K_FDB_FLUSH = 1,
-+      QCA8K_FDB_LOAD = 2,
-+      QCA8K_FDB_PURGE = 3,
-+      QCA8K_FDB_FLUSH_PORT = 5,
-+      QCA8K_FDB_NEXT = 6,
-+      QCA8K_FDB_SEARCH = 7,
-+};
-+
-+enum qca8k_vlan_cmd {
-+      QCA8K_VLAN_FLUSH = 1,
-+      QCA8K_VLAN_LOAD = 2,
-+      QCA8K_VLAN_PURGE = 3,
-+      QCA8K_VLAN_REMOVE_PORT = 4,
-+      QCA8K_VLAN_NEXT = 5,
-+      QCA8K_VLAN_READ = 6,
-+};
-+
-+enum qca8k_mid_cmd {
-+      QCA8K_MIB_FLUSH = 1,
-+      QCA8K_MIB_FLUSH_PORT = 2,
-+      QCA8K_MIB_CAST = 3,
-+};
-+
-+struct qca8k_match_data {
-+      u8 id;
-+      bool reduced_package;
-+      u8 mib_count;
-+};
-+
-+enum {
-+      QCA8K_CPU_PORT0,
-+      QCA8K_CPU_PORT6,
-+};
-+
-+struct qca8k_mgmt_eth_data {
-+      struct completion rw_done;
-+      struct mutex mutex; /* Enforce one mdio read/write at time */
-+      bool ack;
-+      u32 seq;
-+      u32 data[4];
-+};
-+
-+struct qca8k_mib_eth_data {
-+      struct completion rw_done;
-+      struct mutex mutex; /* Process one command at time */
-+      refcount_t port_parsed; /* Counter to track parsed port */
-+      u8 req_port;
-+      u64 *data; /* pointer to ethtool data */
-+};
-+
-+struct qca8k_ports_config {
-+      bool sgmii_rx_clk_falling_edge;
-+      bool sgmii_tx_clk_falling_edge;
-+      bool sgmii_enable_pll;
-+      u8 rgmii_rx_delay[QCA8K_NUM_CPU_PORTS]; /* 0: CPU port0, 1: CPU port6 */
-+      u8 rgmii_tx_delay[QCA8K_NUM_CPU_PORTS]; /* 0: CPU port0, 1: CPU port6 */
-+};
-+
-+struct qca8k_mdio_cache {
-+/* The 32bit switch registers are accessed indirectly. To achieve this we need
-+ * to set the page of the register. Track the last page that was set to reduce
-+ * mdio writes
-+ */
-+      u16 page;
-+/* lo and hi can also be cached and from Documentation we can skip one
-+ * extra mdio write if lo or hi is didn't change.
-+ */
-+      u16 lo;
-+      u16 hi;
-+};
-+
-+struct qca8k_priv {
-+      u8 switch_id;
-+      u8 switch_revision;
-+      u8 mirror_rx;
-+      u8 mirror_tx;
-+      u8 lag_hash_mode;
-+      /* Each bit correspond to a port. This switch can support a max of 7 port.
-+       * Bit 1: port enabled. Bit 0: port disabled.
-+       */
-+      u8 port_enabled_map;
-+      struct qca8k_ports_config ports_config;
-+      struct regmap *regmap;
-+      struct mii_bus *bus;
-+      struct dsa_switch *ds;
-+      struct mutex reg_mutex;
-+      struct device *dev;
-+      struct gpio_desc *reset_gpio;
-+      struct net_device *mgmt_master; /* Track if mdio/mib Ethernet is available */
-+      struct qca8k_mgmt_eth_data mgmt_eth_data;
-+      struct qca8k_mib_eth_data mib_eth_data;
-+      struct qca8k_mdio_cache mdio_cache;
-+};
-+
-+struct qca8k_mib_desc {
-+      unsigned int size;
-+      unsigned int offset;
-+      const char *name;
-+};
-+
-+struct qca8k_fdb {
-+      u16 vid;
-+      u8 port_mask;
-+      u8 aging;
-+      u8 mac[6];
-+};
-+
-+#endif /* __QCA8K_H */
---- a/drivers/net/dsa/qca8k.c
-+++ /dev/null
-@@ -1,3243 +0,0 @@
--// SPDX-License-Identifier: GPL-2.0
--/*
-- * Copyright (C) 2009 Felix Fietkau <[email protected]>
-- * Copyright (C) 2011-2012 Gabor Juhos <[email protected]>
-- * Copyright (c) 2015, 2019, The Linux Foundation. All rights reserved.
-- * Copyright (c) 2016 John Crispin <[email protected]>
-- */
--
--#include <linux/module.h>
--#include <linux/phy.h>
--#include <linux/netdevice.h>
--#include <linux/bitfield.h>
--#include <linux/regmap.h>
--#include <net/dsa.h>
--#include <linux/of_net.h>
--#include <linux/of_mdio.h>
--#include <linux/of_platform.h>
--#include <linux/if_bridge.h>
--#include <linux/mdio.h>
--#include <linux/phylink.h>
--#include <linux/gpio/consumer.h>
--#include <linux/etherdevice.h>
--#include <linux/dsa/tag_qca.h>
--
--#include "qca8k.h"
--
--#define MIB_DESC(_s, _o, _n)  \
--      {                       \
--              .size = (_s),   \
--              .offset = (_o), \
--              .name = (_n),   \
--      }
--
--static const struct qca8k_mib_desc ar8327_mib[] = {
--      MIB_DESC(1, 0x00, "RxBroad"),
--      MIB_DESC(1, 0x04, "RxPause"),
--      MIB_DESC(1, 0x08, "RxMulti"),
--      MIB_DESC(1, 0x0c, "RxFcsErr"),
--      MIB_DESC(1, 0x10, "RxAlignErr"),
--      MIB_DESC(1, 0x14, "RxRunt"),
--      MIB_DESC(1, 0x18, "RxFragment"),
--      MIB_DESC(1, 0x1c, "Rx64Byte"),
--      MIB_DESC(1, 0x20, "Rx128Byte"),
--      MIB_DESC(1, 0x24, "Rx256Byte"),
--      MIB_DESC(1, 0x28, "Rx512Byte"),
--      MIB_DESC(1, 0x2c, "Rx1024Byte"),
--      MIB_DESC(1, 0x30, "Rx1518Byte"),
--      MIB_DESC(1, 0x34, "RxMaxByte"),
--      MIB_DESC(1, 0x38, "RxTooLong"),
--      MIB_DESC(2, 0x3c, "RxGoodByte"),
--      MIB_DESC(2, 0x44, "RxBadByte"),
--      MIB_DESC(1, 0x4c, "RxOverFlow"),
--      MIB_DESC(1, 0x50, "Filtered"),
--      MIB_DESC(1, 0x54, "TxBroad"),
--      MIB_DESC(1, 0x58, "TxPause"),
--      MIB_DESC(1, 0x5c, "TxMulti"),
--      MIB_DESC(1, 0x60, "TxUnderRun"),
--      MIB_DESC(1, 0x64, "Tx64Byte"),
--      MIB_DESC(1, 0x68, "Tx128Byte"),
--      MIB_DESC(1, 0x6c, "Tx256Byte"),
--      MIB_DESC(1, 0x70, "Tx512Byte"),
--      MIB_DESC(1, 0x74, "Tx1024Byte"),
--      MIB_DESC(1, 0x78, "Tx1518Byte"),
--      MIB_DESC(1, 0x7c, "TxMaxByte"),
--      MIB_DESC(1, 0x80, "TxOverSize"),
--      MIB_DESC(2, 0x84, "TxByte"),
--      MIB_DESC(1, 0x8c, "TxCollision"),
--      MIB_DESC(1, 0x90, "TxAbortCol"),
--      MIB_DESC(1, 0x94, "TxMultiCol"),
--      MIB_DESC(1, 0x98, "TxSingleCol"),
--      MIB_DESC(1, 0x9c, "TxExcDefer"),
--      MIB_DESC(1, 0xa0, "TxDefer"),
--      MIB_DESC(1, 0xa4, "TxLateCol"),
--      MIB_DESC(1, 0xa8, "RXUnicast"),
--      MIB_DESC(1, 0xac, "TXUnicast"),
--};
--
--static void
--qca8k_split_addr(u32 regaddr, u16 *r1, u16 *r2, u16 *page)
--{
--      regaddr >>= 1;
--      *r1 = regaddr & 0x1e;
--
--      regaddr >>= 5;
--      *r2 = regaddr & 0x7;
--
--      regaddr >>= 3;
--      *page = regaddr & 0x3ff;
--}
--
--static int
--qca8k_set_lo(struct qca8k_priv *priv, int phy_id, u32 regnum, u16 lo)
--{
--      u16 *cached_lo = &priv->mdio_cache.lo;
--      struct mii_bus *bus = priv->bus;
--      int ret;
--
--      if (lo == *cached_lo)
--              return 0;
--
--      ret = bus->write(bus, phy_id, regnum, lo);
--      if (ret < 0)
--              dev_err_ratelimited(&bus->dev,
--                                  "failed to write qca8k 32bit lo register\n");
--
--      *cached_lo = lo;
--      return 0;
--}
--
--static int
--qca8k_set_hi(struct qca8k_priv *priv, int phy_id, u32 regnum, u16 hi)
--{
--      u16 *cached_hi = &priv->mdio_cache.hi;
--      struct mii_bus *bus = priv->bus;
--      int ret;
--
--      if (hi == *cached_hi)
--              return 0;
--
--      ret = bus->write(bus, phy_id, regnum, hi);
--      if (ret < 0)
--              dev_err_ratelimited(&bus->dev,
--                                  "failed to write qca8k 32bit hi register\n");
--
--      *cached_hi = hi;
--      return 0;
--}
--
--static int
--qca8k_mii_read32(struct mii_bus *bus, int phy_id, u32 regnum, u32 *val)
--{
--      int ret;
--
--      ret = bus->read(bus, phy_id, regnum);
--      if (ret >= 0) {
--              *val = ret;
--              ret = bus->read(bus, phy_id, regnum + 1);
--              *val |= ret << 16;
--      }
--
--      if (ret < 0) {
--              dev_err_ratelimited(&bus->dev,
--                                  "failed to read qca8k 32bit register\n");
--              *val = 0;
--              return ret;
--      }
--
--      return 0;
--}
--
--static void
--qca8k_mii_write32(struct qca8k_priv *priv, int phy_id, u32 regnum, u32 val)
--{
--      u16 lo, hi;
--      int ret;
--
--      lo = val & 0xffff;
--      hi = (u16)(val >> 16);
--
--      ret = qca8k_set_lo(priv, phy_id, regnum, lo);
--      if (ret >= 0)
--              ret = qca8k_set_hi(priv, phy_id, regnum + 1, hi);
--}
--
--static int
--qca8k_set_page(struct qca8k_priv *priv, u16 page)
--{
--      u16 *cached_page = &priv->mdio_cache.page;
--      struct mii_bus *bus = priv->bus;
--      int ret;
--
--      if (page == *cached_page)
--              return 0;
--
--      ret = bus->write(bus, 0x18, 0, page);
--      if (ret < 0) {
--              dev_err_ratelimited(&bus->dev,
--                                  "failed to set qca8k page\n");
--              return ret;
--      }
--
--      *cached_page = page;
--      usleep_range(1000, 2000);
--      return 0;
--}
--
--static int
--qca8k_read(struct qca8k_priv *priv, u32 reg, u32 *val)
--{
--      return regmap_read(priv->regmap, reg, val);
--}
--
--static int
--qca8k_write(struct qca8k_priv *priv, u32 reg, u32 val)
--{
--      return regmap_write(priv->regmap, reg, val);
--}
--
--static int
--qca8k_rmw(struct qca8k_priv *priv, u32 reg, u32 mask, u32 write_val)
--{
--      return regmap_update_bits(priv->regmap, reg, mask, write_val);
--}
--
--static void qca8k_rw_reg_ack_handler(struct dsa_switch *ds, struct sk_buff *skb)
--{
--      struct qca8k_mgmt_eth_data *mgmt_eth_data;
--      struct qca8k_priv *priv = ds->priv;
--      struct qca_mgmt_ethhdr *mgmt_ethhdr;
--      u8 len, cmd;
--
--      mgmt_ethhdr = (struct qca_mgmt_ethhdr *)skb_mac_header(skb);
--      mgmt_eth_data = &priv->mgmt_eth_data;
--
--      cmd = FIELD_GET(QCA_HDR_MGMT_CMD, mgmt_ethhdr->command);
--      len = FIELD_GET(QCA_HDR_MGMT_LENGTH, mgmt_ethhdr->command);
--
--      /* Make sure the seq match the requested packet */
--      if (mgmt_ethhdr->seq == mgmt_eth_data->seq)
--              mgmt_eth_data->ack = true;
--
--      if (cmd == MDIO_READ) {
--              mgmt_eth_data->data[0] = mgmt_ethhdr->mdio_data;
--
--              /* Get the rest of the 12 byte of data.
--               * The read/write function will extract the requested data.
--               */
--              if (len > QCA_HDR_MGMT_DATA1_LEN)
--                      memcpy(mgmt_eth_data->data + 1, skb->data,
--                             QCA_HDR_MGMT_DATA2_LEN);
--      }
--
--      complete(&mgmt_eth_data->rw_done);
--}
--
--static struct sk_buff *qca8k_alloc_mdio_header(enum mdio_cmd cmd, u32 reg, u32 *val,
--                                             int priority, unsigned int len)
--{
--      struct qca_mgmt_ethhdr *mgmt_ethhdr;
--      unsigned int real_len;
--      struct sk_buff *skb;
--      u32 *data2;
--      u16 hdr;
--
--      skb = dev_alloc_skb(QCA_HDR_MGMT_PKT_LEN);
--      if (!skb)
--              return NULL;
--
--      /* Max value for len reg is 15 (0xf) but the switch actually return 16 byte
--       * Actually for some reason the steps are:
--       * 0: nothing
--       * 1-4: first 4 byte
--       * 5-6: first 12 byte
--       * 7-15: all 16 byte
--       */
--      if (len == 16)
--              real_len = 15;
--      else
--              real_len = len;
--
--      skb_reset_mac_header(skb);
--      skb_set_network_header(skb, skb->len);
--
--      mgmt_ethhdr = skb_push(skb, QCA_HDR_MGMT_HEADER_LEN + QCA_HDR_LEN);
--
--      hdr = FIELD_PREP(QCA_HDR_XMIT_VERSION, QCA_HDR_VERSION);
--      hdr |= FIELD_PREP(QCA_HDR_XMIT_PRIORITY, priority);
--      hdr |= QCA_HDR_XMIT_FROM_CPU;
--      hdr |= FIELD_PREP(QCA_HDR_XMIT_DP_BIT, BIT(0));
--      hdr |= FIELD_PREP(QCA_HDR_XMIT_CONTROL, QCA_HDR_XMIT_TYPE_RW_REG);
--
--      mgmt_ethhdr->command = FIELD_PREP(QCA_HDR_MGMT_ADDR, reg);
--      mgmt_ethhdr->command |= FIELD_PREP(QCA_HDR_MGMT_LENGTH, real_len);
--      mgmt_ethhdr->command |= FIELD_PREP(QCA_HDR_MGMT_CMD, cmd);
--      mgmt_ethhdr->command |= FIELD_PREP(QCA_HDR_MGMT_CHECK_CODE,
--                                         QCA_HDR_MGMT_CHECK_CODE_VAL);
--
--      if (cmd == MDIO_WRITE)
--              mgmt_ethhdr->mdio_data = *val;
--
--      mgmt_ethhdr->hdr = htons(hdr);
--
--      data2 = skb_put_zero(skb, QCA_HDR_MGMT_DATA2_LEN + QCA_HDR_MGMT_PADDING_LEN);
--      if (cmd == MDIO_WRITE && len > QCA_HDR_MGMT_DATA1_LEN)
--              memcpy(data2, val + 1, len - QCA_HDR_MGMT_DATA1_LEN);
--
--      return skb;
--}
--
--static void qca8k_mdio_header_fill_seq_num(struct sk_buff *skb, u32 seq_num)
--{
--      struct qca_mgmt_ethhdr *mgmt_ethhdr;
--
--      mgmt_ethhdr = (struct qca_mgmt_ethhdr *)skb->data;
--      mgmt_ethhdr->seq = FIELD_PREP(QCA_HDR_MGMT_SEQ_NUM, seq_num);
--}
--
--static int qca8k_read_eth(struct qca8k_priv *priv, u32 reg, u32 *val, int len)
--{
--      struct qca8k_mgmt_eth_data *mgmt_eth_data = &priv->mgmt_eth_data;
--      struct sk_buff *skb;
--      bool ack;
--      int ret;
--
--      skb = qca8k_alloc_mdio_header(MDIO_READ, reg, NULL,
--                                    QCA8K_ETHERNET_MDIO_PRIORITY, len);
--      if (!skb)
--              return -ENOMEM;
--
--      mutex_lock(&mgmt_eth_data->mutex);
--
--      /* Check mgmt_master if is operational */
--      if (!priv->mgmt_master) {
--              kfree_skb(skb);
--              mutex_unlock(&mgmt_eth_data->mutex);
--              return -EINVAL;
--      }
--
--      skb->dev = priv->mgmt_master;
--
--      reinit_completion(&mgmt_eth_data->rw_done);
--
--      /* Increment seq_num and set it in the mdio pkt */
--      mgmt_eth_data->seq++;
--      qca8k_mdio_header_fill_seq_num(skb, mgmt_eth_data->seq);
--      mgmt_eth_data->ack = false;
--
--      dev_queue_xmit(skb);
--
--      ret = wait_for_completion_timeout(&mgmt_eth_data->rw_done,
--                                        msecs_to_jiffies(QCA8K_ETHERNET_TIMEOUT));
--
--      *val = mgmt_eth_data->data[0];
--      if (len > QCA_HDR_MGMT_DATA1_LEN)
--              memcpy(val + 1, mgmt_eth_data->data + 1, len - QCA_HDR_MGMT_DATA1_LEN);
--
--      ack = mgmt_eth_data->ack;
--
--      mutex_unlock(&mgmt_eth_data->mutex);
--
--      if (ret <= 0)
--              return -ETIMEDOUT;
--
--      if (!ack)
--              return -EINVAL;
--
--      return 0;
--}
--
--static int qca8k_write_eth(struct qca8k_priv *priv, u32 reg, u32 *val, int len)
--{
--      struct qca8k_mgmt_eth_data *mgmt_eth_data = &priv->mgmt_eth_data;
--      struct sk_buff *skb;
--      bool ack;
--      int ret;
--
--      skb = qca8k_alloc_mdio_header(MDIO_WRITE, reg, val,
--                                    QCA8K_ETHERNET_MDIO_PRIORITY, len);
--      if (!skb)
--              return -ENOMEM;
--
--      mutex_lock(&mgmt_eth_data->mutex);
--
--      /* Check mgmt_master if is operational */
--      if (!priv->mgmt_master) {
--              kfree_skb(skb);
--              mutex_unlock(&mgmt_eth_data->mutex);
--              return -EINVAL;
--      }
--
--      skb->dev = priv->mgmt_master;
--
--      reinit_completion(&mgmt_eth_data->rw_done);
--
--      /* Increment seq_num and set it in the mdio pkt */
--      mgmt_eth_data->seq++;
--      qca8k_mdio_header_fill_seq_num(skb, mgmt_eth_data->seq);
--      mgmt_eth_data->ack = false;
--
--      dev_queue_xmit(skb);
--
--      ret = wait_for_completion_timeout(&mgmt_eth_data->rw_done,
--                                        msecs_to_jiffies(QCA8K_ETHERNET_TIMEOUT));
--
--      ack = mgmt_eth_data->ack;
--
--      mutex_unlock(&mgmt_eth_data->mutex);
--
--      if (ret <= 0)
--              return -ETIMEDOUT;
--
--      if (!ack)
--              return -EINVAL;
--
--      return 0;
--}
--
--static int
--qca8k_regmap_update_bits_eth(struct qca8k_priv *priv, u32 reg, u32 mask, u32 write_val)
--{
--      u32 val = 0;
--      int ret;
--
--      ret = qca8k_read_eth(priv, reg, &val, sizeof(val));
--      if (ret)
--              return ret;
--
--      val &= ~mask;
--      val |= write_val;
--
--      return qca8k_write_eth(priv, reg, &val, sizeof(val));
--}
--
--static int
--qca8k_bulk_read(struct qca8k_priv *priv, u32 reg, u32 *val, int len)
--{
--      int i, count = len / sizeof(u32), ret;
--
--      if (priv->mgmt_master && !qca8k_read_eth(priv, reg, val, len))
--              return 0;
--
--      for (i = 0; i < count; i++) {
--              ret = regmap_read(priv->regmap, reg + (i * 4), val + i);
--              if (ret < 0)
--                      return ret;
--      }
--
--      return 0;
--}
--
--static int
--qca8k_bulk_write(struct qca8k_priv *priv, u32 reg, u32 *val, int len)
--{
--      int i, count = len / sizeof(u32), ret;
--      u32 tmp;
--
--      if (priv->mgmt_master && !qca8k_write_eth(priv, reg, val, len))
--              return 0;
--
--      for (i = 0; i < count; i++) {
--              tmp = val[i];
--
--              ret = regmap_write(priv->regmap, reg + (i * 4), tmp);
--              if (ret < 0)
--                      return ret;
--      }
--
--      return 0;
--}
--
--static int
--qca8k_regmap_read(void *ctx, uint32_t reg, uint32_t *val)
--{
--      struct qca8k_priv *priv = (struct qca8k_priv *)ctx;
--      struct mii_bus *bus = priv->bus;
--      u16 r1, r2, page;
--      int ret;
--
--      if (!qca8k_read_eth(priv, reg, val, sizeof(*val)))
--              return 0;
--
--      qca8k_split_addr(reg, &r1, &r2, &page);
--
--      mutex_lock_nested(&bus->mdio_lock, MDIO_MUTEX_NESTED);
--
--      ret = qca8k_set_page(priv, page);
--      if (ret < 0)
--              goto exit;
--
--      ret = qca8k_mii_read32(bus, 0x10 | r2, r1, val);
--
--exit:
--      mutex_unlock(&bus->mdio_lock);
--      return ret;
--}
--
--static int
--qca8k_regmap_write(void *ctx, uint32_t reg, uint32_t val)
--{
--      struct qca8k_priv *priv = (struct qca8k_priv *)ctx;
--      struct mii_bus *bus = priv->bus;
--      u16 r1, r2, page;
--      int ret;
--
--      if (!qca8k_write_eth(priv, reg, &val, sizeof(val)))
--              return 0;
--
--      qca8k_split_addr(reg, &r1, &r2, &page);
--
--      mutex_lock_nested(&bus->mdio_lock, MDIO_MUTEX_NESTED);
--
--      ret = qca8k_set_page(priv, page);
--      if (ret < 0)
--              goto exit;
--
--      qca8k_mii_write32(priv, 0x10 | r2, r1, val);
--
--exit:
--      mutex_unlock(&bus->mdio_lock);
--      return ret;
--}
--
--static int
--qca8k_regmap_update_bits(void *ctx, uint32_t reg, uint32_t mask, uint32_t write_val)
--{
--      struct qca8k_priv *priv = (struct qca8k_priv *)ctx;
--      struct mii_bus *bus = priv->bus;
--      u16 r1, r2, page;
--      u32 val;
--      int ret;
--
--      if (!qca8k_regmap_update_bits_eth(priv, reg, mask, write_val))
--              return 0;
--
--      qca8k_split_addr(reg, &r1, &r2, &page);
--
--      mutex_lock_nested(&bus->mdio_lock, MDIO_MUTEX_NESTED);
--
--      ret = qca8k_set_page(priv, page);
--      if (ret < 0)
--              goto exit;
--
--      ret = qca8k_mii_read32(bus, 0x10 | r2, r1, &val);
--      if (ret < 0)
--              goto exit;
--
--      val &= ~mask;
--      val |= write_val;
--      qca8k_mii_write32(priv, 0x10 | r2, r1, val);
--
--exit:
--      mutex_unlock(&bus->mdio_lock);
--
--      return ret;
--}
--
--static const struct regmap_range qca8k_readable_ranges[] = {
--      regmap_reg_range(0x0000, 0x00e4), /* Global control */
--      regmap_reg_range(0x0100, 0x0168), /* EEE control */
--      regmap_reg_range(0x0200, 0x0270), /* Parser control */
--      regmap_reg_range(0x0400, 0x0454), /* ACL */
--      regmap_reg_range(0x0600, 0x0718), /* Lookup */
--      regmap_reg_range(0x0800, 0x0b70), /* QM */
--      regmap_reg_range(0x0c00, 0x0c80), /* PKT */
--      regmap_reg_range(0x0e00, 0x0e98), /* L3 */
--      regmap_reg_range(0x1000, 0x10ac), /* MIB - Port0 */
--      regmap_reg_range(0x1100, 0x11ac), /* MIB - Port1 */
--      regmap_reg_range(0x1200, 0x12ac), /* MIB - Port2 */
--      regmap_reg_range(0x1300, 0x13ac), /* MIB - Port3 */
--      regmap_reg_range(0x1400, 0x14ac), /* MIB - Port4 */
--      regmap_reg_range(0x1500, 0x15ac), /* MIB - Port5 */
--      regmap_reg_range(0x1600, 0x16ac), /* MIB - Port6 */
--
--};
--
--static const struct regmap_access_table qca8k_readable_table = {
--      .yes_ranges = qca8k_readable_ranges,
--      .n_yes_ranges = ARRAY_SIZE(qca8k_readable_ranges),
--};
--
--static struct regmap_config qca8k_regmap_config = {
--      .reg_bits = 16,
--      .val_bits = 32,
--      .reg_stride = 4,
--      .max_register = 0x16ac, /* end MIB - Port6 range */
--      .reg_read = qca8k_regmap_read,
--      .reg_write = qca8k_regmap_write,
--      .reg_update_bits = qca8k_regmap_update_bits,
--      .rd_table = &qca8k_readable_table,
--      .disable_locking = true, /* Locking is handled by qca8k read/write */
--      .cache_type = REGCACHE_NONE, /* Explicitly disable CACHE */
--};
--
--static int
--qca8k_busy_wait(struct qca8k_priv *priv, u32 reg, u32 mask)
--{
--      u32 val;
--
--      return regmap_read_poll_timeout(priv->regmap, reg, val, !(val & mask), 0,
--                                     QCA8K_BUSY_WAIT_TIMEOUT * USEC_PER_MSEC);
--}
--
--static int
--qca8k_fdb_read(struct qca8k_priv *priv, struct qca8k_fdb *fdb)
--{
--      u32 reg[3];
--      int ret;
--
--      /* load the ARL table into an array */
--      ret = qca8k_bulk_read(priv, QCA8K_REG_ATU_DATA0, reg, sizeof(reg));
--      if (ret)
--              return ret;
--
--      /* vid - 83:72 */
--      fdb->vid = FIELD_GET(QCA8K_ATU_VID_MASK, reg[2]);
--      /* aging - 67:64 */
--      fdb->aging = FIELD_GET(QCA8K_ATU_STATUS_MASK, reg[2]);
--      /* portmask - 54:48 */
--      fdb->port_mask = FIELD_GET(QCA8K_ATU_PORT_MASK, reg[1]);
--      /* mac - 47:0 */
--      fdb->mac[0] = FIELD_GET(QCA8K_ATU_ADDR0_MASK, reg[1]);
--      fdb->mac[1] = FIELD_GET(QCA8K_ATU_ADDR1_MASK, reg[1]);
--      fdb->mac[2] = FIELD_GET(QCA8K_ATU_ADDR2_MASK, reg[0]);
--      fdb->mac[3] = FIELD_GET(QCA8K_ATU_ADDR3_MASK, reg[0]);
--      fdb->mac[4] = FIELD_GET(QCA8K_ATU_ADDR4_MASK, reg[0]);
--      fdb->mac[5] = FIELD_GET(QCA8K_ATU_ADDR5_MASK, reg[0]);
--
--      return 0;
--}
--
--static void
--qca8k_fdb_write(struct qca8k_priv *priv, u16 vid, u8 port_mask, const u8 *mac,
--              u8 aging)
--{
--      u32 reg[3] = { 0 };
--
--      /* vid - 83:72 */
--      reg[2] = FIELD_PREP(QCA8K_ATU_VID_MASK, vid);
--      /* aging - 67:64 */
--      reg[2] |= FIELD_PREP(QCA8K_ATU_STATUS_MASK, aging);
--      /* portmask - 54:48 */
--      reg[1] = FIELD_PREP(QCA8K_ATU_PORT_MASK, port_mask);
--      /* mac - 47:0 */
--      reg[1] |= FIELD_PREP(QCA8K_ATU_ADDR0_MASK, mac[0]);
--      reg[1] |= FIELD_PREP(QCA8K_ATU_ADDR1_MASK, mac[1]);
--      reg[0] |= FIELD_PREP(QCA8K_ATU_ADDR2_MASK, mac[2]);
--      reg[0] |= FIELD_PREP(QCA8K_ATU_ADDR3_MASK, mac[3]);
--      reg[0] |= FIELD_PREP(QCA8K_ATU_ADDR4_MASK, mac[4]);
--      reg[0] |= FIELD_PREP(QCA8K_ATU_ADDR5_MASK, mac[5]);
--
--      /* load the array into the ARL table */
--      qca8k_bulk_write(priv, QCA8K_REG_ATU_DATA0, reg, sizeof(reg));
--}
--
--static int
--qca8k_fdb_access(struct qca8k_priv *priv, enum qca8k_fdb_cmd cmd, int port)
--{
--      u32 reg;
--      int ret;
--
--      /* Set the command and FDB index */
--      reg = QCA8K_ATU_FUNC_BUSY;
--      reg |= cmd;
--      if (port >= 0) {
--              reg |= QCA8K_ATU_FUNC_PORT_EN;
--              reg |= FIELD_PREP(QCA8K_ATU_FUNC_PORT_MASK, port);
--      }
--
--      /* Write the function register triggering the table access */
--      ret = qca8k_write(priv, QCA8K_REG_ATU_FUNC, reg);
--      if (ret)
--              return ret;
--
--      /* wait for completion */
--      ret = qca8k_busy_wait(priv, QCA8K_REG_ATU_FUNC, QCA8K_ATU_FUNC_BUSY);
--      if (ret)
--              return ret;
--
--      /* Check for table full violation when adding an entry */
--      if (cmd == QCA8K_FDB_LOAD) {
--              ret = qca8k_read(priv, QCA8K_REG_ATU_FUNC, &reg);
--              if (ret < 0)
--                      return ret;
--              if (reg & QCA8K_ATU_FUNC_FULL)
--                      return -1;
--      }
--
--      return 0;
--}
--
--static int
--qca8k_fdb_next(struct qca8k_priv *priv, struct qca8k_fdb *fdb, int port)
--{
--      int ret;
--
--      qca8k_fdb_write(priv, fdb->vid, fdb->port_mask, fdb->mac, fdb->aging);
--      ret = qca8k_fdb_access(priv, QCA8K_FDB_NEXT, port);
--      if (ret < 0)
--              return ret;
--
--      return qca8k_fdb_read(priv, fdb);
--}
--
--static int
--qca8k_fdb_add(struct qca8k_priv *priv, const u8 *mac, u16 port_mask,
--            u16 vid, u8 aging)
--{
--      int ret;
--
--      mutex_lock(&priv->reg_mutex);
--      qca8k_fdb_write(priv, vid, port_mask, mac, aging);
--      ret = qca8k_fdb_access(priv, QCA8K_FDB_LOAD, -1);
--      mutex_unlock(&priv->reg_mutex);
--
--      return ret;
--}
--
--static int
--qca8k_fdb_del(struct qca8k_priv *priv, const u8 *mac, u16 port_mask, u16 vid)
--{
--      int ret;
--
--      mutex_lock(&priv->reg_mutex);
--      qca8k_fdb_write(priv, vid, port_mask, mac, 0);
--      ret = qca8k_fdb_access(priv, QCA8K_FDB_PURGE, -1);
--      mutex_unlock(&priv->reg_mutex);
--
--      return ret;
--}
--
--static void
--qca8k_fdb_flush(struct qca8k_priv *priv)
--{
--      mutex_lock(&priv->reg_mutex);
--      qca8k_fdb_access(priv, QCA8K_FDB_FLUSH, -1);
--      mutex_unlock(&priv->reg_mutex);
--}
--
--static int
--qca8k_fdb_search_and_insert(struct qca8k_priv *priv, u8 port_mask,
--                          const u8 *mac, u16 vid)
--{
--      struct qca8k_fdb fdb = { 0 };
--      int ret;
--
--      mutex_lock(&priv->reg_mutex);
--
--      qca8k_fdb_write(priv, vid, 0, mac, 0);
--      ret = qca8k_fdb_access(priv, QCA8K_FDB_SEARCH, -1);
--      if (ret < 0)
--              goto exit;
--
--      ret = qca8k_fdb_read(priv, &fdb);
--      if (ret < 0)
--              goto exit;
--
--      /* Rule exist. Delete first */
--      if (!fdb.aging) {
--              ret = qca8k_fdb_access(priv, QCA8K_FDB_PURGE, -1);
--              if (ret)
--                      goto exit;
--      }
--
--      /* Add port to fdb portmask */
--      fdb.port_mask |= port_mask;
--
--      qca8k_fdb_write(priv, vid, fdb.port_mask, mac, fdb.aging);
--      ret = qca8k_fdb_access(priv, QCA8K_FDB_LOAD, -1);
--
--exit:
--      mutex_unlock(&priv->reg_mutex);
--      return ret;
--}
--
--static int
--qca8k_fdb_search_and_del(struct qca8k_priv *priv, u8 port_mask,
--                       const u8 *mac, u16 vid)
--{
--      struct qca8k_fdb fdb = { 0 };
--      int ret;
--
--      mutex_lock(&priv->reg_mutex);
--
--      qca8k_fdb_write(priv, vid, 0, mac, 0);
--      ret = qca8k_fdb_access(priv, QCA8K_FDB_SEARCH, -1);
--      if (ret < 0)
--              goto exit;
--
--      /* Rule doesn't exist. Why delete? */
--      if (!fdb.aging) {
--              ret = -EINVAL;
--              goto exit;
--      }
--
--      ret = qca8k_fdb_access(priv, QCA8K_FDB_PURGE, -1);
--      if (ret)
--              goto exit;
--
--      /* Only port in the rule is this port. Don't re insert */
--      if (fdb.port_mask == port_mask)
--              goto exit;
--
--      /* Remove port from port mask */
--      fdb.port_mask &= ~port_mask;
--
--      qca8k_fdb_write(priv, vid, fdb.port_mask, mac, fdb.aging);
--      ret = qca8k_fdb_access(priv, QCA8K_FDB_LOAD, -1);
--
--exit:
--      mutex_unlock(&priv->reg_mutex);
--      return ret;
--}
--
--static int
--qca8k_vlan_access(struct qca8k_priv *priv, enum qca8k_vlan_cmd cmd, u16 vid)
--{
--      u32 reg;
--      int ret;
--
--      /* Set the command and VLAN index */
--      reg = QCA8K_VTU_FUNC1_BUSY;
--      reg |= cmd;
--      reg |= FIELD_PREP(QCA8K_VTU_FUNC1_VID_MASK, vid);
--
--      /* Write the function register triggering the table access */
--      ret = qca8k_write(priv, QCA8K_REG_VTU_FUNC1, reg);
--      if (ret)
--              return ret;
--
--      /* wait for completion */
--      ret = qca8k_busy_wait(priv, QCA8K_REG_VTU_FUNC1, QCA8K_VTU_FUNC1_BUSY);
--      if (ret)
--              return ret;
--
--      /* Check for table full violation when adding an entry */
--      if (cmd == QCA8K_VLAN_LOAD) {
--              ret = qca8k_read(priv, QCA8K_REG_VTU_FUNC1, &reg);
--              if (ret < 0)
--                      return ret;
--              if (reg & QCA8K_VTU_FUNC1_FULL)
--                      return -ENOMEM;
--      }
--
--      return 0;
--}
--
--static int
--qca8k_vlan_add(struct qca8k_priv *priv, u8 port, u16 vid, bool untagged)
--{
--      u32 reg;
--      int ret;
--
--      /*
--         We do the right thing with VLAN 0 and treat it as untagged while
--         preserving the tag on egress.
--       */
--      if (vid == 0)
--              return 0;
--
--      mutex_lock(&priv->reg_mutex);
--      ret = qca8k_vlan_access(priv, QCA8K_VLAN_READ, vid);
--      if (ret < 0)
--              goto out;
--
--      ret = qca8k_read(priv, QCA8K_REG_VTU_FUNC0, &reg);
--      if (ret < 0)
--              goto out;
--      reg |= QCA8K_VTU_FUNC0_VALID | QCA8K_VTU_FUNC0_IVL_EN;
--      reg &= ~QCA8K_VTU_FUNC0_EG_MODE_PORT_MASK(port);
--      if (untagged)
--              reg |= QCA8K_VTU_FUNC0_EG_MODE_PORT_UNTAG(port);
--      else
--              reg |= QCA8K_VTU_FUNC0_EG_MODE_PORT_TAG(port);
--
--      ret = qca8k_write(priv, QCA8K_REG_VTU_FUNC0, reg);
--      if (ret)
--              goto out;
--      ret = qca8k_vlan_access(priv, QCA8K_VLAN_LOAD, vid);
--
--out:
--      mutex_unlock(&priv->reg_mutex);
--
--      return ret;
--}
--
--static int
--qca8k_vlan_del(struct qca8k_priv *priv, u8 port, u16 vid)
--{
--      u32 reg, mask;
--      int ret, i;
--      bool del;
--
--      mutex_lock(&priv->reg_mutex);
--      ret = qca8k_vlan_access(priv, QCA8K_VLAN_READ, vid);
--      if (ret < 0)
--              goto out;
--
--      ret = qca8k_read(priv, QCA8K_REG_VTU_FUNC0, &reg);
--      if (ret < 0)
--              goto out;
--      reg &= ~QCA8K_VTU_FUNC0_EG_MODE_PORT_MASK(port);
--      reg |= QCA8K_VTU_FUNC0_EG_MODE_PORT_NOT(port);
--
--      /* Check if we're the last member to be removed */
--      del = true;
--      for (i = 0; i < QCA8K_NUM_PORTS; i++) {
--              mask = QCA8K_VTU_FUNC0_EG_MODE_PORT_NOT(i);
--
--              if ((reg & mask) != mask) {
--                      del = false;
--                      break;
--              }
--      }
--
--      if (del) {
--              ret = qca8k_vlan_access(priv, QCA8K_VLAN_PURGE, vid);
--      } else {
--              ret = qca8k_write(priv, QCA8K_REG_VTU_FUNC0, reg);
--              if (ret)
--                      goto out;
--              ret = qca8k_vlan_access(priv, QCA8K_VLAN_LOAD, vid);
--      }
--
--out:
--      mutex_unlock(&priv->reg_mutex);
--
--      return ret;
--}
--
--static int
--qca8k_mib_init(struct qca8k_priv *priv)
--{
--      int ret;
--
--      mutex_lock(&priv->reg_mutex);
--      ret = regmap_update_bits(priv->regmap, QCA8K_REG_MIB,
--                               QCA8K_MIB_FUNC | QCA8K_MIB_BUSY,
--                               FIELD_PREP(QCA8K_MIB_FUNC, QCA8K_MIB_FLUSH) |
--                               QCA8K_MIB_BUSY);
--      if (ret)
--              goto exit;
--
--      ret = qca8k_busy_wait(priv, QCA8K_REG_MIB, QCA8K_MIB_BUSY);
--      if (ret)
--              goto exit;
--
--      ret = regmap_set_bits(priv->regmap, QCA8K_REG_MIB, QCA8K_MIB_CPU_KEEP);
--      if (ret)
--              goto exit;
--
--      ret = qca8k_write(priv, QCA8K_REG_MODULE_EN, QCA8K_MODULE_EN_MIB);
--
--exit:
--      mutex_unlock(&priv->reg_mutex);
--      return ret;
--}
--
--static void
--qca8k_port_set_status(struct qca8k_priv *priv, int port, int enable)
--{
--      u32 mask = QCA8K_PORT_STATUS_TXMAC | QCA8K_PORT_STATUS_RXMAC;
--
--      /* Port 0 and 6 have no internal PHY */
--      if (port > 0 && port < 6)
--              mask |= QCA8K_PORT_STATUS_LINK_AUTO;
--
--      if (enable)
--              regmap_set_bits(priv->regmap, QCA8K_REG_PORT_STATUS(port), mask);
--      else
--              regmap_clear_bits(priv->regmap, QCA8K_REG_PORT_STATUS(port), mask);
--}
--
--static int
--qca8k_phy_eth_busy_wait(struct qca8k_mgmt_eth_data *mgmt_eth_data,
--                      struct sk_buff *read_skb, u32 *val)
--{
--      struct sk_buff *skb = skb_copy(read_skb, GFP_KERNEL);
--      bool ack;
--      int ret;
--
--      reinit_completion(&mgmt_eth_data->rw_done);
--
--      /* Increment seq_num and set it in the copy pkt */
--      mgmt_eth_data->seq++;
--      qca8k_mdio_header_fill_seq_num(skb, mgmt_eth_data->seq);
--      mgmt_eth_data->ack = false;
--
--      dev_queue_xmit(skb);
--
--      ret = wait_for_completion_timeout(&mgmt_eth_data->rw_done,
--                                        QCA8K_ETHERNET_TIMEOUT);
--
--      ack = mgmt_eth_data->ack;
--
--      if (ret <= 0)
--              return -ETIMEDOUT;
--
--      if (!ack)
--              return -EINVAL;
--
--      *val = mgmt_eth_data->data[0];
--
--      return 0;
--}
--
--static int
--qca8k_phy_eth_command(struct qca8k_priv *priv, bool read, int phy,
--                    int regnum, u16 data)
--{
--      struct sk_buff *write_skb, *clear_skb, *read_skb;
--      struct qca8k_mgmt_eth_data *mgmt_eth_data;
--      u32 write_val, clear_val = 0, val;
--      struct net_device *mgmt_master;
--      int ret, ret1;
--      bool ack;
--
--      if (regnum >= QCA8K_MDIO_MASTER_MAX_REG)
--              return -EINVAL;
--
--      mgmt_eth_data = &priv->mgmt_eth_data;
--
--      write_val = QCA8K_MDIO_MASTER_BUSY | QCA8K_MDIO_MASTER_EN |
--                  QCA8K_MDIO_MASTER_PHY_ADDR(phy) |
--                  QCA8K_MDIO_MASTER_REG_ADDR(regnum);
--
--      if (read) {
--              write_val |= QCA8K_MDIO_MASTER_READ;
--      } else {
--              write_val |= QCA8K_MDIO_MASTER_WRITE;
--              write_val |= QCA8K_MDIO_MASTER_DATA(data);
--      }
--
--      /* Prealloc all the needed skb before the lock */
--      write_skb = qca8k_alloc_mdio_header(MDIO_WRITE, QCA8K_MDIO_MASTER_CTRL, &write_val,
--                                          QCA8K_ETHERNET_PHY_PRIORITY, sizeof(write_val));
--      if (!write_skb)
--              return -ENOMEM;
--
--      clear_skb = qca8k_alloc_mdio_header(MDIO_WRITE, QCA8K_MDIO_MASTER_CTRL, &clear_val,
--                                          QCA8K_ETHERNET_PHY_PRIORITY, sizeof(clear_val));
--      if (!clear_skb) {
--              ret = -ENOMEM;
--              goto err_clear_skb;
--      }
--
--      read_skb = qca8k_alloc_mdio_header(MDIO_READ, QCA8K_MDIO_MASTER_CTRL, &clear_val,
--                                         QCA8K_ETHERNET_PHY_PRIORITY, sizeof(clear_val));
--      if (!read_skb) {
--              ret = -ENOMEM;
--              goto err_read_skb;
--      }
--
--      /* Actually start the request:
--       * 1. Send mdio master packet
--       * 2. Busy Wait for mdio master command
--       * 3. Get the data if we are reading
--       * 4. Reset the mdio master (even with error)
--       */
--      mutex_lock(&mgmt_eth_data->mutex);
--
--      /* Check if mgmt_master is operational */
--      mgmt_master = priv->mgmt_master;
--      if (!mgmt_master) {
--              mutex_unlock(&mgmt_eth_data->mutex);
--              ret = -EINVAL;
--              goto err_mgmt_master;
--      }
--
--      read_skb->dev = mgmt_master;
--      clear_skb->dev = mgmt_master;
--      write_skb->dev = mgmt_master;
--
--      reinit_completion(&mgmt_eth_data->rw_done);
--
--      /* Increment seq_num and set it in the write pkt */
--      mgmt_eth_data->seq++;
--      qca8k_mdio_header_fill_seq_num(write_skb, mgmt_eth_data->seq);
--      mgmt_eth_data->ack = false;
--
--      dev_queue_xmit(write_skb);
--
--      ret = wait_for_completion_timeout(&mgmt_eth_data->rw_done,
--                                        QCA8K_ETHERNET_TIMEOUT);
--
--      ack = mgmt_eth_data->ack;
--
--      if (ret <= 0) {
--              ret = -ETIMEDOUT;
--              kfree_skb(read_skb);
--              goto exit;
--      }
--
--      if (!ack) {
--              ret = -EINVAL;
--              kfree_skb(read_skb);
--              goto exit;
--      }
--
--      ret = read_poll_timeout(qca8k_phy_eth_busy_wait, ret1,
--                              !(val & QCA8K_MDIO_MASTER_BUSY), 0,
--                              QCA8K_BUSY_WAIT_TIMEOUT * USEC_PER_MSEC, false,
--                              mgmt_eth_data, read_skb, &val);
--
--      if (ret < 0 && ret1 < 0) {
--              ret = ret1;
--              goto exit;
--      }
--
--      if (read) {
--              reinit_completion(&mgmt_eth_data->rw_done);
--
--              /* Increment seq_num and set it in the read pkt */
--              mgmt_eth_data->seq++;
--              qca8k_mdio_header_fill_seq_num(read_skb, mgmt_eth_data->seq);
--              mgmt_eth_data->ack = false;
--
--              dev_queue_xmit(read_skb);
--
--              ret = wait_for_completion_timeout(&mgmt_eth_data->rw_done,
--                                                QCA8K_ETHERNET_TIMEOUT);
--
--              ack = mgmt_eth_data->ack;
--
--              if (ret <= 0) {
--                      ret = -ETIMEDOUT;
--                      goto exit;
--              }
--
--              if (!ack) {
--                      ret = -EINVAL;
--                      goto exit;
--              }
--
--              ret = mgmt_eth_data->data[0] & QCA8K_MDIO_MASTER_DATA_MASK;
--      } else {
--              kfree_skb(read_skb);
--      }
--exit:
--      reinit_completion(&mgmt_eth_data->rw_done);
--
--      /* Increment seq_num and set it in the clear pkt */
--      mgmt_eth_data->seq++;
--      qca8k_mdio_header_fill_seq_num(clear_skb, mgmt_eth_data->seq);
--      mgmt_eth_data->ack = false;
--
--      dev_queue_xmit(clear_skb);
--
--      wait_for_completion_timeout(&mgmt_eth_data->rw_done,
--                                  QCA8K_ETHERNET_TIMEOUT);
--
--      mutex_unlock(&mgmt_eth_data->mutex);
--
--      return ret;
--
--      /* Error handling before lock */
--err_mgmt_master:
--      kfree_skb(read_skb);
--err_read_skb:
--      kfree_skb(clear_skb);
--err_clear_skb:
--      kfree_skb(write_skb);
--
--      return ret;
--}
--
--static u32
--qca8k_port_to_phy(int port)
--{
--      /* From Andrew Lunn:
--       * Port 0 has no internal phy.
--       * Port 1 has an internal PHY at MDIO address 0.
--       * Port 2 has an internal PHY at MDIO address 1.
--       * ...
--       * Port 5 has an internal PHY at MDIO address 4.
--       * Port 6 has no internal PHY.
--       */
--
--      return port - 1;
--}
--
--static int
--qca8k_mdio_busy_wait(struct mii_bus *bus, u32 reg, u32 mask)
--{
--      u16 r1, r2, page;
--      u32 val;
--      int ret, ret1;
--
--      qca8k_split_addr(reg, &r1, &r2, &page);
--
--      ret = read_poll_timeout(qca8k_mii_read32, ret1, !(val & mask), 0,
--                              QCA8K_BUSY_WAIT_TIMEOUT * USEC_PER_MSEC, false,
--                              bus, 0x10 | r2, r1, &val);
--
--      /* Check if qca8k_read has failed for a different reason
--       * before returnting -ETIMEDOUT
--       */
--      if (ret < 0 && ret1 < 0)
--              return ret1;
--
--      return ret;
--}
--
--static int
--qca8k_mdio_write(struct qca8k_priv *priv, int phy, int regnum, u16 data)
--{
--      struct mii_bus *bus = priv->bus;
--      u16 r1, r2, page;
--      u32 val;
--      int ret;
--
--      if (regnum >= QCA8K_MDIO_MASTER_MAX_REG)
--              return -EINVAL;
--
--      val = QCA8K_MDIO_MASTER_BUSY | QCA8K_MDIO_MASTER_EN |
--            QCA8K_MDIO_MASTER_WRITE | QCA8K_MDIO_MASTER_PHY_ADDR(phy) |
--            QCA8K_MDIO_MASTER_REG_ADDR(regnum) |
--            QCA8K_MDIO_MASTER_DATA(data);
--
--      qca8k_split_addr(QCA8K_MDIO_MASTER_CTRL, &r1, &r2, &page);
--
--      mutex_lock_nested(&bus->mdio_lock, MDIO_MUTEX_NESTED);
--
--      ret = qca8k_set_page(priv, page);
--      if (ret)
--              goto exit;
--
--      qca8k_mii_write32(priv, 0x10 | r2, r1, val);
--
--      ret = qca8k_mdio_busy_wait(bus, QCA8K_MDIO_MASTER_CTRL,
--                                 QCA8K_MDIO_MASTER_BUSY);
--
--exit:
--      /* even if the busy_wait timeouts try to clear the MASTER_EN */
--      qca8k_mii_write32(priv, 0x10 | r2, r1, 0);
--
--      mutex_unlock(&bus->mdio_lock);
--
--      return ret;
--}
--
--static int
--qca8k_mdio_read(struct qca8k_priv *priv, int phy, int regnum)
--{
--      struct mii_bus *bus = priv->bus;
--      u16 r1, r2, page;
--      u32 val;
--      int ret;
--
--      if (regnum >= QCA8K_MDIO_MASTER_MAX_REG)
--              return -EINVAL;
--
--      val = QCA8K_MDIO_MASTER_BUSY | QCA8K_MDIO_MASTER_EN |
--            QCA8K_MDIO_MASTER_READ | QCA8K_MDIO_MASTER_PHY_ADDR(phy) |
--            QCA8K_MDIO_MASTER_REG_ADDR(regnum);
--
--      qca8k_split_addr(QCA8K_MDIO_MASTER_CTRL, &r1, &r2, &page);
--
--      mutex_lock_nested(&bus->mdio_lock, MDIO_MUTEX_NESTED);
--
--      ret = qca8k_set_page(priv, page);
--      if (ret)
--              goto exit;
--
--      qca8k_mii_write32(priv, 0x10 | r2, r1, val);
--
--      ret = qca8k_mdio_busy_wait(bus, QCA8K_MDIO_MASTER_CTRL,
--                                 QCA8K_MDIO_MASTER_BUSY);
--      if (ret)
--              goto exit;
--
--      ret = qca8k_mii_read32(bus, 0x10 | r2, r1, &val);
--
--exit:
--      /* even if the busy_wait timeouts try to clear the MASTER_EN */
--      qca8k_mii_write32(priv, 0x10 | r2, r1, 0);
--
--      mutex_unlock(&bus->mdio_lock);
--
--      if (ret >= 0)
--              ret = val & QCA8K_MDIO_MASTER_DATA_MASK;
--
--      return ret;
--}
--
--static int
--qca8k_internal_mdio_write(struct mii_bus *slave_bus, int phy, int regnum, u16 data)
--{
--      struct qca8k_priv *priv = slave_bus->priv;
--      int ret;
--
--      /* Use mdio Ethernet when available, fallback to legacy one on error */
--      ret = qca8k_phy_eth_command(priv, false, phy, regnum, data);
--      if (!ret)
--              return 0;
--
--      return qca8k_mdio_write(priv, phy, regnum, data);
--}
--
--static int
--qca8k_internal_mdio_read(struct mii_bus *slave_bus, int phy, int regnum)
--{
--      struct qca8k_priv *priv = slave_bus->priv;
--      int ret;
--
--      /* Use mdio Ethernet when available, fallback to legacy one on error */
--      ret = qca8k_phy_eth_command(priv, true, phy, regnum, 0);
--      if (ret >= 0)
--              return ret;
--
--      ret = qca8k_mdio_read(priv, phy, regnum);
--
--      if (ret < 0)
--              return 0xffff;
--
--      return ret;
--}
--
--static int
--qca8k_legacy_mdio_write(struct mii_bus *slave_bus, int port, int regnum, u16 data)
--{
--      port = qca8k_port_to_phy(port) % PHY_MAX_ADDR;
--
--      return qca8k_internal_mdio_write(slave_bus, port, regnum, data);
--}
--
--static int
--qca8k_legacy_mdio_read(struct mii_bus *slave_bus, int port, int regnum)
--{
--      port = qca8k_port_to_phy(port) % PHY_MAX_ADDR;
--
--      return qca8k_internal_mdio_read(slave_bus, port, regnum);
--}
--
--static int
--qca8k_mdio_register(struct qca8k_priv *priv)
--{
--      struct dsa_switch *ds = priv->ds;
--      struct device_node *mdio;
--      struct mii_bus *bus;
--
--      bus = devm_mdiobus_alloc(ds->dev);
--      if (!bus)
--              return -ENOMEM;
--
--      bus->priv = (void *)priv;
--      snprintf(bus->id, MII_BUS_ID_SIZE, "qca8k-%d.%d",
--               ds->dst->index, ds->index);
--      bus->parent = ds->dev;
--      bus->phy_mask = ~ds->phys_mii_mask;
--      ds->slave_mii_bus = bus;
--
--      /* Check if the devicetree declare the port:phy mapping */
--      mdio = of_get_child_by_name(priv->dev->of_node, "mdio");
--      if (of_device_is_available(mdio)) {
--              bus->name = "qca8k slave mii";
--              bus->read = qca8k_internal_mdio_read;
--              bus->write = qca8k_internal_mdio_write;
--              return devm_of_mdiobus_register(priv->dev, bus, mdio);
--      }
--
--      /* If a mapping can't be found the legacy mapping is used,
--       * using the qca8k_port_to_phy function
--       */
--      bus->name = "qca8k-legacy slave mii";
--      bus->read = qca8k_legacy_mdio_read;
--      bus->write = qca8k_legacy_mdio_write;
--      return devm_mdiobus_register(priv->dev, bus);
--}
--
--static int
--qca8k_setup_mdio_bus(struct qca8k_priv *priv)
--{
--      u32 internal_mdio_mask = 0, external_mdio_mask = 0, reg;
--      struct device_node *ports, *port;
--      phy_interface_t mode;
--      int err;
--
--      ports = of_get_child_by_name(priv->dev->of_node, "ports");
--      if (!ports)
--              ports = of_get_child_by_name(priv->dev->of_node, "ethernet-ports");
--
--      if (!ports)
--              return -EINVAL;
--
--      for_each_available_child_of_node(ports, port) {
--              err = of_property_read_u32(port, "reg", &reg);
--              if (err) {
--                      of_node_put(port);
--                      of_node_put(ports);
--                      return err;
--              }
--
--              if (!dsa_is_user_port(priv->ds, reg))
--                      continue;
--
--              of_get_phy_mode(port, &mode);
--
--              if (of_property_read_bool(port, "phy-handle") &&
--                  mode != PHY_INTERFACE_MODE_INTERNAL)
--                      external_mdio_mask |= BIT(reg);
--              else
--                      internal_mdio_mask |= BIT(reg);
--      }
--
--      of_node_put(ports);
--      if (!external_mdio_mask && !internal_mdio_mask) {
--              dev_err(priv->dev, "no PHYs are defined.\n");
--              return -EINVAL;
--      }
--
--      /* The QCA8K_MDIO_MASTER_EN Bit, which grants access to PHYs through
--       * the MDIO_MASTER register also _disconnects_ the external MDC
--       * passthrough to the internal PHYs. It's not possible to use both
--       * configurations at the same time!
--       *
--       * Because this came up during the review process:
--       * If the external mdio-bus driver is capable magically disabling
--       * the QCA8K_MDIO_MASTER_EN and mutex/spin-locking out the qca8k's
--       * accessors for the time being, it would be possible to pull this
--       * off.
--       */
--      if (!!external_mdio_mask && !!internal_mdio_mask) {
--              dev_err(priv->dev, "either internal or external mdio bus configuration is supported.\n");
--              return -EINVAL;
--      }
--
--      if (external_mdio_mask) {
--              /* Make sure to disable the internal mdio bus in cases
--               * a dt-overlay and driver reload changed the configuration
--               */
--
--              return regmap_clear_bits(priv->regmap, QCA8K_MDIO_MASTER_CTRL,
--                                       QCA8K_MDIO_MASTER_EN);
--      }
--
--      return qca8k_mdio_register(priv);
--}
--
--static int
--qca8k_setup_mac_pwr_sel(struct qca8k_priv *priv)
--{
--      u32 mask = 0;
--      int ret = 0;
--
--      /* SoC specific settings for ipq8064.
--       * If more device require this consider adding
--       * a dedicated binding.
--       */
--      if (of_machine_is_compatible("qcom,ipq8064"))
--              mask |= QCA8K_MAC_PWR_RGMII0_1_8V;
--
--      /* SoC specific settings for ipq8065 */
--      if (of_machine_is_compatible("qcom,ipq8065"))
--              mask |= QCA8K_MAC_PWR_RGMII1_1_8V;
--
--      if (mask) {
--              ret = qca8k_rmw(priv, QCA8K_REG_MAC_PWR_SEL,
--                              QCA8K_MAC_PWR_RGMII0_1_8V |
--                              QCA8K_MAC_PWR_RGMII1_1_8V,
--                              mask);
--      }
--
--      return ret;
--}
--
--static int qca8k_find_cpu_port(struct dsa_switch *ds)
--{
--      struct qca8k_priv *priv = ds->priv;
--
--      /* Find the connected cpu port. Valid port are 0 or 6 */
--      if (dsa_is_cpu_port(ds, 0))
--              return 0;
--
--      dev_dbg(priv->dev, "port 0 is not the CPU port. Checking port 6");
--
--      if (dsa_is_cpu_port(ds, 6))
--              return 6;
--
--      return -EINVAL;
--}
--
--static int
--qca8k_setup_of_pws_reg(struct qca8k_priv *priv)
--{
--      struct device_node *node = priv->dev->of_node;
--      const struct qca8k_match_data *data;
--      u32 val = 0;
--      int ret;
--
--      /* QCA8327 require to set to the correct mode.
--       * His bigger brother QCA8328 have the 172 pin layout.
--       * Should be applied by default but we set this just to make sure.
--       */
--      if (priv->switch_id == QCA8K_ID_QCA8327) {
--              data = of_device_get_match_data(priv->dev);
--
--              /* Set the correct package of 148 pin for QCA8327 */
--              if (data->reduced_package)
--                      val |= QCA8327_PWS_PACKAGE148_EN;
--
--              ret = qca8k_rmw(priv, QCA8K_REG_PWS, QCA8327_PWS_PACKAGE148_EN,
--                              val);
--              if (ret)
--                      return ret;
--      }
--
--      if (of_property_read_bool(node, "qca,ignore-power-on-sel"))
--              val |= QCA8K_PWS_POWER_ON_SEL;
--
--      if (of_property_read_bool(node, "qca,led-open-drain")) {
--              if (!(val & QCA8K_PWS_POWER_ON_SEL)) {
--                      dev_err(priv->dev, "qca,led-open-drain require qca,ignore-power-on-sel to be set.");
--                      return -EINVAL;
--              }
--
--              val |= QCA8K_PWS_LED_OPEN_EN_CSR;
--      }
--
--      return qca8k_rmw(priv, QCA8K_REG_PWS,
--                      QCA8K_PWS_LED_OPEN_EN_CSR | QCA8K_PWS_POWER_ON_SEL,
--                      val);
--}
--
--static int
--qca8k_parse_port_config(struct qca8k_priv *priv)
--{
--      int port, cpu_port_index = -1, ret;
--      struct device_node *port_dn;
--      phy_interface_t mode;
--      struct dsa_port *dp;
--      u32 delay;
--
--      /* We have 2 CPU port. Check them */
--      for (port = 0; port < QCA8K_NUM_PORTS; port++) {
--              /* Skip every other port */
--              if (port != 0 && port != 6)
--                      continue;
--
--              dp = dsa_to_port(priv->ds, port);
--              port_dn = dp->dn;
--              cpu_port_index++;
--
--              if (!of_device_is_available(port_dn))
--                      continue;
--
--              ret = of_get_phy_mode(port_dn, &mode);
--              if (ret)
--                      continue;
--
--              switch (mode) {
--              case PHY_INTERFACE_MODE_RGMII:
--              case PHY_INTERFACE_MODE_RGMII_ID:
--              case PHY_INTERFACE_MODE_RGMII_TXID:
--              case PHY_INTERFACE_MODE_RGMII_RXID:
--              case PHY_INTERFACE_MODE_SGMII:
--                      delay = 0;
--
--                      if (!of_property_read_u32(port_dn, "tx-internal-delay-ps", &delay))
--                              /* Switch regs accept value in ns, convert ps to ns */
--                              delay = delay / 1000;
--                      else if (mode == PHY_INTERFACE_MODE_RGMII_ID ||
--                               mode == PHY_INTERFACE_MODE_RGMII_TXID)
--                              delay = 1;
--
--                      if (!FIELD_FIT(QCA8K_PORT_PAD_RGMII_TX_DELAY_MASK, delay)) {
--                              dev_err(priv->dev, "rgmii tx delay is limited to a max value of 3ns, setting to the max value");
--                              delay = 3;
--                      }
--
--                      priv->ports_config.rgmii_tx_delay[cpu_port_index] = delay;
--
--                      delay = 0;
--
--                      if (!of_property_read_u32(port_dn, "rx-internal-delay-ps", &delay))
--                              /* Switch regs accept value in ns, convert ps to ns */
--                              delay = delay / 1000;
--                      else if (mode == PHY_INTERFACE_MODE_RGMII_ID ||
--                               mode == PHY_INTERFACE_MODE_RGMII_RXID)
--                              delay = 2;
--
--                      if (!FIELD_FIT(QCA8K_PORT_PAD_RGMII_RX_DELAY_MASK, delay)) {
--                              dev_err(priv->dev, "rgmii rx delay is limited to a max value of 3ns, setting to the max value");
--                              delay = 3;
--                      }
--
--                      priv->ports_config.rgmii_rx_delay[cpu_port_index] = delay;
--
--                      /* Skip sgmii parsing for rgmii* mode */
--                      if (mode == PHY_INTERFACE_MODE_RGMII ||
--                          mode == PHY_INTERFACE_MODE_RGMII_ID ||
--                          mode == PHY_INTERFACE_MODE_RGMII_TXID ||
--                          mode == PHY_INTERFACE_MODE_RGMII_RXID)
--                              break;
--
--                      if (of_property_read_bool(port_dn, "qca,sgmii-txclk-falling-edge"))
--                              priv->ports_config.sgmii_tx_clk_falling_edge = true;
--
--                      if (of_property_read_bool(port_dn, "qca,sgmii-rxclk-falling-edge"))
--                              priv->ports_config.sgmii_rx_clk_falling_edge = true;
--
--                      if (of_property_read_bool(port_dn, "qca,sgmii-enable-pll")) {
--                              priv->ports_config.sgmii_enable_pll = true;
--
--                              if (priv->switch_id == QCA8K_ID_QCA8327) {
--                                      dev_err(priv->dev, "SGMII PLL should NOT be enabled for qca8327. Aborting enabling");
--                                      priv->ports_config.sgmii_enable_pll = false;
--                              }
--
--                              if (priv->switch_revision < 2)
--                                      dev_warn(priv->dev, "SGMII PLL should NOT be enabled for qca8337 with revision 2 or more.");
--                      }
--
--                      break;
--              default:
--                      continue;
--              }
--      }
--
--      return 0;
--}
--
--static int
--qca8k_setup(struct dsa_switch *ds)
--{
--      struct qca8k_priv *priv = (struct qca8k_priv *)ds->priv;
--      int cpu_port, ret, i;
--      u32 mask;
--
--      cpu_port = qca8k_find_cpu_port(ds);
--      if (cpu_port < 0) {
--              dev_err(priv->dev, "No cpu port configured in both cpu port0 and port6");
--              return cpu_port;
--      }
--
--      /* Parse CPU port config to be later used in phy_link mac_config */
--      ret = qca8k_parse_port_config(priv);
--      if (ret)
--              return ret;
--
--      ret = qca8k_setup_mdio_bus(priv);
--      if (ret)
--              return ret;
--
--      ret = qca8k_setup_of_pws_reg(priv);
--      if (ret)
--              return ret;
--
--      ret = qca8k_setup_mac_pwr_sel(priv);
--      if (ret)
--              return ret;
--
--      /* Make sure MAC06 is disabled */
--      ret = regmap_clear_bits(priv->regmap, QCA8K_REG_PORT0_PAD_CTRL,
--                              QCA8K_PORT0_PAD_MAC06_EXCHANGE_EN);
--      if (ret) {
--              dev_err(priv->dev, "failed disabling MAC06 exchange");
--              return ret;
--      }
--
--      /* Enable CPU Port */
--      ret = regmap_set_bits(priv->regmap, QCA8K_REG_GLOBAL_FW_CTRL0,
--                            QCA8K_GLOBAL_FW_CTRL0_CPU_PORT_EN);
--      if (ret) {
--              dev_err(priv->dev, "failed enabling CPU port");
--              return ret;
--      }
--
--      /* Enable MIB counters */
--      ret = qca8k_mib_init(priv);
--      if (ret)
--              dev_warn(priv->dev, "mib init failed");
--
--      /* Initial setup of all ports */
--      for (i = 0; i < QCA8K_NUM_PORTS; i++) {
--              /* Disable forwarding by default on all ports */
--              ret = qca8k_rmw(priv, QCA8K_PORT_LOOKUP_CTRL(i),
--                              QCA8K_PORT_LOOKUP_MEMBER, 0);
--              if (ret)
--                      return ret;
--
--              /* Enable QCA header mode on all cpu ports */
--              if (dsa_is_cpu_port(ds, i)) {
--                      ret = qca8k_write(priv, QCA8K_REG_PORT_HDR_CTRL(i),
--                                        FIELD_PREP(QCA8K_PORT_HDR_CTRL_TX_MASK, QCA8K_PORT_HDR_CTRL_ALL) |
--                                        FIELD_PREP(QCA8K_PORT_HDR_CTRL_RX_MASK, QCA8K_PORT_HDR_CTRL_ALL));
--                      if (ret) {
--                              dev_err(priv->dev, "failed enabling QCA header mode");
--                              return ret;
--                      }
--              }
--
--              /* Disable MAC by default on all user ports */
--              if (dsa_is_user_port(ds, i))
--                      qca8k_port_set_status(priv, i, 0);
--      }
--
--      /* Forward all unknown frames to CPU port for Linux processing
--       * Notice that in multi-cpu config only one port should be set
--       * for igmp, unknown, multicast and broadcast packet
--       */
--      ret = qca8k_write(priv, QCA8K_REG_GLOBAL_FW_CTRL1,
--                        FIELD_PREP(QCA8K_GLOBAL_FW_CTRL1_IGMP_DP_MASK, BIT(cpu_port)) |
--                        FIELD_PREP(QCA8K_GLOBAL_FW_CTRL1_BC_DP_MASK, BIT(cpu_port)) |
--                        FIELD_PREP(QCA8K_GLOBAL_FW_CTRL1_MC_DP_MASK, BIT(cpu_port)) |
--                        FIELD_PREP(QCA8K_GLOBAL_FW_CTRL1_UC_DP_MASK, BIT(cpu_port)));
--      if (ret)
--              return ret;
--
--      /* Setup connection between CPU port & user ports
--       * Configure specific switch configuration for ports
--       */
--      for (i = 0; i < QCA8K_NUM_PORTS; i++) {
--              /* CPU port gets connected to all user ports of the switch */
--              if (dsa_is_cpu_port(ds, i)) {
--                      ret = qca8k_rmw(priv, QCA8K_PORT_LOOKUP_CTRL(i),
--                                      QCA8K_PORT_LOOKUP_MEMBER, dsa_user_ports(ds));
--                      if (ret)
--                              return ret;
--              }
--
--              /* Individual user ports get connected to CPU port only */
--              if (dsa_is_user_port(ds, i)) {
--                      ret = qca8k_rmw(priv, QCA8K_PORT_LOOKUP_CTRL(i),
--                                      QCA8K_PORT_LOOKUP_MEMBER,
--                                      BIT(cpu_port));
--                      if (ret)
--                              return ret;
--
--                      /* Enable ARP Auto-learning by default */
--                      ret = regmap_set_bits(priv->regmap, QCA8K_PORT_LOOKUP_CTRL(i),
--                                            QCA8K_PORT_LOOKUP_LEARN);
--                      if (ret)
--                              return ret;
--
--                      /* For port based vlans to work we need to set the
--                       * default egress vid
--                       */
--                      ret = qca8k_rmw(priv, QCA8K_EGRESS_VLAN(i),
--                                      QCA8K_EGREES_VLAN_PORT_MASK(i),
--                                      QCA8K_EGREES_VLAN_PORT(i, QCA8K_PORT_VID_DEF));
--                      if (ret)
--                              return ret;
--
--                      ret = qca8k_write(priv, QCA8K_REG_PORT_VLAN_CTRL0(i),
--                                        QCA8K_PORT_VLAN_CVID(QCA8K_PORT_VID_DEF) |
--                                        QCA8K_PORT_VLAN_SVID(QCA8K_PORT_VID_DEF));
--                      if (ret)
--                              return ret;
--              }
--
--              /* The port 5 of the qca8337 have some problem in flood condition. The
--               * original legacy driver had some specific buffer and priority settings
--               * for the different port suggested by the QCA switch team. Add this
--               * missing settings to improve switch stability under load condition.
--               * This problem is limited to qca8337 and other qca8k switch are not affected.
--               */
--              if (priv->switch_id == QCA8K_ID_QCA8337) {
--                      switch (i) {
--                      /* The 2 CPU port and port 5 requires some different
--                       * priority than any other ports.
--                       */
--                      case 0:
--                      case 5:
--                      case 6:
--                              mask = QCA8K_PORT_HOL_CTRL0_EG_PRI0(0x3) |
--                                      QCA8K_PORT_HOL_CTRL0_EG_PRI1(0x4) |
--                                      QCA8K_PORT_HOL_CTRL0_EG_PRI2(0x4) |
--                                      QCA8K_PORT_HOL_CTRL0_EG_PRI3(0x4) |
--                                      QCA8K_PORT_HOL_CTRL0_EG_PRI4(0x6) |
--                                      QCA8K_PORT_HOL_CTRL0_EG_PRI5(0x8) |
--                                      QCA8K_PORT_HOL_CTRL0_EG_PORT(0x1e);
--                              break;
--                      default:
--                              mask = QCA8K_PORT_HOL_CTRL0_EG_PRI0(0x3) |
--                                      QCA8K_PORT_HOL_CTRL0_EG_PRI1(0x4) |
--                                      QCA8K_PORT_HOL_CTRL0_EG_PRI2(0x6) |
--                                      QCA8K_PORT_HOL_CTRL0_EG_PRI3(0x8) |
--                                      QCA8K_PORT_HOL_CTRL0_EG_PORT(0x19);
--                      }
--                      qca8k_write(priv, QCA8K_REG_PORT_HOL_CTRL0(i), mask);
--
--                      mask = QCA8K_PORT_HOL_CTRL1_ING(0x6) |
--                      QCA8K_PORT_HOL_CTRL1_EG_PRI_BUF_EN |
--                      QCA8K_PORT_HOL_CTRL1_EG_PORT_BUF_EN |
--                      QCA8K_PORT_HOL_CTRL1_WRED_EN;
--                      qca8k_rmw(priv, QCA8K_REG_PORT_HOL_CTRL1(i),
--                                QCA8K_PORT_HOL_CTRL1_ING_BUF_MASK |
--                                QCA8K_PORT_HOL_CTRL1_EG_PRI_BUF_EN |
--                                QCA8K_PORT_HOL_CTRL1_EG_PORT_BUF_EN |
--                                QCA8K_PORT_HOL_CTRL1_WRED_EN,
--                                mask);
--              }
--      }
--
--      /* Special GLOBAL_FC_THRESH value are needed for ar8327 switch */
--      if (priv->switch_id == QCA8K_ID_QCA8327) {
--              mask = QCA8K_GLOBAL_FC_GOL_XON_THRES(288) |
--                     QCA8K_GLOBAL_FC_GOL_XOFF_THRES(496);
--              qca8k_rmw(priv, QCA8K_REG_GLOBAL_FC_THRESH,
--                        QCA8K_GLOBAL_FC_GOL_XON_THRES_MASK |
--                        QCA8K_GLOBAL_FC_GOL_XOFF_THRES_MASK,
--                        mask);
--      }
--
--      /* Setup our port MTUs to match power on defaults */
--      ret = qca8k_write(priv, QCA8K_MAX_FRAME_SIZE, ETH_FRAME_LEN + ETH_FCS_LEN);
--      if (ret)
--              dev_warn(priv->dev, "failed setting MTU settings");
--
--      /* Flush the FDB table */
--      qca8k_fdb_flush(priv);
--
--      /* We don't have interrupts for link changes, so we need to poll */
--      ds->pcs_poll = true;
--
--      /* Set min a max ageing value supported */
--      ds->ageing_time_min = 7000;
--      ds->ageing_time_max = 458745000;
--
--      /* Set max number of LAGs supported */
--      ds->num_lag_ids = QCA8K_NUM_LAGS;
--
--      return 0;
--}
--
--static void
--qca8k_mac_config_setup_internal_delay(struct qca8k_priv *priv, int cpu_port_index,
--                                    u32 reg)
--{
--      u32 delay, val = 0;
--      int ret;
--
--      /* Delay can be declared in 3 different way.
--       * Mode to rgmii and internal-delay standard binding defined
--       * rgmii-id or rgmii-tx/rx phy mode set.
--       * The parse logic set a delay different than 0 only when one
--       * of the 3 different way is used. In all other case delay is
--       * not enabled. With ID or TX/RXID delay is enabled and set
--       * to the default and recommended value.
--       */
--      if (priv->ports_config.rgmii_tx_delay[cpu_port_index]) {
--              delay = priv->ports_config.rgmii_tx_delay[cpu_port_index];
--
--              val |= QCA8K_PORT_PAD_RGMII_TX_DELAY(delay) |
--                      QCA8K_PORT_PAD_RGMII_TX_DELAY_EN;
--      }
--
--      if (priv->ports_config.rgmii_rx_delay[cpu_port_index]) {
--              delay = priv->ports_config.rgmii_rx_delay[cpu_port_index];
--
--              val |= QCA8K_PORT_PAD_RGMII_RX_DELAY(delay) |
--                      QCA8K_PORT_PAD_RGMII_RX_DELAY_EN;
--      }
--
--      /* Set RGMII delay based on the selected values */
--      ret = qca8k_rmw(priv, reg,
--                      QCA8K_PORT_PAD_RGMII_TX_DELAY_MASK |
--                      QCA8K_PORT_PAD_RGMII_RX_DELAY_MASK |
--                      QCA8K_PORT_PAD_RGMII_TX_DELAY_EN |
--                      QCA8K_PORT_PAD_RGMII_RX_DELAY_EN,
--                      val);
--      if (ret)
--              dev_err(priv->dev, "Failed to set internal delay for CPU port%d",
--                      cpu_port_index == QCA8K_CPU_PORT0 ? 0 : 6);
--}
--
--static void
--qca8k_phylink_mac_config(struct dsa_switch *ds, int port, unsigned int mode,
--                       const struct phylink_link_state *state)
--{
--      struct qca8k_priv *priv = ds->priv;
--      int cpu_port_index, ret;
--      u32 reg, val;
--
--      switch (port) {
--      case 0: /* 1st CPU port */
--              if (state->interface != PHY_INTERFACE_MODE_RGMII &&
--                  state->interface != PHY_INTERFACE_MODE_RGMII_ID &&
--                  state->interface != PHY_INTERFACE_MODE_RGMII_TXID &&
--                  state->interface != PHY_INTERFACE_MODE_RGMII_RXID &&
--                  state->interface != PHY_INTERFACE_MODE_SGMII)
--                      return;
--
--              reg = QCA8K_REG_PORT0_PAD_CTRL;
--              cpu_port_index = QCA8K_CPU_PORT0;
--              break;
--      case 1:
--      case 2:
--      case 3:
--      case 4:
--      case 5:
--              /* Internal PHY, nothing to do */
--              return;
--      case 6: /* 2nd CPU port / external PHY */
--              if (state->interface != PHY_INTERFACE_MODE_RGMII &&
--                  state->interface != PHY_INTERFACE_MODE_RGMII_ID &&
--                  state->interface != PHY_INTERFACE_MODE_RGMII_TXID &&
--                  state->interface != PHY_INTERFACE_MODE_RGMII_RXID &&
--                  state->interface != PHY_INTERFACE_MODE_SGMII &&
--                  state->interface != PHY_INTERFACE_MODE_1000BASEX)
--                      return;
--
--              reg = QCA8K_REG_PORT6_PAD_CTRL;
--              cpu_port_index = QCA8K_CPU_PORT6;
--              break;
--      default:
--              dev_err(ds->dev, "%s: unsupported port: %i\n", __func__, port);
--              return;
--      }
--
--      if (port != 6 && phylink_autoneg_inband(mode)) {
--              dev_err(ds->dev, "%s: in-band negotiation unsupported\n",
--                      __func__);
--              return;
--      }
--
--      switch (state->interface) {
--      case PHY_INTERFACE_MODE_RGMII:
--      case PHY_INTERFACE_MODE_RGMII_ID:
--      case PHY_INTERFACE_MODE_RGMII_TXID:
--      case PHY_INTERFACE_MODE_RGMII_RXID:
--              qca8k_write(priv, reg, QCA8K_PORT_PAD_RGMII_EN);
--
--              /* Configure rgmii delay */
--              qca8k_mac_config_setup_internal_delay(priv, cpu_port_index, reg);
--
--              /* QCA8337 requires to set rgmii rx delay for all ports.
--               * This is enabled through PORT5_PAD_CTRL for all ports,
--               * rather than individual port registers.
--               */
--              if (priv->switch_id == QCA8K_ID_QCA8337)
--                      qca8k_write(priv, QCA8K_REG_PORT5_PAD_CTRL,
--                                  QCA8K_PORT_PAD_RGMII_RX_DELAY_EN);
--              break;
--      case PHY_INTERFACE_MODE_SGMII:
--      case PHY_INTERFACE_MODE_1000BASEX:
--              /* Enable SGMII on the port */
--              qca8k_write(priv, reg, QCA8K_PORT_PAD_SGMII_EN);
--
--              /* Enable/disable SerDes auto-negotiation as necessary */
--              ret = qca8k_read(priv, QCA8K_REG_PWS, &val);
--              if (ret)
--                      return;
--              if (phylink_autoneg_inband(mode))
--                      val &= ~QCA8K_PWS_SERDES_AEN_DIS;
--              else
--                      val |= QCA8K_PWS_SERDES_AEN_DIS;
--              qca8k_write(priv, QCA8K_REG_PWS, val);
--
--              /* Configure the SGMII parameters */
--              ret = qca8k_read(priv, QCA8K_REG_SGMII_CTRL, &val);
--              if (ret)
--                      return;
--
--              val |= QCA8K_SGMII_EN_SD;
--
--              if (priv->ports_config.sgmii_enable_pll)
--                      val |= QCA8K_SGMII_EN_PLL | QCA8K_SGMII_EN_RX |
--                             QCA8K_SGMII_EN_TX;
--
--              if (dsa_is_cpu_port(ds, port)) {
--                      /* CPU port, we're talking to the CPU MAC, be a PHY */
--                      val &= ~QCA8K_SGMII_MODE_CTRL_MASK;
--                      val |= QCA8K_SGMII_MODE_CTRL_PHY;
--              } else if (state->interface == PHY_INTERFACE_MODE_SGMII) {
--                      val &= ~QCA8K_SGMII_MODE_CTRL_MASK;
--                      val |= QCA8K_SGMII_MODE_CTRL_MAC;
--              } else if (state->interface == PHY_INTERFACE_MODE_1000BASEX) {
--                      val &= ~QCA8K_SGMII_MODE_CTRL_MASK;
--                      val |= QCA8K_SGMII_MODE_CTRL_BASEX;
--              }
--
--              qca8k_write(priv, QCA8K_REG_SGMII_CTRL, val);
--
--              /* From original code is reported port instability as SGMII also
--               * require delay set. Apply advised values here or take them from DT.
--               */
--              if (state->interface == PHY_INTERFACE_MODE_SGMII)
--                      qca8k_mac_config_setup_internal_delay(priv, cpu_port_index, reg);
--
--              /* For qca8327/qca8328/qca8334/qca8338 sgmii is unique and
--               * falling edge is set writing in the PORT0 PAD reg
--               */
--              if (priv->switch_id == QCA8K_ID_QCA8327 ||
--                  priv->switch_id == QCA8K_ID_QCA8337)
--                      reg = QCA8K_REG_PORT0_PAD_CTRL;
--
--              val = 0;
--
--              /* SGMII Clock phase configuration */
--              if (priv->ports_config.sgmii_rx_clk_falling_edge)
--                      val |= QCA8K_PORT0_PAD_SGMII_RXCLK_FALLING_EDGE;
--
--              if (priv->ports_config.sgmii_tx_clk_falling_edge)
--                      val |= QCA8K_PORT0_PAD_SGMII_TXCLK_FALLING_EDGE;
--
--              if (val)
--                      ret = qca8k_rmw(priv, reg,
--                                      QCA8K_PORT0_PAD_SGMII_RXCLK_FALLING_EDGE |
--                                      QCA8K_PORT0_PAD_SGMII_TXCLK_FALLING_EDGE,
--                                      val);
--
--              break;
--      default:
--              dev_err(ds->dev, "xMII mode %s not supported for port %d\n",
--                      phy_modes(state->interface), port);
--              return;
--      }
--}
--
--static void
--qca8k_phylink_validate(struct dsa_switch *ds, int port,
--                     unsigned long *supported,
--                     struct phylink_link_state *state)
--{
--      __ETHTOOL_DECLARE_LINK_MODE_MASK(mask) = { 0, };
--
--      switch (port) {
--      case 0: /* 1st CPU port */
--              if (state->interface != PHY_INTERFACE_MODE_NA &&
--                  state->interface != PHY_INTERFACE_MODE_RGMII &&
--                  state->interface != PHY_INTERFACE_MODE_RGMII_ID &&
--                  state->interface != PHY_INTERFACE_MODE_RGMII_TXID &&
--                  state->interface != PHY_INTERFACE_MODE_RGMII_RXID &&
--                  state->interface != PHY_INTERFACE_MODE_SGMII)
--                      goto unsupported;
--              break;
--      case 1:
--      case 2:
--      case 3:
--      case 4:
--      case 5:
--              /* Internal PHY */
--              if (state->interface != PHY_INTERFACE_MODE_NA &&
--                  state->interface != PHY_INTERFACE_MODE_GMII &&
--                  state->interface != PHY_INTERFACE_MODE_INTERNAL)
--                      goto unsupported;
--              break;
--      case 6: /* 2nd CPU port / external PHY */
--              if (state->interface != PHY_INTERFACE_MODE_NA &&
--                  state->interface != PHY_INTERFACE_MODE_RGMII &&
--                  state->interface != PHY_INTERFACE_MODE_RGMII_ID &&
--                  state->interface != PHY_INTERFACE_MODE_RGMII_TXID &&
--                  state->interface != PHY_INTERFACE_MODE_RGMII_RXID &&
--                  state->interface != PHY_INTERFACE_MODE_SGMII &&
--                  state->interface != PHY_INTERFACE_MODE_1000BASEX)
--                      goto unsupported;
--              break;
--      default:
--unsupported:
--              linkmode_zero(supported);
--              return;
--      }
--
--      phylink_set_port_modes(mask);
--      phylink_set(mask, Autoneg);
--
--      phylink_set(mask, 1000baseT_Full);
--      phylink_set(mask, 10baseT_Half);
--      phylink_set(mask, 10baseT_Full);
--      phylink_set(mask, 100baseT_Half);
--      phylink_set(mask, 100baseT_Full);
--
--      if (state->interface == PHY_INTERFACE_MODE_1000BASEX)
--              phylink_set(mask, 1000baseX_Full);
--
--      phylink_set(mask, Pause);
--      phylink_set(mask, Asym_Pause);
--
--      linkmode_and(supported, supported, mask);
--      linkmode_and(state->advertising, state->advertising, mask);
--}
--
--static int
--qca8k_phylink_mac_link_state(struct dsa_switch *ds, int port,
--                           struct phylink_link_state *state)
--{
--      struct qca8k_priv *priv = ds->priv;
--      u32 reg;
--      int ret;
--
--      ret = qca8k_read(priv, QCA8K_REG_PORT_STATUS(port), &reg);
--      if (ret < 0)
--              return ret;
--
--      state->link = !!(reg & QCA8K_PORT_STATUS_LINK_UP);
--      state->an_complete = state->link;
--      state->an_enabled = !!(reg & QCA8K_PORT_STATUS_LINK_AUTO);
--      state->duplex = (reg & QCA8K_PORT_STATUS_DUPLEX) ? DUPLEX_FULL :
--                                                         DUPLEX_HALF;
--
--      switch (reg & QCA8K_PORT_STATUS_SPEED) {
--      case QCA8K_PORT_STATUS_SPEED_10:
--              state->speed = SPEED_10;
--              break;
--      case QCA8K_PORT_STATUS_SPEED_100:
--              state->speed = SPEED_100;
--              break;
--      case QCA8K_PORT_STATUS_SPEED_1000:
--              state->speed = SPEED_1000;
--              break;
--      default:
--              state->speed = SPEED_UNKNOWN;
--              break;
--      }
--
--      state->pause = MLO_PAUSE_NONE;
--      if (reg & QCA8K_PORT_STATUS_RXFLOW)
--              state->pause |= MLO_PAUSE_RX;
--      if (reg & QCA8K_PORT_STATUS_TXFLOW)
--              state->pause |= MLO_PAUSE_TX;
--
--      return 1;
--}
--
--static void
--qca8k_phylink_mac_link_down(struct dsa_switch *ds, int port, unsigned int mode,
--                          phy_interface_t interface)
--{
--      struct qca8k_priv *priv = ds->priv;
--
--      qca8k_port_set_status(priv, port, 0);
--}
--
--static void
--qca8k_phylink_mac_link_up(struct dsa_switch *ds, int port, unsigned int mode,
--                        phy_interface_t interface, struct phy_device *phydev,
--                        int speed, int duplex, bool tx_pause, bool rx_pause)
--{
--      struct qca8k_priv *priv = ds->priv;
--      u32 reg;
--
--      if (phylink_autoneg_inband(mode)) {
--              reg = QCA8K_PORT_STATUS_LINK_AUTO;
--      } else {
--              switch (speed) {
--              case SPEED_10:
--                      reg = QCA8K_PORT_STATUS_SPEED_10;
--                      break;
--              case SPEED_100:
--                      reg = QCA8K_PORT_STATUS_SPEED_100;
--                      break;
--              case SPEED_1000:
--                      reg = QCA8K_PORT_STATUS_SPEED_1000;
--                      break;
--              default:
--                      reg = QCA8K_PORT_STATUS_LINK_AUTO;
--                      break;
--              }
--
--              if (duplex == DUPLEX_FULL)
--                      reg |= QCA8K_PORT_STATUS_DUPLEX;
--
--              if (rx_pause || dsa_is_cpu_port(ds, port))
--                      reg |= QCA8K_PORT_STATUS_RXFLOW;
--
--              if (tx_pause || dsa_is_cpu_port(ds, port))
--                      reg |= QCA8K_PORT_STATUS_TXFLOW;
--      }
--
--      reg |= QCA8K_PORT_STATUS_TXMAC | QCA8K_PORT_STATUS_RXMAC;
--
--      qca8k_write(priv, QCA8K_REG_PORT_STATUS(port), reg);
--}
--
--static void
--qca8k_get_strings(struct dsa_switch *ds, int port, u32 stringset, uint8_t *data)
--{
--      const struct qca8k_match_data *match_data;
--      struct qca8k_priv *priv = ds->priv;
--      int i;
--
--      if (stringset != ETH_SS_STATS)
--              return;
--
--      match_data = of_device_get_match_data(priv->dev);
--
--      for (i = 0; i < match_data->mib_count; i++)
--              strncpy(data + i * ETH_GSTRING_LEN, ar8327_mib[i].name,
--                      ETH_GSTRING_LEN);
--}
--
--static void qca8k_mib_autocast_handler(struct dsa_switch *ds, struct sk_buff *skb)
--{
--      const struct qca8k_match_data *match_data;
--      struct qca8k_mib_eth_data *mib_eth_data;
--      struct qca8k_priv *priv = ds->priv;
--      const struct qca8k_mib_desc *mib;
--      struct mib_ethhdr *mib_ethhdr;
--      int i, mib_len, offset = 0;
--      u64 *data;
--      u8 port;
--
--      mib_ethhdr = (struct mib_ethhdr *)skb_mac_header(skb);
--      mib_eth_data = &priv->mib_eth_data;
--
--      /* The switch autocast every port. Ignore other packet and
--       * parse only the requested one.
--       */
--      port = FIELD_GET(QCA_HDR_RECV_SOURCE_PORT, ntohs(mib_ethhdr->hdr));
--      if (port != mib_eth_data->req_port)
--              goto exit;
--
--      match_data = device_get_match_data(priv->dev);
--      data = mib_eth_data->data;
--
--      for (i = 0; i < match_data->mib_count; i++) {
--              mib = &ar8327_mib[i];
--
--              /* First 3 mib are present in the skb head */
--              if (i < 3) {
--                      data[i] = mib_ethhdr->data[i];
--                      continue;
--              }
--
--              mib_len = sizeof(uint32_t);
--
--              /* Some mib are 64 bit wide */
--              if (mib->size == 2)
--                      mib_len = sizeof(uint64_t);
--
--              /* Copy the mib value from packet to the */
--              memcpy(data + i, skb->data + offset, mib_len);
--
--              /* Set the offset for the next mib */
--              offset += mib_len;
--      }
--
--exit:
--      /* Complete on receiving all the mib packet */
--      if (refcount_dec_and_test(&mib_eth_data->port_parsed))
--              complete(&mib_eth_data->rw_done);
--}
--
--static int
--qca8k_get_ethtool_stats_eth(struct dsa_switch *ds, int port, u64 *data)
--{
--      struct dsa_port *dp = dsa_to_port(ds, port);
--      struct qca8k_mib_eth_data *mib_eth_data;
--      struct qca8k_priv *priv = ds->priv;
--      int ret;
--
--      mib_eth_data = &priv->mib_eth_data;
--
--      mutex_lock(&mib_eth_data->mutex);
--
--      reinit_completion(&mib_eth_data->rw_done);
--
--      mib_eth_data->req_port = dp->index;
--      mib_eth_data->data = data;
--      refcount_set(&mib_eth_data->port_parsed, QCA8K_NUM_PORTS);
--
--      mutex_lock(&priv->reg_mutex);
--
--      /* Send mib autocast request */
--      ret = regmap_update_bits(priv->regmap, QCA8K_REG_MIB,
--                               QCA8K_MIB_FUNC | QCA8K_MIB_BUSY,
--                               FIELD_PREP(QCA8K_MIB_FUNC, QCA8K_MIB_CAST) |
--                               QCA8K_MIB_BUSY);
--
--      mutex_unlock(&priv->reg_mutex);
--
--      if (ret)
--              goto exit;
--
--      ret = wait_for_completion_timeout(&mib_eth_data->rw_done, QCA8K_ETHERNET_TIMEOUT);
--
--exit:
--      mutex_unlock(&mib_eth_data->mutex);
--
--      return ret;
--}
--
--static void
--qca8k_get_ethtool_stats(struct dsa_switch *ds, int port,
--                      uint64_t *data)
--{
--      struct qca8k_priv *priv = (struct qca8k_priv *)ds->priv;
--      const struct qca8k_match_data *match_data;
--      const struct qca8k_mib_desc *mib;
--      u32 reg, i, val;
--      u32 hi = 0;
--      int ret;
--
--      if (priv->mgmt_master &&
--          qca8k_get_ethtool_stats_eth(ds, port, data) > 0)
--              return;
--
--      match_data = of_device_get_match_data(priv->dev);
--
--      for (i = 0; i < match_data->mib_count; i++) {
--              mib = &ar8327_mib[i];
--              reg = QCA8K_PORT_MIB_COUNTER(port) + mib->offset;
--
--              ret = qca8k_read(priv, reg, &val);
--              if (ret < 0)
--                      continue;
--
--              if (mib->size == 2) {
--                      ret = qca8k_read(priv, reg + 4, &hi);
--                      if (ret < 0)
--                              continue;
--              }
--
--              data[i] = val;
--              if (mib->size == 2)
--                      data[i] |= (u64)hi << 32;
--      }
--}
--
--static int
--qca8k_get_sset_count(struct dsa_switch *ds, int port, int sset)
--{
--      const struct qca8k_match_data *match_data;
--      struct qca8k_priv *priv = ds->priv;
--
--      if (sset != ETH_SS_STATS)
--              return 0;
--
--      match_data = of_device_get_match_data(priv->dev);
--
--      return match_data->mib_count;
--}
--
--static int
--qca8k_set_mac_eee(struct dsa_switch *ds, int port, struct ethtool_eee *eee)
--{
--      struct qca8k_priv *priv = (struct qca8k_priv *)ds->priv;
--      u32 lpi_en = QCA8K_REG_EEE_CTRL_LPI_EN(port);
--      u32 reg;
--      int ret;
--
--      mutex_lock(&priv->reg_mutex);
--      ret = qca8k_read(priv, QCA8K_REG_EEE_CTRL, &reg);
--      if (ret < 0)
--              goto exit;
--
--      if (eee->eee_enabled)
--              reg |= lpi_en;
--      else
--              reg &= ~lpi_en;
--      ret = qca8k_write(priv, QCA8K_REG_EEE_CTRL, reg);
--
--exit:
--      mutex_unlock(&priv->reg_mutex);
--      return ret;
--}
--
--static int
--qca8k_get_mac_eee(struct dsa_switch *ds, int port, struct ethtool_eee *e)
--{
--      /* Nothing to do on the port's MAC */
--      return 0;
--}
--
--static void
--qca8k_port_stp_state_set(struct dsa_switch *ds, int port, u8 state)
--{
--      struct qca8k_priv *priv = (struct qca8k_priv *)ds->priv;
--      u32 stp_state;
--
--      switch (state) {
--      case BR_STATE_DISABLED:
--              stp_state = QCA8K_PORT_LOOKUP_STATE_DISABLED;
--              break;
--      case BR_STATE_BLOCKING:
--              stp_state = QCA8K_PORT_LOOKUP_STATE_BLOCKING;
--              break;
--      case BR_STATE_LISTENING:
--              stp_state = QCA8K_PORT_LOOKUP_STATE_LISTENING;
--              break;
--      case BR_STATE_LEARNING:
--              stp_state = QCA8K_PORT_LOOKUP_STATE_LEARNING;
--              break;
--      case BR_STATE_FORWARDING:
--      default:
--              stp_state = QCA8K_PORT_LOOKUP_STATE_FORWARD;
--              break;
--      }
--
--      qca8k_rmw(priv, QCA8K_PORT_LOOKUP_CTRL(port),
--                QCA8K_PORT_LOOKUP_STATE_MASK, stp_state);
--}
--
--static int
--qca8k_port_bridge_join(struct dsa_switch *ds, int port, struct net_device *br)
--{
--      struct qca8k_priv *priv = (struct qca8k_priv *)ds->priv;
--      int port_mask, cpu_port;
--      int i, ret;
--
--      cpu_port = dsa_to_port(ds, port)->cpu_dp->index;
--      port_mask = BIT(cpu_port);
--
--      for (i = 0; i < QCA8K_NUM_PORTS; i++) {
--              if (dsa_is_cpu_port(ds, i))
--                      continue;
--              if (dsa_to_port(ds, i)->bridge_dev != br)
--                      continue;
--              /* Add this port to the portvlan mask of the other ports
--               * in the bridge
--               */
--              ret = regmap_set_bits(priv->regmap,
--                                    QCA8K_PORT_LOOKUP_CTRL(i),
--                                    BIT(port));
--              if (ret)
--                      return ret;
--              if (i != port)
--                      port_mask |= BIT(i);
--      }
--
--      /* Add all other ports to this ports portvlan mask */
--      ret = qca8k_rmw(priv, QCA8K_PORT_LOOKUP_CTRL(port),
--                      QCA8K_PORT_LOOKUP_MEMBER, port_mask);
--
--      return ret;
--}
--
--static void
--qca8k_port_bridge_leave(struct dsa_switch *ds, int port, struct net_device *br)
--{
--      struct qca8k_priv *priv = (struct qca8k_priv *)ds->priv;
--      int cpu_port, i;
--
--      cpu_port = dsa_to_port(ds, port)->cpu_dp->index;
--
--      for (i = 0; i < QCA8K_NUM_PORTS; i++) {
--              if (dsa_is_cpu_port(ds, i))
--                      continue;
--              if (dsa_to_port(ds, i)->bridge_dev != br)
--                      continue;
--              /* Remove this port to the portvlan mask of the other ports
--               * in the bridge
--               */
--              regmap_clear_bits(priv->regmap,
--                                QCA8K_PORT_LOOKUP_CTRL(i),
--                                BIT(port));
--      }
--
--      /* Set the cpu port to be the only one in the portvlan mask of
--       * this port
--       */
--      qca8k_rmw(priv, QCA8K_PORT_LOOKUP_CTRL(port),
--                QCA8K_PORT_LOOKUP_MEMBER, BIT(cpu_port));
--}
--
--static void
--qca8k_port_fast_age(struct dsa_switch *ds, int port)
--{
--      struct qca8k_priv *priv = ds->priv;
--
--      mutex_lock(&priv->reg_mutex);
--      qca8k_fdb_access(priv, QCA8K_FDB_FLUSH_PORT, port);
--      mutex_unlock(&priv->reg_mutex);
--}
--
--static int
--qca8k_set_ageing_time(struct dsa_switch *ds, unsigned int msecs)
--{
--      struct qca8k_priv *priv = ds->priv;
--      unsigned int secs = msecs / 1000;
--      u32 val;
--
--      /* AGE_TIME reg is set in 7s step */
--      val = secs / 7;
--
--      /* Handle case with 0 as val to NOT disable
--       * learning
--       */
--      if (!val)
--              val = 1;
--
--      return regmap_update_bits(priv->regmap, QCA8K_REG_ATU_CTRL, QCA8K_ATU_AGE_TIME_MASK,
--                                QCA8K_ATU_AGE_TIME(val));
--}
--
--static int
--qca8k_port_enable(struct dsa_switch *ds, int port,
--                struct phy_device *phy)
--{
--      struct qca8k_priv *priv = (struct qca8k_priv *)ds->priv;
--
--      qca8k_port_set_status(priv, port, 1);
--      priv->port_enabled_map |= BIT(port);
--
--      if (dsa_is_user_port(ds, port))
--              phy_support_asym_pause(phy);
--
--      return 0;
--}
--
--static void
--qca8k_port_disable(struct dsa_switch *ds, int port)
--{
--      struct qca8k_priv *priv = (struct qca8k_priv *)ds->priv;
--
--      qca8k_port_set_status(priv, port, 0);
--      priv->port_enabled_map &= ~BIT(port);
--}
--
--static int
--qca8k_port_change_mtu(struct dsa_switch *ds, int port, int new_mtu)
--{
--      struct qca8k_priv *priv = ds->priv;
--      int ret;
--
--      /* We have only have a general MTU setting.
--       * DSA always set the CPU port's MTU to the largest MTU of the slave
--       * ports.
--       * Setting MTU just for the CPU port is sufficient to correctly set a
--       * value for every port.
--       */
--      if (!dsa_is_cpu_port(ds, port))
--              return 0;
--
--      /* To change the MAX_FRAME_SIZE the cpu ports must be off or
--       * the switch panics.
--       * Turn off both cpu ports before applying the new value to prevent
--       * this.
--       */
--      if (priv->port_enabled_map & BIT(0))
--              qca8k_port_set_status(priv, 0, 0);
--
--      if (priv->port_enabled_map & BIT(6))
--              qca8k_port_set_status(priv, 6, 0);
--
--      /* Include L2 header / FCS length */
--      ret = qca8k_write(priv, QCA8K_MAX_FRAME_SIZE, new_mtu + ETH_HLEN + ETH_FCS_LEN);
--
--      if (priv->port_enabled_map & BIT(0))
--              qca8k_port_set_status(priv, 0, 1);
--
--      if (priv->port_enabled_map & BIT(6))
--              qca8k_port_set_status(priv, 6, 1);
--
--      return ret;
--}
--
--static int
--qca8k_port_max_mtu(struct dsa_switch *ds, int port)
--{
--      return QCA8K_MAX_MTU;
--}
--
--static int
--qca8k_port_fdb_insert(struct qca8k_priv *priv, const u8 *addr,
--                    u16 port_mask, u16 vid)
--{
--      /* Set the vid to the port vlan id if no vid is set */
--      if (!vid)
--              vid = QCA8K_PORT_VID_DEF;
--
--      return qca8k_fdb_add(priv, addr, port_mask, vid,
--                           QCA8K_ATU_STATUS_STATIC);
--}
--
--static int
--qca8k_port_fdb_add(struct dsa_switch *ds, int port,
--                 const unsigned char *addr, u16 vid)
--{
--      struct qca8k_priv *priv = (struct qca8k_priv *)ds->priv;
--      u16 port_mask = BIT(port);
--
--      return qca8k_port_fdb_insert(priv, addr, port_mask, vid);
--}
--
--static int
--qca8k_port_fdb_del(struct dsa_switch *ds, int port,
--                 const unsigned char *addr, u16 vid)
--{
--      struct qca8k_priv *priv = (struct qca8k_priv *)ds->priv;
--      u16 port_mask = BIT(port);
--
--      if (!vid)
--              vid = QCA8K_PORT_VID_DEF;
--
--      return qca8k_fdb_del(priv, addr, port_mask, vid);
--}
--
--static int
--qca8k_port_fdb_dump(struct dsa_switch *ds, int port,
--                  dsa_fdb_dump_cb_t *cb, void *data)
--{
--      struct qca8k_priv *priv = (struct qca8k_priv *)ds->priv;
--      struct qca8k_fdb _fdb = { 0 };
--      int cnt = QCA8K_NUM_FDB_RECORDS;
--      bool is_static;
--      int ret = 0;
--
--      mutex_lock(&priv->reg_mutex);
--      while (cnt-- && !qca8k_fdb_next(priv, &_fdb, port)) {
--              if (!_fdb.aging)
--                      break;
--              is_static = (_fdb.aging == QCA8K_ATU_STATUS_STATIC);
--              ret = cb(_fdb.mac, _fdb.vid, is_static, data);
--              if (ret)
--                      break;
--      }
--      mutex_unlock(&priv->reg_mutex);
--
--      return 0;
--}
--
--static int
--qca8k_port_mdb_add(struct dsa_switch *ds, int port,
--                 const struct switchdev_obj_port_mdb *mdb)
--{
--      struct qca8k_priv *priv = ds->priv;
--      const u8 *addr = mdb->addr;
--      u16 vid = mdb->vid;
--
--      return qca8k_fdb_search_and_insert(priv, BIT(port), addr, vid);
--}
--
--static int
--qca8k_port_mdb_del(struct dsa_switch *ds, int port,
--                 const struct switchdev_obj_port_mdb *mdb)
--{
--      struct qca8k_priv *priv = ds->priv;
--      const u8 *addr = mdb->addr;
--      u16 vid = mdb->vid;
--
--      return qca8k_fdb_search_and_del(priv, BIT(port), addr, vid);
--}
--
--static int
--qca8k_port_mirror_add(struct dsa_switch *ds, int port,
--                    struct dsa_mall_mirror_tc_entry *mirror,
--                    bool ingress)
--{
--      struct qca8k_priv *priv = ds->priv;
--      int monitor_port, ret;
--      u32 reg, val;
--
--      /* Check for existent entry */
--      if ((ingress ? priv->mirror_rx : priv->mirror_tx) & BIT(port))
--              return -EEXIST;
--
--      ret = regmap_read(priv->regmap, QCA8K_REG_GLOBAL_FW_CTRL0, &val);
--      if (ret)
--              return ret;
--
--      /* QCA83xx can have only one port set to mirror mode.
--       * Check that the correct port is requested and return error otherwise.
--       * When no mirror port is set, the values is set to 0xF
--       */
--      monitor_port = FIELD_GET(QCA8K_GLOBAL_FW_CTRL0_MIRROR_PORT_NUM, val);
--      if (monitor_port != 0xF && monitor_port != mirror->to_local_port)
--              return -EEXIST;
--
--      /* Set the monitor port */
--      val = FIELD_PREP(QCA8K_GLOBAL_FW_CTRL0_MIRROR_PORT_NUM,
--                       mirror->to_local_port);
--      ret = regmap_update_bits(priv->regmap, QCA8K_REG_GLOBAL_FW_CTRL0,
--                               QCA8K_GLOBAL_FW_CTRL0_MIRROR_PORT_NUM, val);
--      if (ret)
--              return ret;
--
--      if (ingress) {
--              reg = QCA8K_PORT_LOOKUP_CTRL(port);
--              val = QCA8K_PORT_LOOKUP_ING_MIRROR_EN;
--      } else {
--              reg = QCA8K_REG_PORT_HOL_CTRL1(port);
--              val = QCA8K_PORT_HOL_CTRL1_EG_MIRROR_EN;
--      }
--
--      ret = regmap_update_bits(priv->regmap, reg, val, val);
--      if (ret)
--              return ret;
--
--      /* Track mirror port for tx and rx to decide when the
--       * mirror port has to be disabled.
--       */
--      if (ingress)
--              priv->mirror_rx |= BIT(port);
--      else
--              priv->mirror_tx |= BIT(port);
--
--      return 0;
--}
--
--static void
--qca8k_port_mirror_del(struct dsa_switch *ds, int port,
--                    struct dsa_mall_mirror_tc_entry *mirror)
--{
--      struct qca8k_priv *priv = ds->priv;
--      u32 reg, val;
--      int ret;
--
--      if (mirror->ingress) {
--              reg = QCA8K_PORT_LOOKUP_CTRL(port);
--              val = QCA8K_PORT_LOOKUP_ING_MIRROR_EN;
--      } else {
--              reg = QCA8K_REG_PORT_HOL_CTRL1(port);
--              val = QCA8K_PORT_HOL_CTRL1_EG_MIRROR_EN;
--      }
--
--      ret = regmap_clear_bits(priv->regmap, reg, val);
--      if (ret)
--              goto err;
--
--      if (mirror->ingress)
--              priv->mirror_rx &= ~BIT(port);
--      else
--              priv->mirror_tx &= ~BIT(port);
--
--      /* No port set to send packet to mirror port. Disable mirror port */
--      if (!priv->mirror_rx && !priv->mirror_tx) {
--              val = FIELD_PREP(QCA8K_GLOBAL_FW_CTRL0_MIRROR_PORT_NUM, 0xF);
--              ret = regmap_update_bits(priv->regmap, QCA8K_REG_GLOBAL_FW_CTRL0,
--                                       QCA8K_GLOBAL_FW_CTRL0_MIRROR_PORT_NUM, val);
--              if (ret)
--                      goto err;
--      }
--err:
--      dev_err(priv->dev, "Failed to del mirror port from %d", port);
--}
--
--static int
--qca8k_port_vlan_filtering(struct dsa_switch *ds, int port, bool vlan_filtering,
--                        struct netlink_ext_ack *extack)
--{
--      struct qca8k_priv *priv = ds->priv;
--      int ret;
--
--      if (vlan_filtering) {
--              ret = qca8k_rmw(priv, QCA8K_PORT_LOOKUP_CTRL(port),
--                              QCA8K_PORT_LOOKUP_VLAN_MODE_MASK,
--                              QCA8K_PORT_LOOKUP_VLAN_MODE_SECURE);
--      } else {
--              ret = qca8k_rmw(priv, QCA8K_PORT_LOOKUP_CTRL(port),
--                              QCA8K_PORT_LOOKUP_VLAN_MODE_MASK,
--                              QCA8K_PORT_LOOKUP_VLAN_MODE_NONE);
--      }
--
--      return ret;
--}
--
--static int
--qca8k_port_vlan_add(struct dsa_switch *ds, int port,
--                  const struct switchdev_obj_port_vlan *vlan,
--                  struct netlink_ext_ack *extack)
--{
--      bool untagged = vlan->flags & BRIDGE_VLAN_INFO_UNTAGGED;
--      bool pvid = vlan->flags & BRIDGE_VLAN_INFO_PVID;
--      struct qca8k_priv *priv = ds->priv;
--      int ret;
--
--      ret = qca8k_vlan_add(priv, port, vlan->vid, untagged);
--      if (ret) {
--              dev_err(priv->dev, "Failed to add VLAN to port %d (%d)", port, ret);
--              return ret;
--      }
--
--      if (pvid) {
--              ret = qca8k_rmw(priv, QCA8K_EGRESS_VLAN(port),
--                              QCA8K_EGREES_VLAN_PORT_MASK(port),
--                              QCA8K_EGREES_VLAN_PORT(port, vlan->vid));
--              if (ret)
--                      return ret;
--
--              ret = qca8k_write(priv, QCA8K_REG_PORT_VLAN_CTRL0(port),
--                                QCA8K_PORT_VLAN_CVID(vlan->vid) |
--                                QCA8K_PORT_VLAN_SVID(vlan->vid));
--      }
--
--      return ret;
--}
--
--static int
--qca8k_port_vlan_del(struct dsa_switch *ds, int port,
--                  const struct switchdev_obj_port_vlan *vlan)
--{
--      struct qca8k_priv *priv = ds->priv;
--      int ret;
--
--      ret = qca8k_vlan_del(priv, port, vlan->vid);
--      if (ret)
--              dev_err(priv->dev, "Failed to delete VLAN from port %d (%d)", port, ret);
--
--      return ret;
--}
--
--static u32 qca8k_get_phy_flags(struct dsa_switch *ds, int port)
--{
--      struct qca8k_priv *priv = ds->priv;
--
--      /* Communicate to the phy internal driver the switch revision.
--       * Based on the switch revision different values needs to be
--       * set to the dbg and mmd reg on the phy.
--       * The first 2 bit are used to communicate the switch revision
--       * to the phy driver.
--       */
--      if (port > 0 && port < 6)
--              return priv->switch_revision;
--
--      return 0;
--}
--
--static enum dsa_tag_protocol
--qca8k_get_tag_protocol(struct dsa_switch *ds, int port,
--                     enum dsa_tag_protocol mp)
--{
--      return DSA_TAG_PROTO_QCA;
--}
--
--static bool
--qca8k_lag_can_offload(struct dsa_switch *ds,
--                    struct net_device *lag,
--                    struct netdev_lag_upper_info *info)
--{
--      struct dsa_port *dp;
--      int id, members = 0;
--
--      id = dsa_lag_id(ds->dst, lag);
--      if (id < 0 || id >= ds->num_lag_ids)
--              return false;
--
--      dsa_lag_foreach_port(dp, ds->dst, lag)
--              /* Includes the port joining the LAG */
--              members++;
--
--      if (members > QCA8K_NUM_PORTS_FOR_LAG)
--              return false;
--
--      if (info->tx_type != NETDEV_LAG_TX_TYPE_HASH)
--              return false;
--
--      if (info->hash_type != NETDEV_LAG_HASH_L2 &&
--          info->hash_type != NETDEV_LAG_HASH_L23)
--              return false;
--
--      return true;
--}
--
--static int
--qca8k_lag_setup_hash(struct dsa_switch *ds,
--                   struct net_device *lag,
--                   struct netdev_lag_upper_info *info)
--{
--      struct qca8k_priv *priv = ds->priv;
--      bool unique_lag = true;
--      u32 hash = 0;
--      int i, id;
--
--      id = dsa_lag_id(ds->dst, lag);
--
--      switch (info->hash_type) {
--      case NETDEV_LAG_HASH_L23:
--              hash |= QCA8K_TRUNK_HASH_SIP_EN;
--              hash |= QCA8K_TRUNK_HASH_DIP_EN;
--              fallthrough;
--      case NETDEV_LAG_HASH_L2:
--              hash |= QCA8K_TRUNK_HASH_SA_EN;
--              hash |= QCA8K_TRUNK_HASH_DA_EN;
--              break;
--      default: /* We should NEVER reach this */
--              return -EOPNOTSUPP;
--      }
--
--      /* Check if we are the unique configured LAG */
--      dsa_lags_foreach_id(i, ds->dst)
--              if (i != id && dsa_lag_dev(ds->dst, i)) {
--                      unique_lag = false;
--                      break;
--              }
--
--      /* Hash Mode is global. Make sure the same Hash Mode
--       * is set to all the 4 possible lag.
--       * If we are the unique LAG we can set whatever hash
--       * mode we want.
--       * To change hash mode it's needed to remove all LAG
--       * and change the mode with the latest.
--       */
--      if (unique_lag) {
--              priv->lag_hash_mode = hash;
--      } else if (priv->lag_hash_mode != hash) {
--              netdev_err(lag, "Error: Mismateched Hash Mode across different lag is not supported\n");
--              return -EOPNOTSUPP;
--      }
--
--      return regmap_update_bits(priv->regmap, QCA8K_TRUNK_HASH_EN_CTRL,
--                                QCA8K_TRUNK_HASH_MASK, hash);
--}
--
--static int
--qca8k_lag_refresh_portmap(struct dsa_switch *ds, int port,
--                        struct net_device *lag, bool delete)
--{
--      struct qca8k_priv *priv = ds->priv;
--      int ret, id, i;
--      u32 val;
--
--      id = dsa_lag_id(ds->dst, lag);
--
--      /* Read current port member */
--      ret = regmap_read(priv->regmap, QCA8K_REG_GOL_TRUNK_CTRL0, &val);
--      if (ret)
--              return ret;
--
--      /* Shift val to the correct trunk */
--      val >>= QCA8K_REG_GOL_TRUNK_SHIFT(id);
--      val &= QCA8K_REG_GOL_TRUNK_MEMBER_MASK;
--      if (delete)
--              val &= ~BIT(port);
--      else
--              val |= BIT(port);
--
--      /* Update port member. With empty portmap disable trunk */
--      ret = regmap_update_bits(priv->regmap, QCA8K_REG_GOL_TRUNK_CTRL0,
--                               QCA8K_REG_GOL_TRUNK_MEMBER(id) |
--                               QCA8K_REG_GOL_TRUNK_EN(id),
--                               !val << QCA8K_REG_GOL_TRUNK_SHIFT(id) |
--                               val << QCA8K_REG_GOL_TRUNK_SHIFT(id));
--
--      /* Search empty member if adding or port on deleting */
--      for (i = 0; i < QCA8K_NUM_PORTS_FOR_LAG; i++) {
--              ret = regmap_read(priv->regmap, QCA8K_REG_GOL_TRUNK_CTRL(id), &val);
--              if (ret)
--                      return ret;
--
--              val >>= QCA8K_REG_GOL_TRUNK_ID_MEM_ID_SHIFT(id, i);
--              val &= QCA8K_REG_GOL_TRUNK_ID_MEM_ID_MASK;
--
--              if (delete) {
--                      /* If port flagged to be disabled assume this member is
--                       * empty
--                       */
--                      if (val != QCA8K_REG_GOL_TRUNK_ID_MEM_ID_EN_MASK)
--                              continue;
--
--                      val &= QCA8K_REG_GOL_TRUNK_ID_MEM_ID_PORT_MASK;
--                      if (val != port)
--                              continue;
--              } else {
--                      /* If port flagged to be enabled assume this member is
--                       * already set
--                       */
--                      if (val == QCA8K_REG_GOL_TRUNK_ID_MEM_ID_EN_MASK)
--                              continue;
--              }
--
--              /* We have found the member to add/remove */
--              break;
--      }
--
--      /* Set port in the correct port mask or disable port if in delete mode */
--      return regmap_update_bits(priv->regmap, QCA8K_REG_GOL_TRUNK_CTRL(id),
--                                QCA8K_REG_GOL_TRUNK_ID_MEM_ID_EN(id, i) |
--                                QCA8K_REG_GOL_TRUNK_ID_MEM_ID_PORT(id, i),
--                                !delete << QCA8K_REG_GOL_TRUNK_ID_MEM_ID_SHIFT(id, i) |
--                                port << QCA8K_REG_GOL_TRUNK_ID_MEM_ID_SHIFT(id, i));
--}
--
--static int
--qca8k_port_lag_join(struct dsa_switch *ds, int port,
--                  struct net_device *lag,
--                  struct netdev_lag_upper_info *info)
--{
--      int ret;
--
--      if (!qca8k_lag_can_offload(ds, lag, info))
--              return -EOPNOTSUPP;
--
--      ret = qca8k_lag_setup_hash(ds, lag, info);
--      if (ret)
--              return ret;
--
--      return qca8k_lag_refresh_portmap(ds, port, lag, false);
--}
--
--static int
--qca8k_port_lag_leave(struct dsa_switch *ds, int port,
--                   struct net_device *lag)
--{
--      return qca8k_lag_refresh_portmap(ds, port, lag, true);
--}
--
--static void
--qca8k_master_change(struct dsa_switch *ds, const struct net_device *master,
--                  bool operational)
--{
--      struct dsa_port *dp = master->dsa_ptr;
--      struct qca8k_priv *priv = ds->priv;
--
--      /* Ethernet MIB/MDIO is only supported for CPU port 0 */
--      if (dp->index != 0)
--              return;
--
--      mutex_lock(&priv->mgmt_eth_data.mutex);
--      mutex_lock(&priv->mib_eth_data.mutex);
--
--      priv->mgmt_master = operational ? (struct net_device *)master : NULL;
--
--      mutex_unlock(&priv->mib_eth_data.mutex);
--      mutex_unlock(&priv->mgmt_eth_data.mutex);
--}
--
--static int qca8k_connect_tag_protocol(struct dsa_switch *ds,
--                                    enum dsa_tag_protocol proto)
--{
--      struct qca_tagger_data *tagger_data;
--
--      switch (proto) {
--      case DSA_TAG_PROTO_QCA:
--              tagger_data = ds->tagger_data;
--
--              tagger_data->rw_reg_ack_handler = qca8k_rw_reg_ack_handler;
--              tagger_data->mib_autocast_handler = qca8k_mib_autocast_handler;
--
--              break;
--      default:
--              return -EOPNOTSUPP;
--      }
--
--      return 0;
--}
--
--static const struct dsa_switch_ops qca8k_switch_ops = {
--      .get_tag_protocol       = qca8k_get_tag_protocol,
--      .setup                  = qca8k_setup,
--      .get_strings            = qca8k_get_strings,
--      .get_ethtool_stats      = qca8k_get_ethtool_stats,
--      .get_sset_count         = qca8k_get_sset_count,
--      .set_ageing_time        = qca8k_set_ageing_time,
--      .get_mac_eee            = qca8k_get_mac_eee,
--      .set_mac_eee            = qca8k_set_mac_eee,
--      .port_enable            = qca8k_port_enable,
--      .port_disable           = qca8k_port_disable,
--      .port_change_mtu        = qca8k_port_change_mtu,
--      .port_max_mtu           = qca8k_port_max_mtu,
--      .port_stp_state_set     = qca8k_port_stp_state_set,
--      .port_bridge_join       = qca8k_port_bridge_join,
--      .port_bridge_leave      = qca8k_port_bridge_leave,
--      .port_fast_age          = qca8k_port_fast_age,
--      .port_fdb_add           = qca8k_port_fdb_add,
--      .port_fdb_del           = qca8k_port_fdb_del,
--      .port_fdb_dump          = qca8k_port_fdb_dump,
--      .port_mdb_add           = qca8k_port_mdb_add,
--      .port_mdb_del           = qca8k_port_mdb_del,
--      .port_mirror_add        = qca8k_port_mirror_add,
--      .port_mirror_del        = qca8k_port_mirror_del,
--      .port_vlan_filtering    = qca8k_port_vlan_filtering,
--      .port_vlan_add          = qca8k_port_vlan_add,
--      .port_vlan_del          = qca8k_port_vlan_del,
--      .phylink_validate       = qca8k_phylink_validate,
--      .phylink_mac_link_state = qca8k_phylink_mac_link_state,
--      .phylink_mac_config     = qca8k_phylink_mac_config,
--      .phylink_mac_link_down  = qca8k_phylink_mac_link_down,
--      .phylink_mac_link_up    = qca8k_phylink_mac_link_up,
--      .get_phy_flags          = qca8k_get_phy_flags,
--      .port_lag_join          = qca8k_port_lag_join,
--      .port_lag_leave         = qca8k_port_lag_leave,
--      .master_state_change    = qca8k_master_change,
--      .connect_tag_protocol   = qca8k_connect_tag_protocol,
--};
--
--static int qca8k_read_switch_id(struct qca8k_priv *priv)
--{
--      const struct qca8k_match_data *data;
--      u32 val;
--      u8 id;
--      int ret;
--
--      /* get the switches ID from the compatible */
--      data = of_device_get_match_data(priv->dev);
--      if (!data)
--              return -ENODEV;
--
--      ret = qca8k_read(priv, QCA8K_REG_MASK_CTRL, &val);
--      if (ret < 0)
--              return -ENODEV;
--
--      id = QCA8K_MASK_CTRL_DEVICE_ID(val);
--      if (id != data->id) {
--              dev_err(priv->dev, "Switch id detected %x but expected %x", id, data->id);
--              return -ENODEV;
--      }
--
--      priv->switch_id = id;
--
--      /* Save revision to communicate to the internal PHY driver */
--      priv->switch_revision = QCA8K_MASK_CTRL_REV_ID(val);
--
--      return 0;
--}
--
--static int
--qca8k_sw_probe(struct mdio_device *mdiodev)
--{
--      struct qca8k_priv *priv;
--      int ret;
--
--      /* allocate the private data struct so that we can probe the switches
--       * ID register
--       */
--      priv = devm_kzalloc(&mdiodev->dev, sizeof(*priv), GFP_KERNEL);
--      if (!priv)
--              return -ENOMEM;
--
--      priv->bus = mdiodev->bus;
--      priv->dev = &mdiodev->dev;
--
--      priv->reset_gpio = devm_gpiod_get_optional(priv->dev, "reset",
--                                                 GPIOD_ASIS);
--      if (IS_ERR(priv->reset_gpio))
--              return PTR_ERR(priv->reset_gpio);
--
--      if (priv->reset_gpio) {
--              gpiod_set_value_cansleep(priv->reset_gpio, 1);
--              /* The active low duration must be greater than 10 ms
--               * and checkpatch.pl wants 20 ms.
--               */
--              msleep(20);
--              gpiod_set_value_cansleep(priv->reset_gpio, 0);
--      }
--
--      /* Start by setting up the register mapping */
--      priv->regmap = devm_regmap_init(&mdiodev->dev, NULL, priv,
--                                      &qca8k_regmap_config);
--      if (IS_ERR(priv->regmap)) {
--              dev_err(priv->dev, "regmap initialization failed");
--              return PTR_ERR(priv->regmap);
--      }
--
--      priv->mdio_cache.page = 0xffff;
--      priv->mdio_cache.lo = 0xffff;
--      priv->mdio_cache.hi = 0xffff;
--
--      /* Check the detected switch id */
--      ret = qca8k_read_switch_id(priv);
--      if (ret)
--              return ret;
--
--      priv->ds = devm_kzalloc(&mdiodev->dev, sizeof(*priv->ds), GFP_KERNEL);
--      if (!priv->ds)
--              return -ENOMEM;
--
--      mutex_init(&priv->mgmt_eth_data.mutex);
--      init_completion(&priv->mgmt_eth_data.rw_done);
--
--      mutex_init(&priv->mib_eth_data.mutex);
--      init_completion(&priv->mib_eth_data.rw_done);
--
--      priv->ds->dev = &mdiodev->dev;
--      priv->ds->num_ports = QCA8K_NUM_PORTS;
--      priv->ds->priv = priv;
--      priv->ds->ops = &qca8k_switch_ops;
--      mutex_init(&priv->reg_mutex);
--      dev_set_drvdata(&mdiodev->dev, priv);
--
--      return dsa_register_switch(priv->ds);
--}
--
--static void
--qca8k_sw_remove(struct mdio_device *mdiodev)
--{
--      struct qca8k_priv *priv = dev_get_drvdata(&mdiodev->dev);
--      int i;
--
--      if (!priv)
--              return;
--
--      for (i = 0; i < QCA8K_NUM_PORTS; i++)
--              qca8k_port_set_status(priv, i, 0);
--
--      dsa_unregister_switch(priv->ds);
--
--      dev_set_drvdata(&mdiodev->dev, NULL);
--}
--
--static void qca8k_sw_shutdown(struct mdio_device *mdiodev)
--{
--      struct qca8k_priv *priv = dev_get_drvdata(&mdiodev->dev);
--
--      if (!priv)
--              return;
--
--      dsa_switch_shutdown(priv->ds);
--
--      dev_set_drvdata(&mdiodev->dev, NULL);
--}
--
--#ifdef CONFIG_PM_SLEEP
--static void
--qca8k_set_pm(struct qca8k_priv *priv, int enable)
--{
--      int port;
--
--      for (port = 0; port < QCA8K_NUM_PORTS; port++) {
--              /* Do not enable on resume if the port was
--               * disabled before.
--               */
--              if (!(priv->port_enabled_map & BIT(port)))
--                      continue;
--
--              qca8k_port_set_status(priv, port, enable);
--      }
--}
--
--static int qca8k_suspend(struct device *dev)
--{
--      struct qca8k_priv *priv = dev_get_drvdata(dev);
--
--      qca8k_set_pm(priv, 0);
--
--      return dsa_switch_suspend(priv->ds);
--}
--
--static int qca8k_resume(struct device *dev)
--{
--      struct qca8k_priv *priv = dev_get_drvdata(dev);
--
--      qca8k_set_pm(priv, 1);
--
--      return dsa_switch_resume(priv->ds);
--}
--#endif /* CONFIG_PM_SLEEP */
--
--static SIMPLE_DEV_PM_OPS(qca8k_pm_ops,
--                       qca8k_suspend, qca8k_resume);
--
--static const struct qca8k_match_data qca8327 = {
--      .id = QCA8K_ID_QCA8327,
--      .reduced_package = true,
--      .mib_count = QCA8K_QCA832X_MIB_COUNT,
--};
--
--static const struct qca8k_match_data qca8328 = {
--      .id = QCA8K_ID_QCA8327,
--      .mib_count = QCA8K_QCA832X_MIB_COUNT,
--};
--
--static const struct qca8k_match_data qca833x = {
--      .id = QCA8K_ID_QCA8337,
--      .mib_count = QCA8K_QCA833X_MIB_COUNT,
--};
--
--static const struct of_device_id qca8k_of_match[] = {
--      { .compatible = "qca,qca8327", .data = &qca8327 },
--      { .compatible = "qca,qca8328", .data = &qca8328 },
--      { .compatible = "qca,qca8334", .data = &qca833x },
--      { .compatible = "qca,qca8337", .data = &qca833x },
--      { /* sentinel */ },
--};
--
--static struct mdio_driver qca8kmdio_driver = {
--      .probe  = qca8k_sw_probe,
--      .remove = qca8k_sw_remove,
--      .shutdown = qca8k_sw_shutdown,
--      .mdiodrv.driver = {
--              .name = "qca8k",
--              .of_match_table = qca8k_of_match,
--              .pm = &qca8k_pm_ops,
--      },
--};
--
--mdio_module_driver(qca8kmdio_driver);
--
--MODULE_AUTHOR("Mathieu Olivari, John Crispin <[email protected]>");
--MODULE_DESCRIPTION("Driver for QCA8K ethernet switch family");
--MODULE_LICENSE("GPL v2");
--MODULE_ALIAS("platform:qca8k");
---- a/drivers/net/dsa/qca8k.h
-+++ /dev/null
-@@ -1,411 +0,0 @@
--/* SPDX-License-Identifier: GPL-2.0-only */
--/*
-- * Copyright (C) 2009 Felix Fietkau <[email protected]>
-- * Copyright (C) 2011-2012 Gabor Juhos <[email protected]>
-- * Copyright (c) 2015, The Linux Foundation. All rights reserved.
-- */
--
--#ifndef __QCA8K_H
--#define __QCA8K_H
--
--#include <linux/delay.h>
--#include <linux/regmap.h>
--#include <linux/gpio.h>
--#include <linux/dsa/tag_qca.h>
--
--#define QCA8K_ETHERNET_MDIO_PRIORITY                  7
--#define QCA8K_ETHERNET_PHY_PRIORITY                   6
--#define QCA8K_ETHERNET_TIMEOUT                                100
--
--#define QCA8K_NUM_PORTS                                       7
--#define QCA8K_NUM_CPU_PORTS                           2
--#define QCA8K_MAX_MTU                                 9000
--#define QCA8K_NUM_LAGS                                        4
--#define QCA8K_NUM_PORTS_FOR_LAG                               4
--
--#define PHY_ID_QCA8327                                        0x004dd034
--#define QCA8K_ID_QCA8327                              0x12
--#define PHY_ID_QCA8337                                        0x004dd036
--#define QCA8K_ID_QCA8337                              0x13
--
--#define QCA8K_QCA832X_MIB_COUNT                               39
--#define QCA8K_QCA833X_MIB_COUNT                               41
--
--#define QCA8K_BUSY_WAIT_TIMEOUT                               2000
--
--#define QCA8K_NUM_FDB_RECORDS                         2048
--
--#define QCA8K_PORT_VID_DEF                            1
--
--/* Global control registers */
--#define QCA8K_REG_MASK_CTRL                           0x000
--#define   QCA8K_MASK_CTRL_REV_ID_MASK                 GENMASK(7, 0)
--#define   QCA8K_MASK_CTRL_REV_ID(x)                   FIELD_GET(QCA8K_MASK_CTRL_REV_ID_MASK, x)
--#define   QCA8K_MASK_CTRL_DEVICE_ID_MASK              GENMASK(15, 8)
--#define   QCA8K_MASK_CTRL_DEVICE_ID(x)                        FIELD_GET(QCA8K_MASK_CTRL_DEVICE_ID_MASK, x)
--#define QCA8K_REG_PORT0_PAD_CTRL                      0x004
--#define   QCA8K_PORT0_PAD_MAC06_EXCHANGE_EN           BIT(31)
--#define   QCA8K_PORT0_PAD_SGMII_RXCLK_FALLING_EDGE    BIT(19)
--#define   QCA8K_PORT0_PAD_SGMII_TXCLK_FALLING_EDGE    BIT(18)
--#define QCA8K_REG_PORT5_PAD_CTRL                      0x008
--#define QCA8K_REG_PORT6_PAD_CTRL                      0x00c
--#define   QCA8K_PORT_PAD_RGMII_EN                     BIT(26)
--#define   QCA8K_PORT_PAD_RGMII_TX_DELAY_MASK          GENMASK(23, 22)
--#define   QCA8K_PORT_PAD_RGMII_TX_DELAY(x)            FIELD_PREP(QCA8K_PORT_PAD_RGMII_TX_DELAY_MASK, x)
--#define   QCA8K_PORT_PAD_RGMII_RX_DELAY_MASK          GENMASK(21, 20)
--#define   QCA8K_PORT_PAD_RGMII_RX_DELAY(x)            FIELD_PREP(QCA8K_PORT_PAD_RGMII_RX_DELAY_MASK, x)
--#define         QCA8K_PORT_PAD_RGMII_TX_DELAY_EN              BIT(25)
--#define   QCA8K_PORT_PAD_RGMII_RX_DELAY_EN            BIT(24)
--#define   QCA8K_PORT_PAD_SGMII_EN                     BIT(7)
--#define QCA8K_REG_PWS                                 0x010
--#define   QCA8K_PWS_POWER_ON_SEL                      BIT(31)
--/* This reg is only valid for QCA832x and toggle the package
-- * type from 176 pin (by default) to 148 pin used on QCA8327
-- */
--#define   QCA8327_PWS_PACKAGE148_EN                   BIT(30)
--#define   QCA8K_PWS_LED_OPEN_EN_CSR                   BIT(24)
--#define   QCA8K_PWS_SERDES_AEN_DIS                    BIT(7)
--#define QCA8K_REG_MODULE_EN                           0x030
--#define   QCA8K_MODULE_EN_MIB                         BIT(0)
--#define QCA8K_REG_MIB                                 0x034
--#define   QCA8K_MIB_FUNC                              GENMASK(26, 24)
--#define   QCA8K_MIB_CPU_KEEP                          BIT(20)
--#define   QCA8K_MIB_BUSY                              BIT(17)
--#define QCA8K_MDIO_MASTER_CTRL                                0x3c
--#define   QCA8K_MDIO_MASTER_BUSY                      BIT(31)
--#define   QCA8K_MDIO_MASTER_EN                                BIT(30)
--#define   QCA8K_MDIO_MASTER_READ                      BIT(27)
--#define   QCA8K_MDIO_MASTER_WRITE                     0
--#define   QCA8K_MDIO_MASTER_SUP_PRE                   BIT(26)
--#define   QCA8K_MDIO_MASTER_PHY_ADDR_MASK             GENMASK(25, 21)
--#define   QCA8K_MDIO_MASTER_PHY_ADDR(x)                       FIELD_PREP(QCA8K_MDIO_MASTER_PHY_ADDR_MASK, x)
--#define   QCA8K_MDIO_MASTER_REG_ADDR_MASK             GENMASK(20, 16)
--#define   QCA8K_MDIO_MASTER_REG_ADDR(x)                       FIELD_PREP(QCA8K_MDIO_MASTER_REG_ADDR_MASK, x)
--#define   QCA8K_MDIO_MASTER_DATA_MASK                 GENMASK(15, 0)
--#define   QCA8K_MDIO_MASTER_DATA(x)                   FIELD_PREP(QCA8K_MDIO_MASTER_DATA_MASK, x)
--#define   QCA8K_MDIO_MASTER_MAX_PORTS                 5
--#define   QCA8K_MDIO_MASTER_MAX_REG                   32
--#define QCA8K_GOL_MAC_ADDR0                           0x60
--#define QCA8K_GOL_MAC_ADDR1                           0x64
--#define QCA8K_MAX_FRAME_SIZE                          0x78
--#define QCA8K_REG_PORT_STATUS(_i)                     (0x07c + (_i) * 4)
--#define   QCA8K_PORT_STATUS_SPEED                     GENMASK(1, 0)
--#define   QCA8K_PORT_STATUS_SPEED_10                  0
--#define   QCA8K_PORT_STATUS_SPEED_100                 0x1
--#define   QCA8K_PORT_STATUS_SPEED_1000                        0x2
--#define   QCA8K_PORT_STATUS_TXMAC                     BIT(2)
--#define   QCA8K_PORT_STATUS_RXMAC                     BIT(3)
--#define   QCA8K_PORT_STATUS_TXFLOW                    BIT(4)
--#define   QCA8K_PORT_STATUS_RXFLOW                    BIT(5)
--#define   QCA8K_PORT_STATUS_DUPLEX                    BIT(6)
--#define   QCA8K_PORT_STATUS_LINK_UP                   BIT(8)
--#define   QCA8K_PORT_STATUS_LINK_AUTO                 BIT(9)
--#define   QCA8K_PORT_STATUS_LINK_PAUSE                        BIT(10)
--#define   QCA8K_PORT_STATUS_FLOW_AUTO                 BIT(12)
--#define QCA8K_REG_PORT_HDR_CTRL(_i)                   (0x9c + (_i * 4))
--#define   QCA8K_PORT_HDR_CTRL_RX_MASK                 GENMASK(3, 2)
--#define   QCA8K_PORT_HDR_CTRL_TX_MASK                 GENMASK(1, 0)
--#define   QCA8K_PORT_HDR_CTRL_ALL                     2
--#define   QCA8K_PORT_HDR_CTRL_MGMT                    1
--#define   QCA8K_PORT_HDR_CTRL_NONE                    0
--#define QCA8K_REG_SGMII_CTRL                          0x0e0
--#define   QCA8K_SGMII_EN_PLL                          BIT(1)
--#define   QCA8K_SGMII_EN_RX                           BIT(2)
--#define   QCA8K_SGMII_EN_TX                           BIT(3)
--#define   QCA8K_SGMII_EN_SD                           BIT(4)
--#define   QCA8K_SGMII_CLK125M_DELAY                   BIT(7)
--#define   QCA8K_SGMII_MODE_CTRL_MASK                  GENMASK(23, 22)
--#define   QCA8K_SGMII_MODE_CTRL(x)                    FIELD_PREP(QCA8K_SGMII_MODE_CTRL_MASK, x)
--#define   QCA8K_SGMII_MODE_CTRL_BASEX                 QCA8K_SGMII_MODE_CTRL(0x0)
--#define   QCA8K_SGMII_MODE_CTRL_PHY                   QCA8K_SGMII_MODE_CTRL(0x1)
--#define   QCA8K_SGMII_MODE_CTRL_MAC                   QCA8K_SGMII_MODE_CTRL(0x2)
--
--/* MAC_PWR_SEL registers */
--#define QCA8K_REG_MAC_PWR_SEL                         0x0e4
--#define   QCA8K_MAC_PWR_RGMII1_1_8V                   BIT(18)
--#define   QCA8K_MAC_PWR_RGMII0_1_8V                   BIT(19)
--
--/* EEE control registers */
--#define QCA8K_REG_EEE_CTRL                            0x100
--#define  QCA8K_REG_EEE_CTRL_LPI_EN(_i)                        ((_i + 1) * 2)
--
--/* TRUNK_HASH_EN registers */
--#define QCA8K_TRUNK_HASH_EN_CTRL                      0x270
--#define   QCA8K_TRUNK_HASH_SIP_EN                     BIT(3)
--#define   QCA8K_TRUNK_HASH_DIP_EN                     BIT(2)
--#define   QCA8K_TRUNK_HASH_SA_EN                      BIT(1)
--#define   QCA8K_TRUNK_HASH_DA_EN                      BIT(0)
--#define   QCA8K_TRUNK_HASH_MASK                               GENMASK(3, 0)
--
--/* ACL registers */
--#define QCA8K_REG_PORT_VLAN_CTRL0(_i)                 (0x420 + (_i * 8))
--#define   QCA8K_PORT_VLAN_CVID_MASK                   GENMASK(27, 16)
--#define   QCA8K_PORT_VLAN_CVID(x)                     FIELD_PREP(QCA8K_PORT_VLAN_CVID_MASK, x)
--#define   QCA8K_PORT_VLAN_SVID_MASK                   GENMASK(11, 0)
--#define   QCA8K_PORT_VLAN_SVID(x)                     FIELD_PREP(QCA8K_PORT_VLAN_SVID_MASK, x)
--#define QCA8K_REG_PORT_VLAN_CTRL1(_i)                 (0x424 + (_i * 8))
--#define QCA8K_REG_IPV4_PRI_BASE_ADDR                  0x470
--#define QCA8K_REG_IPV4_PRI_ADDR_MASK                  0x474
--
--/* Lookup registers */
--#define QCA8K_REG_ATU_DATA0                           0x600
--#define   QCA8K_ATU_ADDR2_MASK                                GENMASK(31, 24)
--#define   QCA8K_ATU_ADDR3_MASK                                GENMASK(23, 16)
--#define   QCA8K_ATU_ADDR4_MASK                                GENMASK(15, 8)
--#define   QCA8K_ATU_ADDR5_MASK                                GENMASK(7, 0)
--#define QCA8K_REG_ATU_DATA1                           0x604
--#define   QCA8K_ATU_PORT_MASK                         GENMASK(22, 16)
--#define   QCA8K_ATU_ADDR0_MASK                                GENMASK(15, 8)
--#define   QCA8K_ATU_ADDR1_MASK                                GENMASK(7, 0)
--#define QCA8K_REG_ATU_DATA2                           0x608
--#define   QCA8K_ATU_VID_MASK                          GENMASK(19, 8)
--#define   QCA8K_ATU_STATUS_MASK                               GENMASK(3, 0)
--#define   QCA8K_ATU_STATUS_STATIC                     0xf
--#define QCA8K_REG_ATU_FUNC                            0x60c
--#define   QCA8K_ATU_FUNC_BUSY                         BIT(31)
--#define   QCA8K_ATU_FUNC_PORT_EN                      BIT(14)
--#define   QCA8K_ATU_FUNC_MULTI_EN                     BIT(13)
--#define   QCA8K_ATU_FUNC_FULL                         BIT(12)
--#define   QCA8K_ATU_FUNC_PORT_MASK                    GENMASK(11, 8)
--#define QCA8K_REG_VTU_FUNC0                           0x610
--#define   QCA8K_VTU_FUNC0_VALID                               BIT(20)
--#define   QCA8K_VTU_FUNC0_IVL_EN                      BIT(19)
--/*        QCA8K_VTU_FUNC0_EG_MODE_MASK                        GENMASK(17, 4)
-- *          It does contain VLAN_MODE for each port [5:4] for port0,
-- *          [7:6] for port1 ... [17:16] for port6. Use virtual port
-- *          define to handle this.
-- */
--#define   QCA8K_VTU_FUNC0_EG_MODE_PORT_SHIFT(_i)      (4 + (_i) * 2)
--#define   QCA8K_VTU_FUNC0_EG_MODE_MASK                        GENMASK(1, 0)
--#define   QCA8K_VTU_FUNC0_EG_MODE_PORT_MASK(_i)               (GENMASK(1, 0) << QCA8K_VTU_FUNC0_EG_MODE_PORT_SHIFT(_i))
--#define   QCA8K_VTU_FUNC0_EG_MODE_UNMOD                       FIELD_PREP(QCA8K_VTU_FUNC0_EG_MODE_MASK, 0x0)
--#define   QCA8K_VTU_FUNC0_EG_MODE_PORT_UNMOD(_i)      (QCA8K_VTU_FUNC0_EG_MODE_UNMOD << QCA8K_VTU_FUNC0_EG_MODE_PORT_SHIFT(_i))
--#define   QCA8K_VTU_FUNC0_EG_MODE_UNTAG                       FIELD_PREP(QCA8K_VTU_FUNC0_EG_MODE_MASK, 0x1)
--#define   QCA8K_VTU_FUNC0_EG_MODE_PORT_UNTAG(_i)      (QCA8K_VTU_FUNC0_EG_MODE_UNTAG << QCA8K_VTU_FUNC0_EG_MODE_PORT_SHIFT(_i))
--#define   QCA8K_VTU_FUNC0_EG_MODE_TAG                 FIELD_PREP(QCA8K_VTU_FUNC0_EG_MODE_MASK, 0x2)
--#define   QCA8K_VTU_FUNC0_EG_MODE_PORT_TAG(_i)                (QCA8K_VTU_FUNC0_EG_MODE_TAG << QCA8K_VTU_FUNC0_EG_MODE_PORT_SHIFT(_i))
--#define   QCA8K_VTU_FUNC0_EG_MODE_NOT                 FIELD_PREP(QCA8K_VTU_FUNC0_EG_MODE_MASK, 0x3)
--#define   QCA8K_VTU_FUNC0_EG_MODE_PORT_NOT(_i)                (QCA8K_VTU_FUNC0_EG_MODE_NOT << QCA8K_VTU_FUNC0_EG_MODE_PORT_SHIFT(_i))
--#define QCA8K_REG_VTU_FUNC1                           0x614
--#define   QCA8K_VTU_FUNC1_BUSY                                BIT(31)
--#define   QCA8K_VTU_FUNC1_VID_MASK                    GENMASK(27, 16)
--#define   QCA8K_VTU_FUNC1_FULL                                BIT(4)
--#define QCA8K_REG_ATU_CTRL                            0x618
--#define   QCA8K_ATU_AGE_TIME_MASK                     GENMASK(15, 0)
--#define   QCA8K_ATU_AGE_TIME(x)                               FIELD_PREP(QCA8K_ATU_AGE_TIME_MASK, (x))
--#define QCA8K_REG_GLOBAL_FW_CTRL0                     0x620
--#define   QCA8K_GLOBAL_FW_CTRL0_CPU_PORT_EN           BIT(10)
--#define   QCA8K_GLOBAL_FW_CTRL0_MIRROR_PORT_NUM               GENMASK(7, 4)
--#define QCA8K_REG_GLOBAL_FW_CTRL1                     0x624
--#define   QCA8K_GLOBAL_FW_CTRL1_IGMP_DP_MASK          GENMASK(30, 24)
--#define   QCA8K_GLOBAL_FW_CTRL1_BC_DP_MASK            GENMASK(22, 16)
--#define   QCA8K_GLOBAL_FW_CTRL1_MC_DP_MASK            GENMASK(14, 8)
--#define   QCA8K_GLOBAL_FW_CTRL1_UC_DP_MASK            GENMASK(6, 0)
--#define QCA8K_PORT_LOOKUP_CTRL(_i)                    (0x660 + (_i) * 0xc)
--#define   QCA8K_PORT_LOOKUP_MEMBER                    GENMASK(6, 0)
--#define   QCA8K_PORT_LOOKUP_VLAN_MODE_MASK            GENMASK(9, 8)
--#define   QCA8K_PORT_LOOKUP_VLAN_MODE(x)              FIELD_PREP(QCA8K_PORT_LOOKUP_VLAN_MODE_MASK, x)
--#define   QCA8K_PORT_LOOKUP_VLAN_MODE_NONE            QCA8K_PORT_LOOKUP_VLAN_MODE(0x0)
--#define   QCA8K_PORT_LOOKUP_VLAN_MODE_FALLBACK                QCA8K_PORT_LOOKUP_VLAN_MODE(0x1)
--#define   QCA8K_PORT_LOOKUP_VLAN_MODE_CHECK           QCA8K_PORT_LOOKUP_VLAN_MODE(0x2)
--#define   QCA8K_PORT_LOOKUP_VLAN_MODE_SECURE          QCA8K_PORT_LOOKUP_VLAN_MODE(0x3)
--#define   QCA8K_PORT_LOOKUP_STATE_MASK                        GENMASK(18, 16)
--#define   QCA8K_PORT_LOOKUP_STATE(x)                  FIELD_PREP(QCA8K_PORT_LOOKUP_STATE_MASK, x)
--#define   QCA8K_PORT_LOOKUP_STATE_DISABLED            QCA8K_PORT_LOOKUP_STATE(0x0)
--#define   QCA8K_PORT_LOOKUP_STATE_BLOCKING            QCA8K_PORT_LOOKUP_STATE(0x1)
--#define   QCA8K_PORT_LOOKUP_STATE_LISTENING           QCA8K_PORT_LOOKUP_STATE(0x2)
--#define   QCA8K_PORT_LOOKUP_STATE_LEARNING            QCA8K_PORT_LOOKUP_STATE(0x3)
--#define   QCA8K_PORT_LOOKUP_STATE_FORWARD             QCA8K_PORT_LOOKUP_STATE(0x4)
--#define   QCA8K_PORT_LOOKUP_LEARN                     BIT(20)
--#define   QCA8K_PORT_LOOKUP_ING_MIRROR_EN             BIT(25)
--
--#define QCA8K_REG_GOL_TRUNK_CTRL0                     0x700
--/* 4 max trunk first
-- * first 6 bit for member bitmap
-- * 7th bit is to enable trunk port
-- */
--#define QCA8K_REG_GOL_TRUNK_SHIFT(_i)                 ((_i) * 8)
--#define QCA8K_REG_GOL_TRUNK_EN_MASK                   BIT(7)
--#define QCA8K_REG_GOL_TRUNK_EN(_i)                    (QCA8K_REG_GOL_TRUNK_EN_MASK << QCA8K_REG_GOL_TRUNK_SHIFT(_i))
--#define QCA8K_REG_GOL_TRUNK_MEMBER_MASK                       GENMASK(6, 0)
--#define QCA8K_REG_GOL_TRUNK_MEMBER(_i)                        (QCA8K_REG_GOL_TRUNK_MEMBER_MASK << QCA8K_REG_GOL_TRUNK_SHIFT(_i))
--/* 0x704 for TRUNK 0-1 --- 0x708 for TRUNK 2-3 */
--#define QCA8K_REG_GOL_TRUNK_CTRL(_i)                  (0x704 + (((_i) / 2) * 4))
--#define QCA8K_REG_GOL_TRUNK_ID_MEM_ID_MASK            GENMASK(3, 0)
--#define QCA8K_REG_GOL_TRUNK_ID_MEM_ID_EN_MASK         BIT(3)
--#define QCA8K_REG_GOL_TRUNK_ID_MEM_ID_PORT_MASK               GENMASK(2, 0)
--#define QCA8K_REG_GOL_TRUNK_ID_SHIFT(_i)              (((_i) / 2) * 16)
--#define QCA8K_REG_GOL_MEM_ID_SHIFT(_i)                        ((_i) * 4)
--/* Complex shift: FIRST shift for port THEN shift for trunk */
--#define QCA8K_REG_GOL_TRUNK_ID_MEM_ID_SHIFT(_i, _j)   (QCA8K_REG_GOL_MEM_ID_SHIFT(_j) + QCA8K_REG_GOL_TRUNK_ID_SHIFT(_i))
--#define QCA8K_REG_GOL_TRUNK_ID_MEM_ID_EN(_i, _j)      (QCA8K_REG_GOL_TRUNK_ID_MEM_ID_EN_MASK << QCA8K_REG_GOL_TRUNK_ID_MEM_ID_SHIFT(_i, _j))
--#define QCA8K_REG_GOL_TRUNK_ID_MEM_ID_PORT(_i, _j)    (QCA8K_REG_GOL_TRUNK_ID_MEM_ID_PORT_MASK << QCA8K_REG_GOL_TRUNK_ID_MEM_ID_SHIFT(_i, _j))
--
--#define QCA8K_REG_GLOBAL_FC_THRESH                    0x800
--#define   QCA8K_GLOBAL_FC_GOL_XON_THRES_MASK          GENMASK(24, 16)
--#define   QCA8K_GLOBAL_FC_GOL_XON_THRES(x)            FIELD_PREP(QCA8K_GLOBAL_FC_GOL_XON_THRES_MASK, x)
--#define   QCA8K_GLOBAL_FC_GOL_XOFF_THRES_MASK         GENMASK(8, 0)
--#define   QCA8K_GLOBAL_FC_GOL_XOFF_THRES(x)           FIELD_PREP(QCA8K_GLOBAL_FC_GOL_XOFF_THRES_MASK, x)
--
--#define QCA8K_REG_PORT_HOL_CTRL0(_i)                  (0x970 + (_i) * 0x8)
--#define   QCA8K_PORT_HOL_CTRL0_EG_PRI0_BUF_MASK               GENMASK(3, 0)
--#define   QCA8K_PORT_HOL_CTRL0_EG_PRI0(x)             FIELD_PREP(QCA8K_PORT_HOL_CTRL0_EG_PRI0_BUF_MASK, x)
--#define   QCA8K_PORT_HOL_CTRL0_EG_PRI1_BUF_MASK               GENMASK(7, 4)
--#define   QCA8K_PORT_HOL_CTRL0_EG_PRI1(x)             FIELD_PREP(QCA8K_PORT_HOL_CTRL0_EG_PRI1_BUF_MASK, x)
--#define   QCA8K_PORT_HOL_CTRL0_EG_PRI2_BUF_MASK               GENMASK(11, 8)
--#define   QCA8K_PORT_HOL_CTRL0_EG_PRI2(x)             FIELD_PREP(QCA8K_PORT_HOL_CTRL0_EG_PRI2_BUF_MASK, x)
--#define   QCA8K_PORT_HOL_CTRL0_EG_PRI3_BUF_MASK               GENMASK(15, 12)
--#define   QCA8K_PORT_HOL_CTRL0_EG_PRI3(x)             FIELD_PREP(QCA8K_PORT_HOL_CTRL0_EG_PRI3_BUF_MASK, x)
--#define   QCA8K_PORT_HOL_CTRL0_EG_PRI4_BUF_MASK               GENMASK(19, 16)
--#define   QCA8K_PORT_HOL_CTRL0_EG_PRI4(x)             FIELD_PREP(QCA8K_PORT_HOL_CTRL0_EG_PRI4_BUF_MASK, x)
--#define   QCA8K_PORT_HOL_CTRL0_EG_PRI5_BUF_MASK               GENMASK(23, 20)
--#define   QCA8K_PORT_HOL_CTRL0_EG_PRI5(x)             FIELD_PREP(QCA8K_PORT_HOL_CTRL0_EG_PRI5_BUF_MASK, x)
--#define   QCA8K_PORT_HOL_CTRL0_EG_PORT_BUF_MASK               GENMASK(29, 24)
--#define   QCA8K_PORT_HOL_CTRL0_EG_PORT(x)             FIELD_PREP(QCA8K_PORT_HOL_CTRL0_EG_PORT_BUF_MASK, x)
--
--#define QCA8K_REG_PORT_HOL_CTRL1(_i)                  (0x974 + (_i) * 0x8)
--#define   QCA8K_PORT_HOL_CTRL1_ING_BUF_MASK           GENMASK(3, 0)
--#define   QCA8K_PORT_HOL_CTRL1_ING(x)                 FIELD_PREP(QCA8K_PORT_HOL_CTRL1_ING_BUF_MASK, x)
--#define   QCA8K_PORT_HOL_CTRL1_EG_PRI_BUF_EN          BIT(6)
--#define   QCA8K_PORT_HOL_CTRL1_EG_PORT_BUF_EN         BIT(7)
--#define   QCA8K_PORT_HOL_CTRL1_WRED_EN                        BIT(8)
--#define   QCA8K_PORT_HOL_CTRL1_EG_MIRROR_EN           BIT(16)
--
--/* Pkt edit registers */
--#define QCA8K_EGREES_VLAN_PORT_SHIFT(_i)              (16 * ((_i) % 2))
--#define QCA8K_EGREES_VLAN_PORT_MASK(_i)                       (GENMASK(11, 0) << QCA8K_EGREES_VLAN_PORT_SHIFT(_i))
--#define QCA8K_EGREES_VLAN_PORT(_i, x)                 ((x) << QCA8K_EGREES_VLAN_PORT_SHIFT(_i))
--#define QCA8K_EGRESS_VLAN(x)                          (0x0c70 + (4 * (x / 2)))
--
--/* L3 registers */
--#define QCA8K_HROUTER_CONTROL                         0xe00
--#define   QCA8K_HROUTER_CONTROL_GLB_LOCKTIME_M                GENMASK(17, 16)
--#define   QCA8K_HROUTER_CONTROL_GLB_LOCKTIME_S                16
--#define   QCA8K_HROUTER_CONTROL_ARP_AGE_MODE          1
--#define QCA8K_HROUTER_PBASED_CONTROL1                 0xe08
--#define QCA8K_HROUTER_PBASED_CONTROL2                 0xe0c
--#define QCA8K_HNAT_CONTROL                            0xe38
--
--/* MIB registers */
--#define QCA8K_PORT_MIB_COUNTER(_i)                    (0x1000 + (_i) * 0x100)
--
--/* QCA specific MII registers */
--#define MII_ATH_MMD_ADDR                              0x0d
--#define MII_ATH_MMD_DATA                              0x0e
--
--enum {
--      QCA8K_PORT_SPEED_10M = 0,
--      QCA8K_PORT_SPEED_100M = 1,
--      QCA8K_PORT_SPEED_1000M = 2,
--      QCA8K_PORT_SPEED_ERR = 3,
--};
--
--enum qca8k_fdb_cmd {
--      QCA8K_FDB_FLUSH = 1,
--      QCA8K_FDB_LOAD = 2,
--      QCA8K_FDB_PURGE = 3,
--      QCA8K_FDB_FLUSH_PORT = 5,
--      QCA8K_FDB_NEXT = 6,
--      QCA8K_FDB_SEARCH = 7,
--};
--
--enum qca8k_vlan_cmd {
--      QCA8K_VLAN_FLUSH = 1,
--      QCA8K_VLAN_LOAD = 2,
--      QCA8K_VLAN_PURGE = 3,
--      QCA8K_VLAN_REMOVE_PORT = 4,
--      QCA8K_VLAN_NEXT = 5,
--      QCA8K_VLAN_READ = 6,
--};
--
--enum qca8k_mid_cmd {
--      QCA8K_MIB_FLUSH = 1,
--      QCA8K_MIB_FLUSH_PORT = 2,
--      QCA8K_MIB_CAST = 3,
--};
--
--struct qca8k_match_data {
--      u8 id;
--      bool reduced_package;
--      u8 mib_count;
--};
--
--enum {
--      QCA8K_CPU_PORT0,
--      QCA8K_CPU_PORT6,
--};
--
--struct qca8k_mgmt_eth_data {
--      struct completion rw_done;
--      struct mutex mutex; /* Enforce one mdio read/write at time */
--      bool ack;
--      u32 seq;
--      u32 data[4];
--};
--
--struct qca8k_mib_eth_data {
--      struct completion rw_done;
--      struct mutex mutex; /* Process one command at time */
--      refcount_t port_parsed; /* Counter to track parsed port */
--      u8 req_port;
--      u64 *data; /* pointer to ethtool data */
--};
--
--struct qca8k_ports_config {
--      bool sgmii_rx_clk_falling_edge;
--      bool sgmii_tx_clk_falling_edge;
--      bool sgmii_enable_pll;
--      u8 rgmii_rx_delay[QCA8K_NUM_CPU_PORTS]; /* 0: CPU port0, 1: CPU port6 */
--      u8 rgmii_tx_delay[QCA8K_NUM_CPU_PORTS]; /* 0: CPU port0, 1: CPU port6 */
--};
--
--struct qca8k_mdio_cache {
--/* The 32bit switch registers are accessed indirectly. To achieve this we need
-- * to set the page of the register. Track the last page that was set to reduce
-- * mdio writes
-- */
--      u16 page;
--/* lo and hi can also be cached and from Documentation we can skip one
-- * extra mdio write if lo or hi is didn't change.
-- */
--      u16 lo;
--      u16 hi;
--};
--
--struct qca8k_priv {
--      u8 switch_id;
--      u8 switch_revision;
--      u8 mirror_rx;
--      u8 mirror_tx;
--      u8 lag_hash_mode;
--      /* Each bit correspond to a port. This switch can support a max of 7 port.
--       * Bit 1: port enabled. Bit 0: port disabled.
--       */
--      u8 port_enabled_map;
--      struct qca8k_ports_config ports_config;
--      struct regmap *regmap;
--      struct mii_bus *bus;
--      struct dsa_switch *ds;
--      struct mutex reg_mutex;
--      struct device *dev;
--      struct gpio_desc *reset_gpio;
--      struct net_device *mgmt_master; /* Track if mdio/mib Ethernet is available */
--      struct qca8k_mgmt_eth_data mgmt_eth_data;
--      struct qca8k_mib_eth_data mib_eth_data;
--      struct qca8k_mdio_cache mdio_cache;
--};
--
--struct qca8k_mib_desc {
--      unsigned int size;
--      unsigned int offset;
--      const char *name;
--};
--
--struct qca8k_fdb {
--      u16 vid;
--      u8 port_mask;
--      u8 aging;
--      u8 mac[6];
--};
--
--#endif /* __QCA8K_H */
diff --git a/target/linux/generic/backport-5.15/771-v6.0-01-net-dsa-qca8k-cache-match-data-to-speed-up-access.patch b/target/linux/generic/backport-5.15/771-v6.0-01-net-dsa-qca8k-cache-match-data-to-speed-up-access.patch
deleted file mode 100644 (file)
index 77fe646..0000000
+++ /dev/null
@@ -1,157 +0,0 @@
-From 3bb0844e7bcd0fb0bcfab6202b5edd349ef5250a Mon Sep 17 00:00:00 2001
-From: Christian Marangi <[email protected]>
-Date: Wed, 27 Jul 2022 13:35:10 +0200
-Subject: [PATCH 01/14] net: dsa: qca8k: cache match data to speed up access
-
-Using of_device_get_match_data is expensive. Cache match data to speed
-up access and rework user of match data to use the new cached value.
-
-Signed-off-by: Christian Marangi <[email protected]>
-Reviewed-by: Vladimir Oltean <[email protected]>
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- drivers/net/dsa/qca/qca8k.c | 35 +++++++++++------------------------
- drivers/net/dsa/qca/qca8k.h |  1 +
- 2 files changed, 12 insertions(+), 24 deletions(-)
-
---- a/drivers/net/dsa/qca/qca8k.c
-+++ b/drivers/net/dsa/qca/qca8k.c
-@@ -1462,8 +1462,8 @@ static int qca8k_find_cpu_port(struct ds
- static int
- qca8k_setup_of_pws_reg(struct qca8k_priv *priv)
- {
-+      const struct qca8k_match_data *data = priv->info;
-       struct device_node *node = priv->dev->of_node;
--      const struct qca8k_match_data *data;
-       u32 val = 0;
-       int ret;
-@@ -1472,8 +1472,6 @@ qca8k_setup_of_pws_reg(struct qca8k_priv
-        * Should be applied by default but we set this just to make sure.
-        */
-       if (priv->switch_id == QCA8K_ID_QCA8327) {
--              data = of_device_get_match_data(priv->dev);
--
-               /* Set the correct package of 148 pin for QCA8327 */
-               if (data->reduced_package)
-                       val |= QCA8327_PWS_PACKAGE148_EN;
-@@ -2146,23 +2144,19 @@ qca8k_phylink_mac_link_up(struct dsa_swi
- static void
- qca8k_get_strings(struct dsa_switch *ds, int port, u32 stringset, uint8_t *data)
- {
--      const struct qca8k_match_data *match_data;
-       struct qca8k_priv *priv = ds->priv;
-       int i;
-       if (stringset != ETH_SS_STATS)
-               return;
--      match_data = of_device_get_match_data(priv->dev);
--
--      for (i = 0; i < match_data->mib_count; i++)
-+      for (i = 0; i < priv->info->mib_count; i++)
-               strncpy(data + i * ETH_GSTRING_LEN, ar8327_mib[i].name,
-                       ETH_GSTRING_LEN);
- }
- static void qca8k_mib_autocast_handler(struct dsa_switch *ds, struct sk_buff *skb)
- {
--      const struct qca8k_match_data *match_data;
-       struct qca8k_mib_eth_data *mib_eth_data;
-       struct qca8k_priv *priv = ds->priv;
-       const struct qca8k_mib_desc *mib;
-@@ -2181,10 +2175,9 @@ static void qca8k_mib_autocast_handler(s
-       if (port != mib_eth_data->req_port)
-               goto exit;
--      match_data = device_get_match_data(priv->dev);
-       data = mib_eth_data->data;
--      for (i = 0; i < match_data->mib_count; i++) {
-+      for (i = 0; i < priv->info->mib_count; i++) {
-               mib = &ar8327_mib[i];
-               /* First 3 mib are present in the skb head */
-@@ -2256,7 +2249,6 @@ qca8k_get_ethtool_stats(struct dsa_switc
-                       uint64_t *data)
- {
-       struct qca8k_priv *priv = (struct qca8k_priv *)ds->priv;
--      const struct qca8k_match_data *match_data;
-       const struct qca8k_mib_desc *mib;
-       u32 reg, i, val;
-       u32 hi = 0;
-@@ -2266,9 +2258,7 @@ qca8k_get_ethtool_stats(struct dsa_switc
-           qca8k_get_ethtool_stats_eth(ds, port, data) > 0)
-               return;
--      match_data = of_device_get_match_data(priv->dev);
--
--      for (i = 0; i < match_data->mib_count; i++) {
-+      for (i = 0; i < priv->info->mib_count; i++) {
-               mib = &ar8327_mib[i];
-               reg = QCA8K_PORT_MIB_COUNTER(port) + mib->offset;
-@@ -2291,15 +2281,12 @@ qca8k_get_ethtool_stats(struct dsa_switc
- static int
- qca8k_get_sset_count(struct dsa_switch *ds, int port, int sset)
- {
--      const struct qca8k_match_data *match_data;
-       struct qca8k_priv *priv = ds->priv;
-       if (sset != ETH_SS_STATS)
-               return 0;
--      match_data = of_device_get_match_data(priv->dev);
--
--      return match_data->mib_count;
-+      return priv->info->mib_count;
- }
- static int
-@@ -3037,14 +3024,11 @@ static const struct dsa_switch_ops qca8k
- static int qca8k_read_switch_id(struct qca8k_priv *priv)
- {
--      const struct qca8k_match_data *data;
-       u32 val;
-       u8 id;
-       int ret;
--      /* get the switches ID from the compatible */
--      data = of_device_get_match_data(priv->dev);
--      if (!data)
-+      if (!priv->info)
-               return -ENODEV;
-       ret = qca8k_read(priv, QCA8K_REG_MASK_CTRL, &val);
-@@ -3052,8 +3036,10 @@ static int qca8k_read_switch_id(struct q
-               return -ENODEV;
-       id = QCA8K_MASK_CTRL_DEVICE_ID(val);
--      if (id != data->id) {
--              dev_err(priv->dev, "Switch id detected %x but expected %x", id, data->id);
-+      if (id != priv->info->id) {
-+              dev_err(priv->dev,
-+                      "Switch id detected %x but expected %x",
-+                      id, priv->info->id);
-               return -ENODEV;
-       }
-@@ -3078,6 +3064,7 @@ qca8k_sw_probe(struct mdio_device *mdiod
-       if (!priv)
-               return -ENOMEM;
-+      priv->info = of_device_get_match_data(priv->dev);
-       priv->bus = mdiodev->bus;
-       priv->dev = &mdiodev->dev;
---- a/drivers/net/dsa/qca/qca8k.h
-+++ b/drivers/net/dsa/qca/qca8k.h
-@@ -393,6 +393,7 @@ struct qca8k_priv {
-       struct qca8k_mgmt_eth_data mgmt_eth_data;
-       struct qca8k_mib_eth_data mib_eth_data;
-       struct qca8k_mdio_cache mdio_cache;
-+      const struct qca8k_match_data *info;
- };
- struct qca8k_mib_desc {
diff --git a/target/linux/generic/backport-5.15/771-v6.0-02-net-dsa-qca8k-make-mib-autocast-feature-optional.patch b/target/linux/generic/backport-5.15/771-v6.0-02-net-dsa-qca8k-make-mib-autocast-feature-optional.patch
deleted file mode 100644 (file)
index 5b2dce4..0000000
+++ /dev/null
@@ -1,77 +0,0 @@
-From 533c64bca62a8654f00698bc893f639013e38c7b Mon Sep 17 00:00:00 2001
-From: Christian Marangi <[email protected]>
-Date: Wed, 27 Jul 2022 13:35:11 +0200
-Subject: [PATCH 02/14] net: dsa: qca8k: make mib autocast feature optional
-
-Some switch may not support mib autocast feature and require the legacy
-way of reading the regs directly.
-Make the mib autocast feature optional and permit to declare support for
-it using match_data struct in a dedicated qca8k_info_ops struct.
-
-Signed-off-by: Christian Marangi <[email protected]>
-Reviewed-by: Vladimir Oltean <[email protected]>
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- drivers/net/dsa/qca/qca8k.c | 11 +++++++++--
- drivers/net/dsa/qca/qca8k.h |  5 +++++
- 2 files changed, 14 insertions(+), 2 deletions(-)
-
---- a/drivers/net/dsa/qca/qca8k.c
-+++ b/drivers/net/dsa/qca/qca8k.c
-@@ -2254,8 +2254,8 @@ qca8k_get_ethtool_stats(struct dsa_switc
-       u32 hi = 0;
-       int ret;
--      if (priv->mgmt_master &&
--          qca8k_get_ethtool_stats_eth(ds, port, data) > 0)
-+      if (priv->mgmt_master && priv->info->ops->autocast_mib &&
-+          priv->info->ops->autocast_mib(ds, port, data) > 0)
-               return;
-       for (i = 0; i < priv->info->mib_count; i++) {
-@@ -3187,20 +3187,27 @@ static int qca8k_resume(struct device *d
- static SIMPLE_DEV_PM_OPS(qca8k_pm_ops,
-                        qca8k_suspend, qca8k_resume);
-+static const struct qca8k_info_ops qca8xxx_ops = {
-+      .autocast_mib = qca8k_get_ethtool_stats_eth,
-+};
-+
- static const struct qca8k_match_data qca8327 = {
-       .id = QCA8K_ID_QCA8327,
-       .reduced_package = true,
-       .mib_count = QCA8K_QCA832X_MIB_COUNT,
-+      .ops = &qca8xxx_ops,
- };
- static const struct qca8k_match_data qca8328 = {
-       .id = QCA8K_ID_QCA8327,
-       .mib_count = QCA8K_QCA832X_MIB_COUNT,
-+      .ops = &qca8xxx_ops,
- };
- static const struct qca8k_match_data qca833x = {
-       .id = QCA8K_ID_QCA8337,
-       .mib_count = QCA8K_QCA833X_MIB_COUNT,
-+      .ops = &qca8xxx_ops,
- };
- static const struct of_device_id qca8k_of_match[] = {
---- a/drivers/net/dsa/qca/qca8k.h
-+++ b/drivers/net/dsa/qca/qca8k.h
-@@ -324,10 +324,15 @@ enum qca8k_mid_cmd {
-       QCA8K_MIB_CAST = 3,
- };
-+struct qca8k_info_ops {
-+      int (*autocast_mib)(struct dsa_switch *ds, int port, u64 *data);
-+};
-+
- struct qca8k_match_data {
-       u8 id;
-       bool reduced_package;
-       u8 mib_count;
-+      const struct qca8k_info_ops *ops;
- };
- enum {
diff --git a/target/linux/generic/backport-5.15/771-v6.0-03-net-dsa-qca8k-move-mib-struct-to-common-code.patch b/target/linux/generic/backport-5.15/771-v6.0-03-net-dsa-qca8k-move-mib-struct-to-common-code.patch
deleted file mode 100644 (file)
index afa4666..0000000
+++ /dev/null
@@ -1,6532 +0,0 @@
-From 027152b830434e3632ad5dd678cc5d4740358dbb Mon Sep 17 00:00:00 2001
-From: Christian Marangi <[email protected]>
-Date: Wed, 27 Jul 2022 13:35:12 +0200
-Subject: [PATCH 03/14] net: dsa: qca8k: move mib struct to common code
-
-The same MIB struct is used by drivers based on qca8k family switch. Move
-it to common code to make it accessible also by other drivers.
-
-Signed-off-by: Christian Marangi <[email protected]>
-Reviewed-by: Vladimir Oltean <[email protected]>
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- drivers/net/dsa/qca/Makefile                  |  1 +
- drivers/net/dsa/qca/{qca8k.c => qca8k-8xxx.c} | 51 ---------------
- drivers/net/dsa/qca/qca8k-common.c            | 63 +++++++++++++++++++
- drivers/net/dsa/qca/qca8k.h                   |  3 +
- 4 files changed, 67 insertions(+), 51 deletions(-)
- rename drivers/net/dsa/qca/{qca8k.c => qca8k-8xxx.c} (98%)
- create mode 100644 drivers/net/dsa/qca/qca8k-common.c
-
---- a/drivers/net/dsa/qca/Makefile
-+++ b/drivers/net/dsa/qca/Makefile
-@@ -1,3 +1,4 @@
- # SPDX-License-Identifier: GPL-2.0-only
- obj-$(CONFIG_NET_DSA_AR9331)  += ar9331.o
- obj-$(CONFIG_NET_DSA_QCA8K)   += qca8k.o
-+qca8k-y                       += qca8k-common.o qca8k-8xxx.o
---- a/drivers/net/dsa/qca/qca8k.c
-+++ /dev/null
-@@ -1,3237 +0,0 @@
--// SPDX-License-Identifier: GPL-2.0
--/*
-- * Copyright (C) 2009 Felix Fietkau <[email protected]>
-- * Copyright (C) 2011-2012 Gabor Juhos <[email protected]>
-- * Copyright (c) 2015, 2019, The Linux Foundation. All rights reserved.
-- * Copyright (c) 2016 John Crispin <[email protected]>
-- */
--
--#include <linux/module.h>
--#include <linux/phy.h>
--#include <linux/netdevice.h>
--#include <linux/bitfield.h>
--#include <linux/regmap.h>
--#include <net/dsa.h>
--#include <linux/of_net.h>
--#include <linux/of_mdio.h>
--#include <linux/of_platform.h>
--#include <linux/if_bridge.h>
--#include <linux/mdio.h>
--#include <linux/phylink.h>
--#include <linux/gpio/consumer.h>
--#include <linux/etherdevice.h>
--#include <linux/dsa/tag_qca.h>
--
--#include "qca8k.h"
--
--#define MIB_DESC(_s, _o, _n)  \
--      {                       \
--              .size = (_s),   \
--              .offset = (_o), \
--              .name = (_n),   \
--      }
--
--static const struct qca8k_mib_desc ar8327_mib[] = {
--      MIB_DESC(1, 0x00, "RxBroad"),
--      MIB_DESC(1, 0x04, "RxPause"),
--      MIB_DESC(1, 0x08, "RxMulti"),
--      MIB_DESC(1, 0x0c, "RxFcsErr"),
--      MIB_DESC(1, 0x10, "RxAlignErr"),
--      MIB_DESC(1, 0x14, "RxRunt"),
--      MIB_DESC(1, 0x18, "RxFragment"),
--      MIB_DESC(1, 0x1c, "Rx64Byte"),
--      MIB_DESC(1, 0x20, "Rx128Byte"),
--      MIB_DESC(1, 0x24, "Rx256Byte"),
--      MIB_DESC(1, 0x28, "Rx512Byte"),
--      MIB_DESC(1, 0x2c, "Rx1024Byte"),
--      MIB_DESC(1, 0x30, "Rx1518Byte"),
--      MIB_DESC(1, 0x34, "RxMaxByte"),
--      MIB_DESC(1, 0x38, "RxTooLong"),
--      MIB_DESC(2, 0x3c, "RxGoodByte"),
--      MIB_DESC(2, 0x44, "RxBadByte"),
--      MIB_DESC(1, 0x4c, "RxOverFlow"),
--      MIB_DESC(1, 0x50, "Filtered"),
--      MIB_DESC(1, 0x54, "TxBroad"),
--      MIB_DESC(1, 0x58, "TxPause"),
--      MIB_DESC(1, 0x5c, "TxMulti"),
--      MIB_DESC(1, 0x60, "TxUnderRun"),
--      MIB_DESC(1, 0x64, "Tx64Byte"),
--      MIB_DESC(1, 0x68, "Tx128Byte"),
--      MIB_DESC(1, 0x6c, "Tx256Byte"),
--      MIB_DESC(1, 0x70, "Tx512Byte"),
--      MIB_DESC(1, 0x74, "Tx1024Byte"),
--      MIB_DESC(1, 0x78, "Tx1518Byte"),
--      MIB_DESC(1, 0x7c, "TxMaxByte"),
--      MIB_DESC(1, 0x80, "TxOverSize"),
--      MIB_DESC(2, 0x84, "TxByte"),
--      MIB_DESC(1, 0x8c, "TxCollision"),
--      MIB_DESC(1, 0x90, "TxAbortCol"),
--      MIB_DESC(1, 0x94, "TxMultiCol"),
--      MIB_DESC(1, 0x98, "TxSingleCol"),
--      MIB_DESC(1, 0x9c, "TxExcDefer"),
--      MIB_DESC(1, 0xa0, "TxDefer"),
--      MIB_DESC(1, 0xa4, "TxLateCol"),
--      MIB_DESC(1, 0xa8, "RXUnicast"),
--      MIB_DESC(1, 0xac, "TXUnicast"),
--};
--
--static void
--qca8k_split_addr(u32 regaddr, u16 *r1, u16 *r2, u16 *page)
--{
--      regaddr >>= 1;
--      *r1 = regaddr & 0x1e;
--
--      regaddr >>= 5;
--      *r2 = regaddr & 0x7;
--
--      regaddr >>= 3;
--      *page = regaddr & 0x3ff;
--}
--
--static int
--qca8k_set_lo(struct qca8k_priv *priv, int phy_id, u32 regnum, u16 lo)
--{
--      u16 *cached_lo = &priv->mdio_cache.lo;
--      struct mii_bus *bus = priv->bus;
--      int ret;
--
--      if (lo == *cached_lo)
--              return 0;
--
--      ret = bus->write(bus, phy_id, regnum, lo);
--      if (ret < 0)
--              dev_err_ratelimited(&bus->dev,
--                                  "failed to write qca8k 32bit lo register\n");
--
--      *cached_lo = lo;
--      return 0;
--}
--
--static int
--qca8k_set_hi(struct qca8k_priv *priv, int phy_id, u32 regnum, u16 hi)
--{
--      u16 *cached_hi = &priv->mdio_cache.hi;
--      struct mii_bus *bus = priv->bus;
--      int ret;
--
--      if (hi == *cached_hi)
--              return 0;
--
--      ret = bus->write(bus, phy_id, regnum, hi);
--      if (ret < 0)
--              dev_err_ratelimited(&bus->dev,
--                                  "failed to write qca8k 32bit hi register\n");
--
--      *cached_hi = hi;
--      return 0;
--}
--
--static int
--qca8k_mii_read32(struct mii_bus *bus, int phy_id, u32 regnum, u32 *val)
--{
--      int ret;
--
--      ret = bus->read(bus, phy_id, regnum);
--      if (ret >= 0) {
--              *val = ret;
--              ret = bus->read(bus, phy_id, regnum + 1);
--              *val |= ret << 16;
--      }
--
--      if (ret < 0) {
--              dev_err_ratelimited(&bus->dev,
--                                  "failed to read qca8k 32bit register\n");
--              *val = 0;
--              return ret;
--      }
--
--      return 0;
--}
--
--static void
--qca8k_mii_write32(struct qca8k_priv *priv, int phy_id, u32 regnum, u32 val)
--{
--      u16 lo, hi;
--      int ret;
--
--      lo = val & 0xffff;
--      hi = (u16)(val >> 16);
--
--      ret = qca8k_set_lo(priv, phy_id, regnum, lo);
--      if (ret >= 0)
--              ret = qca8k_set_hi(priv, phy_id, regnum + 1, hi);
--}
--
--static int
--qca8k_set_page(struct qca8k_priv *priv, u16 page)
--{
--      u16 *cached_page = &priv->mdio_cache.page;
--      struct mii_bus *bus = priv->bus;
--      int ret;
--
--      if (page == *cached_page)
--              return 0;
--
--      ret = bus->write(bus, 0x18, 0, page);
--      if (ret < 0) {
--              dev_err_ratelimited(&bus->dev,
--                                  "failed to set qca8k page\n");
--              return ret;
--      }
--
--      *cached_page = page;
--      usleep_range(1000, 2000);
--      return 0;
--}
--
--static int
--qca8k_read(struct qca8k_priv *priv, u32 reg, u32 *val)
--{
--      return regmap_read(priv->regmap, reg, val);
--}
--
--static int
--qca8k_write(struct qca8k_priv *priv, u32 reg, u32 val)
--{
--      return regmap_write(priv->regmap, reg, val);
--}
--
--static int
--qca8k_rmw(struct qca8k_priv *priv, u32 reg, u32 mask, u32 write_val)
--{
--      return regmap_update_bits(priv->regmap, reg, mask, write_val);
--}
--
--static void qca8k_rw_reg_ack_handler(struct dsa_switch *ds, struct sk_buff *skb)
--{
--      struct qca8k_mgmt_eth_data *mgmt_eth_data;
--      struct qca8k_priv *priv = ds->priv;
--      struct qca_mgmt_ethhdr *mgmt_ethhdr;
--      u8 len, cmd;
--
--      mgmt_ethhdr = (struct qca_mgmt_ethhdr *)skb_mac_header(skb);
--      mgmt_eth_data = &priv->mgmt_eth_data;
--
--      cmd = FIELD_GET(QCA_HDR_MGMT_CMD, mgmt_ethhdr->command);
--      len = FIELD_GET(QCA_HDR_MGMT_LENGTH, mgmt_ethhdr->command);
--
--      /* Make sure the seq match the requested packet */
--      if (mgmt_ethhdr->seq == mgmt_eth_data->seq)
--              mgmt_eth_data->ack = true;
--
--      if (cmd == MDIO_READ) {
--              mgmt_eth_data->data[0] = mgmt_ethhdr->mdio_data;
--
--              /* Get the rest of the 12 byte of data.
--               * The read/write function will extract the requested data.
--               */
--              if (len > QCA_HDR_MGMT_DATA1_LEN)
--                      memcpy(mgmt_eth_data->data + 1, skb->data,
--                             QCA_HDR_MGMT_DATA2_LEN);
--      }
--
--      complete(&mgmt_eth_data->rw_done);
--}
--
--static struct sk_buff *qca8k_alloc_mdio_header(enum mdio_cmd cmd, u32 reg, u32 *val,
--                                             int priority, unsigned int len)
--{
--      struct qca_mgmt_ethhdr *mgmt_ethhdr;
--      unsigned int real_len;
--      struct sk_buff *skb;
--      u32 *data2;
--      u16 hdr;
--
--      skb = dev_alloc_skb(QCA_HDR_MGMT_PKT_LEN);
--      if (!skb)
--              return NULL;
--
--      /* Max value for len reg is 15 (0xf) but the switch actually return 16 byte
--       * Actually for some reason the steps are:
--       * 0: nothing
--       * 1-4: first 4 byte
--       * 5-6: first 12 byte
--       * 7-15: all 16 byte
--       */
--      if (len == 16)
--              real_len = 15;
--      else
--              real_len = len;
--
--      skb_reset_mac_header(skb);
--      skb_set_network_header(skb, skb->len);
--
--      mgmt_ethhdr = skb_push(skb, QCA_HDR_MGMT_HEADER_LEN + QCA_HDR_LEN);
--
--      hdr = FIELD_PREP(QCA_HDR_XMIT_VERSION, QCA_HDR_VERSION);
--      hdr |= FIELD_PREP(QCA_HDR_XMIT_PRIORITY, priority);
--      hdr |= QCA_HDR_XMIT_FROM_CPU;
--      hdr |= FIELD_PREP(QCA_HDR_XMIT_DP_BIT, BIT(0));
--      hdr |= FIELD_PREP(QCA_HDR_XMIT_CONTROL, QCA_HDR_XMIT_TYPE_RW_REG);
--
--      mgmt_ethhdr->command = FIELD_PREP(QCA_HDR_MGMT_ADDR, reg);
--      mgmt_ethhdr->command |= FIELD_PREP(QCA_HDR_MGMT_LENGTH, real_len);
--      mgmt_ethhdr->command |= FIELD_PREP(QCA_HDR_MGMT_CMD, cmd);
--      mgmt_ethhdr->command |= FIELD_PREP(QCA_HDR_MGMT_CHECK_CODE,
--                                         QCA_HDR_MGMT_CHECK_CODE_VAL);
--
--      if (cmd == MDIO_WRITE)
--              mgmt_ethhdr->mdio_data = *val;
--
--      mgmt_ethhdr->hdr = htons(hdr);
--
--      data2 = skb_put_zero(skb, QCA_HDR_MGMT_DATA2_LEN + QCA_HDR_MGMT_PADDING_LEN);
--      if (cmd == MDIO_WRITE && len > QCA_HDR_MGMT_DATA1_LEN)
--              memcpy(data2, val + 1, len - QCA_HDR_MGMT_DATA1_LEN);
--
--      return skb;
--}
--
--static void qca8k_mdio_header_fill_seq_num(struct sk_buff *skb, u32 seq_num)
--{
--      struct qca_mgmt_ethhdr *mgmt_ethhdr;
--
--      mgmt_ethhdr = (struct qca_mgmt_ethhdr *)skb->data;
--      mgmt_ethhdr->seq = FIELD_PREP(QCA_HDR_MGMT_SEQ_NUM, seq_num);
--}
--
--static int qca8k_read_eth(struct qca8k_priv *priv, u32 reg, u32 *val, int len)
--{
--      struct qca8k_mgmt_eth_data *mgmt_eth_data = &priv->mgmt_eth_data;
--      struct sk_buff *skb;
--      bool ack;
--      int ret;
--
--      skb = qca8k_alloc_mdio_header(MDIO_READ, reg, NULL,
--                                    QCA8K_ETHERNET_MDIO_PRIORITY, len);
--      if (!skb)
--              return -ENOMEM;
--
--      mutex_lock(&mgmt_eth_data->mutex);
--
--      /* Check mgmt_master if is operational */
--      if (!priv->mgmt_master) {
--              kfree_skb(skb);
--              mutex_unlock(&mgmt_eth_data->mutex);
--              return -EINVAL;
--      }
--
--      skb->dev = priv->mgmt_master;
--
--      reinit_completion(&mgmt_eth_data->rw_done);
--
--      /* Increment seq_num and set it in the mdio pkt */
--      mgmt_eth_data->seq++;
--      qca8k_mdio_header_fill_seq_num(skb, mgmt_eth_data->seq);
--      mgmt_eth_data->ack = false;
--
--      dev_queue_xmit(skb);
--
--      ret = wait_for_completion_timeout(&mgmt_eth_data->rw_done,
--                                        msecs_to_jiffies(QCA8K_ETHERNET_TIMEOUT));
--
--      *val = mgmt_eth_data->data[0];
--      if (len > QCA_HDR_MGMT_DATA1_LEN)
--              memcpy(val + 1, mgmt_eth_data->data + 1, len - QCA_HDR_MGMT_DATA1_LEN);
--
--      ack = mgmt_eth_data->ack;
--
--      mutex_unlock(&mgmt_eth_data->mutex);
--
--      if (ret <= 0)
--              return -ETIMEDOUT;
--
--      if (!ack)
--              return -EINVAL;
--
--      return 0;
--}
--
--static int qca8k_write_eth(struct qca8k_priv *priv, u32 reg, u32 *val, int len)
--{
--      struct qca8k_mgmt_eth_data *mgmt_eth_data = &priv->mgmt_eth_data;
--      struct sk_buff *skb;
--      bool ack;
--      int ret;
--
--      skb = qca8k_alloc_mdio_header(MDIO_WRITE, reg, val,
--                                    QCA8K_ETHERNET_MDIO_PRIORITY, len);
--      if (!skb)
--              return -ENOMEM;
--
--      mutex_lock(&mgmt_eth_data->mutex);
--
--      /* Check mgmt_master if is operational */
--      if (!priv->mgmt_master) {
--              kfree_skb(skb);
--              mutex_unlock(&mgmt_eth_data->mutex);
--              return -EINVAL;
--      }
--
--      skb->dev = priv->mgmt_master;
--
--      reinit_completion(&mgmt_eth_data->rw_done);
--
--      /* Increment seq_num and set it in the mdio pkt */
--      mgmt_eth_data->seq++;
--      qca8k_mdio_header_fill_seq_num(skb, mgmt_eth_data->seq);
--      mgmt_eth_data->ack = false;
--
--      dev_queue_xmit(skb);
--
--      ret = wait_for_completion_timeout(&mgmt_eth_data->rw_done,
--                                        msecs_to_jiffies(QCA8K_ETHERNET_TIMEOUT));
--
--      ack = mgmt_eth_data->ack;
--
--      mutex_unlock(&mgmt_eth_data->mutex);
--
--      if (ret <= 0)
--              return -ETIMEDOUT;
--
--      if (!ack)
--              return -EINVAL;
--
--      return 0;
--}
--
--static int
--qca8k_regmap_update_bits_eth(struct qca8k_priv *priv, u32 reg, u32 mask, u32 write_val)
--{
--      u32 val = 0;
--      int ret;
--
--      ret = qca8k_read_eth(priv, reg, &val, sizeof(val));
--      if (ret)
--              return ret;
--
--      val &= ~mask;
--      val |= write_val;
--
--      return qca8k_write_eth(priv, reg, &val, sizeof(val));
--}
--
--static int
--qca8k_bulk_read(struct qca8k_priv *priv, u32 reg, u32 *val, int len)
--{
--      int i, count = len / sizeof(u32), ret;
--
--      if (priv->mgmt_master && !qca8k_read_eth(priv, reg, val, len))
--              return 0;
--
--      for (i = 0; i < count; i++) {
--              ret = regmap_read(priv->regmap, reg + (i * 4), val + i);
--              if (ret < 0)
--                      return ret;
--      }
--
--      return 0;
--}
--
--static int
--qca8k_bulk_write(struct qca8k_priv *priv, u32 reg, u32 *val, int len)
--{
--      int i, count = len / sizeof(u32), ret;
--      u32 tmp;
--
--      if (priv->mgmt_master && !qca8k_write_eth(priv, reg, val, len))
--              return 0;
--
--      for (i = 0; i < count; i++) {
--              tmp = val[i];
--
--              ret = regmap_write(priv->regmap, reg + (i * 4), tmp);
--              if (ret < 0)
--                      return ret;
--      }
--
--      return 0;
--}
--
--static int
--qca8k_regmap_read(void *ctx, uint32_t reg, uint32_t *val)
--{
--      struct qca8k_priv *priv = (struct qca8k_priv *)ctx;
--      struct mii_bus *bus = priv->bus;
--      u16 r1, r2, page;
--      int ret;
--
--      if (!qca8k_read_eth(priv, reg, val, sizeof(*val)))
--              return 0;
--
--      qca8k_split_addr(reg, &r1, &r2, &page);
--
--      mutex_lock_nested(&bus->mdio_lock, MDIO_MUTEX_NESTED);
--
--      ret = qca8k_set_page(priv, page);
--      if (ret < 0)
--              goto exit;
--
--      ret = qca8k_mii_read32(bus, 0x10 | r2, r1, val);
--
--exit:
--      mutex_unlock(&bus->mdio_lock);
--      return ret;
--}
--
--static int
--qca8k_regmap_write(void *ctx, uint32_t reg, uint32_t val)
--{
--      struct qca8k_priv *priv = (struct qca8k_priv *)ctx;
--      struct mii_bus *bus = priv->bus;
--      u16 r1, r2, page;
--      int ret;
--
--      if (!qca8k_write_eth(priv, reg, &val, sizeof(val)))
--              return 0;
--
--      qca8k_split_addr(reg, &r1, &r2, &page);
--
--      mutex_lock_nested(&bus->mdio_lock, MDIO_MUTEX_NESTED);
--
--      ret = qca8k_set_page(priv, page);
--      if (ret < 0)
--              goto exit;
--
--      qca8k_mii_write32(priv, 0x10 | r2, r1, val);
--
--exit:
--      mutex_unlock(&bus->mdio_lock);
--      return ret;
--}
--
--static int
--qca8k_regmap_update_bits(void *ctx, uint32_t reg, uint32_t mask, uint32_t write_val)
--{
--      struct qca8k_priv *priv = (struct qca8k_priv *)ctx;
--      struct mii_bus *bus = priv->bus;
--      u16 r1, r2, page;
--      u32 val;
--      int ret;
--
--      if (!qca8k_regmap_update_bits_eth(priv, reg, mask, write_val))
--              return 0;
--
--      qca8k_split_addr(reg, &r1, &r2, &page);
--
--      mutex_lock_nested(&bus->mdio_lock, MDIO_MUTEX_NESTED);
--
--      ret = qca8k_set_page(priv, page);
--      if (ret < 0)
--              goto exit;
--
--      ret = qca8k_mii_read32(bus, 0x10 | r2, r1, &val);
--      if (ret < 0)
--              goto exit;
--
--      val &= ~mask;
--      val |= write_val;
--      qca8k_mii_write32(priv, 0x10 | r2, r1, val);
--
--exit:
--      mutex_unlock(&bus->mdio_lock);
--
--      return ret;
--}
--
--static const struct regmap_range qca8k_readable_ranges[] = {
--      regmap_reg_range(0x0000, 0x00e4), /* Global control */
--      regmap_reg_range(0x0100, 0x0168), /* EEE control */
--      regmap_reg_range(0x0200, 0x0270), /* Parser control */
--      regmap_reg_range(0x0400, 0x0454), /* ACL */
--      regmap_reg_range(0x0600, 0x0718), /* Lookup */
--      regmap_reg_range(0x0800, 0x0b70), /* QM */
--      regmap_reg_range(0x0c00, 0x0c80), /* PKT */
--      regmap_reg_range(0x0e00, 0x0e98), /* L3 */
--      regmap_reg_range(0x1000, 0x10ac), /* MIB - Port0 */
--      regmap_reg_range(0x1100, 0x11ac), /* MIB - Port1 */
--      regmap_reg_range(0x1200, 0x12ac), /* MIB - Port2 */
--      regmap_reg_range(0x1300, 0x13ac), /* MIB - Port3 */
--      regmap_reg_range(0x1400, 0x14ac), /* MIB - Port4 */
--      regmap_reg_range(0x1500, 0x15ac), /* MIB - Port5 */
--      regmap_reg_range(0x1600, 0x16ac), /* MIB - Port6 */
--
--};
--
--static const struct regmap_access_table qca8k_readable_table = {
--      .yes_ranges = qca8k_readable_ranges,
--      .n_yes_ranges = ARRAY_SIZE(qca8k_readable_ranges),
--};
--
--static struct regmap_config qca8k_regmap_config = {
--      .reg_bits = 16,
--      .val_bits = 32,
--      .reg_stride = 4,
--      .max_register = 0x16ac, /* end MIB - Port6 range */
--      .reg_read = qca8k_regmap_read,
--      .reg_write = qca8k_regmap_write,
--      .reg_update_bits = qca8k_regmap_update_bits,
--      .rd_table = &qca8k_readable_table,
--      .disable_locking = true, /* Locking is handled by qca8k read/write */
--      .cache_type = REGCACHE_NONE, /* Explicitly disable CACHE */
--};
--
--static int
--qca8k_busy_wait(struct qca8k_priv *priv, u32 reg, u32 mask)
--{
--      u32 val;
--
--      return regmap_read_poll_timeout(priv->regmap, reg, val, !(val & mask), 0,
--                                     QCA8K_BUSY_WAIT_TIMEOUT * USEC_PER_MSEC);
--}
--
--static int
--qca8k_fdb_read(struct qca8k_priv *priv, struct qca8k_fdb *fdb)
--{
--      u32 reg[3];
--      int ret;
--
--      /* load the ARL table into an array */
--      ret = qca8k_bulk_read(priv, QCA8K_REG_ATU_DATA0, reg, sizeof(reg));
--      if (ret)
--              return ret;
--
--      /* vid - 83:72 */
--      fdb->vid = FIELD_GET(QCA8K_ATU_VID_MASK, reg[2]);
--      /* aging - 67:64 */
--      fdb->aging = FIELD_GET(QCA8K_ATU_STATUS_MASK, reg[2]);
--      /* portmask - 54:48 */
--      fdb->port_mask = FIELD_GET(QCA8K_ATU_PORT_MASK, reg[1]);
--      /* mac - 47:0 */
--      fdb->mac[0] = FIELD_GET(QCA8K_ATU_ADDR0_MASK, reg[1]);
--      fdb->mac[1] = FIELD_GET(QCA8K_ATU_ADDR1_MASK, reg[1]);
--      fdb->mac[2] = FIELD_GET(QCA8K_ATU_ADDR2_MASK, reg[0]);
--      fdb->mac[3] = FIELD_GET(QCA8K_ATU_ADDR3_MASK, reg[0]);
--      fdb->mac[4] = FIELD_GET(QCA8K_ATU_ADDR4_MASK, reg[0]);
--      fdb->mac[5] = FIELD_GET(QCA8K_ATU_ADDR5_MASK, reg[0]);
--
--      return 0;
--}
--
--static void
--qca8k_fdb_write(struct qca8k_priv *priv, u16 vid, u8 port_mask, const u8 *mac,
--              u8 aging)
--{
--      u32 reg[3] = { 0 };
--
--      /* vid - 83:72 */
--      reg[2] = FIELD_PREP(QCA8K_ATU_VID_MASK, vid);
--      /* aging - 67:64 */
--      reg[2] |= FIELD_PREP(QCA8K_ATU_STATUS_MASK, aging);
--      /* portmask - 54:48 */
--      reg[1] = FIELD_PREP(QCA8K_ATU_PORT_MASK, port_mask);
--      /* mac - 47:0 */
--      reg[1] |= FIELD_PREP(QCA8K_ATU_ADDR0_MASK, mac[0]);
--      reg[1] |= FIELD_PREP(QCA8K_ATU_ADDR1_MASK, mac[1]);
--      reg[0] |= FIELD_PREP(QCA8K_ATU_ADDR2_MASK, mac[2]);
--      reg[0] |= FIELD_PREP(QCA8K_ATU_ADDR3_MASK, mac[3]);
--      reg[0] |= FIELD_PREP(QCA8K_ATU_ADDR4_MASK, mac[4]);
--      reg[0] |= FIELD_PREP(QCA8K_ATU_ADDR5_MASK, mac[5]);
--
--      /* load the array into the ARL table */
--      qca8k_bulk_write(priv, QCA8K_REG_ATU_DATA0, reg, sizeof(reg));
--}
--
--static int
--qca8k_fdb_access(struct qca8k_priv *priv, enum qca8k_fdb_cmd cmd, int port)
--{
--      u32 reg;
--      int ret;
--
--      /* Set the command and FDB index */
--      reg = QCA8K_ATU_FUNC_BUSY;
--      reg |= cmd;
--      if (port >= 0) {
--              reg |= QCA8K_ATU_FUNC_PORT_EN;
--              reg |= FIELD_PREP(QCA8K_ATU_FUNC_PORT_MASK, port);
--      }
--
--      /* Write the function register triggering the table access */
--      ret = qca8k_write(priv, QCA8K_REG_ATU_FUNC, reg);
--      if (ret)
--              return ret;
--
--      /* wait for completion */
--      ret = qca8k_busy_wait(priv, QCA8K_REG_ATU_FUNC, QCA8K_ATU_FUNC_BUSY);
--      if (ret)
--              return ret;
--
--      /* Check for table full violation when adding an entry */
--      if (cmd == QCA8K_FDB_LOAD) {
--              ret = qca8k_read(priv, QCA8K_REG_ATU_FUNC, &reg);
--              if (ret < 0)
--                      return ret;
--              if (reg & QCA8K_ATU_FUNC_FULL)
--                      return -1;
--      }
--
--      return 0;
--}
--
--static int
--qca8k_fdb_next(struct qca8k_priv *priv, struct qca8k_fdb *fdb, int port)
--{
--      int ret;
--
--      qca8k_fdb_write(priv, fdb->vid, fdb->port_mask, fdb->mac, fdb->aging);
--      ret = qca8k_fdb_access(priv, QCA8K_FDB_NEXT, port);
--      if (ret < 0)
--              return ret;
--
--      return qca8k_fdb_read(priv, fdb);
--}
--
--static int
--qca8k_fdb_add(struct qca8k_priv *priv, const u8 *mac, u16 port_mask,
--            u16 vid, u8 aging)
--{
--      int ret;
--
--      mutex_lock(&priv->reg_mutex);
--      qca8k_fdb_write(priv, vid, port_mask, mac, aging);
--      ret = qca8k_fdb_access(priv, QCA8K_FDB_LOAD, -1);
--      mutex_unlock(&priv->reg_mutex);
--
--      return ret;
--}
--
--static int
--qca8k_fdb_del(struct qca8k_priv *priv, const u8 *mac, u16 port_mask, u16 vid)
--{
--      int ret;
--
--      mutex_lock(&priv->reg_mutex);
--      qca8k_fdb_write(priv, vid, port_mask, mac, 0);
--      ret = qca8k_fdb_access(priv, QCA8K_FDB_PURGE, -1);
--      mutex_unlock(&priv->reg_mutex);
--
--      return ret;
--}
--
--static void
--qca8k_fdb_flush(struct qca8k_priv *priv)
--{
--      mutex_lock(&priv->reg_mutex);
--      qca8k_fdb_access(priv, QCA8K_FDB_FLUSH, -1);
--      mutex_unlock(&priv->reg_mutex);
--}
--
--static int
--qca8k_fdb_search_and_insert(struct qca8k_priv *priv, u8 port_mask,
--                          const u8 *mac, u16 vid)
--{
--      struct qca8k_fdb fdb = { 0 };
--      int ret;
--
--      mutex_lock(&priv->reg_mutex);
--
--      qca8k_fdb_write(priv, vid, 0, mac, 0);
--      ret = qca8k_fdb_access(priv, QCA8K_FDB_SEARCH, -1);
--      if (ret < 0)
--              goto exit;
--
--      ret = qca8k_fdb_read(priv, &fdb);
--      if (ret < 0)
--              goto exit;
--
--      /* Rule exist. Delete first */
--      if (!fdb.aging) {
--              ret = qca8k_fdb_access(priv, QCA8K_FDB_PURGE, -1);
--              if (ret)
--                      goto exit;
--      }
--
--      /* Add port to fdb portmask */
--      fdb.port_mask |= port_mask;
--
--      qca8k_fdb_write(priv, vid, fdb.port_mask, mac, fdb.aging);
--      ret = qca8k_fdb_access(priv, QCA8K_FDB_LOAD, -1);
--
--exit:
--      mutex_unlock(&priv->reg_mutex);
--      return ret;
--}
--
--static int
--qca8k_fdb_search_and_del(struct qca8k_priv *priv, u8 port_mask,
--                       const u8 *mac, u16 vid)
--{
--      struct qca8k_fdb fdb = { 0 };
--      int ret;
--
--      mutex_lock(&priv->reg_mutex);
--
--      qca8k_fdb_write(priv, vid, 0, mac, 0);
--      ret = qca8k_fdb_access(priv, QCA8K_FDB_SEARCH, -1);
--      if (ret < 0)
--              goto exit;
--
--      /* Rule doesn't exist. Why delete? */
--      if (!fdb.aging) {
--              ret = -EINVAL;
--              goto exit;
--      }
--
--      ret = qca8k_fdb_access(priv, QCA8K_FDB_PURGE, -1);
--      if (ret)
--              goto exit;
--
--      /* Only port in the rule is this port. Don't re insert */
--      if (fdb.port_mask == port_mask)
--              goto exit;
--
--      /* Remove port from port mask */
--      fdb.port_mask &= ~port_mask;
--
--      qca8k_fdb_write(priv, vid, fdb.port_mask, mac, fdb.aging);
--      ret = qca8k_fdb_access(priv, QCA8K_FDB_LOAD, -1);
--
--exit:
--      mutex_unlock(&priv->reg_mutex);
--      return ret;
--}
--
--static int
--qca8k_vlan_access(struct qca8k_priv *priv, enum qca8k_vlan_cmd cmd, u16 vid)
--{
--      u32 reg;
--      int ret;
--
--      /* Set the command and VLAN index */
--      reg = QCA8K_VTU_FUNC1_BUSY;
--      reg |= cmd;
--      reg |= FIELD_PREP(QCA8K_VTU_FUNC1_VID_MASK, vid);
--
--      /* Write the function register triggering the table access */
--      ret = qca8k_write(priv, QCA8K_REG_VTU_FUNC1, reg);
--      if (ret)
--              return ret;
--
--      /* wait for completion */
--      ret = qca8k_busy_wait(priv, QCA8K_REG_VTU_FUNC1, QCA8K_VTU_FUNC1_BUSY);
--      if (ret)
--              return ret;
--
--      /* Check for table full violation when adding an entry */
--      if (cmd == QCA8K_VLAN_LOAD) {
--              ret = qca8k_read(priv, QCA8K_REG_VTU_FUNC1, &reg);
--              if (ret < 0)
--                      return ret;
--              if (reg & QCA8K_VTU_FUNC1_FULL)
--                      return -ENOMEM;
--      }
--
--      return 0;
--}
--
--static int
--qca8k_vlan_add(struct qca8k_priv *priv, u8 port, u16 vid, bool untagged)
--{
--      u32 reg;
--      int ret;
--
--      /*
--         We do the right thing with VLAN 0 and treat it as untagged while
--         preserving the tag on egress.
--       */
--      if (vid == 0)
--              return 0;
--
--      mutex_lock(&priv->reg_mutex);
--      ret = qca8k_vlan_access(priv, QCA8K_VLAN_READ, vid);
--      if (ret < 0)
--              goto out;
--
--      ret = qca8k_read(priv, QCA8K_REG_VTU_FUNC0, &reg);
--      if (ret < 0)
--              goto out;
--      reg |= QCA8K_VTU_FUNC0_VALID | QCA8K_VTU_FUNC0_IVL_EN;
--      reg &= ~QCA8K_VTU_FUNC0_EG_MODE_PORT_MASK(port);
--      if (untagged)
--              reg |= QCA8K_VTU_FUNC0_EG_MODE_PORT_UNTAG(port);
--      else
--              reg |= QCA8K_VTU_FUNC0_EG_MODE_PORT_TAG(port);
--
--      ret = qca8k_write(priv, QCA8K_REG_VTU_FUNC0, reg);
--      if (ret)
--              goto out;
--      ret = qca8k_vlan_access(priv, QCA8K_VLAN_LOAD, vid);
--
--out:
--      mutex_unlock(&priv->reg_mutex);
--
--      return ret;
--}
--
--static int
--qca8k_vlan_del(struct qca8k_priv *priv, u8 port, u16 vid)
--{
--      u32 reg, mask;
--      int ret, i;
--      bool del;
--
--      mutex_lock(&priv->reg_mutex);
--      ret = qca8k_vlan_access(priv, QCA8K_VLAN_READ, vid);
--      if (ret < 0)
--              goto out;
--
--      ret = qca8k_read(priv, QCA8K_REG_VTU_FUNC0, &reg);
--      if (ret < 0)
--              goto out;
--      reg &= ~QCA8K_VTU_FUNC0_EG_MODE_PORT_MASK(port);
--      reg |= QCA8K_VTU_FUNC0_EG_MODE_PORT_NOT(port);
--
--      /* Check if we're the last member to be removed */
--      del = true;
--      for (i = 0; i < QCA8K_NUM_PORTS; i++) {
--              mask = QCA8K_VTU_FUNC0_EG_MODE_PORT_NOT(i);
--
--              if ((reg & mask) != mask) {
--                      del = false;
--                      break;
--              }
--      }
--
--      if (del) {
--              ret = qca8k_vlan_access(priv, QCA8K_VLAN_PURGE, vid);
--      } else {
--              ret = qca8k_write(priv, QCA8K_REG_VTU_FUNC0, reg);
--              if (ret)
--                      goto out;
--              ret = qca8k_vlan_access(priv, QCA8K_VLAN_LOAD, vid);
--      }
--
--out:
--      mutex_unlock(&priv->reg_mutex);
--
--      return ret;
--}
--
--static int
--qca8k_mib_init(struct qca8k_priv *priv)
--{
--      int ret;
--
--      mutex_lock(&priv->reg_mutex);
--      ret = regmap_update_bits(priv->regmap, QCA8K_REG_MIB,
--                               QCA8K_MIB_FUNC | QCA8K_MIB_BUSY,
--                               FIELD_PREP(QCA8K_MIB_FUNC, QCA8K_MIB_FLUSH) |
--                               QCA8K_MIB_BUSY);
--      if (ret)
--              goto exit;
--
--      ret = qca8k_busy_wait(priv, QCA8K_REG_MIB, QCA8K_MIB_BUSY);
--      if (ret)
--              goto exit;
--
--      ret = regmap_set_bits(priv->regmap, QCA8K_REG_MIB, QCA8K_MIB_CPU_KEEP);
--      if (ret)
--              goto exit;
--
--      ret = qca8k_write(priv, QCA8K_REG_MODULE_EN, QCA8K_MODULE_EN_MIB);
--
--exit:
--      mutex_unlock(&priv->reg_mutex);
--      return ret;
--}
--
--static void
--qca8k_port_set_status(struct qca8k_priv *priv, int port, int enable)
--{
--      u32 mask = QCA8K_PORT_STATUS_TXMAC | QCA8K_PORT_STATUS_RXMAC;
--
--      /* Port 0 and 6 have no internal PHY */
--      if (port > 0 && port < 6)
--              mask |= QCA8K_PORT_STATUS_LINK_AUTO;
--
--      if (enable)
--              regmap_set_bits(priv->regmap, QCA8K_REG_PORT_STATUS(port), mask);
--      else
--              regmap_clear_bits(priv->regmap, QCA8K_REG_PORT_STATUS(port), mask);
--}
--
--static int
--qca8k_phy_eth_busy_wait(struct qca8k_mgmt_eth_data *mgmt_eth_data,
--                      struct sk_buff *read_skb, u32 *val)
--{
--      struct sk_buff *skb = skb_copy(read_skb, GFP_KERNEL);
--      bool ack;
--      int ret;
--
--      reinit_completion(&mgmt_eth_data->rw_done);
--
--      /* Increment seq_num and set it in the copy pkt */
--      mgmt_eth_data->seq++;
--      qca8k_mdio_header_fill_seq_num(skb, mgmt_eth_data->seq);
--      mgmt_eth_data->ack = false;
--
--      dev_queue_xmit(skb);
--
--      ret = wait_for_completion_timeout(&mgmt_eth_data->rw_done,
--                                        QCA8K_ETHERNET_TIMEOUT);
--
--      ack = mgmt_eth_data->ack;
--
--      if (ret <= 0)
--              return -ETIMEDOUT;
--
--      if (!ack)
--              return -EINVAL;
--
--      *val = mgmt_eth_data->data[0];
--
--      return 0;
--}
--
--static int
--qca8k_phy_eth_command(struct qca8k_priv *priv, bool read, int phy,
--                    int regnum, u16 data)
--{
--      struct sk_buff *write_skb, *clear_skb, *read_skb;
--      struct qca8k_mgmt_eth_data *mgmt_eth_data;
--      u32 write_val, clear_val = 0, val;
--      struct net_device *mgmt_master;
--      int ret, ret1;
--      bool ack;
--
--      if (regnum >= QCA8K_MDIO_MASTER_MAX_REG)
--              return -EINVAL;
--
--      mgmt_eth_data = &priv->mgmt_eth_data;
--
--      write_val = QCA8K_MDIO_MASTER_BUSY | QCA8K_MDIO_MASTER_EN |
--                  QCA8K_MDIO_MASTER_PHY_ADDR(phy) |
--                  QCA8K_MDIO_MASTER_REG_ADDR(regnum);
--
--      if (read) {
--              write_val |= QCA8K_MDIO_MASTER_READ;
--      } else {
--              write_val |= QCA8K_MDIO_MASTER_WRITE;
--              write_val |= QCA8K_MDIO_MASTER_DATA(data);
--      }
--
--      /* Prealloc all the needed skb before the lock */
--      write_skb = qca8k_alloc_mdio_header(MDIO_WRITE, QCA8K_MDIO_MASTER_CTRL, &write_val,
--                                          QCA8K_ETHERNET_PHY_PRIORITY, sizeof(write_val));
--      if (!write_skb)
--              return -ENOMEM;
--
--      clear_skb = qca8k_alloc_mdio_header(MDIO_WRITE, QCA8K_MDIO_MASTER_CTRL, &clear_val,
--                                          QCA8K_ETHERNET_PHY_PRIORITY, sizeof(clear_val));
--      if (!clear_skb) {
--              ret = -ENOMEM;
--              goto err_clear_skb;
--      }
--
--      read_skb = qca8k_alloc_mdio_header(MDIO_READ, QCA8K_MDIO_MASTER_CTRL, &clear_val,
--                                         QCA8K_ETHERNET_PHY_PRIORITY, sizeof(clear_val));
--      if (!read_skb) {
--              ret = -ENOMEM;
--              goto err_read_skb;
--      }
--
--      /* Actually start the request:
--       * 1. Send mdio master packet
--       * 2. Busy Wait for mdio master command
--       * 3. Get the data if we are reading
--       * 4. Reset the mdio master (even with error)
--       */
--      mutex_lock(&mgmt_eth_data->mutex);
--
--      /* Check if mgmt_master is operational */
--      mgmt_master = priv->mgmt_master;
--      if (!mgmt_master) {
--              mutex_unlock(&mgmt_eth_data->mutex);
--              ret = -EINVAL;
--              goto err_mgmt_master;
--      }
--
--      read_skb->dev = mgmt_master;
--      clear_skb->dev = mgmt_master;
--      write_skb->dev = mgmt_master;
--
--      reinit_completion(&mgmt_eth_data->rw_done);
--
--      /* Increment seq_num and set it in the write pkt */
--      mgmt_eth_data->seq++;
--      qca8k_mdio_header_fill_seq_num(write_skb, mgmt_eth_data->seq);
--      mgmt_eth_data->ack = false;
--
--      dev_queue_xmit(write_skb);
--
--      ret = wait_for_completion_timeout(&mgmt_eth_data->rw_done,
--                                        QCA8K_ETHERNET_TIMEOUT);
--
--      ack = mgmt_eth_data->ack;
--
--      if (ret <= 0) {
--              ret = -ETIMEDOUT;
--              kfree_skb(read_skb);
--              goto exit;
--      }
--
--      if (!ack) {
--              ret = -EINVAL;
--              kfree_skb(read_skb);
--              goto exit;
--      }
--
--      ret = read_poll_timeout(qca8k_phy_eth_busy_wait, ret1,
--                              !(val & QCA8K_MDIO_MASTER_BUSY), 0,
--                              QCA8K_BUSY_WAIT_TIMEOUT * USEC_PER_MSEC, false,
--                              mgmt_eth_data, read_skb, &val);
--
--      if (ret < 0 && ret1 < 0) {
--              ret = ret1;
--              goto exit;
--      }
--
--      if (read) {
--              reinit_completion(&mgmt_eth_data->rw_done);
--
--              /* Increment seq_num and set it in the read pkt */
--              mgmt_eth_data->seq++;
--              qca8k_mdio_header_fill_seq_num(read_skb, mgmt_eth_data->seq);
--              mgmt_eth_data->ack = false;
--
--              dev_queue_xmit(read_skb);
--
--              ret = wait_for_completion_timeout(&mgmt_eth_data->rw_done,
--                                                QCA8K_ETHERNET_TIMEOUT);
--
--              ack = mgmt_eth_data->ack;
--
--              if (ret <= 0) {
--                      ret = -ETIMEDOUT;
--                      goto exit;
--              }
--
--              if (!ack) {
--                      ret = -EINVAL;
--                      goto exit;
--              }
--
--              ret = mgmt_eth_data->data[0] & QCA8K_MDIO_MASTER_DATA_MASK;
--      } else {
--              kfree_skb(read_skb);
--      }
--exit:
--      reinit_completion(&mgmt_eth_data->rw_done);
--
--      /* Increment seq_num and set it in the clear pkt */
--      mgmt_eth_data->seq++;
--      qca8k_mdio_header_fill_seq_num(clear_skb, mgmt_eth_data->seq);
--      mgmt_eth_data->ack = false;
--
--      dev_queue_xmit(clear_skb);
--
--      wait_for_completion_timeout(&mgmt_eth_data->rw_done,
--                                  QCA8K_ETHERNET_TIMEOUT);
--
--      mutex_unlock(&mgmt_eth_data->mutex);
--
--      return ret;
--
--      /* Error handling before lock */
--err_mgmt_master:
--      kfree_skb(read_skb);
--err_read_skb:
--      kfree_skb(clear_skb);
--err_clear_skb:
--      kfree_skb(write_skb);
--
--      return ret;
--}
--
--static u32
--qca8k_port_to_phy(int port)
--{
--      /* From Andrew Lunn:
--       * Port 0 has no internal phy.
--       * Port 1 has an internal PHY at MDIO address 0.
--       * Port 2 has an internal PHY at MDIO address 1.
--       * ...
--       * Port 5 has an internal PHY at MDIO address 4.
--       * Port 6 has no internal PHY.
--       */
--
--      return port - 1;
--}
--
--static int
--qca8k_mdio_busy_wait(struct mii_bus *bus, u32 reg, u32 mask)
--{
--      u16 r1, r2, page;
--      u32 val;
--      int ret, ret1;
--
--      qca8k_split_addr(reg, &r1, &r2, &page);
--
--      ret = read_poll_timeout(qca8k_mii_read32, ret1, !(val & mask), 0,
--                              QCA8K_BUSY_WAIT_TIMEOUT * USEC_PER_MSEC, false,
--                              bus, 0x10 | r2, r1, &val);
--
--      /* Check if qca8k_read has failed for a different reason
--       * before returnting -ETIMEDOUT
--       */
--      if (ret < 0 && ret1 < 0)
--              return ret1;
--
--      return ret;
--}
--
--static int
--qca8k_mdio_write(struct qca8k_priv *priv, int phy, int regnum, u16 data)
--{
--      struct mii_bus *bus = priv->bus;
--      u16 r1, r2, page;
--      u32 val;
--      int ret;
--
--      if (regnum >= QCA8K_MDIO_MASTER_MAX_REG)
--              return -EINVAL;
--
--      val = QCA8K_MDIO_MASTER_BUSY | QCA8K_MDIO_MASTER_EN |
--            QCA8K_MDIO_MASTER_WRITE | QCA8K_MDIO_MASTER_PHY_ADDR(phy) |
--            QCA8K_MDIO_MASTER_REG_ADDR(regnum) |
--            QCA8K_MDIO_MASTER_DATA(data);
--
--      qca8k_split_addr(QCA8K_MDIO_MASTER_CTRL, &r1, &r2, &page);
--
--      mutex_lock_nested(&bus->mdio_lock, MDIO_MUTEX_NESTED);
--
--      ret = qca8k_set_page(priv, page);
--      if (ret)
--              goto exit;
--
--      qca8k_mii_write32(priv, 0x10 | r2, r1, val);
--
--      ret = qca8k_mdio_busy_wait(bus, QCA8K_MDIO_MASTER_CTRL,
--                                 QCA8K_MDIO_MASTER_BUSY);
--
--exit:
--      /* even if the busy_wait timeouts try to clear the MASTER_EN */
--      qca8k_mii_write32(priv, 0x10 | r2, r1, 0);
--
--      mutex_unlock(&bus->mdio_lock);
--
--      return ret;
--}
--
--static int
--qca8k_mdio_read(struct qca8k_priv *priv, int phy, int regnum)
--{
--      struct mii_bus *bus = priv->bus;
--      u16 r1, r2, page;
--      u32 val;
--      int ret;
--
--      if (regnum >= QCA8K_MDIO_MASTER_MAX_REG)
--              return -EINVAL;
--
--      val = QCA8K_MDIO_MASTER_BUSY | QCA8K_MDIO_MASTER_EN |
--            QCA8K_MDIO_MASTER_READ | QCA8K_MDIO_MASTER_PHY_ADDR(phy) |
--            QCA8K_MDIO_MASTER_REG_ADDR(regnum);
--
--      qca8k_split_addr(QCA8K_MDIO_MASTER_CTRL, &r1, &r2, &page);
--
--      mutex_lock_nested(&bus->mdio_lock, MDIO_MUTEX_NESTED);
--
--      ret = qca8k_set_page(priv, page);
--      if (ret)
--              goto exit;
--
--      qca8k_mii_write32(priv, 0x10 | r2, r1, val);
--
--      ret = qca8k_mdio_busy_wait(bus, QCA8K_MDIO_MASTER_CTRL,
--                                 QCA8K_MDIO_MASTER_BUSY);
--      if (ret)
--              goto exit;
--
--      ret = qca8k_mii_read32(bus, 0x10 | r2, r1, &val);
--
--exit:
--      /* even if the busy_wait timeouts try to clear the MASTER_EN */
--      qca8k_mii_write32(priv, 0x10 | r2, r1, 0);
--
--      mutex_unlock(&bus->mdio_lock);
--
--      if (ret >= 0)
--              ret = val & QCA8K_MDIO_MASTER_DATA_MASK;
--
--      return ret;
--}
--
--static int
--qca8k_internal_mdio_write(struct mii_bus *slave_bus, int phy, int regnum, u16 data)
--{
--      struct qca8k_priv *priv = slave_bus->priv;
--      int ret;
--
--      /* Use mdio Ethernet when available, fallback to legacy one on error */
--      ret = qca8k_phy_eth_command(priv, false, phy, regnum, data);
--      if (!ret)
--              return 0;
--
--      return qca8k_mdio_write(priv, phy, regnum, data);
--}
--
--static int
--qca8k_internal_mdio_read(struct mii_bus *slave_bus, int phy, int regnum)
--{
--      struct qca8k_priv *priv = slave_bus->priv;
--      int ret;
--
--      /* Use mdio Ethernet when available, fallback to legacy one on error */
--      ret = qca8k_phy_eth_command(priv, true, phy, regnum, 0);
--      if (ret >= 0)
--              return ret;
--
--      ret = qca8k_mdio_read(priv, phy, regnum);
--
--      if (ret < 0)
--              return 0xffff;
--
--      return ret;
--}
--
--static int
--qca8k_legacy_mdio_write(struct mii_bus *slave_bus, int port, int regnum, u16 data)
--{
--      port = qca8k_port_to_phy(port) % PHY_MAX_ADDR;
--
--      return qca8k_internal_mdio_write(slave_bus, port, regnum, data);
--}
--
--static int
--qca8k_legacy_mdio_read(struct mii_bus *slave_bus, int port, int regnum)
--{
--      port = qca8k_port_to_phy(port) % PHY_MAX_ADDR;
--
--      return qca8k_internal_mdio_read(slave_bus, port, regnum);
--}
--
--static int
--qca8k_mdio_register(struct qca8k_priv *priv)
--{
--      struct dsa_switch *ds = priv->ds;
--      struct device_node *mdio;
--      struct mii_bus *bus;
--
--      bus = devm_mdiobus_alloc(ds->dev);
--      if (!bus)
--              return -ENOMEM;
--
--      bus->priv = (void *)priv;
--      snprintf(bus->id, MII_BUS_ID_SIZE, "qca8k-%d.%d",
--               ds->dst->index, ds->index);
--      bus->parent = ds->dev;
--      bus->phy_mask = ~ds->phys_mii_mask;
--      ds->slave_mii_bus = bus;
--
--      /* Check if the devicetree declare the port:phy mapping */
--      mdio = of_get_child_by_name(priv->dev->of_node, "mdio");
--      if (of_device_is_available(mdio)) {
--              bus->name = "qca8k slave mii";
--              bus->read = qca8k_internal_mdio_read;
--              bus->write = qca8k_internal_mdio_write;
--              return devm_of_mdiobus_register(priv->dev, bus, mdio);
--      }
--
--      /* If a mapping can't be found the legacy mapping is used,
--       * using the qca8k_port_to_phy function
--       */
--      bus->name = "qca8k-legacy slave mii";
--      bus->read = qca8k_legacy_mdio_read;
--      bus->write = qca8k_legacy_mdio_write;
--      return devm_mdiobus_register(priv->dev, bus);
--}
--
--static int
--qca8k_setup_mdio_bus(struct qca8k_priv *priv)
--{
--      u32 internal_mdio_mask = 0, external_mdio_mask = 0, reg;
--      struct device_node *ports, *port;
--      phy_interface_t mode;
--      int err;
--
--      ports = of_get_child_by_name(priv->dev->of_node, "ports");
--      if (!ports)
--              ports = of_get_child_by_name(priv->dev->of_node, "ethernet-ports");
--
--      if (!ports)
--              return -EINVAL;
--
--      for_each_available_child_of_node(ports, port) {
--              err = of_property_read_u32(port, "reg", &reg);
--              if (err) {
--                      of_node_put(port);
--                      of_node_put(ports);
--                      return err;
--              }
--
--              if (!dsa_is_user_port(priv->ds, reg))
--                      continue;
--
--              of_get_phy_mode(port, &mode);
--
--              if (of_property_read_bool(port, "phy-handle") &&
--                  mode != PHY_INTERFACE_MODE_INTERNAL)
--                      external_mdio_mask |= BIT(reg);
--              else
--                      internal_mdio_mask |= BIT(reg);
--      }
--
--      of_node_put(ports);
--      if (!external_mdio_mask && !internal_mdio_mask) {
--              dev_err(priv->dev, "no PHYs are defined.\n");
--              return -EINVAL;
--      }
--
--      /* The QCA8K_MDIO_MASTER_EN Bit, which grants access to PHYs through
--       * the MDIO_MASTER register also _disconnects_ the external MDC
--       * passthrough to the internal PHYs. It's not possible to use both
--       * configurations at the same time!
--       *
--       * Because this came up during the review process:
--       * If the external mdio-bus driver is capable magically disabling
--       * the QCA8K_MDIO_MASTER_EN and mutex/spin-locking out the qca8k's
--       * accessors for the time being, it would be possible to pull this
--       * off.
--       */
--      if (!!external_mdio_mask && !!internal_mdio_mask) {
--              dev_err(priv->dev, "either internal or external mdio bus configuration is supported.\n");
--              return -EINVAL;
--      }
--
--      if (external_mdio_mask) {
--              /* Make sure to disable the internal mdio bus in cases
--               * a dt-overlay and driver reload changed the configuration
--               */
--
--              return regmap_clear_bits(priv->regmap, QCA8K_MDIO_MASTER_CTRL,
--                                       QCA8K_MDIO_MASTER_EN);
--      }
--
--      return qca8k_mdio_register(priv);
--}
--
--static int
--qca8k_setup_mac_pwr_sel(struct qca8k_priv *priv)
--{
--      u32 mask = 0;
--      int ret = 0;
--
--      /* SoC specific settings for ipq8064.
--       * If more device require this consider adding
--       * a dedicated binding.
--       */
--      if (of_machine_is_compatible("qcom,ipq8064"))
--              mask |= QCA8K_MAC_PWR_RGMII0_1_8V;
--
--      /* SoC specific settings for ipq8065 */
--      if (of_machine_is_compatible("qcom,ipq8065"))
--              mask |= QCA8K_MAC_PWR_RGMII1_1_8V;
--
--      if (mask) {
--              ret = qca8k_rmw(priv, QCA8K_REG_MAC_PWR_SEL,
--                              QCA8K_MAC_PWR_RGMII0_1_8V |
--                              QCA8K_MAC_PWR_RGMII1_1_8V,
--                              mask);
--      }
--
--      return ret;
--}
--
--static int qca8k_find_cpu_port(struct dsa_switch *ds)
--{
--      struct qca8k_priv *priv = ds->priv;
--
--      /* Find the connected cpu port. Valid port are 0 or 6 */
--      if (dsa_is_cpu_port(ds, 0))
--              return 0;
--
--      dev_dbg(priv->dev, "port 0 is not the CPU port. Checking port 6");
--
--      if (dsa_is_cpu_port(ds, 6))
--              return 6;
--
--      return -EINVAL;
--}
--
--static int
--qca8k_setup_of_pws_reg(struct qca8k_priv *priv)
--{
--      const struct qca8k_match_data *data = priv->info;
--      struct device_node *node = priv->dev->of_node;
--      u32 val = 0;
--      int ret;
--
--      /* QCA8327 require to set to the correct mode.
--       * His bigger brother QCA8328 have the 172 pin layout.
--       * Should be applied by default but we set this just to make sure.
--       */
--      if (priv->switch_id == QCA8K_ID_QCA8327) {
--              /* Set the correct package of 148 pin for QCA8327 */
--              if (data->reduced_package)
--                      val |= QCA8327_PWS_PACKAGE148_EN;
--
--              ret = qca8k_rmw(priv, QCA8K_REG_PWS, QCA8327_PWS_PACKAGE148_EN,
--                              val);
--              if (ret)
--                      return ret;
--      }
--
--      if (of_property_read_bool(node, "qca,ignore-power-on-sel"))
--              val |= QCA8K_PWS_POWER_ON_SEL;
--
--      if (of_property_read_bool(node, "qca,led-open-drain")) {
--              if (!(val & QCA8K_PWS_POWER_ON_SEL)) {
--                      dev_err(priv->dev, "qca,led-open-drain require qca,ignore-power-on-sel to be set.");
--                      return -EINVAL;
--              }
--
--              val |= QCA8K_PWS_LED_OPEN_EN_CSR;
--      }
--
--      return qca8k_rmw(priv, QCA8K_REG_PWS,
--                      QCA8K_PWS_LED_OPEN_EN_CSR | QCA8K_PWS_POWER_ON_SEL,
--                      val);
--}
--
--static int
--qca8k_parse_port_config(struct qca8k_priv *priv)
--{
--      int port, cpu_port_index = -1, ret;
--      struct device_node *port_dn;
--      phy_interface_t mode;
--      struct dsa_port *dp;
--      u32 delay;
--
--      /* We have 2 CPU port. Check them */
--      for (port = 0; port < QCA8K_NUM_PORTS; port++) {
--              /* Skip every other port */
--              if (port != 0 && port != 6)
--                      continue;
--
--              dp = dsa_to_port(priv->ds, port);
--              port_dn = dp->dn;
--              cpu_port_index++;
--
--              if (!of_device_is_available(port_dn))
--                      continue;
--
--              ret = of_get_phy_mode(port_dn, &mode);
--              if (ret)
--                      continue;
--
--              switch (mode) {
--              case PHY_INTERFACE_MODE_RGMII:
--              case PHY_INTERFACE_MODE_RGMII_ID:
--              case PHY_INTERFACE_MODE_RGMII_TXID:
--              case PHY_INTERFACE_MODE_RGMII_RXID:
--              case PHY_INTERFACE_MODE_SGMII:
--                      delay = 0;
--
--                      if (!of_property_read_u32(port_dn, "tx-internal-delay-ps", &delay))
--                              /* Switch regs accept value in ns, convert ps to ns */
--                              delay = delay / 1000;
--                      else if (mode == PHY_INTERFACE_MODE_RGMII_ID ||
--                               mode == PHY_INTERFACE_MODE_RGMII_TXID)
--                              delay = 1;
--
--                      if (!FIELD_FIT(QCA8K_PORT_PAD_RGMII_TX_DELAY_MASK, delay)) {
--                              dev_err(priv->dev, "rgmii tx delay is limited to a max value of 3ns, setting to the max value");
--                              delay = 3;
--                      }
--
--                      priv->ports_config.rgmii_tx_delay[cpu_port_index] = delay;
--
--                      delay = 0;
--
--                      if (!of_property_read_u32(port_dn, "rx-internal-delay-ps", &delay))
--                              /* Switch regs accept value in ns, convert ps to ns */
--                              delay = delay / 1000;
--                      else if (mode == PHY_INTERFACE_MODE_RGMII_ID ||
--                               mode == PHY_INTERFACE_MODE_RGMII_RXID)
--                              delay = 2;
--
--                      if (!FIELD_FIT(QCA8K_PORT_PAD_RGMII_RX_DELAY_MASK, delay)) {
--                              dev_err(priv->dev, "rgmii rx delay is limited to a max value of 3ns, setting to the max value");
--                              delay = 3;
--                      }
--
--                      priv->ports_config.rgmii_rx_delay[cpu_port_index] = delay;
--
--                      /* Skip sgmii parsing for rgmii* mode */
--                      if (mode == PHY_INTERFACE_MODE_RGMII ||
--                          mode == PHY_INTERFACE_MODE_RGMII_ID ||
--                          mode == PHY_INTERFACE_MODE_RGMII_TXID ||
--                          mode == PHY_INTERFACE_MODE_RGMII_RXID)
--                              break;
--
--                      if (of_property_read_bool(port_dn, "qca,sgmii-txclk-falling-edge"))
--                              priv->ports_config.sgmii_tx_clk_falling_edge = true;
--
--                      if (of_property_read_bool(port_dn, "qca,sgmii-rxclk-falling-edge"))
--                              priv->ports_config.sgmii_rx_clk_falling_edge = true;
--
--                      if (of_property_read_bool(port_dn, "qca,sgmii-enable-pll")) {
--                              priv->ports_config.sgmii_enable_pll = true;
--
--                              if (priv->switch_id == QCA8K_ID_QCA8327) {
--                                      dev_err(priv->dev, "SGMII PLL should NOT be enabled for qca8327. Aborting enabling");
--                                      priv->ports_config.sgmii_enable_pll = false;
--                              }
--
--                              if (priv->switch_revision < 2)
--                                      dev_warn(priv->dev, "SGMII PLL should NOT be enabled for qca8337 with revision 2 or more.");
--                      }
--
--                      break;
--              default:
--                      continue;
--              }
--      }
--
--      return 0;
--}
--
--static int
--qca8k_setup(struct dsa_switch *ds)
--{
--      struct qca8k_priv *priv = (struct qca8k_priv *)ds->priv;
--      int cpu_port, ret, i;
--      u32 mask;
--
--      cpu_port = qca8k_find_cpu_port(ds);
--      if (cpu_port < 0) {
--              dev_err(priv->dev, "No cpu port configured in both cpu port0 and port6");
--              return cpu_port;
--      }
--
--      /* Parse CPU port config to be later used in phy_link mac_config */
--      ret = qca8k_parse_port_config(priv);
--      if (ret)
--              return ret;
--
--      ret = qca8k_setup_mdio_bus(priv);
--      if (ret)
--              return ret;
--
--      ret = qca8k_setup_of_pws_reg(priv);
--      if (ret)
--              return ret;
--
--      ret = qca8k_setup_mac_pwr_sel(priv);
--      if (ret)
--              return ret;
--
--      /* Make sure MAC06 is disabled */
--      ret = regmap_clear_bits(priv->regmap, QCA8K_REG_PORT0_PAD_CTRL,
--                              QCA8K_PORT0_PAD_MAC06_EXCHANGE_EN);
--      if (ret) {
--              dev_err(priv->dev, "failed disabling MAC06 exchange");
--              return ret;
--      }
--
--      /* Enable CPU Port */
--      ret = regmap_set_bits(priv->regmap, QCA8K_REG_GLOBAL_FW_CTRL0,
--                            QCA8K_GLOBAL_FW_CTRL0_CPU_PORT_EN);
--      if (ret) {
--              dev_err(priv->dev, "failed enabling CPU port");
--              return ret;
--      }
--
--      /* Enable MIB counters */
--      ret = qca8k_mib_init(priv);
--      if (ret)
--              dev_warn(priv->dev, "mib init failed");
--
--      /* Initial setup of all ports */
--      for (i = 0; i < QCA8K_NUM_PORTS; i++) {
--              /* Disable forwarding by default on all ports */
--              ret = qca8k_rmw(priv, QCA8K_PORT_LOOKUP_CTRL(i),
--                              QCA8K_PORT_LOOKUP_MEMBER, 0);
--              if (ret)
--                      return ret;
--
--              /* Enable QCA header mode on all cpu ports */
--              if (dsa_is_cpu_port(ds, i)) {
--                      ret = qca8k_write(priv, QCA8K_REG_PORT_HDR_CTRL(i),
--                                        FIELD_PREP(QCA8K_PORT_HDR_CTRL_TX_MASK, QCA8K_PORT_HDR_CTRL_ALL) |
--                                        FIELD_PREP(QCA8K_PORT_HDR_CTRL_RX_MASK, QCA8K_PORT_HDR_CTRL_ALL));
--                      if (ret) {
--                              dev_err(priv->dev, "failed enabling QCA header mode");
--                              return ret;
--                      }
--              }
--
--              /* Disable MAC by default on all user ports */
--              if (dsa_is_user_port(ds, i))
--                      qca8k_port_set_status(priv, i, 0);
--      }
--
--      /* Forward all unknown frames to CPU port for Linux processing
--       * Notice that in multi-cpu config only one port should be set
--       * for igmp, unknown, multicast and broadcast packet
--       */
--      ret = qca8k_write(priv, QCA8K_REG_GLOBAL_FW_CTRL1,
--                        FIELD_PREP(QCA8K_GLOBAL_FW_CTRL1_IGMP_DP_MASK, BIT(cpu_port)) |
--                        FIELD_PREP(QCA8K_GLOBAL_FW_CTRL1_BC_DP_MASK, BIT(cpu_port)) |
--                        FIELD_PREP(QCA8K_GLOBAL_FW_CTRL1_MC_DP_MASK, BIT(cpu_port)) |
--                        FIELD_PREP(QCA8K_GLOBAL_FW_CTRL1_UC_DP_MASK, BIT(cpu_port)));
--      if (ret)
--              return ret;
--
--      /* Setup connection between CPU port & user ports
--       * Configure specific switch configuration for ports
--       */
--      for (i = 0; i < QCA8K_NUM_PORTS; i++) {
--              /* CPU port gets connected to all user ports of the switch */
--              if (dsa_is_cpu_port(ds, i)) {
--                      ret = qca8k_rmw(priv, QCA8K_PORT_LOOKUP_CTRL(i),
--                                      QCA8K_PORT_LOOKUP_MEMBER, dsa_user_ports(ds));
--                      if (ret)
--                              return ret;
--              }
--
--              /* Individual user ports get connected to CPU port only */
--              if (dsa_is_user_port(ds, i)) {
--                      ret = qca8k_rmw(priv, QCA8K_PORT_LOOKUP_CTRL(i),
--                                      QCA8K_PORT_LOOKUP_MEMBER,
--                                      BIT(cpu_port));
--                      if (ret)
--                              return ret;
--
--                      /* Enable ARP Auto-learning by default */
--                      ret = regmap_set_bits(priv->regmap, QCA8K_PORT_LOOKUP_CTRL(i),
--                                            QCA8K_PORT_LOOKUP_LEARN);
--                      if (ret)
--                              return ret;
--
--                      /* For port based vlans to work we need to set the
--                       * default egress vid
--                       */
--                      ret = qca8k_rmw(priv, QCA8K_EGRESS_VLAN(i),
--                                      QCA8K_EGREES_VLAN_PORT_MASK(i),
--                                      QCA8K_EGREES_VLAN_PORT(i, QCA8K_PORT_VID_DEF));
--                      if (ret)
--                              return ret;
--
--                      ret = qca8k_write(priv, QCA8K_REG_PORT_VLAN_CTRL0(i),
--                                        QCA8K_PORT_VLAN_CVID(QCA8K_PORT_VID_DEF) |
--                                        QCA8K_PORT_VLAN_SVID(QCA8K_PORT_VID_DEF));
--                      if (ret)
--                              return ret;
--              }
--
--              /* The port 5 of the qca8337 have some problem in flood condition. The
--               * original legacy driver had some specific buffer and priority settings
--               * for the different port suggested by the QCA switch team. Add this
--               * missing settings to improve switch stability under load condition.
--               * This problem is limited to qca8337 and other qca8k switch are not affected.
--               */
--              if (priv->switch_id == QCA8K_ID_QCA8337) {
--                      switch (i) {
--                      /* The 2 CPU port and port 5 requires some different
--                       * priority than any other ports.
--                       */
--                      case 0:
--                      case 5:
--                      case 6:
--                              mask = QCA8K_PORT_HOL_CTRL0_EG_PRI0(0x3) |
--                                      QCA8K_PORT_HOL_CTRL0_EG_PRI1(0x4) |
--                                      QCA8K_PORT_HOL_CTRL0_EG_PRI2(0x4) |
--                                      QCA8K_PORT_HOL_CTRL0_EG_PRI3(0x4) |
--                                      QCA8K_PORT_HOL_CTRL0_EG_PRI4(0x6) |
--                                      QCA8K_PORT_HOL_CTRL0_EG_PRI5(0x8) |
--                                      QCA8K_PORT_HOL_CTRL0_EG_PORT(0x1e);
--                              break;
--                      default:
--                              mask = QCA8K_PORT_HOL_CTRL0_EG_PRI0(0x3) |
--                                      QCA8K_PORT_HOL_CTRL0_EG_PRI1(0x4) |
--                                      QCA8K_PORT_HOL_CTRL0_EG_PRI2(0x6) |
--                                      QCA8K_PORT_HOL_CTRL0_EG_PRI3(0x8) |
--                                      QCA8K_PORT_HOL_CTRL0_EG_PORT(0x19);
--                      }
--                      qca8k_write(priv, QCA8K_REG_PORT_HOL_CTRL0(i), mask);
--
--                      mask = QCA8K_PORT_HOL_CTRL1_ING(0x6) |
--                      QCA8K_PORT_HOL_CTRL1_EG_PRI_BUF_EN |
--                      QCA8K_PORT_HOL_CTRL1_EG_PORT_BUF_EN |
--                      QCA8K_PORT_HOL_CTRL1_WRED_EN;
--                      qca8k_rmw(priv, QCA8K_REG_PORT_HOL_CTRL1(i),
--                                QCA8K_PORT_HOL_CTRL1_ING_BUF_MASK |
--                                QCA8K_PORT_HOL_CTRL1_EG_PRI_BUF_EN |
--                                QCA8K_PORT_HOL_CTRL1_EG_PORT_BUF_EN |
--                                QCA8K_PORT_HOL_CTRL1_WRED_EN,
--                                mask);
--              }
--      }
--
--      /* Special GLOBAL_FC_THRESH value are needed for ar8327 switch */
--      if (priv->switch_id == QCA8K_ID_QCA8327) {
--              mask = QCA8K_GLOBAL_FC_GOL_XON_THRES(288) |
--                     QCA8K_GLOBAL_FC_GOL_XOFF_THRES(496);
--              qca8k_rmw(priv, QCA8K_REG_GLOBAL_FC_THRESH,
--                        QCA8K_GLOBAL_FC_GOL_XON_THRES_MASK |
--                        QCA8K_GLOBAL_FC_GOL_XOFF_THRES_MASK,
--                        mask);
--      }
--
--      /* Setup our port MTUs to match power on defaults */
--      ret = qca8k_write(priv, QCA8K_MAX_FRAME_SIZE, ETH_FRAME_LEN + ETH_FCS_LEN);
--      if (ret)
--              dev_warn(priv->dev, "failed setting MTU settings");
--
--      /* Flush the FDB table */
--      qca8k_fdb_flush(priv);
--
--      /* We don't have interrupts for link changes, so we need to poll */
--      ds->pcs_poll = true;
--
--      /* Set min a max ageing value supported */
--      ds->ageing_time_min = 7000;
--      ds->ageing_time_max = 458745000;
--
--      /* Set max number of LAGs supported */
--      ds->num_lag_ids = QCA8K_NUM_LAGS;
--
--      return 0;
--}
--
--static void
--qca8k_mac_config_setup_internal_delay(struct qca8k_priv *priv, int cpu_port_index,
--                                    u32 reg)
--{
--      u32 delay, val = 0;
--      int ret;
--
--      /* Delay can be declared in 3 different way.
--       * Mode to rgmii and internal-delay standard binding defined
--       * rgmii-id or rgmii-tx/rx phy mode set.
--       * The parse logic set a delay different than 0 only when one
--       * of the 3 different way is used. In all other case delay is
--       * not enabled. With ID or TX/RXID delay is enabled and set
--       * to the default and recommended value.
--       */
--      if (priv->ports_config.rgmii_tx_delay[cpu_port_index]) {
--              delay = priv->ports_config.rgmii_tx_delay[cpu_port_index];
--
--              val |= QCA8K_PORT_PAD_RGMII_TX_DELAY(delay) |
--                      QCA8K_PORT_PAD_RGMII_TX_DELAY_EN;
--      }
--
--      if (priv->ports_config.rgmii_rx_delay[cpu_port_index]) {
--              delay = priv->ports_config.rgmii_rx_delay[cpu_port_index];
--
--              val |= QCA8K_PORT_PAD_RGMII_RX_DELAY(delay) |
--                      QCA8K_PORT_PAD_RGMII_RX_DELAY_EN;
--      }
--
--      /* Set RGMII delay based on the selected values */
--      ret = qca8k_rmw(priv, reg,
--                      QCA8K_PORT_PAD_RGMII_TX_DELAY_MASK |
--                      QCA8K_PORT_PAD_RGMII_RX_DELAY_MASK |
--                      QCA8K_PORT_PAD_RGMII_TX_DELAY_EN |
--                      QCA8K_PORT_PAD_RGMII_RX_DELAY_EN,
--                      val);
--      if (ret)
--              dev_err(priv->dev, "Failed to set internal delay for CPU port%d",
--                      cpu_port_index == QCA8K_CPU_PORT0 ? 0 : 6);
--}
--
--static void
--qca8k_phylink_mac_config(struct dsa_switch *ds, int port, unsigned int mode,
--                       const struct phylink_link_state *state)
--{
--      struct qca8k_priv *priv = ds->priv;
--      int cpu_port_index, ret;
--      u32 reg, val;
--
--      switch (port) {
--      case 0: /* 1st CPU port */
--              if (state->interface != PHY_INTERFACE_MODE_RGMII &&
--                  state->interface != PHY_INTERFACE_MODE_RGMII_ID &&
--                  state->interface != PHY_INTERFACE_MODE_RGMII_TXID &&
--                  state->interface != PHY_INTERFACE_MODE_RGMII_RXID &&
--                  state->interface != PHY_INTERFACE_MODE_SGMII)
--                      return;
--
--              reg = QCA8K_REG_PORT0_PAD_CTRL;
--              cpu_port_index = QCA8K_CPU_PORT0;
--              break;
--      case 1:
--      case 2:
--      case 3:
--      case 4:
--      case 5:
--              /* Internal PHY, nothing to do */
--              return;
--      case 6: /* 2nd CPU port / external PHY */
--              if (state->interface != PHY_INTERFACE_MODE_RGMII &&
--                  state->interface != PHY_INTERFACE_MODE_RGMII_ID &&
--                  state->interface != PHY_INTERFACE_MODE_RGMII_TXID &&
--                  state->interface != PHY_INTERFACE_MODE_RGMII_RXID &&
--                  state->interface != PHY_INTERFACE_MODE_SGMII &&
--                  state->interface != PHY_INTERFACE_MODE_1000BASEX)
--                      return;
--
--              reg = QCA8K_REG_PORT6_PAD_CTRL;
--              cpu_port_index = QCA8K_CPU_PORT6;
--              break;
--      default:
--              dev_err(ds->dev, "%s: unsupported port: %i\n", __func__, port);
--              return;
--      }
--
--      if (port != 6 && phylink_autoneg_inband(mode)) {
--              dev_err(ds->dev, "%s: in-band negotiation unsupported\n",
--                      __func__);
--              return;
--      }
--
--      switch (state->interface) {
--      case PHY_INTERFACE_MODE_RGMII:
--      case PHY_INTERFACE_MODE_RGMII_ID:
--      case PHY_INTERFACE_MODE_RGMII_TXID:
--      case PHY_INTERFACE_MODE_RGMII_RXID:
--              qca8k_write(priv, reg, QCA8K_PORT_PAD_RGMII_EN);
--
--              /* Configure rgmii delay */
--              qca8k_mac_config_setup_internal_delay(priv, cpu_port_index, reg);
--
--              /* QCA8337 requires to set rgmii rx delay for all ports.
--               * This is enabled through PORT5_PAD_CTRL for all ports,
--               * rather than individual port registers.
--               */
--              if (priv->switch_id == QCA8K_ID_QCA8337)
--                      qca8k_write(priv, QCA8K_REG_PORT5_PAD_CTRL,
--                                  QCA8K_PORT_PAD_RGMII_RX_DELAY_EN);
--              break;
--      case PHY_INTERFACE_MODE_SGMII:
--      case PHY_INTERFACE_MODE_1000BASEX:
--              /* Enable SGMII on the port */
--              qca8k_write(priv, reg, QCA8K_PORT_PAD_SGMII_EN);
--
--              /* Enable/disable SerDes auto-negotiation as necessary */
--              ret = qca8k_read(priv, QCA8K_REG_PWS, &val);
--              if (ret)
--                      return;
--              if (phylink_autoneg_inband(mode))
--                      val &= ~QCA8K_PWS_SERDES_AEN_DIS;
--              else
--                      val |= QCA8K_PWS_SERDES_AEN_DIS;
--              qca8k_write(priv, QCA8K_REG_PWS, val);
--
--              /* Configure the SGMII parameters */
--              ret = qca8k_read(priv, QCA8K_REG_SGMII_CTRL, &val);
--              if (ret)
--                      return;
--
--              val |= QCA8K_SGMII_EN_SD;
--
--              if (priv->ports_config.sgmii_enable_pll)
--                      val |= QCA8K_SGMII_EN_PLL | QCA8K_SGMII_EN_RX |
--                             QCA8K_SGMII_EN_TX;
--
--              if (dsa_is_cpu_port(ds, port)) {
--                      /* CPU port, we're talking to the CPU MAC, be a PHY */
--                      val &= ~QCA8K_SGMII_MODE_CTRL_MASK;
--                      val |= QCA8K_SGMII_MODE_CTRL_PHY;
--              } else if (state->interface == PHY_INTERFACE_MODE_SGMII) {
--                      val &= ~QCA8K_SGMII_MODE_CTRL_MASK;
--                      val |= QCA8K_SGMII_MODE_CTRL_MAC;
--              } else if (state->interface == PHY_INTERFACE_MODE_1000BASEX) {
--                      val &= ~QCA8K_SGMII_MODE_CTRL_MASK;
--                      val |= QCA8K_SGMII_MODE_CTRL_BASEX;
--              }
--
--              qca8k_write(priv, QCA8K_REG_SGMII_CTRL, val);
--
--              /* From original code is reported port instability as SGMII also
--               * require delay set. Apply advised values here or take them from DT.
--               */
--              if (state->interface == PHY_INTERFACE_MODE_SGMII)
--                      qca8k_mac_config_setup_internal_delay(priv, cpu_port_index, reg);
--
--              /* For qca8327/qca8328/qca8334/qca8338 sgmii is unique and
--               * falling edge is set writing in the PORT0 PAD reg
--               */
--              if (priv->switch_id == QCA8K_ID_QCA8327 ||
--                  priv->switch_id == QCA8K_ID_QCA8337)
--                      reg = QCA8K_REG_PORT0_PAD_CTRL;
--
--              val = 0;
--
--              /* SGMII Clock phase configuration */
--              if (priv->ports_config.sgmii_rx_clk_falling_edge)
--                      val |= QCA8K_PORT0_PAD_SGMII_RXCLK_FALLING_EDGE;
--
--              if (priv->ports_config.sgmii_tx_clk_falling_edge)
--                      val |= QCA8K_PORT0_PAD_SGMII_TXCLK_FALLING_EDGE;
--
--              if (val)
--                      ret = qca8k_rmw(priv, reg,
--                                      QCA8K_PORT0_PAD_SGMII_RXCLK_FALLING_EDGE |
--                                      QCA8K_PORT0_PAD_SGMII_TXCLK_FALLING_EDGE,
--                                      val);
--
--              break;
--      default:
--              dev_err(ds->dev, "xMII mode %s not supported for port %d\n",
--                      phy_modes(state->interface), port);
--              return;
--      }
--}
--
--static void
--qca8k_phylink_validate(struct dsa_switch *ds, int port,
--                     unsigned long *supported,
--                     struct phylink_link_state *state)
--{
--      __ETHTOOL_DECLARE_LINK_MODE_MASK(mask) = { 0, };
--
--      switch (port) {
--      case 0: /* 1st CPU port */
--              if (state->interface != PHY_INTERFACE_MODE_NA &&
--                  state->interface != PHY_INTERFACE_MODE_RGMII &&
--                  state->interface != PHY_INTERFACE_MODE_RGMII_ID &&
--                  state->interface != PHY_INTERFACE_MODE_RGMII_TXID &&
--                  state->interface != PHY_INTERFACE_MODE_RGMII_RXID &&
--                  state->interface != PHY_INTERFACE_MODE_SGMII)
--                      goto unsupported;
--              break;
--      case 1:
--      case 2:
--      case 3:
--      case 4:
--      case 5:
--              /* Internal PHY */
--              if (state->interface != PHY_INTERFACE_MODE_NA &&
--                  state->interface != PHY_INTERFACE_MODE_GMII &&
--                  state->interface != PHY_INTERFACE_MODE_INTERNAL)
--                      goto unsupported;
--              break;
--      case 6: /* 2nd CPU port / external PHY */
--              if (state->interface != PHY_INTERFACE_MODE_NA &&
--                  state->interface != PHY_INTERFACE_MODE_RGMII &&
--                  state->interface != PHY_INTERFACE_MODE_RGMII_ID &&
--                  state->interface != PHY_INTERFACE_MODE_RGMII_TXID &&
--                  state->interface != PHY_INTERFACE_MODE_RGMII_RXID &&
--                  state->interface != PHY_INTERFACE_MODE_SGMII &&
--                  state->interface != PHY_INTERFACE_MODE_1000BASEX)
--                      goto unsupported;
--              break;
--      default:
--unsupported:
--              linkmode_zero(supported);
--              return;
--      }
--
--      phylink_set_port_modes(mask);
--      phylink_set(mask, Autoneg);
--
--      phylink_set(mask, 1000baseT_Full);
--      phylink_set(mask, 10baseT_Half);
--      phylink_set(mask, 10baseT_Full);
--      phylink_set(mask, 100baseT_Half);
--      phylink_set(mask, 100baseT_Full);
--
--      if (state->interface == PHY_INTERFACE_MODE_1000BASEX)
--              phylink_set(mask, 1000baseX_Full);
--
--      phylink_set(mask, Pause);
--      phylink_set(mask, Asym_Pause);
--
--      linkmode_and(supported, supported, mask);
--      linkmode_and(state->advertising, state->advertising, mask);
--}
--
--static int
--qca8k_phylink_mac_link_state(struct dsa_switch *ds, int port,
--                           struct phylink_link_state *state)
--{
--      struct qca8k_priv *priv = ds->priv;
--      u32 reg;
--      int ret;
--
--      ret = qca8k_read(priv, QCA8K_REG_PORT_STATUS(port), &reg);
--      if (ret < 0)
--              return ret;
--
--      state->link = !!(reg & QCA8K_PORT_STATUS_LINK_UP);
--      state->an_complete = state->link;
--      state->an_enabled = !!(reg & QCA8K_PORT_STATUS_LINK_AUTO);
--      state->duplex = (reg & QCA8K_PORT_STATUS_DUPLEX) ? DUPLEX_FULL :
--                                                         DUPLEX_HALF;
--
--      switch (reg & QCA8K_PORT_STATUS_SPEED) {
--      case QCA8K_PORT_STATUS_SPEED_10:
--              state->speed = SPEED_10;
--              break;
--      case QCA8K_PORT_STATUS_SPEED_100:
--              state->speed = SPEED_100;
--              break;
--      case QCA8K_PORT_STATUS_SPEED_1000:
--              state->speed = SPEED_1000;
--              break;
--      default:
--              state->speed = SPEED_UNKNOWN;
--              break;
--      }
--
--      state->pause = MLO_PAUSE_NONE;
--      if (reg & QCA8K_PORT_STATUS_RXFLOW)
--              state->pause |= MLO_PAUSE_RX;
--      if (reg & QCA8K_PORT_STATUS_TXFLOW)
--              state->pause |= MLO_PAUSE_TX;
--
--      return 1;
--}
--
--static void
--qca8k_phylink_mac_link_down(struct dsa_switch *ds, int port, unsigned int mode,
--                          phy_interface_t interface)
--{
--      struct qca8k_priv *priv = ds->priv;
--
--      qca8k_port_set_status(priv, port, 0);
--}
--
--static void
--qca8k_phylink_mac_link_up(struct dsa_switch *ds, int port, unsigned int mode,
--                        phy_interface_t interface, struct phy_device *phydev,
--                        int speed, int duplex, bool tx_pause, bool rx_pause)
--{
--      struct qca8k_priv *priv = ds->priv;
--      u32 reg;
--
--      if (phylink_autoneg_inband(mode)) {
--              reg = QCA8K_PORT_STATUS_LINK_AUTO;
--      } else {
--              switch (speed) {
--              case SPEED_10:
--                      reg = QCA8K_PORT_STATUS_SPEED_10;
--                      break;
--              case SPEED_100:
--                      reg = QCA8K_PORT_STATUS_SPEED_100;
--                      break;
--              case SPEED_1000:
--                      reg = QCA8K_PORT_STATUS_SPEED_1000;
--                      break;
--              default:
--                      reg = QCA8K_PORT_STATUS_LINK_AUTO;
--                      break;
--              }
--
--              if (duplex == DUPLEX_FULL)
--                      reg |= QCA8K_PORT_STATUS_DUPLEX;
--
--              if (rx_pause || dsa_is_cpu_port(ds, port))
--                      reg |= QCA8K_PORT_STATUS_RXFLOW;
--
--              if (tx_pause || dsa_is_cpu_port(ds, port))
--                      reg |= QCA8K_PORT_STATUS_TXFLOW;
--      }
--
--      reg |= QCA8K_PORT_STATUS_TXMAC | QCA8K_PORT_STATUS_RXMAC;
--
--      qca8k_write(priv, QCA8K_REG_PORT_STATUS(port), reg);
--}
--
--static void
--qca8k_get_strings(struct dsa_switch *ds, int port, u32 stringset, uint8_t *data)
--{
--      struct qca8k_priv *priv = ds->priv;
--      int i;
--
--      if (stringset != ETH_SS_STATS)
--              return;
--
--      for (i = 0; i < priv->info->mib_count; i++)
--              strncpy(data + i * ETH_GSTRING_LEN, ar8327_mib[i].name,
--                      ETH_GSTRING_LEN);
--}
--
--static void qca8k_mib_autocast_handler(struct dsa_switch *ds, struct sk_buff *skb)
--{
--      struct qca8k_mib_eth_data *mib_eth_data;
--      struct qca8k_priv *priv = ds->priv;
--      const struct qca8k_mib_desc *mib;
--      struct mib_ethhdr *mib_ethhdr;
--      int i, mib_len, offset = 0;
--      u64 *data;
--      u8 port;
--
--      mib_ethhdr = (struct mib_ethhdr *)skb_mac_header(skb);
--      mib_eth_data = &priv->mib_eth_data;
--
--      /* The switch autocast every port. Ignore other packet and
--       * parse only the requested one.
--       */
--      port = FIELD_GET(QCA_HDR_RECV_SOURCE_PORT, ntohs(mib_ethhdr->hdr));
--      if (port != mib_eth_data->req_port)
--              goto exit;
--
--      data = mib_eth_data->data;
--
--      for (i = 0; i < priv->info->mib_count; i++) {
--              mib = &ar8327_mib[i];
--
--              /* First 3 mib are present in the skb head */
--              if (i < 3) {
--                      data[i] = mib_ethhdr->data[i];
--                      continue;
--              }
--
--              mib_len = sizeof(uint32_t);
--
--              /* Some mib are 64 bit wide */
--              if (mib->size == 2)
--                      mib_len = sizeof(uint64_t);
--
--              /* Copy the mib value from packet to the */
--              memcpy(data + i, skb->data + offset, mib_len);
--
--              /* Set the offset for the next mib */
--              offset += mib_len;
--      }
--
--exit:
--      /* Complete on receiving all the mib packet */
--      if (refcount_dec_and_test(&mib_eth_data->port_parsed))
--              complete(&mib_eth_data->rw_done);
--}
--
--static int
--qca8k_get_ethtool_stats_eth(struct dsa_switch *ds, int port, u64 *data)
--{
--      struct dsa_port *dp = dsa_to_port(ds, port);
--      struct qca8k_mib_eth_data *mib_eth_data;
--      struct qca8k_priv *priv = ds->priv;
--      int ret;
--
--      mib_eth_data = &priv->mib_eth_data;
--
--      mutex_lock(&mib_eth_data->mutex);
--
--      reinit_completion(&mib_eth_data->rw_done);
--
--      mib_eth_data->req_port = dp->index;
--      mib_eth_data->data = data;
--      refcount_set(&mib_eth_data->port_parsed, QCA8K_NUM_PORTS);
--
--      mutex_lock(&priv->reg_mutex);
--
--      /* Send mib autocast request */
--      ret = regmap_update_bits(priv->regmap, QCA8K_REG_MIB,
--                               QCA8K_MIB_FUNC | QCA8K_MIB_BUSY,
--                               FIELD_PREP(QCA8K_MIB_FUNC, QCA8K_MIB_CAST) |
--                               QCA8K_MIB_BUSY);
--
--      mutex_unlock(&priv->reg_mutex);
--
--      if (ret)
--              goto exit;
--
--      ret = wait_for_completion_timeout(&mib_eth_data->rw_done, QCA8K_ETHERNET_TIMEOUT);
--
--exit:
--      mutex_unlock(&mib_eth_data->mutex);
--
--      return ret;
--}
--
--static void
--qca8k_get_ethtool_stats(struct dsa_switch *ds, int port,
--                      uint64_t *data)
--{
--      struct qca8k_priv *priv = (struct qca8k_priv *)ds->priv;
--      const struct qca8k_mib_desc *mib;
--      u32 reg, i, val;
--      u32 hi = 0;
--      int ret;
--
--      if (priv->mgmt_master && priv->info->ops->autocast_mib &&
--          priv->info->ops->autocast_mib(ds, port, data) > 0)
--              return;
--
--      for (i = 0; i < priv->info->mib_count; i++) {
--              mib = &ar8327_mib[i];
--              reg = QCA8K_PORT_MIB_COUNTER(port) + mib->offset;
--
--              ret = qca8k_read(priv, reg, &val);
--              if (ret < 0)
--                      continue;
--
--              if (mib->size == 2) {
--                      ret = qca8k_read(priv, reg + 4, &hi);
--                      if (ret < 0)
--                              continue;
--              }
--
--              data[i] = val;
--              if (mib->size == 2)
--                      data[i] |= (u64)hi << 32;
--      }
--}
--
--static int
--qca8k_get_sset_count(struct dsa_switch *ds, int port, int sset)
--{
--      struct qca8k_priv *priv = ds->priv;
--
--      if (sset != ETH_SS_STATS)
--              return 0;
--
--      return priv->info->mib_count;
--}
--
--static int
--qca8k_set_mac_eee(struct dsa_switch *ds, int port, struct ethtool_eee *eee)
--{
--      struct qca8k_priv *priv = (struct qca8k_priv *)ds->priv;
--      u32 lpi_en = QCA8K_REG_EEE_CTRL_LPI_EN(port);
--      u32 reg;
--      int ret;
--
--      mutex_lock(&priv->reg_mutex);
--      ret = qca8k_read(priv, QCA8K_REG_EEE_CTRL, &reg);
--      if (ret < 0)
--              goto exit;
--
--      if (eee->eee_enabled)
--              reg |= lpi_en;
--      else
--              reg &= ~lpi_en;
--      ret = qca8k_write(priv, QCA8K_REG_EEE_CTRL, reg);
--
--exit:
--      mutex_unlock(&priv->reg_mutex);
--      return ret;
--}
--
--static int
--qca8k_get_mac_eee(struct dsa_switch *ds, int port, struct ethtool_eee *e)
--{
--      /* Nothing to do on the port's MAC */
--      return 0;
--}
--
--static void
--qca8k_port_stp_state_set(struct dsa_switch *ds, int port, u8 state)
--{
--      struct qca8k_priv *priv = (struct qca8k_priv *)ds->priv;
--      u32 stp_state;
--
--      switch (state) {
--      case BR_STATE_DISABLED:
--              stp_state = QCA8K_PORT_LOOKUP_STATE_DISABLED;
--              break;
--      case BR_STATE_BLOCKING:
--              stp_state = QCA8K_PORT_LOOKUP_STATE_BLOCKING;
--              break;
--      case BR_STATE_LISTENING:
--              stp_state = QCA8K_PORT_LOOKUP_STATE_LISTENING;
--              break;
--      case BR_STATE_LEARNING:
--              stp_state = QCA8K_PORT_LOOKUP_STATE_LEARNING;
--              break;
--      case BR_STATE_FORWARDING:
--      default:
--              stp_state = QCA8K_PORT_LOOKUP_STATE_FORWARD;
--              break;
--      }
--
--      qca8k_rmw(priv, QCA8K_PORT_LOOKUP_CTRL(port),
--                QCA8K_PORT_LOOKUP_STATE_MASK, stp_state);
--}
--
--static int
--qca8k_port_bridge_join(struct dsa_switch *ds, int port, struct net_device *br)
--{
--      struct qca8k_priv *priv = (struct qca8k_priv *)ds->priv;
--      int port_mask, cpu_port;
--      int i, ret;
--
--      cpu_port = dsa_to_port(ds, port)->cpu_dp->index;
--      port_mask = BIT(cpu_port);
--
--      for (i = 0; i < QCA8K_NUM_PORTS; i++) {
--              if (dsa_is_cpu_port(ds, i))
--                      continue;
--              if (dsa_to_port(ds, i)->bridge_dev != br)
--                      continue;
--              /* Add this port to the portvlan mask of the other ports
--               * in the bridge
--               */
--              ret = regmap_set_bits(priv->regmap,
--                                    QCA8K_PORT_LOOKUP_CTRL(i),
--                                    BIT(port));
--              if (ret)
--                      return ret;
--              if (i != port)
--                      port_mask |= BIT(i);
--      }
--
--      /* Add all other ports to this ports portvlan mask */
--      ret = qca8k_rmw(priv, QCA8K_PORT_LOOKUP_CTRL(port),
--                      QCA8K_PORT_LOOKUP_MEMBER, port_mask);
--
--      return ret;
--}
--
--static void
--qca8k_port_bridge_leave(struct dsa_switch *ds, int port, struct net_device *br)
--{
--      struct qca8k_priv *priv = (struct qca8k_priv *)ds->priv;
--      int cpu_port, i;
--
--      cpu_port = dsa_to_port(ds, port)->cpu_dp->index;
--
--      for (i = 0; i < QCA8K_NUM_PORTS; i++) {
--              if (dsa_is_cpu_port(ds, i))
--                      continue;
--              if (dsa_to_port(ds, i)->bridge_dev != br)
--                      continue;
--              /* Remove this port to the portvlan mask of the other ports
--               * in the bridge
--               */
--              regmap_clear_bits(priv->regmap,
--                                QCA8K_PORT_LOOKUP_CTRL(i),
--                                BIT(port));
--      }
--
--      /* Set the cpu port to be the only one in the portvlan mask of
--       * this port
--       */
--      qca8k_rmw(priv, QCA8K_PORT_LOOKUP_CTRL(port),
--                QCA8K_PORT_LOOKUP_MEMBER, BIT(cpu_port));
--}
--
--static void
--qca8k_port_fast_age(struct dsa_switch *ds, int port)
--{
--      struct qca8k_priv *priv = ds->priv;
--
--      mutex_lock(&priv->reg_mutex);
--      qca8k_fdb_access(priv, QCA8K_FDB_FLUSH_PORT, port);
--      mutex_unlock(&priv->reg_mutex);
--}
--
--static int
--qca8k_set_ageing_time(struct dsa_switch *ds, unsigned int msecs)
--{
--      struct qca8k_priv *priv = ds->priv;
--      unsigned int secs = msecs / 1000;
--      u32 val;
--
--      /* AGE_TIME reg is set in 7s step */
--      val = secs / 7;
--
--      /* Handle case with 0 as val to NOT disable
--       * learning
--       */
--      if (!val)
--              val = 1;
--
--      return regmap_update_bits(priv->regmap, QCA8K_REG_ATU_CTRL, QCA8K_ATU_AGE_TIME_MASK,
--                                QCA8K_ATU_AGE_TIME(val));
--}
--
--static int
--qca8k_port_enable(struct dsa_switch *ds, int port,
--                struct phy_device *phy)
--{
--      struct qca8k_priv *priv = (struct qca8k_priv *)ds->priv;
--
--      qca8k_port_set_status(priv, port, 1);
--      priv->port_enabled_map |= BIT(port);
--
--      if (dsa_is_user_port(ds, port))
--              phy_support_asym_pause(phy);
--
--      return 0;
--}
--
--static void
--qca8k_port_disable(struct dsa_switch *ds, int port)
--{
--      struct qca8k_priv *priv = (struct qca8k_priv *)ds->priv;
--
--      qca8k_port_set_status(priv, port, 0);
--      priv->port_enabled_map &= ~BIT(port);
--}
--
--static int
--qca8k_port_change_mtu(struct dsa_switch *ds, int port, int new_mtu)
--{
--      struct qca8k_priv *priv = ds->priv;
--      int ret;
--
--      /* We have only have a general MTU setting.
--       * DSA always set the CPU port's MTU to the largest MTU of the slave
--       * ports.
--       * Setting MTU just for the CPU port is sufficient to correctly set a
--       * value for every port.
--       */
--      if (!dsa_is_cpu_port(ds, port))
--              return 0;
--
--      /* To change the MAX_FRAME_SIZE the cpu ports must be off or
--       * the switch panics.
--       * Turn off both cpu ports before applying the new value to prevent
--       * this.
--       */
--      if (priv->port_enabled_map & BIT(0))
--              qca8k_port_set_status(priv, 0, 0);
--
--      if (priv->port_enabled_map & BIT(6))
--              qca8k_port_set_status(priv, 6, 0);
--
--      /* Include L2 header / FCS length */
--      ret = qca8k_write(priv, QCA8K_MAX_FRAME_SIZE, new_mtu + ETH_HLEN + ETH_FCS_LEN);
--
--      if (priv->port_enabled_map & BIT(0))
--              qca8k_port_set_status(priv, 0, 1);
--
--      if (priv->port_enabled_map & BIT(6))
--              qca8k_port_set_status(priv, 6, 1);
--
--      return ret;
--}
--
--static int
--qca8k_port_max_mtu(struct dsa_switch *ds, int port)
--{
--      return QCA8K_MAX_MTU;
--}
--
--static int
--qca8k_port_fdb_insert(struct qca8k_priv *priv, const u8 *addr,
--                    u16 port_mask, u16 vid)
--{
--      /* Set the vid to the port vlan id if no vid is set */
--      if (!vid)
--              vid = QCA8K_PORT_VID_DEF;
--
--      return qca8k_fdb_add(priv, addr, port_mask, vid,
--                           QCA8K_ATU_STATUS_STATIC);
--}
--
--static int
--qca8k_port_fdb_add(struct dsa_switch *ds, int port,
--                 const unsigned char *addr, u16 vid)
--{
--      struct qca8k_priv *priv = (struct qca8k_priv *)ds->priv;
--      u16 port_mask = BIT(port);
--
--      return qca8k_port_fdb_insert(priv, addr, port_mask, vid);
--}
--
--static int
--qca8k_port_fdb_del(struct dsa_switch *ds, int port,
--                 const unsigned char *addr, u16 vid)
--{
--      struct qca8k_priv *priv = (struct qca8k_priv *)ds->priv;
--      u16 port_mask = BIT(port);
--
--      if (!vid)
--              vid = QCA8K_PORT_VID_DEF;
--
--      return qca8k_fdb_del(priv, addr, port_mask, vid);
--}
--
--static int
--qca8k_port_fdb_dump(struct dsa_switch *ds, int port,
--                  dsa_fdb_dump_cb_t *cb, void *data)
--{
--      struct qca8k_priv *priv = (struct qca8k_priv *)ds->priv;
--      struct qca8k_fdb _fdb = { 0 };
--      int cnt = QCA8K_NUM_FDB_RECORDS;
--      bool is_static;
--      int ret = 0;
--
--      mutex_lock(&priv->reg_mutex);
--      while (cnt-- && !qca8k_fdb_next(priv, &_fdb, port)) {
--              if (!_fdb.aging)
--                      break;
--              is_static = (_fdb.aging == QCA8K_ATU_STATUS_STATIC);
--              ret = cb(_fdb.mac, _fdb.vid, is_static, data);
--              if (ret)
--                      break;
--      }
--      mutex_unlock(&priv->reg_mutex);
--
--      return 0;
--}
--
--static int
--qca8k_port_mdb_add(struct dsa_switch *ds, int port,
--                 const struct switchdev_obj_port_mdb *mdb)
--{
--      struct qca8k_priv *priv = ds->priv;
--      const u8 *addr = mdb->addr;
--      u16 vid = mdb->vid;
--
--      return qca8k_fdb_search_and_insert(priv, BIT(port), addr, vid);
--}
--
--static int
--qca8k_port_mdb_del(struct dsa_switch *ds, int port,
--                 const struct switchdev_obj_port_mdb *mdb)
--{
--      struct qca8k_priv *priv = ds->priv;
--      const u8 *addr = mdb->addr;
--      u16 vid = mdb->vid;
--
--      return qca8k_fdb_search_and_del(priv, BIT(port), addr, vid);
--}
--
--static int
--qca8k_port_mirror_add(struct dsa_switch *ds, int port,
--                    struct dsa_mall_mirror_tc_entry *mirror,
--                    bool ingress)
--{
--      struct qca8k_priv *priv = ds->priv;
--      int monitor_port, ret;
--      u32 reg, val;
--
--      /* Check for existent entry */
--      if ((ingress ? priv->mirror_rx : priv->mirror_tx) & BIT(port))
--              return -EEXIST;
--
--      ret = regmap_read(priv->regmap, QCA8K_REG_GLOBAL_FW_CTRL0, &val);
--      if (ret)
--              return ret;
--
--      /* QCA83xx can have only one port set to mirror mode.
--       * Check that the correct port is requested and return error otherwise.
--       * When no mirror port is set, the values is set to 0xF
--       */
--      monitor_port = FIELD_GET(QCA8K_GLOBAL_FW_CTRL0_MIRROR_PORT_NUM, val);
--      if (monitor_port != 0xF && monitor_port != mirror->to_local_port)
--              return -EEXIST;
--
--      /* Set the monitor port */
--      val = FIELD_PREP(QCA8K_GLOBAL_FW_CTRL0_MIRROR_PORT_NUM,
--                       mirror->to_local_port);
--      ret = regmap_update_bits(priv->regmap, QCA8K_REG_GLOBAL_FW_CTRL0,
--                               QCA8K_GLOBAL_FW_CTRL0_MIRROR_PORT_NUM, val);
--      if (ret)
--              return ret;
--
--      if (ingress) {
--              reg = QCA8K_PORT_LOOKUP_CTRL(port);
--              val = QCA8K_PORT_LOOKUP_ING_MIRROR_EN;
--      } else {
--              reg = QCA8K_REG_PORT_HOL_CTRL1(port);
--              val = QCA8K_PORT_HOL_CTRL1_EG_MIRROR_EN;
--      }
--
--      ret = regmap_update_bits(priv->regmap, reg, val, val);
--      if (ret)
--              return ret;
--
--      /* Track mirror port for tx and rx to decide when the
--       * mirror port has to be disabled.
--       */
--      if (ingress)
--              priv->mirror_rx |= BIT(port);
--      else
--              priv->mirror_tx |= BIT(port);
--
--      return 0;
--}
--
--static void
--qca8k_port_mirror_del(struct dsa_switch *ds, int port,
--                    struct dsa_mall_mirror_tc_entry *mirror)
--{
--      struct qca8k_priv *priv = ds->priv;
--      u32 reg, val;
--      int ret;
--
--      if (mirror->ingress) {
--              reg = QCA8K_PORT_LOOKUP_CTRL(port);
--              val = QCA8K_PORT_LOOKUP_ING_MIRROR_EN;
--      } else {
--              reg = QCA8K_REG_PORT_HOL_CTRL1(port);
--              val = QCA8K_PORT_HOL_CTRL1_EG_MIRROR_EN;
--      }
--
--      ret = regmap_clear_bits(priv->regmap, reg, val);
--      if (ret)
--              goto err;
--
--      if (mirror->ingress)
--              priv->mirror_rx &= ~BIT(port);
--      else
--              priv->mirror_tx &= ~BIT(port);
--
--      /* No port set to send packet to mirror port. Disable mirror port */
--      if (!priv->mirror_rx && !priv->mirror_tx) {
--              val = FIELD_PREP(QCA8K_GLOBAL_FW_CTRL0_MIRROR_PORT_NUM, 0xF);
--              ret = regmap_update_bits(priv->regmap, QCA8K_REG_GLOBAL_FW_CTRL0,
--                                       QCA8K_GLOBAL_FW_CTRL0_MIRROR_PORT_NUM, val);
--              if (ret)
--                      goto err;
--      }
--err:
--      dev_err(priv->dev, "Failed to del mirror port from %d", port);
--}
--
--static int
--qca8k_port_vlan_filtering(struct dsa_switch *ds, int port, bool vlan_filtering,
--                        struct netlink_ext_ack *extack)
--{
--      struct qca8k_priv *priv = ds->priv;
--      int ret;
--
--      if (vlan_filtering) {
--              ret = qca8k_rmw(priv, QCA8K_PORT_LOOKUP_CTRL(port),
--                              QCA8K_PORT_LOOKUP_VLAN_MODE_MASK,
--                              QCA8K_PORT_LOOKUP_VLAN_MODE_SECURE);
--      } else {
--              ret = qca8k_rmw(priv, QCA8K_PORT_LOOKUP_CTRL(port),
--                              QCA8K_PORT_LOOKUP_VLAN_MODE_MASK,
--                              QCA8K_PORT_LOOKUP_VLAN_MODE_NONE);
--      }
--
--      return ret;
--}
--
--static int
--qca8k_port_vlan_add(struct dsa_switch *ds, int port,
--                  const struct switchdev_obj_port_vlan *vlan,
--                  struct netlink_ext_ack *extack)
--{
--      bool untagged = vlan->flags & BRIDGE_VLAN_INFO_UNTAGGED;
--      bool pvid = vlan->flags & BRIDGE_VLAN_INFO_PVID;
--      struct qca8k_priv *priv = ds->priv;
--      int ret;
--
--      ret = qca8k_vlan_add(priv, port, vlan->vid, untagged);
--      if (ret) {
--              dev_err(priv->dev, "Failed to add VLAN to port %d (%d)", port, ret);
--              return ret;
--      }
--
--      if (pvid) {
--              ret = qca8k_rmw(priv, QCA8K_EGRESS_VLAN(port),
--                              QCA8K_EGREES_VLAN_PORT_MASK(port),
--                              QCA8K_EGREES_VLAN_PORT(port, vlan->vid));
--              if (ret)
--                      return ret;
--
--              ret = qca8k_write(priv, QCA8K_REG_PORT_VLAN_CTRL0(port),
--                                QCA8K_PORT_VLAN_CVID(vlan->vid) |
--                                QCA8K_PORT_VLAN_SVID(vlan->vid));
--      }
--
--      return ret;
--}
--
--static int
--qca8k_port_vlan_del(struct dsa_switch *ds, int port,
--                  const struct switchdev_obj_port_vlan *vlan)
--{
--      struct qca8k_priv *priv = ds->priv;
--      int ret;
--
--      ret = qca8k_vlan_del(priv, port, vlan->vid);
--      if (ret)
--              dev_err(priv->dev, "Failed to delete VLAN from port %d (%d)", port, ret);
--
--      return ret;
--}
--
--static u32 qca8k_get_phy_flags(struct dsa_switch *ds, int port)
--{
--      struct qca8k_priv *priv = ds->priv;
--
--      /* Communicate to the phy internal driver the switch revision.
--       * Based on the switch revision different values needs to be
--       * set to the dbg and mmd reg on the phy.
--       * The first 2 bit are used to communicate the switch revision
--       * to the phy driver.
--       */
--      if (port > 0 && port < 6)
--              return priv->switch_revision;
--
--      return 0;
--}
--
--static enum dsa_tag_protocol
--qca8k_get_tag_protocol(struct dsa_switch *ds, int port,
--                     enum dsa_tag_protocol mp)
--{
--      return DSA_TAG_PROTO_QCA;
--}
--
--static bool
--qca8k_lag_can_offload(struct dsa_switch *ds,
--                    struct net_device *lag,
--                    struct netdev_lag_upper_info *info)
--{
--      struct dsa_port *dp;
--      int id, members = 0;
--
--      id = dsa_lag_id(ds->dst, lag);
--      if (id < 0 || id >= ds->num_lag_ids)
--              return false;
--
--      dsa_lag_foreach_port(dp, ds->dst, lag)
--              /* Includes the port joining the LAG */
--              members++;
--
--      if (members > QCA8K_NUM_PORTS_FOR_LAG)
--              return false;
--
--      if (info->tx_type != NETDEV_LAG_TX_TYPE_HASH)
--              return false;
--
--      if (info->hash_type != NETDEV_LAG_HASH_L2 &&
--          info->hash_type != NETDEV_LAG_HASH_L23)
--              return false;
--
--      return true;
--}
--
--static int
--qca8k_lag_setup_hash(struct dsa_switch *ds,
--                   struct net_device *lag,
--                   struct netdev_lag_upper_info *info)
--{
--      struct qca8k_priv *priv = ds->priv;
--      bool unique_lag = true;
--      u32 hash = 0;
--      int i, id;
--
--      id = dsa_lag_id(ds->dst, lag);
--
--      switch (info->hash_type) {
--      case NETDEV_LAG_HASH_L23:
--              hash |= QCA8K_TRUNK_HASH_SIP_EN;
--              hash |= QCA8K_TRUNK_HASH_DIP_EN;
--              fallthrough;
--      case NETDEV_LAG_HASH_L2:
--              hash |= QCA8K_TRUNK_HASH_SA_EN;
--              hash |= QCA8K_TRUNK_HASH_DA_EN;
--              break;
--      default: /* We should NEVER reach this */
--              return -EOPNOTSUPP;
--      }
--
--      /* Check if we are the unique configured LAG */
--      dsa_lags_foreach_id(i, ds->dst)
--              if (i != id && dsa_lag_dev(ds->dst, i)) {
--                      unique_lag = false;
--                      break;
--              }
--
--      /* Hash Mode is global. Make sure the same Hash Mode
--       * is set to all the 4 possible lag.
--       * If we are the unique LAG we can set whatever hash
--       * mode we want.
--       * To change hash mode it's needed to remove all LAG
--       * and change the mode with the latest.
--       */
--      if (unique_lag) {
--              priv->lag_hash_mode = hash;
--      } else if (priv->lag_hash_mode != hash) {
--              netdev_err(lag, "Error: Mismateched Hash Mode across different lag is not supported\n");
--              return -EOPNOTSUPP;
--      }
--
--      return regmap_update_bits(priv->regmap, QCA8K_TRUNK_HASH_EN_CTRL,
--                                QCA8K_TRUNK_HASH_MASK, hash);
--}
--
--static int
--qca8k_lag_refresh_portmap(struct dsa_switch *ds, int port,
--                        struct net_device *lag, bool delete)
--{
--      struct qca8k_priv *priv = ds->priv;
--      int ret, id, i;
--      u32 val;
--
--      id = dsa_lag_id(ds->dst, lag);
--
--      /* Read current port member */
--      ret = regmap_read(priv->regmap, QCA8K_REG_GOL_TRUNK_CTRL0, &val);
--      if (ret)
--              return ret;
--
--      /* Shift val to the correct trunk */
--      val >>= QCA8K_REG_GOL_TRUNK_SHIFT(id);
--      val &= QCA8K_REG_GOL_TRUNK_MEMBER_MASK;
--      if (delete)
--              val &= ~BIT(port);
--      else
--              val |= BIT(port);
--
--      /* Update port member. With empty portmap disable trunk */
--      ret = regmap_update_bits(priv->regmap, QCA8K_REG_GOL_TRUNK_CTRL0,
--                               QCA8K_REG_GOL_TRUNK_MEMBER(id) |
--                               QCA8K_REG_GOL_TRUNK_EN(id),
--                               !val << QCA8K_REG_GOL_TRUNK_SHIFT(id) |
--                               val << QCA8K_REG_GOL_TRUNK_SHIFT(id));
--
--      /* Search empty member if adding or port on deleting */
--      for (i = 0; i < QCA8K_NUM_PORTS_FOR_LAG; i++) {
--              ret = regmap_read(priv->regmap, QCA8K_REG_GOL_TRUNK_CTRL(id), &val);
--              if (ret)
--                      return ret;
--
--              val >>= QCA8K_REG_GOL_TRUNK_ID_MEM_ID_SHIFT(id, i);
--              val &= QCA8K_REG_GOL_TRUNK_ID_MEM_ID_MASK;
--
--              if (delete) {
--                      /* If port flagged to be disabled assume this member is
--                       * empty
--                       */
--                      if (val != QCA8K_REG_GOL_TRUNK_ID_MEM_ID_EN_MASK)
--                              continue;
--
--                      val &= QCA8K_REG_GOL_TRUNK_ID_MEM_ID_PORT_MASK;
--                      if (val != port)
--                              continue;
--              } else {
--                      /* If port flagged to be enabled assume this member is
--                       * already set
--                       */
--                      if (val == QCA8K_REG_GOL_TRUNK_ID_MEM_ID_EN_MASK)
--                              continue;
--              }
--
--              /* We have found the member to add/remove */
--              break;
--      }
--
--      /* Set port in the correct port mask or disable port if in delete mode */
--      return regmap_update_bits(priv->regmap, QCA8K_REG_GOL_TRUNK_CTRL(id),
--                                QCA8K_REG_GOL_TRUNK_ID_MEM_ID_EN(id, i) |
--                                QCA8K_REG_GOL_TRUNK_ID_MEM_ID_PORT(id, i),
--                                !delete << QCA8K_REG_GOL_TRUNK_ID_MEM_ID_SHIFT(id, i) |
--                                port << QCA8K_REG_GOL_TRUNK_ID_MEM_ID_SHIFT(id, i));
--}
--
--static int
--qca8k_port_lag_join(struct dsa_switch *ds, int port,
--                  struct net_device *lag,
--                  struct netdev_lag_upper_info *info)
--{
--      int ret;
--
--      if (!qca8k_lag_can_offload(ds, lag, info))
--              return -EOPNOTSUPP;
--
--      ret = qca8k_lag_setup_hash(ds, lag, info);
--      if (ret)
--              return ret;
--
--      return qca8k_lag_refresh_portmap(ds, port, lag, false);
--}
--
--static int
--qca8k_port_lag_leave(struct dsa_switch *ds, int port,
--                   struct net_device *lag)
--{
--      return qca8k_lag_refresh_portmap(ds, port, lag, true);
--}
--
--static void
--qca8k_master_change(struct dsa_switch *ds, const struct net_device *master,
--                  bool operational)
--{
--      struct dsa_port *dp = master->dsa_ptr;
--      struct qca8k_priv *priv = ds->priv;
--
--      /* Ethernet MIB/MDIO is only supported for CPU port 0 */
--      if (dp->index != 0)
--              return;
--
--      mutex_lock(&priv->mgmt_eth_data.mutex);
--      mutex_lock(&priv->mib_eth_data.mutex);
--
--      priv->mgmt_master = operational ? (struct net_device *)master : NULL;
--
--      mutex_unlock(&priv->mib_eth_data.mutex);
--      mutex_unlock(&priv->mgmt_eth_data.mutex);
--}
--
--static int qca8k_connect_tag_protocol(struct dsa_switch *ds,
--                                    enum dsa_tag_protocol proto)
--{
--      struct qca_tagger_data *tagger_data;
--
--      switch (proto) {
--      case DSA_TAG_PROTO_QCA:
--              tagger_data = ds->tagger_data;
--
--              tagger_data->rw_reg_ack_handler = qca8k_rw_reg_ack_handler;
--              tagger_data->mib_autocast_handler = qca8k_mib_autocast_handler;
--
--              break;
--      default:
--              return -EOPNOTSUPP;
--      }
--
--      return 0;
--}
--
--static const struct dsa_switch_ops qca8k_switch_ops = {
--      .get_tag_protocol       = qca8k_get_tag_protocol,
--      .setup                  = qca8k_setup,
--      .get_strings            = qca8k_get_strings,
--      .get_ethtool_stats      = qca8k_get_ethtool_stats,
--      .get_sset_count         = qca8k_get_sset_count,
--      .set_ageing_time        = qca8k_set_ageing_time,
--      .get_mac_eee            = qca8k_get_mac_eee,
--      .set_mac_eee            = qca8k_set_mac_eee,
--      .port_enable            = qca8k_port_enable,
--      .port_disable           = qca8k_port_disable,
--      .port_change_mtu        = qca8k_port_change_mtu,
--      .port_max_mtu           = qca8k_port_max_mtu,
--      .port_stp_state_set     = qca8k_port_stp_state_set,
--      .port_bridge_join       = qca8k_port_bridge_join,
--      .port_bridge_leave      = qca8k_port_bridge_leave,
--      .port_fast_age          = qca8k_port_fast_age,
--      .port_fdb_add           = qca8k_port_fdb_add,
--      .port_fdb_del           = qca8k_port_fdb_del,
--      .port_fdb_dump          = qca8k_port_fdb_dump,
--      .port_mdb_add           = qca8k_port_mdb_add,
--      .port_mdb_del           = qca8k_port_mdb_del,
--      .port_mirror_add        = qca8k_port_mirror_add,
--      .port_mirror_del        = qca8k_port_mirror_del,
--      .port_vlan_filtering    = qca8k_port_vlan_filtering,
--      .port_vlan_add          = qca8k_port_vlan_add,
--      .port_vlan_del          = qca8k_port_vlan_del,
--      .phylink_validate       = qca8k_phylink_validate,
--      .phylink_mac_link_state = qca8k_phylink_mac_link_state,
--      .phylink_mac_config     = qca8k_phylink_mac_config,
--      .phylink_mac_link_down  = qca8k_phylink_mac_link_down,
--      .phylink_mac_link_up    = qca8k_phylink_mac_link_up,
--      .get_phy_flags          = qca8k_get_phy_flags,
--      .port_lag_join          = qca8k_port_lag_join,
--      .port_lag_leave         = qca8k_port_lag_leave,
--      .master_state_change    = qca8k_master_change,
--      .connect_tag_protocol   = qca8k_connect_tag_protocol,
--};
--
--static int qca8k_read_switch_id(struct qca8k_priv *priv)
--{
--      u32 val;
--      u8 id;
--      int ret;
--
--      if (!priv->info)
--              return -ENODEV;
--
--      ret = qca8k_read(priv, QCA8K_REG_MASK_CTRL, &val);
--      if (ret < 0)
--              return -ENODEV;
--
--      id = QCA8K_MASK_CTRL_DEVICE_ID(val);
--      if (id != priv->info->id) {
--              dev_err(priv->dev,
--                      "Switch id detected %x but expected %x",
--                      id, priv->info->id);
--              return -ENODEV;
--      }
--
--      priv->switch_id = id;
--
--      /* Save revision to communicate to the internal PHY driver */
--      priv->switch_revision = QCA8K_MASK_CTRL_REV_ID(val);
--
--      return 0;
--}
--
--static int
--qca8k_sw_probe(struct mdio_device *mdiodev)
--{
--      struct qca8k_priv *priv;
--      int ret;
--
--      /* allocate the private data struct so that we can probe the switches
--       * ID register
--       */
--      priv = devm_kzalloc(&mdiodev->dev, sizeof(*priv), GFP_KERNEL);
--      if (!priv)
--              return -ENOMEM;
--
--      priv->info = of_device_get_match_data(priv->dev);
--      priv->bus = mdiodev->bus;
--      priv->dev = &mdiodev->dev;
--
--      priv->reset_gpio = devm_gpiod_get_optional(priv->dev, "reset",
--                                                 GPIOD_ASIS);
--      if (IS_ERR(priv->reset_gpio))
--              return PTR_ERR(priv->reset_gpio);
--
--      if (priv->reset_gpio) {
--              gpiod_set_value_cansleep(priv->reset_gpio, 1);
--              /* The active low duration must be greater than 10 ms
--               * and checkpatch.pl wants 20 ms.
--               */
--              msleep(20);
--              gpiod_set_value_cansleep(priv->reset_gpio, 0);
--      }
--
--      /* Start by setting up the register mapping */
--      priv->regmap = devm_regmap_init(&mdiodev->dev, NULL, priv,
--                                      &qca8k_regmap_config);
--      if (IS_ERR(priv->regmap)) {
--              dev_err(priv->dev, "regmap initialization failed");
--              return PTR_ERR(priv->regmap);
--      }
--
--      priv->mdio_cache.page = 0xffff;
--      priv->mdio_cache.lo = 0xffff;
--      priv->mdio_cache.hi = 0xffff;
--
--      /* Check the detected switch id */
--      ret = qca8k_read_switch_id(priv);
--      if (ret)
--              return ret;
--
--      priv->ds = devm_kzalloc(&mdiodev->dev, sizeof(*priv->ds), GFP_KERNEL);
--      if (!priv->ds)
--              return -ENOMEM;
--
--      mutex_init(&priv->mgmt_eth_data.mutex);
--      init_completion(&priv->mgmt_eth_data.rw_done);
--
--      mutex_init(&priv->mib_eth_data.mutex);
--      init_completion(&priv->mib_eth_data.rw_done);
--
--      priv->ds->dev = &mdiodev->dev;
--      priv->ds->num_ports = QCA8K_NUM_PORTS;
--      priv->ds->priv = priv;
--      priv->ds->ops = &qca8k_switch_ops;
--      mutex_init(&priv->reg_mutex);
--      dev_set_drvdata(&mdiodev->dev, priv);
--
--      return dsa_register_switch(priv->ds);
--}
--
--static void
--qca8k_sw_remove(struct mdio_device *mdiodev)
--{
--      struct qca8k_priv *priv = dev_get_drvdata(&mdiodev->dev);
--      int i;
--
--      if (!priv)
--              return;
--
--      for (i = 0; i < QCA8K_NUM_PORTS; i++)
--              qca8k_port_set_status(priv, i, 0);
--
--      dsa_unregister_switch(priv->ds);
--
--      dev_set_drvdata(&mdiodev->dev, NULL);
--}
--
--static void qca8k_sw_shutdown(struct mdio_device *mdiodev)
--{
--      struct qca8k_priv *priv = dev_get_drvdata(&mdiodev->dev);
--
--      if (!priv)
--              return;
--
--      dsa_switch_shutdown(priv->ds);
--
--      dev_set_drvdata(&mdiodev->dev, NULL);
--}
--
--#ifdef CONFIG_PM_SLEEP
--static void
--qca8k_set_pm(struct qca8k_priv *priv, int enable)
--{
--      int port;
--
--      for (port = 0; port < QCA8K_NUM_PORTS; port++) {
--              /* Do not enable on resume if the port was
--               * disabled before.
--               */
--              if (!(priv->port_enabled_map & BIT(port)))
--                      continue;
--
--              qca8k_port_set_status(priv, port, enable);
--      }
--}
--
--static int qca8k_suspend(struct device *dev)
--{
--      struct qca8k_priv *priv = dev_get_drvdata(dev);
--
--      qca8k_set_pm(priv, 0);
--
--      return dsa_switch_suspend(priv->ds);
--}
--
--static int qca8k_resume(struct device *dev)
--{
--      struct qca8k_priv *priv = dev_get_drvdata(dev);
--
--      qca8k_set_pm(priv, 1);
--
--      return dsa_switch_resume(priv->ds);
--}
--#endif /* CONFIG_PM_SLEEP */
--
--static SIMPLE_DEV_PM_OPS(qca8k_pm_ops,
--                       qca8k_suspend, qca8k_resume);
--
--static const struct qca8k_info_ops qca8xxx_ops = {
--      .autocast_mib = qca8k_get_ethtool_stats_eth,
--};
--
--static const struct qca8k_match_data qca8327 = {
--      .id = QCA8K_ID_QCA8327,
--      .reduced_package = true,
--      .mib_count = QCA8K_QCA832X_MIB_COUNT,
--      .ops = &qca8xxx_ops,
--};
--
--static const struct qca8k_match_data qca8328 = {
--      .id = QCA8K_ID_QCA8327,
--      .mib_count = QCA8K_QCA832X_MIB_COUNT,
--      .ops = &qca8xxx_ops,
--};
--
--static const struct qca8k_match_data qca833x = {
--      .id = QCA8K_ID_QCA8337,
--      .mib_count = QCA8K_QCA833X_MIB_COUNT,
--      .ops = &qca8xxx_ops,
--};
--
--static const struct of_device_id qca8k_of_match[] = {
--      { .compatible = "qca,qca8327", .data = &qca8327 },
--      { .compatible = "qca,qca8328", .data = &qca8328 },
--      { .compatible = "qca,qca8334", .data = &qca833x },
--      { .compatible = "qca,qca8337", .data = &qca833x },
--      { /* sentinel */ },
--};
--
--static struct mdio_driver qca8kmdio_driver = {
--      .probe  = qca8k_sw_probe,
--      .remove = qca8k_sw_remove,
--      .shutdown = qca8k_sw_shutdown,
--      .mdiodrv.driver = {
--              .name = "qca8k",
--              .of_match_table = qca8k_of_match,
--              .pm = &qca8k_pm_ops,
--      },
--};
--
--mdio_module_driver(qca8kmdio_driver);
--
--MODULE_AUTHOR("Mathieu Olivari, John Crispin <[email protected]>");
--MODULE_DESCRIPTION("Driver for QCA8K ethernet switch family");
--MODULE_LICENSE("GPL v2");
--MODULE_ALIAS("platform:qca8k");
---- /dev/null
-+++ b/drivers/net/dsa/qca/qca8k-8xxx.c
-@@ -0,0 +1,3186 @@
-+// SPDX-License-Identifier: GPL-2.0
-+/*
-+ * Copyright (C) 2009 Felix Fietkau <[email protected]>
-+ * Copyright (C) 2011-2012 Gabor Juhos <[email protected]>
-+ * Copyright (c) 2015, 2019, The Linux Foundation. All rights reserved.
-+ * Copyright (c) 2016 John Crispin <[email protected]>
-+ */
-+
-+#include <linux/module.h>
-+#include <linux/phy.h>
-+#include <linux/netdevice.h>
-+#include <linux/bitfield.h>
-+#include <linux/regmap.h>
-+#include <net/dsa.h>
-+#include <linux/of_net.h>
-+#include <linux/of_mdio.h>
-+#include <linux/of_platform.h>
-+#include <linux/if_bridge.h>
-+#include <linux/mdio.h>
-+#include <linux/phylink.h>
-+#include <linux/gpio/consumer.h>
-+#include <linux/etherdevice.h>
-+#include <linux/dsa/tag_qca.h>
-+
-+#include "qca8k.h"
-+
-+static void
-+qca8k_split_addr(u32 regaddr, u16 *r1, u16 *r2, u16 *page)
-+{
-+      regaddr >>= 1;
-+      *r1 = regaddr & 0x1e;
-+
-+      regaddr >>= 5;
-+      *r2 = regaddr & 0x7;
-+
-+      regaddr >>= 3;
-+      *page = regaddr & 0x3ff;
-+}
-+
-+static int
-+qca8k_set_lo(struct qca8k_priv *priv, int phy_id, u32 regnum, u16 lo)
-+{
-+      u16 *cached_lo = &priv->mdio_cache.lo;
-+      struct mii_bus *bus = priv->bus;
-+      int ret;
-+
-+      if (lo == *cached_lo)
-+              return 0;
-+
-+      ret = bus->write(bus, phy_id, regnum, lo);
-+      if (ret < 0)
-+              dev_err_ratelimited(&bus->dev,
-+                                  "failed to write qca8k 32bit lo register\n");
-+
-+      *cached_lo = lo;
-+      return 0;
-+}
-+
-+static int
-+qca8k_set_hi(struct qca8k_priv *priv, int phy_id, u32 regnum, u16 hi)
-+{
-+      u16 *cached_hi = &priv->mdio_cache.hi;
-+      struct mii_bus *bus = priv->bus;
-+      int ret;
-+
-+      if (hi == *cached_hi)
-+              return 0;
-+
-+      ret = bus->write(bus, phy_id, regnum, hi);
-+      if (ret < 0)
-+              dev_err_ratelimited(&bus->dev,
-+                                  "failed to write qca8k 32bit hi register\n");
-+
-+      *cached_hi = hi;
-+      return 0;
-+}
-+
-+static int
-+qca8k_mii_read32(struct mii_bus *bus, int phy_id, u32 regnum, u32 *val)
-+{
-+      int ret;
-+
-+      ret = bus->read(bus, phy_id, regnum);
-+      if (ret >= 0) {
-+              *val = ret;
-+              ret = bus->read(bus, phy_id, regnum + 1);
-+              *val |= ret << 16;
-+      }
-+
-+      if (ret < 0) {
-+              dev_err_ratelimited(&bus->dev,
-+                                  "failed to read qca8k 32bit register\n");
-+              *val = 0;
-+              return ret;
-+      }
-+
-+      return 0;
-+}
-+
-+static void
-+qca8k_mii_write32(struct qca8k_priv *priv, int phy_id, u32 regnum, u32 val)
-+{
-+      u16 lo, hi;
-+      int ret;
-+
-+      lo = val & 0xffff;
-+      hi = (u16)(val >> 16);
-+
-+      ret = qca8k_set_lo(priv, phy_id, regnum, lo);
-+      if (ret >= 0)
-+              ret = qca8k_set_hi(priv, phy_id, regnum + 1, hi);
-+}
-+
-+static int
-+qca8k_set_page(struct qca8k_priv *priv, u16 page)
-+{
-+      u16 *cached_page = &priv->mdio_cache.page;
-+      struct mii_bus *bus = priv->bus;
-+      int ret;
-+
-+      if (page == *cached_page)
-+              return 0;
-+
-+      ret = bus->write(bus, 0x18, 0, page);
-+      if (ret < 0) {
-+              dev_err_ratelimited(&bus->dev,
-+                                  "failed to set qca8k page\n");
-+              return ret;
-+      }
-+
-+      *cached_page = page;
-+      usleep_range(1000, 2000);
-+      return 0;
-+}
-+
-+static int
-+qca8k_read(struct qca8k_priv *priv, u32 reg, u32 *val)
-+{
-+      return regmap_read(priv->regmap, reg, val);
-+}
-+
-+static int
-+qca8k_write(struct qca8k_priv *priv, u32 reg, u32 val)
-+{
-+      return regmap_write(priv->regmap, reg, val);
-+}
-+
-+static int
-+qca8k_rmw(struct qca8k_priv *priv, u32 reg, u32 mask, u32 write_val)
-+{
-+      return regmap_update_bits(priv->regmap, reg, mask, write_val);
-+}
-+
-+static void qca8k_rw_reg_ack_handler(struct dsa_switch *ds, struct sk_buff *skb)
-+{
-+      struct qca8k_mgmt_eth_data *mgmt_eth_data;
-+      struct qca8k_priv *priv = ds->priv;
-+      struct qca_mgmt_ethhdr *mgmt_ethhdr;
-+      u8 len, cmd;
-+
-+      mgmt_ethhdr = (struct qca_mgmt_ethhdr *)skb_mac_header(skb);
-+      mgmt_eth_data = &priv->mgmt_eth_data;
-+
-+      cmd = FIELD_GET(QCA_HDR_MGMT_CMD, mgmt_ethhdr->command);
-+      len = FIELD_GET(QCA_HDR_MGMT_LENGTH, mgmt_ethhdr->command);
-+
-+      /* Make sure the seq match the requested packet */
-+      if (mgmt_ethhdr->seq == mgmt_eth_data->seq)
-+              mgmt_eth_data->ack = true;
-+
-+      if (cmd == MDIO_READ) {
-+              mgmt_eth_data->data[0] = mgmt_ethhdr->mdio_data;
-+
-+              /* Get the rest of the 12 byte of data.
-+               * The read/write function will extract the requested data.
-+               */
-+              if (len > QCA_HDR_MGMT_DATA1_LEN)
-+                      memcpy(mgmt_eth_data->data + 1, skb->data,
-+                             QCA_HDR_MGMT_DATA2_LEN);
-+      }
-+
-+      complete(&mgmt_eth_data->rw_done);
-+}
-+
-+static struct sk_buff *qca8k_alloc_mdio_header(enum mdio_cmd cmd, u32 reg, u32 *val,
-+                                             int priority, unsigned int len)
-+{
-+      struct qca_mgmt_ethhdr *mgmt_ethhdr;
-+      unsigned int real_len;
-+      struct sk_buff *skb;
-+      u32 *data2;
-+      u16 hdr;
-+
-+      skb = dev_alloc_skb(QCA_HDR_MGMT_PKT_LEN);
-+      if (!skb)
-+              return NULL;
-+
-+      /* Max value for len reg is 15 (0xf) but the switch actually return 16 byte
-+       * Actually for some reason the steps are:
-+       * 0: nothing
-+       * 1-4: first 4 byte
-+       * 5-6: first 12 byte
-+       * 7-15: all 16 byte
-+       */
-+      if (len == 16)
-+              real_len = 15;
-+      else
-+              real_len = len;
-+
-+      skb_reset_mac_header(skb);
-+      skb_set_network_header(skb, skb->len);
-+
-+      mgmt_ethhdr = skb_push(skb, QCA_HDR_MGMT_HEADER_LEN + QCA_HDR_LEN);
-+
-+      hdr = FIELD_PREP(QCA_HDR_XMIT_VERSION, QCA_HDR_VERSION);
-+      hdr |= FIELD_PREP(QCA_HDR_XMIT_PRIORITY, priority);
-+      hdr |= QCA_HDR_XMIT_FROM_CPU;
-+      hdr |= FIELD_PREP(QCA_HDR_XMIT_DP_BIT, BIT(0));
-+      hdr |= FIELD_PREP(QCA_HDR_XMIT_CONTROL, QCA_HDR_XMIT_TYPE_RW_REG);
-+
-+      mgmt_ethhdr->command = FIELD_PREP(QCA_HDR_MGMT_ADDR, reg);
-+      mgmt_ethhdr->command |= FIELD_PREP(QCA_HDR_MGMT_LENGTH, real_len);
-+      mgmt_ethhdr->command |= FIELD_PREP(QCA_HDR_MGMT_CMD, cmd);
-+      mgmt_ethhdr->command |= FIELD_PREP(QCA_HDR_MGMT_CHECK_CODE,
-+                                         QCA_HDR_MGMT_CHECK_CODE_VAL);
-+
-+      if (cmd == MDIO_WRITE)
-+              mgmt_ethhdr->mdio_data = *val;
-+
-+      mgmt_ethhdr->hdr = htons(hdr);
-+
-+      data2 = skb_put_zero(skb, QCA_HDR_MGMT_DATA2_LEN + QCA_HDR_MGMT_PADDING_LEN);
-+      if (cmd == MDIO_WRITE && len > QCA_HDR_MGMT_DATA1_LEN)
-+              memcpy(data2, val + 1, len - QCA_HDR_MGMT_DATA1_LEN);
-+
-+      return skb;
-+}
-+
-+static void qca8k_mdio_header_fill_seq_num(struct sk_buff *skb, u32 seq_num)
-+{
-+      struct qca_mgmt_ethhdr *mgmt_ethhdr;
-+
-+      mgmt_ethhdr = (struct qca_mgmt_ethhdr *)skb->data;
-+      mgmt_ethhdr->seq = FIELD_PREP(QCA_HDR_MGMT_SEQ_NUM, seq_num);
-+}
-+
-+static int qca8k_read_eth(struct qca8k_priv *priv, u32 reg, u32 *val, int len)
-+{
-+      struct qca8k_mgmt_eth_data *mgmt_eth_data = &priv->mgmt_eth_data;
-+      struct sk_buff *skb;
-+      bool ack;
-+      int ret;
-+
-+      skb = qca8k_alloc_mdio_header(MDIO_READ, reg, NULL,
-+                                    QCA8K_ETHERNET_MDIO_PRIORITY, len);
-+      if (!skb)
-+              return -ENOMEM;
-+
-+      mutex_lock(&mgmt_eth_data->mutex);
-+
-+      /* Check mgmt_master if is operational */
-+      if (!priv->mgmt_master) {
-+              kfree_skb(skb);
-+              mutex_unlock(&mgmt_eth_data->mutex);
-+              return -EINVAL;
-+      }
-+
-+      skb->dev = priv->mgmt_master;
-+
-+      reinit_completion(&mgmt_eth_data->rw_done);
-+
-+      /* Increment seq_num and set it in the mdio pkt */
-+      mgmt_eth_data->seq++;
-+      qca8k_mdio_header_fill_seq_num(skb, mgmt_eth_data->seq);
-+      mgmt_eth_data->ack = false;
-+
-+      dev_queue_xmit(skb);
-+
-+      ret = wait_for_completion_timeout(&mgmt_eth_data->rw_done,
-+                                        msecs_to_jiffies(QCA8K_ETHERNET_TIMEOUT));
-+
-+      *val = mgmt_eth_data->data[0];
-+      if (len > QCA_HDR_MGMT_DATA1_LEN)
-+              memcpy(val + 1, mgmt_eth_data->data + 1, len - QCA_HDR_MGMT_DATA1_LEN);
-+
-+      ack = mgmt_eth_data->ack;
-+
-+      mutex_unlock(&mgmt_eth_data->mutex);
-+
-+      if (ret <= 0)
-+              return -ETIMEDOUT;
-+
-+      if (!ack)
-+              return -EINVAL;
-+
-+      return 0;
-+}
-+
-+static int qca8k_write_eth(struct qca8k_priv *priv, u32 reg, u32 *val, int len)
-+{
-+      struct qca8k_mgmt_eth_data *mgmt_eth_data = &priv->mgmt_eth_data;
-+      struct sk_buff *skb;
-+      bool ack;
-+      int ret;
-+
-+      skb = qca8k_alloc_mdio_header(MDIO_WRITE, reg, val,
-+                                    QCA8K_ETHERNET_MDIO_PRIORITY, len);
-+      if (!skb)
-+              return -ENOMEM;
-+
-+      mutex_lock(&mgmt_eth_data->mutex);
-+
-+      /* Check mgmt_master if is operational */
-+      if (!priv->mgmt_master) {
-+              kfree_skb(skb);
-+              mutex_unlock(&mgmt_eth_data->mutex);
-+              return -EINVAL;
-+      }
-+
-+      skb->dev = priv->mgmt_master;
-+
-+      reinit_completion(&mgmt_eth_data->rw_done);
-+
-+      /* Increment seq_num and set it in the mdio pkt */
-+      mgmt_eth_data->seq++;
-+      qca8k_mdio_header_fill_seq_num(skb, mgmt_eth_data->seq);
-+      mgmt_eth_data->ack = false;
-+
-+      dev_queue_xmit(skb);
-+
-+      ret = wait_for_completion_timeout(&mgmt_eth_data->rw_done,
-+                                        msecs_to_jiffies(QCA8K_ETHERNET_TIMEOUT));
-+
-+      ack = mgmt_eth_data->ack;
-+
-+      mutex_unlock(&mgmt_eth_data->mutex);
-+
-+      if (ret <= 0)
-+              return -ETIMEDOUT;
-+
-+      if (!ack)
-+              return -EINVAL;
-+
-+      return 0;
-+}
-+
-+static int
-+qca8k_regmap_update_bits_eth(struct qca8k_priv *priv, u32 reg, u32 mask, u32 write_val)
-+{
-+      u32 val = 0;
-+      int ret;
-+
-+      ret = qca8k_read_eth(priv, reg, &val, sizeof(val));
-+      if (ret)
-+              return ret;
-+
-+      val &= ~mask;
-+      val |= write_val;
-+
-+      return qca8k_write_eth(priv, reg, &val, sizeof(val));
-+}
-+
-+static int
-+qca8k_bulk_read(struct qca8k_priv *priv, u32 reg, u32 *val, int len)
-+{
-+      int i, count = len / sizeof(u32), ret;
-+
-+      if (priv->mgmt_master && !qca8k_read_eth(priv, reg, val, len))
-+              return 0;
-+
-+      for (i = 0; i < count; i++) {
-+              ret = regmap_read(priv->regmap, reg + (i * 4), val + i);
-+              if (ret < 0)
-+                      return ret;
-+      }
-+
-+      return 0;
-+}
-+
-+static int
-+qca8k_bulk_write(struct qca8k_priv *priv, u32 reg, u32 *val, int len)
-+{
-+      int i, count = len / sizeof(u32), ret;
-+      u32 tmp;
-+
-+      if (priv->mgmt_master && !qca8k_write_eth(priv, reg, val, len))
-+              return 0;
-+
-+      for (i = 0; i < count; i++) {
-+              tmp = val[i];
-+
-+              ret = regmap_write(priv->regmap, reg + (i * 4), tmp);
-+              if (ret < 0)
-+                      return ret;
-+      }
-+
-+      return 0;
-+}
-+
-+static int
-+qca8k_regmap_read(void *ctx, uint32_t reg, uint32_t *val)
-+{
-+      struct qca8k_priv *priv = (struct qca8k_priv *)ctx;
-+      struct mii_bus *bus = priv->bus;
-+      u16 r1, r2, page;
-+      int ret;
-+
-+      if (!qca8k_read_eth(priv, reg, val, sizeof(*val)))
-+              return 0;
-+
-+      qca8k_split_addr(reg, &r1, &r2, &page);
-+
-+      mutex_lock_nested(&bus->mdio_lock, MDIO_MUTEX_NESTED);
-+
-+      ret = qca8k_set_page(priv, page);
-+      if (ret < 0)
-+              goto exit;
-+
-+      ret = qca8k_mii_read32(bus, 0x10 | r2, r1, val);
-+
-+exit:
-+      mutex_unlock(&bus->mdio_lock);
-+      return ret;
-+}
-+
-+static int
-+qca8k_regmap_write(void *ctx, uint32_t reg, uint32_t val)
-+{
-+      struct qca8k_priv *priv = (struct qca8k_priv *)ctx;
-+      struct mii_bus *bus = priv->bus;
-+      u16 r1, r2, page;
-+      int ret;
-+
-+      if (!qca8k_write_eth(priv, reg, &val, sizeof(val)))
-+              return 0;
-+
-+      qca8k_split_addr(reg, &r1, &r2, &page);
-+
-+      mutex_lock_nested(&bus->mdio_lock, MDIO_MUTEX_NESTED);
-+
-+      ret = qca8k_set_page(priv, page);
-+      if (ret < 0)
-+              goto exit;
-+
-+      qca8k_mii_write32(priv, 0x10 | r2, r1, val);
-+
-+exit:
-+      mutex_unlock(&bus->mdio_lock);
-+      return ret;
-+}
-+
-+static int
-+qca8k_regmap_update_bits(void *ctx, uint32_t reg, uint32_t mask, uint32_t write_val)
-+{
-+      struct qca8k_priv *priv = (struct qca8k_priv *)ctx;
-+      struct mii_bus *bus = priv->bus;
-+      u16 r1, r2, page;
-+      u32 val;
-+      int ret;
-+
-+      if (!qca8k_regmap_update_bits_eth(priv, reg, mask, write_val))
-+              return 0;
-+
-+      qca8k_split_addr(reg, &r1, &r2, &page);
-+
-+      mutex_lock_nested(&bus->mdio_lock, MDIO_MUTEX_NESTED);
-+
-+      ret = qca8k_set_page(priv, page);
-+      if (ret < 0)
-+              goto exit;
-+
-+      ret = qca8k_mii_read32(bus, 0x10 | r2, r1, &val);
-+      if (ret < 0)
-+              goto exit;
-+
-+      val &= ~mask;
-+      val |= write_val;
-+      qca8k_mii_write32(priv, 0x10 | r2, r1, val);
-+
-+exit:
-+      mutex_unlock(&bus->mdio_lock);
-+
-+      return ret;
-+}
-+
-+static const struct regmap_range qca8k_readable_ranges[] = {
-+      regmap_reg_range(0x0000, 0x00e4), /* Global control */
-+      regmap_reg_range(0x0100, 0x0168), /* EEE control */
-+      regmap_reg_range(0x0200, 0x0270), /* Parser control */
-+      regmap_reg_range(0x0400, 0x0454), /* ACL */
-+      regmap_reg_range(0x0600, 0x0718), /* Lookup */
-+      regmap_reg_range(0x0800, 0x0b70), /* QM */
-+      regmap_reg_range(0x0c00, 0x0c80), /* PKT */
-+      regmap_reg_range(0x0e00, 0x0e98), /* L3 */
-+      regmap_reg_range(0x1000, 0x10ac), /* MIB - Port0 */
-+      regmap_reg_range(0x1100, 0x11ac), /* MIB - Port1 */
-+      regmap_reg_range(0x1200, 0x12ac), /* MIB - Port2 */
-+      regmap_reg_range(0x1300, 0x13ac), /* MIB - Port3 */
-+      regmap_reg_range(0x1400, 0x14ac), /* MIB - Port4 */
-+      regmap_reg_range(0x1500, 0x15ac), /* MIB - Port5 */
-+      regmap_reg_range(0x1600, 0x16ac), /* MIB - Port6 */
-+
-+};
-+
-+static const struct regmap_access_table qca8k_readable_table = {
-+      .yes_ranges = qca8k_readable_ranges,
-+      .n_yes_ranges = ARRAY_SIZE(qca8k_readable_ranges),
-+};
-+
-+static struct regmap_config qca8k_regmap_config = {
-+      .reg_bits = 16,
-+      .val_bits = 32,
-+      .reg_stride = 4,
-+      .max_register = 0x16ac, /* end MIB - Port6 range */
-+      .reg_read = qca8k_regmap_read,
-+      .reg_write = qca8k_regmap_write,
-+      .reg_update_bits = qca8k_regmap_update_bits,
-+      .rd_table = &qca8k_readable_table,
-+      .disable_locking = true, /* Locking is handled by qca8k read/write */
-+      .cache_type = REGCACHE_NONE, /* Explicitly disable CACHE */
-+};
-+
-+static int
-+qca8k_busy_wait(struct qca8k_priv *priv, u32 reg, u32 mask)
-+{
-+      u32 val;
-+
-+      return regmap_read_poll_timeout(priv->regmap, reg, val, !(val & mask), 0,
-+                                     QCA8K_BUSY_WAIT_TIMEOUT * USEC_PER_MSEC);
-+}
-+
-+static int
-+qca8k_fdb_read(struct qca8k_priv *priv, struct qca8k_fdb *fdb)
-+{
-+      u32 reg[3];
-+      int ret;
-+
-+      /* load the ARL table into an array */
-+      ret = qca8k_bulk_read(priv, QCA8K_REG_ATU_DATA0, reg, sizeof(reg));
-+      if (ret)
-+              return ret;
-+
-+      /* vid - 83:72 */
-+      fdb->vid = FIELD_GET(QCA8K_ATU_VID_MASK, reg[2]);
-+      /* aging - 67:64 */
-+      fdb->aging = FIELD_GET(QCA8K_ATU_STATUS_MASK, reg[2]);
-+      /* portmask - 54:48 */
-+      fdb->port_mask = FIELD_GET(QCA8K_ATU_PORT_MASK, reg[1]);
-+      /* mac - 47:0 */
-+      fdb->mac[0] = FIELD_GET(QCA8K_ATU_ADDR0_MASK, reg[1]);
-+      fdb->mac[1] = FIELD_GET(QCA8K_ATU_ADDR1_MASK, reg[1]);
-+      fdb->mac[2] = FIELD_GET(QCA8K_ATU_ADDR2_MASK, reg[0]);
-+      fdb->mac[3] = FIELD_GET(QCA8K_ATU_ADDR3_MASK, reg[0]);
-+      fdb->mac[4] = FIELD_GET(QCA8K_ATU_ADDR4_MASK, reg[0]);
-+      fdb->mac[5] = FIELD_GET(QCA8K_ATU_ADDR5_MASK, reg[0]);
-+
-+      return 0;
-+}
-+
-+static void
-+qca8k_fdb_write(struct qca8k_priv *priv, u16 vid, u8 port_mask, const u8 *mac,
-+              u8 aging)
-+{
-+      u32 reg[3] = { 0 };
-+
-+      /* vid - 83:72 */
-+      reg[2] = FIELD_PREP(QCA8K_ATU_VID_MASK, vid);
-+      /* aging - 67:64 */
-+      reg[2] |= FIELD_PREP(QCA8K_ATU_STATUS_MASK, aging);
-+      /* portmask - 54:48 */
-+      reg[1] = FIELD_PREP(QCA8K_ATU_PORT_MASK, port_mask);
-+      /* mac - 47:0 */
-+      reg[1] |= FIELD_PREP(QCA8K_ATU_ADDR0_MASK, mac[0]);
-+      reg[1] |= FIELD_PREP(QCA8K_ATU_ADDR1_MASK, mac[1]);
-+      reg[0] |= FIELD_PREP(QCA8K_ATU_ADDR2_MASK, mac[2]);
-+      reg[0] |= FIELD_PREP(QCA8K_ATU_ADDR3_MASK, mac[3]);
-+      reg[0] |= FIELD_PREP(QCA8K_ATU_ADDR4_MASK, mac[4]);
-+      reg[0] |= FIELD_PREP(QCA8K_ATU_ADDR5_MASK, mac[5]);
-+
-+      /* load the array into the ARL table */
-+      qca8k_bulk_write(priv, QCA8K_REG_ATU_DATA0, reg, sizeof(reg));
-+}
-+
-+static int
-+qca8k_fdb_access(struct qca8k_priv *priv, enum qca8k_fdb_cmd cmd, int port)
-+{
-+      u32 reg;
-+      int ret;
-+
-+      /* Set the command and FDB index */
-+      reg = QCA8K_ATU_FUNC_BUSY;
-+      reg |= cmd;
-+      if (port >= 0) {
-+              reg |= QCA8K_ATU_FUNC_PORT_EN;
-+              reg |= FIELD_PREP(QCA8K_ATU_FUNC_PORT_MASK, port);
-+      }
-+
-+      /* Write the function register triggering the table access */
-+      ret = qca8k_write(priv, QCA8K_REG_ATU_FUNC, reg);
-+      if (ret)
-+              return ret;
-+
-+      /* wait for completion */
-+      ret = qca8k_busy_wait(priv, QCA8K_REG_ATU_FUNC, QCA8K_ATU_FUNC_BUSY);
-+      if (ret)
-+              return ret;
-+
-+      /* Check for table full violation when adding an entry */
-+      if (cmd == QCA8K_FDB_LOAD) {
-+              ret = qca8k_read(priv, QCA8K_REG_ATU_FUNC, &reg);
-+              if (ret < 0)
-+                      return ret;
-+              if (reg & QCA8K_ATU_FUNC_FULL)
-+                      return -1;
-+      }
-+
-+      return 0;
-+}
-+
-+static int
-+qca8k_fdb_next(struct qca8k_priv *priv, struct qca8k_fdb *fdb, int port)
-+{
-+      int ret;
-+
-+      qca8k_fdb_write(priv, fdb->vid, fdb->port_mask, fdb->mac, fdb->aging);
-+      ret = qca8k_fdb_access(priv, QCA8K_FDB_NEXT, port);
-+      if (ret < 0)
-+              return ret;
-+
-+      return qca8k_fdb_read(priv, fdb);
-+}
-+
-+static int
-+qca8k_fdb_add(struct qca8k_priv *priv, const u8 *mac, u16 port_mask,
-+            u16 vid, u8 aging)
-+{
-+      int ret;
-+
-+      mutex_lock(&priv->reg_mutex);
-+      qca8k_fdb_write(priv, vid, port_mask, mac, aging);
-+      ret = qca8k_fdb_access(priv, QCA8K_FDB_LOAD, -1);
-+      mutex_unlock(&priv->reg_mutex);
-+
-+      return ret;
-+}
-+
-+static int
-+qca8k_fdb_del(struct qca8k_priv *priv, const u8 *mac, u16 port_mask, u16 vid)
-+{
-+      int ret;
-+
-+      mutex_lock(&priv->reg_mutex);
-+      qca8k_fdb_write(priv, vid, port_mask, mac, 0);
-+      ret = qca8k_fdb_access(priv, QCA8K_FDB_PURGE, -1);
-+      mutex_unlock(&priv->reg_mutex);
-+
-+      return ret;
-+}
-+
-+static void
-+qca8k_fdb_flush(struct qca8k_priv *priv)
-+{
-+      mutex_lock(&priv->reg_mutex);
-+      qca8k_fdb_access(priv, QCA8K_FDB_FLUSH, -1);
-+      mutex_unlock(&priv->reg_mutex);
-+}
-+
-+static int
-+qca8k_fdb_search_and_insert(struct qca8k_priv *priv, u8 port_mask,
-+                          const u8 *mac, u16 vid)
-+{
-+      struct qca8k_fdb fdb = { 0 };
-+      int ret;
-+
-+      mutex_lock(&priv->reg_mutex);
-+
-+      qca8k_fdb_write(priv, vid, 0, mac, 0);
-+      ret = qca8k_fdb_access(priv, QCA8K_FDB_SEARCH, -1);
-+      if (ret < 0)
-+              goto exit;
-+
-+      ret = qca8k_fdb_read(priv, &fdb);
-+      if (ret < 0)
-+              goto exit;
-+
-+      /* Rule exist. Delete first */
-+      if (!fdb.aging) {
-+              ret = qca8k_fdb_access(priv, QCA8K_FDB_PURGE, -1);
-+              if (ret)
-+                      goto exit;
-+      }
-+
-+      /* Add port to fdb portmask */
-+      fdb.port_mask |= port_mask;
-+
-+      qca8k_fdb_write(priv, vid, fdb.port_mask, mac, fdb.aging);
-+      ret = qca8k_fdb_access(priv, QCA8K_FDB_LOAD, -1);
-+
-+exit:
-+      mutex_unlock(&priv->reg_mutex);
-+      return ret;
-+}
-+
-+static int
-+qca8k_fdb_search_and_del(struct qca8k_priv *priv, u8 port_mask,
-+                       const u8 *mac, u16 vid)
-+{
-+      struct qca8k_fdb fdb = { 0 };
-+      int ret;
-+
-+      mutex_lock(&priv->reg_mutex);
-+
-+      qca8k_fdb_write(priv, vid, 0, mac, 0);
-+      ret = qca8k_fdb_access(priv, QCA8K_FDB_SEARCH, -1);
-+      if (ret < 0)
-+              goto exit;
-+
-+      /* Rule doesn't exist. Why delete? */
-+      if (!fdb.aging) {
-+              ret = -EINVAL;
-+              goto exit;
-+      }
-+
-+      ret = qca8k_fdb_access(priv, QCA8K_FDB_PURGE, -1);
-+      if (ret)
-+              goto exit;
-+
-+      /* Only port in the rule is this port. Don't re insert */
-+      if (fdb.port_mask == port_mask)
-+              goto exit;
-+
-+      /* Remove port from port mask */
-+      fdb.port_mask &= ~port_mask;
-+
-+      qca8k_fdb_write(priv, vid, fdb.port_mask, mac, fdb.aging);
-+      ret = qca8k_fdb_access(priv, QCA8K_FDB_LOAD, -1);
-+
-+exit:
-+      mutex_unlock(&priv->reg_mutex);
-+      return ret;
-+}
-+
-+static int
-+qca8k_vlan_access(struct qca8k_priv *priv, enum qca8k_vlan_cmd cmd, u16 vid)
-+{
-+      u32 reg;
-+      int ret;
-+
-+      /* Set the command and VLAN index */
-+      reg = QCA8K_VTU_FUNC1_BUSY;
-+      reg |= cmd;
-+      reg |= FIELD_PREP(QCA8K_VTU_FUNC1_VID_MASK, vid);
-+
-+      /* Write the function register triggering the table access */
-+      ret = qca8k_write(priv, QCA8K_REG_VTU_FUNC1, reg);
-+      if (ret)
-+              return ret;
-+
-+      /* wait for completion */
-+      ret = qca8k_busy_wait(priv, QCA8K_REG_VTU_FUNC1, QCA8K_VTU_FUNC1_BUSY);
-+      if (ret)
-+              return ret;
-+
-+      /* Check for table full violation when adding an entry */
-+      if (cmd == QCA8K_VLAN_LOAD) {
-+              ret = qca8k_read(priv, QCA8K_REG_VTU_FUNC1, &reg);
-+              if (ret < 0)
-+                      return ret;
-+              if (reg & QCA8K_VTU_FUNC1_FULL)
-+                      return -ENOMEM;
-+      }
-+
-+      return 0;
-+}
-+
-+static int
-+qca8k_vlan_add(struct qca8k_priv *priv, u8 port, u16 vid, bool untagged)
-+{
-+      u32 reg;
-+      int ret;
-+
-+      /*
-+         We do the right thing with VLAN 0 and treat it as untagged while
-+         preserving the tag on egress.
-+       */
-+      if (vid == 0)
-+              return 0;
-+
-+      mutex_lock(&priv->reg_mutex);
-+      ret = qca8k_vlan_access(priv, QCA8K_VLAN_READ, vid);
-+      if (ret < 0)
-+              goto out;
-+
-+      ret = qca8k_read(priv, QCA8K_REG_VTU_FUNC0, &reg);
-+      if (ret < 0)
-+              goto out;
-+      reg |= QCA8K_VTU_FUNC0_VALID | QCA8K_VTU_FUNC0_IVL_EN;
-+      reg &= ~QCA8K_VTU_FUNC0_EG_MODE_PORT_MASK(port);
-+      if (untagged)
-+              reg |= QCA8K_VTU_FUNC0_EG_MODE_PORT_UNTAG(port);
-+      else
-+              reg |= QCA8K_VTU_FUNC0_EG_MODE_PORT_TAG(port);
-+
-+      ret = qca8k_write(priv, QCA8K_REG_VTU_FUNC0, reg);
-+      if (ret)
-+              goto out;
-+      ret = qca8k_vlan_access(priv, QCA8K_VLAN_LOAD, vid);
-+
-+out:
-+      mutex_unlock(&priv->reg_mutex);
-+
-+      return ret;
-+}
-+
-+static int
-+qca8k_vlan_del(struct qca8k_priv *priv, u8 port, u16 vid)
-+{
-+      u32 reg, mask;
-+      int ret, i;
-+      bool del;
-+
-+      mutex_lock(&priv->reg_mutex);
-+      ret = qca8k_vlan_access(priv, QCA8K_VLAN_READ, vid);
-+      if (ret < 0)
-+              goto out;
-+
-+      ret = qca8k_read(priv, QCA8K_REG_VTU_FUNC0, &reg);
-+      if (ret < 0)
-+              goto out;
-+      reg &= ~QCA8K_VTU_FUNC0_EG_MODE_PORT_MASK(port);
-+      reg |= QCA8K_VTU_FUNC0_EG_MODE_PORT_NOT(port);
-+
-+      /* Check if we're the last member to be removed */
-+      del = true;
-+      for (i = 0; i < QCA8K_NUM_PORTS; i++) {
-+              mask = QCA8K_VTU_FUNC0_EG_MODE_PORT_NOT(i);
-+
-+              if ((reg & mask) != mask) {
-+                      del = false;
-+                      break;
-+              }
-+      }
-+
-+      if (del) {
-+              ret = qca8k_vlan_access(priv, QCA8K_VLAN_PURGE, vid);
-+      } else {
-+              ret = qca8k_write(priv, QCA8K_REG_VTU_FUNC0, reg);
-+              if (ret)
-+                      goto out;
-+              ret = qca8k_vlan_access(priv, QCA8K_VLAN_LOAD, vid);
-+      }
-+
-+out:
-+      mutex_unlock(&priv->reg_mutex);
-+
-+      return ret;
-+}
-+
-+static int
-+qca8k_mib_init(struct qca8k_priv *priv)
-+{
-+      int ret;
-+
-+      mutex_lock(&priv->reg_mutex);
-+      ret = regmap_update_bits(priv->regmap, QCA8K_REG_MIB,
-+                               QCA8K_MIB_FUNC | QCA8K_MIB_BUSY,
-+                               FIELD_PREP(QCA8K_MIB_FUNC, QCA8K_MIB_FLUSH) |
-+                               QCA8K_MIB_BUSY);
-+      if (ret)
-+              goto exit;
-+
-+      ret = qca8k_busy_wait(priv, QCA8K_REG_MIB, QCA8K_MIB_BUSY);
-+      if (ret)
-+              goto exit;
-+
-+      ret = regmap_set_bits(priv->regmap, QCA8K_REG_MIB, QCA8K_MIB_CPU_KEEP);
-+      if (ret)
-+              goto exit;
-+
-+      ret = qca8k_write(priv, QCA8K_REG_MODULE_EN, QCA8K_MODULE_EN_MIB);
-+
-+exit:
-+      mutex_unlock(&priv->reg_mutex);
-+      return ret;
-+}
-+
-+static void
-+qca8k_port_set_status(struct qca8k_priv *priv, int port, int enable)
-+{
-+      u32 mask = QCA8K_PORT_STATUS_TXMAC | QCA8K_PORT_STATUS_RXMAC;
-+
-+      /* Port 0 and 6 have no internal PHY */
-+      if (port > 0 && port < 6)
-+              mask |= QCA8K_PORT_STATUS_LINK_AUTO;
-+
-+      if (enable)
-+              regmap_set_bits(priv->regmap, QCA8K_REG_PORT_STATUS(port), mask);
-+      else
-+              regmap_clear_bits(priv->regmap, QCA8K_REG_PORT_STATUS(port), mask);
-+}
-+
-+static int
-+qca8k_phy_eth_busy_wait(struct qca8k_mgmt_eth_data *mgmt_eth_data,
-+                      struct sk_buff *read_skb, u32 *val)
-+{
-+      struct sk_buff *skb = skb_copy(read_skb, GFP_KERNEL);
-+      bool ack;
-+      int ret;
-+
-+      reinit_completion(&mgmt_eth_data->rw_done);
-+
-+      /* Increment seq_num and set it in the copy pkt */
-+      mgmt_eth_data->seq++;
-+      qca8k_mdio_header_fill_seq_num(skb, mgmt_eth_data->seq);
-+      mgmt_eth_data->ack = false;
-+
-+      dev_queue_xmit(skb);
-+
-+      ret = wait_for_completion_timeout(&mgmt_eth_data->rw_done,
-+                                        QCA8K_ETHERNET_TIMEOUT);
-+
-+      ack = mgmt_eth_data->ack;
-+
-+      if (ret <= 0)
-+              return -ETIMEDOUT;
-+
-+      if (!ack)
-+              return -EINVAL;
-+
-+      *val = mgmt_eth_data->data[0];
-+
-+      return 0;
-+}
-+
-+static int
-+qca8k_phy_eth_command(struct qca8k_priv *priv, bool read, int phy,
-+                    int regnum, u16 data)
-+{
-+      struct sk_buff *write_skb, *clear_skb, *read_skb;
-+      struct qca8k_mgmt_eth_data *mgmt_eth_data;
-+      u32 write_val, clear_val = 0, val;
-+      struct net_device *mgmt_master;
-+      int ret, ret1;
-+      bool ack;
-+
-+      if (regnum >= QCA8K_MDIO_MASTER_MAX_REG)
-+              return -EINVAL;
-+
-+      mgmt_eth_data = &priv->mgmt_eth_data;
-+
-+      write_val = QCA8K_MDIO_MASTER_BUSY | QCA8K_MDIO_MASTER_EN |
-+                  QCA8K_MDIO_MASTER_PHY_ADDR(phy) |
-+                  QCA8K_MDIO_MASTER_REG_ADDR(regnum);
-+
-+      if (read) {
-+              write_val |= QCA8K_MDIO_MASTER_READ;
-+      } else {
-+              write_val |= QCA8K_MDIO_MASTER_WRITE;
-+              write_val |= QCA8K_MDIO_MASTER_DATA(data);
-+      }
-+
-+      /* Prealloc all the needed skb before the lock */
-+      write_skb = qca8k_alloc_mdio_header(MDIO_WRITE, QCA8K_MDIO_MASTER_CTRL, &write_val,
-+                                          QCA8K_ETHERNET_PHY_PRIORITY, sizeof(write_val));
-+      if (!write_skb)
-+              return -ENOMEM;
-+
-+      clear_skb = qca8k_alloc_mdio_header(MDIO_WRITE, QCA8K_MDIO_MASTER_CTRL, &clear_val,
-+                                          QCA8K_ETHERNET_PHY_PRIORITY, sizeof(clear_val));
-+      if (!clear_skb) {
-+              ret = -ENOMEM;
-+              goto err_clear_skb;
-+      }
-+
-+      read_skb = qca8k_alloc_mdio_header(MDIO_READ, QCA8K_MDIO_MASTER_CTRL, &clear_val,
-+                                         QCA8K_ETHERNET_PHY_PRIORITY, sizeof(clear_val));
-+      if (!read_skb) {
-+              ret = -ENOMEM;
-+              goto err_read_skb;
-+      }
-+
-+      /* Actually start the request:
-+       * 1. Send mdio master packet
-+       * 2. Busy Wait for mdio master command
-+       * 3. Get the data if we are reading
-+       * 4. Reset the mdio master (even with error)
-+       */
-+      mutex_lock(&mgmt_eth_data->mutex);
-+
-+      /* Check if mgmt_master is operational */
-+      mgmt_master = priv->mgmt_master;
-+      if (!mgmt_master) {
-+              mutex_unlock(&mgmt_eth_data->mutex);
-+              ret = -EINVAL;
-+              goto err_mgmt_master;
-+      }
-+
-+      read_skb->dev = mgmt_master;
-+      clear_skb->dev = mgmt_master;
-+      write_skb->dev = mgmt_master;
-+
-+      reinit_completion(&mgmt_eth_data->rw_done);
-+
-+      /* Increment seq_num and set it in the write pkt */
-+      mgmt_eth_data->seq++;
-+      qca8k_mdio_header_fill_seq_num(write_skb, mgmt_eth_data->seq);
-+      mgmt_eth_data->ack = false;
-+
-+      dev_queue_xmit(write_skb);
-+
-+      ret = wait_for_completion_timeout(&mgmt_eth_data->rw_done,
-+                                        QCA8K_ETHERNET_TIMEOUT);
-+
-+      ack = mgmt_eth_data->ack;
-+
-+      if (ret <= 0) {
-+              ret = -ETIMEDOUT;
-+              kfree_skb(read_skb);
-+              goto exit;
-+      }
-+
-+      if (!ack) {
-+              ret = -EINVAL;
-+              kfree_skb(read_skb);
-+              goto exit;
-+      }
-+
-+      ret = read_poll_timeout(qca8k_phy_eth_busy_wait, ret1,
-+                              !(val & QCA8K_MDIO_MASTER_BUSY), 0,
-+                              QCA8K_BUSY_WAIT_TIMEOUT * USEC_PER_MSEC, false,
-+                              mgmt_eth_data, read_skb, &val);
-+
-+      if (ret < 0 && ret1 < 0) {
-+              ret = ret1;
-+              goto exit;
-+      }
-+
-+      if (read) {
-+              reinit_completion(&mgmt_eth_data->rw_done);
-+
-+              /* Increment seq_num and set it in the read pkt */
-+              mgmt_eth_data->seq++;
-+              qca8k_mdio_header_fill_seq_num(read_skb, mgmt_eth_data->seq);
-+              mgmt_eth_data->ack = false;
-+
-+              dev_queue_xmit(read_skb);
-+
-+              ret = wait_for_completion_timeout(&mgmt_eth_data->rw_done,
-+                                                QCA8K_ETHERNET_TIMEOUT);
-+
-+              ack = mgmt_eth_data->ack;
-+
-+              if (ret <= 0) {
-+                      ret = -ETIMEDOUT;
-+                      goto exit;
-+              }
-+
-+              if (!ack) {
-+                      ret = -EINVAL;
-+                      goto exit;
-+              }
-+
-+              ret = mgmt_eth_data->data[0] & QCA8K_MDIO_MASTER_DATA_MASK;
-+      } else {
-+              kfree_skb(read_skb);
-+      }
-+exit:
-+      reinit_completion(&mgmt_eth_data->rw_done);
-+
-+      /* Increment seq_num and set it in the clear pkt */
-+      mgmt_eth_data->seq++;
-+      qca8k_mdio_header_fill_seq_num(clear_skb, mgmt_eth_data->seq);
-+      mgmt_eth_data->ack = false;
-+
-+      dev_queue_xmit(clear_skb);
-+
-+      wait_for_completion_timeout(&mgmt_eth_data->rw_done,
-+                                  QCA8K_ETHERNET_TIMEOUT);
-+
-+      mutex_unlock(&mgmt_eth_data->mutex);
-+
-+      return ret;
-+
-+      /* Error handling before lock */
-+err_mgmt_master:
-+      kfree_skb(read_skb);
-+err_read_skb:
-+      kfree_skb(clear_skb);
-+err_clear_skb:
-+      kfree_skb(write_skb);
-+
-+      return ret;
-+}
-+
-+static u32
-+qca8k_port_to_phy(int port)
-+{
-+      /* From Andrew Lunn:
-+       * Port 0 has no internal phy.
-+       * Port 1 has an internal PHY at MDIO address 0.
-+       * Port 2 has an internal PHY at MDIO address 1.
-+       * ...
-+       * Port 5 has an internal PHY at MDIO address 4.
-+       * Port 6 has no internal PHY.
-+       */
-+
-+      return port - 1;
-+}
-+
-+static int
-+qca8k_mdio_busy_wait(struct mii_bus *bus, u32 reg, u32 mask)
-+{
-+      u16 r1, r2, page;
-+      u32 val;
-+      int ret, ret1;
-+
-+      qca8k_split_addr(reg, &r1, &r2, &page);
-+
-+      ret = read_poll_timeout(qca8k_mii_read32, ret1, !(val & mask), 0,
-+                              QCA8K_BUSY_WAIT_TIMEOUT * USEC_PER_MSEC, false,
-+                              bus, 0x10 | r2, r1, &val);
-+
-+      /* Check if qca8k_read has failed for a different reason
-+       * before returnting -ETIMEDOUT
-+       */
-+      if (ret < 0 && ret1 < 0)
-+              return ret1;
-+
-+      return ret;
-+}
-+
-+static int
-+qca8k_mdio_write(struct qca8k_priv *priv, int phy, int regnum, u16 data)
-+{
-+      struct mii_bus *bus = priv->bus;
-+      u16 r1, r2, page;
-+      u32 val;
-+      int ret;
-+
-+      if (regnum >= QCA8K_MDIO_MASTER_MAX_REG)
-+              return -EINVAL;
-+
-+      val = QCA8K_MDIO_MASTER_BUSY | QCA8K_MDIO_MASTER_EN |
-+            QCA8K_MDIO_MASTER_WRITE | QCA8K_MDIO_MASTER_PHY_ADDR(phy) |
-+            QCA8K_MDIO_MASTER_REG_ADDR(regnum) |
-+            QCA8K_MDIO_MASTER_DATA(data);
-+
-+      qca8k_split_addr(QCA8K_MDIO_MASTER_CTRL, &r1, &r2, &page);
-+
-+      mutex_lock_nested(&bus->mdio_lock, MDIO_MUTEX_NESTED);
-+
-+      ret = qca8k_set_page(priv, page);
-+      if (ret)
-+              goto exit;
-+
-+      qca8k_mii_write32(priv, 0x10 | r2, r1, val);
-+
-+      ret = qca8k_mdio_busy_wait(bus, QCA8K_MDIO_MASTER_CTRL,
-+                                 QCA8K_MDIO_MASTER_BUSY);
-+
-+exit:
-+      /* even if the busy_wait timeouts try to clear the MASTER_EN */
-+      qca8k_mii_write32(priv, 0x10 | r2, r1, 0);
-+
-+      mutex_unlock(&bus->mdio_lock);
-+
-+      return ret;
-+}
-+
-+static int
-+qca8k_mdio_read(struct qca8k_priv *priv, int phy, int regnum)
-+{
-+      struct mii_bus *bus = priv->bus;
-+      u16 r1, r2, page;
-+      u32 val;
-+      int ret;
-+
-+      if (regnum >= QCA8K_MDIO_MASTER_MAX_REG)
-+              return -EINVAL;
-+
-+      val = QCA8K_MDIO_MASTER_BUSY | QCA8K_MDIO_MASTER_EN |
-+            QCA8K_MDIO_MASTER_READ | QCA8K_MDIO_MASTER_PHY_ADDR(phy) |
-+            QCA8K_MDIO_MASTER_REG_ADDR(regnum);
-+
-+      qca8k_split_addr(QCA8K_MDIO_MASTER_CTRL, &r1, &r2, &page);
-+
-+      mutex_lock_nested(&bus->mdio_lock, MDIO_MUTEX_NESTED);
-+
-+      ret = qca8k_set_page(priv, page);
-+      if (ret)
-+              goto exit;
-+
-+      qca8k_mii_write32(priv, 0x10 | r2, r1, val);
-+
-+      ret = qca8k_mdio_busy_wait(bus, QCA8K_MDIO_MASTER_CTRL,
-+                                 QCA8K_MDIO_MASTER_BUSY);
-+      if (ret)
-+              goto exit;
-+
-+      ret = qca8k_mii_read32(bus, 0x10 | r2, r1, &val);
-+
-+exit:
-+      /* even if the busy_wait timeouts try to clear the MASTER_EN */
-+      qca8k_mii_write32(priv, 0x10 | r2, r1, 0);
-+
-+      mutex_unlock(&bus->mdio_lock);
-+
-+      if (ret >= 0)
-+              ret = val & QCA8K_MDIO_MASTER_DATA_MASK;
-+
-+      return ret;
-+}
-+
-+static int
-+qca8k_internal_mdio_write(struct mii_bus *slave_bus, int phy, int regnum, u16 data)
-+{
-+      struct qca8k_priv *priv = slave_bus->priv;
-+      int ret;
-+
-+      /* Use mdio Ethernet when available, fallback to legacy one on error */
-+      ret = qca8k_phy_eth_command(priv, false, phy, regnum, data);
-+      if (!ret)
-+              return 0;
-+
-+      return qca8k_mdio_write(priv, phy, regnum, data);
-+}
-+
-+static int
-+qca8k_internal_mdio_read(struct mii_bus *slave_bus, int phy, int regnum)
-+{
-+      struct qca8k_priv *priv = slave_bus->priv;
-+      int ret;
-+
-+      /* Use mdio Ethernet when available, fallback to legacy one on error */
-+      ret = qca8k_phy_eth_command(priv, true, phy, regnum, 0);
-+      if (ret >= 0)
-+              return ret;
-+
-+      ret = qca8k_mdio_read(priv, phy, regnum);
-+
-+      if (ret < 0)
-+              return 0xffff;
-+
-+      return ret;
-+}
-+
-+static int
-+qca8k_legacy_mdio_write(struct mii_bus *slave_bus, int port, int regnum, u16 data)
-+{
-+      port = qca8k_port_to_phy(port) % PHY_MAX_ADDR;
-+
-+      return qca8k_internal_mdio_write(slave_bus, port, regnum, data);
-+}
-+
-+static int
-+qca8k_legacy_mdio_read(struct mii_bus *slave_bus, int port, int regnum)
-+{
-+      port = qca8k_port_to_phy(port) % PHY_MAX_ADDR;
-+
-+      return qca8k_internal_mdio_read(slave_bus, port, regnum);
-+}
-+
-+static int
-+qca8k_mdio_register(struct qca8k_priv *priv)
-+{
-+      struct dsa_switch *ds = priv->ds;
-+      struct device_node *mdio;
-+      struct mii_bus *bus;
-+
-+      bus = devm_mdiobus_alloc(ds->dev);
-+      if (!bus)
-+              return -ENOMEM;
-+
-+      bus->priv = (void *)priv;
-+      snprintf(bus->id, MII_BUS_ID_SIZE, "qca8k-%d.%d",
-+               ds->dst->index, ds->index);
-+      bus->parent = ds->dev;
-+      bus->phy_mask = ~ds->phys_mii_mask;
-+      ds->slave_mii_bus = bus;
-+
-+      /* Check if the devicetree declare the port:phy mapping */
-+      mdio = of_get_child_by_name(priv->dev->of_node, "mdio");
-+      if (of_device_is_available(mdio)) {
-+              bus->name = "qca8k slave mii";
-+              bus->read = qca8k_internal_mdio_read;
-+              bus->write = qca8k_internal_mdio_write;
-+              return devm_of_mdiobus_register(priv->dev, bus, mdio);
-+      }
-+
-+      /* If a mapping can't be found the legacy mapping is used,
-+       * using the qca8k_port_to_phy function
-+       */
-+      bus->name = "qca8k-legacy slave mii";
-+      bus->read = qca8k_legacy_mdio_read;
-+      bus->write = qca8k_legacy_mdio_write;
-+      return devm_mdiobus_register(priv->dev, bus);
-+}
-+
-+static int
-+qca8k_setup_mdio_bus(struct qca8k_priv *priv)
-+{
-+      u32 internal_mdio_mask = 0, external_mdio_mask = 0, reg;
-+      struct device_node *ports, *port;
-+      phy_interface_t mode;
-+      int err;
-+
-+      ports = of_get_child_by_name(priv->dev->of_node, "ports");
-+      if (!ports)
-+              ports = of_get_child_by_name(priv->dev->of_node, "ethernet-ports");
-+
-+      if (!ports)
-+              return -EINVAL;
-+
-+      for_each_available_child_of_node(ports, port) {
-+              err = of_property_read_u32(port, "reg", &reg);
-+              if (err) {
-+                      of_node_put(port);
-+                      of_node_put(ports);
-+                      return err;
-+              }
-+
-+              if (!dsa_is_user_port(priv->ds, reg))
-+                      continue;
-+
-+              of_get_phy_mode(port, &mode);
-+
-+              if (of_property_read_bool(port, "phy-handle") &&
-+                  mode != PHY_INTERFACE_MODE_INTERNAL)
-+                      external_mdio_mask |= BIT(reg);
-+              else
-+                      internal_mdio_mask |= BIT(reg);
-+      }
-+
-+      of_node_put(ports);
-+      if (!external_mdio_mask && !internal_mdio_mask) {
-+              dev_err(priv->dev, "no PHYs are defined.\n");
-+              return -EINVAL;
-+      }
-+
-+      /* The QCA8K_MDIO_MASTER_EN Bit, which grants access to PHYs through
-+       * the MDIO_MASTER register also _disconnects_ the external MDC
-+       * passthrough to the internal PHYs. It's not possible to use both
-+       * configurations at the same time!
-+       *
-+       * Because this came up during the review process:
-+       * If the external mdio-bus driver is capable magically disabling
-+       * the QCA8K_MDIO_MASTER_EN and mutex/spin-locking out the qca8k's
-+       * accessors for the time being, it would be possible to pull this
-+       * off.
-+       */
-+      if (!!external_mdio_mask && !!internal_mdio_mask) {
-+              dev_err(priv->dev, "either internal or external mdio bus configuration is supported.\n");
-+              return -EINVAL;
-+      }
-+
-+      if (external_mdio_mask) {
-+              /* Make sure to disable the internal mdio bus in cases
-+               * a dt-overlay and driver reload changed the configuration
-+               */
-+
-+              return regmap_clear_bits(priv->regmap, QCA8K_MDIO_MASTER_CTRL,
-+                                       QCA8K_MDIO_MASTER_EN);
-+      }
-+
-+      return qca8k_mdio_register(priv);
-+}
-+
-+static int
-+qca8k_setup_mac_pwr_sel(struct qca8k_priv *priv)
-+{
-+      u32 mask = 0;
-+      int ret = 0;
-+
-+      /* SoC specific settings for ipq8064.
-+       * If more device require this consider adding
-+       * a dedicated binding.
-+       */
-+      if (of_machine_is_compatible("qcom,ipq8064"))
-+              mask |= QCA8K_MAC_PWR_RGMII0_1_8V;
-+
-+      /* SoC specific settings for ipq8065 */
-+      if (of_machine_is_compatible("qcom,ipq8065"))
-+              mask |= QCA8K_MAC_PWR_RGMII1_1_8V;
-+
-+      if (mask) {
-+              ret = qca8k_rmw(priv, QCA8K_REG_MAC_PWR_SEL,
-+                              QCA8K_MAC_PWR_RGMII0_1_8V |
-+                              QCA8K_MAC_PWR_RGMII1_1_8V,
-+                              mask);
-+      }
-+
-+      return ret;
-+}
-+
-+static int qca8k_find_cpu_port(struct dsa_switch *ds)
-+{
-+      struct qca8k_priv *priv = ds->priv;
-+
-+      /* Find the connected cpu port. Valid port are 0 or 6 */
-+      if (dsa_is_cpu_port(ds, 0))
-+              return 0;
-+
-+      dev_dbg(priv->dev, "port 0 is not the CPU port. Checking port 6");
-+
-+      if (dsa_is_cpu_port(ds, 6))
-+              return 6;
-+
-+      return -EINVAL;
-+}
-+
-+static int
-+qca8k_setup_of_pws_reg(struct qca8k_priv *priv)
-+{
-+      const struct qca8k_match_data *data = priv->info;
-+      struct device_node *node = priv->dev->of_node;
-+      u32 val = 0;
-+      int ret;
-+
-+      /* QCA8327 require to set to the correct mode.
-+       * His bigger brother QCA8328 have the 172 pin layout.
-+       * Should be applied by default but we set this just to make sure.
-+       */
-+      if (priv->switch_id == QCA8K_ID_QCA8327) {
-+              /* Set the correct package of 148 pin for QCA8327 */
-+              if (data->reduced_package)
-+                      val |= QCA8327_PWS_PACKAGE148_EN;
-+
-+              ret = qca8k_rmw(priv, QCA8K_REG_PWS, QCA8327_PWS_PACKAGE148_EN,
-+                              val);
-+              if (ret)
-+                      return ret;
-+      }
-+
-+      if (of_property_read_bool(node, "qca,ignore-power-on-sel"))
-+              val |= QCA8K_PWS_POWER_ON_SEL;
-+
-+      if (of_property_read_bool(node, "qca,led-open-drain")) {
-+              if (!(val & QCA8K_PWS_POWER_ON_SEL)) {
-+                      dev_err(priv->dev, "qca,led-open-drain require qca,ignore-power-on-sel to be set.");
-+                      return -EINVAL;
-+              }
-+
-+              val |= QCA8K_PWS_LED_OPEN_EN_CSR;
-+      }
-+
-+      return qca8k_rmw(priv, QCA8K_REG_PWS,
-+                      QCA8K_PWS_LED_OPEN_EN_CSR | QCA8K_PWS_POWER_ON_SEL,
-+                      val);
-+}
-+
-+static int
-+qca8k_parse_port_config(struct qca8k_priv *priv)
-+{
-+      int port, cpu_port_index = -1, ret;
-+      struct device_node *port_dn;
-+      phy_interface_t mode;
-+      struct dsa_port *dp;
-+      u32 delay;
-+
-+      /* We have 2 CPU port. Check them */
-+      for (port = 0; port < QCA8K_NUM_PORTS; port++) {
-+              /* Skip every other port */
-+              if (port != 0 && port != 6)
-+                      continue;
-+
-+              dp = dsa_to_port(priv->ds, port);
-+              port_dn = dp->dn;
-+              cpu_port_index++;
-+
-+              if (!of_device_is_available(port_dn))
-+                      continue;
-+
-+              ret = of_get_phy_mode(port_dn, &mode);
-+              if (ret)
-+                      continue;
-+
-+              switch (mode) {
-+              case PHY_INTERFACE_MODE_RGMII:
-+              case PHY_INTERFACE_MODE_RGMII_ID:
-+              case PHY_INTERFACE_MODE_RGMII_TXID:
-+              case PHY_INTERFACE_MODE_RGMII_RXID:
-+              case PHY_INTERFACE_MODE_SGMII:
-+                      delay = 0;
-+
-+                      if (!of_property_read_u32(port_dn, "tx-internal-delay-ps", &delay))
-+                              /* Switch regs accept value in ns, convert ps to ns */
-+                              delay = delay / 1000;
-+                      else if (mode == PHY_INTERFACE_MODE_RGMII_ID ||
-+                               mode == PHY_INTERFACE_MODE_RGMII_TXID)
-+                              delay = 1;
-+
-+                      if (!FIELD_FIT(QCA8K_PORT_PAD_RGMII_TX_DELAY_MASK, delay)) {
-+                              dev_err(priv->dev, "rgmii tx delay is limited to a max value of 3ns, setting to the max value");
-+                              delay = 3;
-+                      }
-+
-+                      priv->ports_config.rgmii_tx_delay[cpu_port_index] = delay;
-+
-+                      delay = 0;
-+
-+                      if (!of_property_read_u32(port_dn, "rx-internal-delay-ps", &delay))
-+                              /* Switch regs accept value in ns, convert ps to ns */
-+                              delay = delay / 1000;
-+                      else if (mode == PHY_INTERFACE_MODE_RGMII_ID ||
-+                               mode == PHY_INTERFACE_MODE_RGMII_RXID)
-+                              delay = 2;
-+
-+                      if (!FIELD_FIT(QCA8K_PORT_PAD_RGMII_RX_DELAY_MASK, delay)) {
-+                              dev_err(priv->dev, "rgmii rx delay is limited to a max value of 3ns, setting to the max value");
-+                              delay = 3;
-+                      }
-+
-+                      priv->ports_config.rgmii_rx_delay[cpu_port_index] = delay;
-+
-+                      /* Skip sgmii parsing for rgmii* mode */
-+                      if (mode == PHY_INTERFACE_MODE_RGMII ||
-+                          mode == PHY_INTERFACE_MODE_RGMII_ID ||
-+                          mode == PHY_INTERFACE_MODE_RGMII_TXID ||
-+                          mode == PHY_INTERFACE_MODE_RGMII_RXID)
-+                              break;
-+
-+                      if (of_property_read_bool(port_dn, "qca,sgmii-txclk-falling-edge"))
-+                              priv->ports_config.sgmii_tx_clk_falling_edge = true;
-+
-+                      if (of_property_read_bool(port_dn, "qca,sgmii-rxclk-falling-edge"))
-+                              priv->ports_config.sgmii_rx_clk_falling_edge = true;
-+
-+                      if (of_property_read_bool(port_dn, "qca,sgmii-enable-pll")) {
-+                              priv->ports_config.sgmii_enable_pll = true;
-+
-+                              if (priv->switch_id == QCA8K_ID_QCA8327) {
-+                                      dev_err(priv->dev, "SGMII PLL should NOT be enabled for qca8327. Aborting enabling");
-+                                      priv->ports_config.sgmii_enable_pll = false;
-+                              }
-+
-+                              if (priv->switch_revision < 2)
-+                                      dev_warn(priv->dev, "SGMII PLL should NOT be enabled for qca8337 with revision 2 or more.");
-+                      }
-+
-+                      break;
-+              default:
-+                      continue;
-+              }
-+      }
-+
-+      return 0;
-+}
-+
-+static int
-+qca8k_setup(struct dsa_switch *ds)
-+{
-+      struct qca8k_priv *priv = (struct qca8k_priv *)ds->priv;
-+      int cpu_port, ret, i;
-+      u32 mask;
-+
-+      cpu_port = qca8k_find_cpu_port(ds);
-+      if (cpu_port < 0) {
-+              dev_err(priv->dev, "No cpu port configured in both cpu port0 and port6");
-+              return cpu_port;
-+      }
-+
-+      /* Parse CPU port config to be later used in phy_link mac_config */
-+      ret = qca8k_parse_port_config(priv);
-+      if (ret)
-+              return ret;
-+
-+      ret = qca8k_setup_mdio_bus(priv);
-+      if (ret)
-+              return ret;
-+
-+      ret = qca8k_setup_of_pws_reg(priv);
-+      if (ret)
-+              return ret;
-+
-+      ret = qca8k_setup_mac_pwr_sel(priv);
-+      if (ret)
-+              return ret;
-+
-+      /* Make sure MAC06 is disabled */
-+      ret = regmap_clear_bits(priv->regmap, QCA8K_REG_PORT0_PAD_CTRL,
-+                              QCA8K_PORT0_PAD_MAC06_EXCHANGE_EN);
-+      if (ret) {
-+              dev_err(priv->dev, "failed disabling MAC06 exchange");
-+              return ret;
-+      }
-+
-+      /* Enable CPU Port */
-+      ret = regmap_set_bits(priv->regmap, QCA8K_REG_GLOBAL_FW_CTRL0,
-+                            QCA8K_GLOBAL_FW_CTRL0_CPU_PORT_EN);
-+      if (ret) {
-+              dev_err(priv->dev, "failed enabling CPU port");
-+              return ret;
-+      }
-+
-+      /* Enable MIB counters */
-+      ret = qca8k_mib_init(priv);
-+      if (ret)
-+              dev_warn(priv->dev, "mib init failed");
-+
-+      /* Initial setup of all ports */
-+      for (i = 0; i < QCA8K_NUM_PORTS; i++) {
-+              /* Disable forwarding by default on all ports */
-+              ret = qca8k_rmw(priv, QCA8K_PORT_LOOKUP_CTRL(i),
-+                              QCA8K_PORT_LOOKUP_MEMBER, 0);
-+              if (ret)
-+                      return ret;
-+
-+              /* Enable QCA header mode on all cpu ports */
-+              if (dsa_is_cpu_port(ds, i)) {
-+                      ret = qca8k_write(priv, QCA8K_REG_PORT_HDR_CTRL(i),
-+                                        FIELD_PREP(QCA8K_PORT_HDR_CTRL_TX_MASK, QCA8K_PORT_HDR_CTRL_ALL) |
-+                                        FIELD_PREP(QCA8K_PORT_HDR_CTRL_RX_MASK, QCA8K_PORT_HDR_CTRL_ALL));
-+                      if (ret) {
-+                              dev_err(priv->dev, "failed enabling QCA header mode");
-+                              return ret;
-+                      }
-+              }
-+
-+              /* Disable MAC by default on all user ports */
-+              if (dsa_is_user_port(ds, i))
-+                      qca8k_port_set_status(priv, i, 0);
-+      }
-+
-+      /* Forward all unknown frames to CPU port for Linux processing
-+       * Notice that in multi-cpu config only one port should be set
-+       * for igmp, unknown, multicast and broadcast packet
-+       */
-+      ret = qca8k_write(priv, QCA8K_REG_GLOBAL_FW_CTRL1,
-+                        FIELD_PREP(QCA8K_GLOBAL_FW_CTRL1_IGMP_DP_MASK, BIT(cpu_port)) |
-+                        FIELD_PREP(QCA8K_GLOBAL_FW_CTRL1_BC_DP_MASK, BIT(cpu_port)) |
-+                        FIELD_PREP(QCA8K_GLOBAL_FW_CTRL1_MC_DP_MASK, BIT(cpu_port)) |
-+                        FIELD_PREP(QCA8K_GLOBAL_FW_CTRL1_UC_DP_MASK, BIT(cpu_port)));
-+      if (ret)
-+              return ret;
-+
-+      /* Setup connection between CPU port & user ports
-+       * Configure specific switch configuration for ports
-+       */
-+      for (i = 0; i < QCA8K_NUM_PORTS; i++) {
-+              /* CPU port gets connected to all user ports of the switch */
-+              if (dsa_is_cpu_port(ds, i)) {
-+                      ret = qca8k_rmw(priv, QCA8K_PORT_LOOKUP_CTRL(i),
-+                                      QCA8K_PORT_LOOKUP_MEMBER, dsa_user_ports(ds));
-+                      if (ret)
-+                              return ret;
-+              }
-+
-+              /* Individual user ports get connected to CPU port only */
-+              if (dsa_is_user_port(ds, i)) {
-+                      ret = qca8k_rmw(priv, QCA8K_PORT_LOOKUP_CTRL(i),
-+                                      QCA8K_PORT_LOOKUP_MEMBER,
-+                                      BIT(cpu_port));
-+                      if (ret)
-+                              return ret;
-+
-+                      /* Enable ARP Auto-learning by default */
-+                      ret = regmap_set_bits(priv->regmap, QCA8K_PORT_LOOKUP_CTRL(i),
-+                                            QCA8K_PORT_LOOKUP_LEARN);
-+                      if (ret)
-+                              return ret;
-+
-+                      /* For port based vlans to work we need to set the
-+                       * default egress vid
-+                       */
-+                      ret = qca8k_rmw(priv, QCA8K_EGRESS_VLAN(i),
-+                                      QCA8K_EGREES_VLAN_PORT_MASK(i),
-+                                      QCA8K_EGREES_VLAN_PORT(i, QCA8K_PORT_VID_DEF));
-+                      if (ret)
-+                              return ret;
-+
-+                      ret = qca8k_write(priv, QCA8K_REG_PORT_VLAN_CTRL0(i),
-+                                        QCA8K_PORT_VLAN_CVID(QCA8K_PORT_VID_DEF) |
-+                                        QCA8K_PORT_VLAN_SVID(QCA8K_PORT_VID_DEF));
-+                      if (ret)
-+                              return ret;
-+              }
-+
-+              /* The port 5 of the qca8337 have some problem in flood condition. The
-+               * original legacy driver had some specific buffer and priority settings
-+               * for the different port suggested by the QCA switch team. Add this
-+               * missing settings to improve switch stability under load condition.
-+               * This problem is limited to qca8337 and other qca8k switch are not affected.
-+               */
-+              if (priv->switch_id == QCA8K_ID_QCA8337) {
-+                      switch (i) {
-+                      /* The 2 CPU port and port 5 requires some different
-+                       * priority than any other ports.
-+                       */
-+                      case 0:
-+                      case 5:
-+                      case 6:
-+                              mask = QCA8K_PORT_HOL_CTRL0_EG_PRI0(0x3) |
-+                                      QCA8K_PORT_HOL_CTRL0_EG_PRI1(0x4) |
-+                                      QCA8K_PORT_HOL_CTRL0_EG_PRI2(0x4) |
-+                                      QCA8K_PORT_HOL_CTRL0_EG_PRI3(0x4) |
-+                                      QCA8K_PORT_HOL_CTRL0_EG_PRI4(0x6) |
-+                                      QCA8K_PORT_HOL_CTRL0_EG_PRI5(0x8) |
-+                                      QCA8K_PORT_HOL_CTRL0_EG_PORT(0x1e);
-+                              break;
-+                      default:
-+                              mask = QCA8K_PORT_HOL_CTRL0_EG_PRI0(0x3) |
-+                                      QCA8K_PORT_HOL_CTRL0_EG_PRI1(0x4) |
-+                                      QCA8K_PORT_HOL_CTRL0_EG_PRI2(0x6) |
-+                                      QCA8K_PORT_HOL_CTRL0_EG_PRI3(0x8) |
-+                                      QCA8K_PORT_HOL_CTRL0_EG_PORT(0x19);
-+                      }
-+                      qca8k_write(priv, QCA8K_REG_PORT_HOL_CTRL0(i), mask);
-+
-+                      mask = QCA8K_PORT_HOL_CTRL1_ING(0x6) |
-+                      QCA8K_PORT_HOL_CTRL1_EG_PRI_BUF_EN |
-+                      QCA8K_PORT_HOL_CTRL1_EG_PORT_BUF_EN |
-+                      QCA8K_PORT_HOL_CTRL1_WRED_EN;
-+                      qca8k_rmw(priv, QCA8K_REG_PORT_HOL_CTRL1(i),
-+                                QCA8K_PORT_HOL_CTRL1_ING_BUF_MASK |
-+                                QCA8K_PORT_HOL_CTRL1_EG_PRI_BUF_EN |
-+                                QCA8K_PORT_HOL_CTRL1_EG_PORT_BUF_EN |
-+                                QCA8K_PORT_HOL_CTRL1_WRED_EN,
-+                                mask);
-+              }
-+      }
-+
-+      /* Special GLOBAL_FC_THRESH value are needed for ar8327 switch */
-+      if (priv->switch_id == QCA8K_ID_QCA8327) {
-+              mask = QCA8K_GLOBAL_FC_GOL_XON_THRES(288) |
-+                     QCA8K_GLOBAL_FC_GOL_XOFF_THRES(496);
-+              qca8k_rmw(priv, QCA8K_REG_GLOBAL_FC_THRESH,
-+                        QCA8K_GLOBAL_FC_GOL_XON_THRES_MASK |
-+                        QCA8K_GLOBAL_FC_GOL_XOFF_THRES_MASK,
-+                        mask);
-+      }
-+
-+      /* Setup our port MTUs to match power on defaults */
-+      ret = qca8k_write(priv, QCA8K_MAX_FRAME_SIZE, ETH_FRAME_LEN + ETH_FCS_LEN);
-+      if (ret)
-+              dev_warn(priv->dev, "failed setting MTU settings");
-+
-+      /* Flush the FDB table */
-+      qca8k_fdb_flush(priv);
-+
-+      /* We don't have interrupts for link changes, so we need to poll */
-+      ds->pcs_poll = true;
-+
-+      /* Set min a max ageing value supported */
-+      ds->ageing_time_min = 7000;
-+      ds->ageing_time_max = 458745000;
-+
-+      /* Set max number of LAGs supported */
-+      ds->num_lag_ids = QCA8K_NUM_LAGS;
-+
-+      return 0;
-+}
-+
-+static void
-+qca8k_mac_config_setup_internal_delay(struct qca8k_priv *priv, int cpu_port_index,
-+                                    u32 reg)
-+{
-+      u32 delay, val = 0;
-+      int ret;
-+
-+      /* Delay can be declared in 3 different way.
-+       * Mode to rgmii and internal-delay standard binding defined
-+       * rgmii-id or rgmii-tx/rx phy mode set.
-+       * The parse logic set a delay different than 0 only when one
-+       * of the 3 different way is used. In all other case delay is
-+       * not enabled. With ID or TX/RXID delay is enabled and set
-+       * to the default and recommended value.
-+       */
-+      if (priv->ports_config.rgmii_tx_delay[cpu_port_index]) {
-+              delay = priv->ports_config.rgmii_tx_delay[cpu_port_index];
-+
-+              val |= QCA8K_PORT_PAD_RGMII_TX_DELAY(delay) |
-+                      QCA8K_PORT_PAD_RGMII_TX_DELAY_EN;
-+      }
-+
-+      if (priv->ports_config.rgmii_rx_delay[cpu_port_index]) {
-+              delay = priv->ports_config.rgmii_rx_delay[cpu_port_index];
-+
-+              val |= QCA8K_PORT_PAD_RGMII_RX_DELAY(delay) |
-+                      QCA8K_PORT_PAD_RGMII_RX_DELAY_EN;
-+      }
-+
-+      /* Set RGMII delay based on the selected values */
-+      ret = qca8k_rmw(priv, reg,
-+                      QCA8K_PORT_PAD_RGMII_TX_DELAY_MASK |
-+                      QCA8K_PORT_PAD_RGMII_RX_DELAY_MASK |
-+                      QCA8K_PORT_PAD_RGMII_TX_DELAY_EN |
-+                      QCA8K_PORT_PAD_RGMII_RX_DELAY_EN,
-+                      val);
-+      if (ret)
-+              dev_err(priv->dev, "Failed to set internal delay for CPU port%d",
-+                      cpu_port_index == QCA8K_CPU_PORT0 ? 0 : 6);
-+}
-+
-+static void
-+qca8k_phylink_mac_config(struct dsa_switch *ds, int port, unsigned int mode,
-+                       const struct phylink_link_state *state)
-+{
-+      struct qca8k_priv *priv = ds->priv;
-+      int cpu_port_index, ret;
-+      u32 reg, val;
-+
-+      switch (port) {
-+      case 0: /* 1st CPU port */
-+              if (state->interface != PHY_INTERFACE_MODE_RGMII &&
-+                  state->interface != PHY_INTERFACE_MODE_RGMII_ID &&
-+                  state->interface != PHY_INTERFACE_MODE_RGMII_TXID &&
-+                  state->interface != PHY_INTERFACE_MODE_RGMII_RXID &&
-+                  state->interface != PHY_INTERFACE_MODE_SGMII)
-+                      return;
-+
-+              reg = QCA8K_REG_PORT0_PAD_CTRL;
-+              cpu_port_index = QCA8K_CPU_PORT0;
-+              break;
-+      case 1:
-+      case 2:
-+      case 3:
-+      case 4:
-+      case 5:
-+              /* Internal PHY, nothing to do */
-+              return;
-+      case 6: /* 2nd CPU port / external PHY */
-+              if (state->interface != PHY_INTERFACE_MODE_RGMII &&
-+                  state->interface != PHY_INTERFACE_MODE_RGMII_ID &&
-+                  state->interface != PHY_INTERFACE_MODE_RGMII_TXID &&
-+                  state->interface != PHY_INTERFACE_MODE_RGMII_RXID &&
-+                  state->interface != PHY_INTERFACE_MODE_SGMII &&
-+                  state->interface != PHY_INTERFACE_MODE_1000BASEX)
-+                      return;
-+
-+              reg = QCA8K_REG_PORT6_PAD_CTRL;
-+              cpu_port_index = QCA8K_CPU_PORT6;
-+              break;
-+      default:
-+              dev_err(ds->dev, "%s: unsupported port: %i\n", __func__, port);
-+              return;
-+      }
-+
-+      if (port != 6 && phylink_autoneg_inband(mode)) {
-+              dev_err(ds->dev, "%s: in-band negotiation unsupported\n",
-+                      __func__);
-+              return;
-+      }
-+
-+      switch (state->interface) {
-+      case PHY_INTERFACE_MODE_RGMII:
-+      case PHY_INTERFACE_MODE_RGMII_ID:
-+      case PHY_INTERFACE_MODE_RGMII_TXID:
-+      case PHY_INTERFACE_MODE_RGMII_RXID:
-+              qca8k_write(priv, reg, QCA8K_PORT_PAD_RGMII_EN);
-+
-+              /* Configure rgmii delay */
-+              qca8k_mac_config_setup_internal_delay(priv, cpu_port_index, reg);
-+
-+              /* QCA8337 requires to set rgmii rx delay for all ports.
-+               * This is enabled through PORT5_PAD_CTRL for all ports,
-+               * rather than individual port registers.
-+               */
-+              if (priv->switch_id == QCA8K_ID_QCA8337)
-+                      qca8k_write(priv, QCA8K_REG_PORT5_PAD_CTRL,
-+                                  QCA8K_PORT_PAD_RGMII_RX_DELAY_EN);
-+              break;
-+      case PHY_INTERFACE_MODE_SGMII:
-+      case PHY_INTERFACE_MODE_1000BASEX:
-+              /* Enable SGMII on the port */
-+              qca8k_write(priv, reg, QCA8K_PORT_PAD_SGMII_EN);
-+
-+              /* Enable/disable SerDes auto-negotiation as necessary */
-+              ret = qca8k_read(priv, QCA8K_REG_PWS, &val);
-+              if (ret)
-+                      return;
-+              if (phylink_autoneg_inband(mode))
-+                      val &= ~QCA8K_PWS_SERDES_AEN_DIS;
-+              else
-+                      val |= QCA8K_PWS_SERDES_AEN_DIS;
-+              qca8k_write(priv, QCA8K_REG_PWS, val);
-+
-+              /* Configure the SGMII parameters */
-+              ret = qca8k_read(priv, QCA8K_REG_SGMII_CTRL, &val);
-+              if (ret)
-+                      return;
-+
-+              val |= QCA8K_SGMII_EN_SD;
-+
-+              if (priv->ports_config.sgmii_enable_pll)
-+                      val |= QCA8K_SGMII_EN_PLL | QCA8K_SGMII_EN_RX |
-+                             QCA8K_SGMII_EN_TX;
-+
-+              if (dsa_is_cpu_port(ds, port)) {
-+                      /* CPU port, we're talking to the CPU MAC, be a PHY */
-+                      val &= ~QCA8K_SGMII_MODE_CTRL_MASK;
-+                      val |= QCA8K_SGMII_MODE_CTRL_PHY;
-+              } else if (state->interface == PHY_INTERFACE_MODE_SGMII) {
-+                      val &= ~QCA8K_SGMII_MODE_CTRL_MASK;
-+                      val |= QCA8K_SGMII_MODE_CTRL_MAC;
-+              } else if (state->interface == PHY_INTERFACE_MODE_1000BASEX) {
-+                      val &= ~QCA8K_SGMII_MODE_CTRL_MASK;
-+                      val |= QCA8K_SGMII_MODE_CTRL_BASEX;
-+              }
-+
-+              qca8k_write(priv, QCA8K_REG_SGMII_CTRL, val);
-+
-+              /* From original code is reported port instability as SGMII also
-+               * require delay set. Apply advised values here or take them from DT.
-+               */
-+              if (state->interface == PHY_INTERFACE_MODE_SGMII)
-+                      qca8k_mac_config_setup_internal_delay(priv, cpu_port_index, reg);
-+
-+              /* For qca8327/qca8328/qca8334/qca8338 sgmii is unique and
-+               * falling edge is set writing in the PORT0 PAD reg
-+               */
-+              if (priv->switch_id == QCA8K_ID_QCA8327 ||
-+                  priv->switch_id == QCA8K_ID_QCA8337)
-+                      reg = QCA8K_REG_PORT0_PAD_CTRL;
-+
-+              val = 0;
-+
-+              /* SGMII Clock phase configuration */
-+              if (priv->ports_config.sgmii_rx_clk_falling_edge)
-+                      val |= QCA8K_PORT0_PAD_SGMII_RXCLK_FALLING_EDGE;
-+
-+              if (priv->ports_config.sgmii_tx_clk_falling_edge)
-+                      val |= QCA8K_PORT0_PAD_SGMII_TXCLK_FALLING_EDGE;
-+
-+              if (val)
-+                      ret = qca8k_rmw(priv, reg,
-+                                      QCA8K_PORT0_PAD_SGMII_RXCLK_FALLING_EDGE |
-+                                      QCA8K_PORT0_PAD_SGMII_TXCLK_FALLING_EDGE,
-+                                      val);
-+
-+              break;
-+      default:
-+              dev_err(ds->dev, "xMII mode %s not supported for port %d\n",
-+                      phy_modes(state->interface), port);
-+              return;
-+      }
-+}
-+
-+static void
-+qca8k_phylink_validate(struct dsa_switch *ds, int port,
-+                     unsigned long *supported,
-+                     struct phylink_link_state *state)
-+{
-+      __ETHTOOL_DECLARE_LINK_MODE_MASK(mask) = { 0, };
-+
-+      switch (port) {
-+      case 0: /* 1st CPU port */
-+              if (state->interface != PHY_INTERFACE_MODE_NA &&
-+                  state->interface != PHY_INTERFACE_MODE_RGMII &&
-+                  state->interface != PHY_INTERFACE_MODE_RGMII_ID &&
-+                  state->interface != PHY_INTERFACE_MODE_RGMII_TXID &&
-+                  state->interface != PHY_INTERFACE_MODE_RGMII_RXID &&
-+                  state->interface != PHY_INTERFACE_MODE_SGMII)
-+                      goto unsupported;
-+              break;
-+      case 1:
-+      case 2:
-+      case 3:
-+      case 4:
-+      case 5:
-+              /* Internal PHY */
-+              if (state->interface != PHY_INTERFACE_MODE_NA &&
-+                  state->interface != PHY_INTERFACE_MODE_GMII &&
-+                  state->interface != PHY_INTERFACE_MODE_INTERNAL)
-+                      goto unsupported;
-+              break;
-+      case 6: /* 2nd CPU port / external PHY */
-+              if (state->interface != PHY_INTERFACE_MODE_NA &&
-+                  state->interface != PHY_INTERFACE_MODE_RGMII &&
-+                  state->interface != PHY_INTERFACE_MODE_RGMII_ID &&
-+                  state->interface != PHY_INTERFACE_MODE_RGMII_TXID &&
-+                  state->interface != PHY_INTERFACE_MODE_RGMII_RXID &&
-+                  state->interface != PHY_INTERFACE_MODE_SGMII &&
-+                  state->interface != PHY_INTERFACE_MODE_1000BASEX)
-+                      goto unsupported;
-+              break;
-+      default:
-+unsupported:
-+              linkmode_zero(supported);
-+              return;
-+      }
-+
-+      phylink_set_port_modes(mask);
-+      phylink_set(mask, Autoneg);
-+
-+      phylink_set(mask, 1000baseT_Full);
-+      phylink_set(mask, 10baseT_Half);
-+      phylink_set(mask, 10baseT_Full);
-+      phylink_set(mask, 100baseT_Half);
-+      phylink_set(mask, 100baseT_Full);
-+
-+      if (state->interface == PHY_INTERFACE_MODE_1000BASEX)
-+              phylink_set(mask, 1000baseX_Full);
-+
-+      phylink_set(mask, Pause);
-+      phylink_set(mask, Asym_Pause);
-+
-+      linkmode_and(supported, supported, mask);
-+      linkmode_and(state->advertising, state->advertising, mask);
-+}
-+
-+static int
-+qca8k_phylink_mac_link_state(struct dsa_switch *ds, int port,
-+                           struct phylink_link_state *state)
-+{
-+      struct qca8k_priv *priv = ds->priv;
-+      u32 reg;
-+      int ret;
-+
-+      ret = qca8k_read(priv, QCA8K_REG_PORT_STATUS(port), &reg);
-+      if (ret < 0)
-+              return ret;
-+
-+      state->link = !!(reg & QCA8K_PORT_STATUS_LINK_UP);
-+      state->an_complete = state->link;
-+      state->an_enabled = !!(reg & QCA8K_PORT_STATUS_LINK_AUTO);
-+      state->duplex = (reg & QCA8K_PORT_STATUS_DUPLEX) ? DUPLEX_FULL :
-+                                                         DUPLEX_HALF;
-+
-+      switch (reg & QCA8K_PORT_STATUS_SPEED) {
-+      case QCA8K_PORT_STATUS_SPEED_10:
-+              state->speed = SPEED_10;
-+              break;
-+      case QCA8K_PORT_STATUS_SPEED_100:
-+              state->speed = SPEED_100;
-+              break;
-+      case QCA8K_PORT_STATUS_SPEED_1000:
-+              state->speed = SPEED_1000;
-+              break;
-+      default:
-+              state->speed = SPEED_UNKNOWN;
-+              break;
-+      }
-+
-+      state->pause = MLO_PAUSE_NONE;
-+      if (reg & QCA8K_PORT_STATUS_RXFLOW)
-+              state->pause |= MLO_PAUSE_RX;
-+      if (reg & QCA8K_PORT_STATUS_TXFLOW)
-+              state->pause |= MLO_PAUSE_TX;
-+
-+      return 1;
-+}
-+
-+static void
-+qca8k_phylink_mac_link_down(struct dsa_switch *ds, int port, unsigned int mode,
-+                          phy_interface_t interface)
-+{
-+      struct qca8k_priv *priv = ds->priv;
-+
-+      qca8k_port_set_status(priv, port, 0);
-+}
-+
-+static void
-+qca8k_phylink_mac_link_up(struct dsa_switch *ds, int port, unsigned int mode,
-+                        phy_interface_t interface, struct phy_device *phydev,
-+                        int speed, int duplex, bool tx_pause, bool rx_pause)
-+{
-+      struct qca8k_priv *priv = ds->priv;
-+      u32 reg;
-+
-+      if (phylink_autoneg_inband(mode)) {
-+              reg = QCA8K_PORT_STATUS_LINK_AUTO;
-+      } else {
-+              switch (speed) {
-+              case SPEED_10:
-+                      reg = QCA8K_PORT_STATUS_SPEED_10;
-+                      break;
-+              case SPEED_100:
-+                      reg = QCA8K_PORT_STATUS_SPEED_100;
-+                      break;
-+              case SPEED_1000:
-+                      reg = QCA8K_PORT_STATUS_SPEED_1000;
-+                      break;
-+              default:
-+                      reg = QCA8K_PORT_STATUS_LINK_AUTO;
-+                      break;
-+              }
-+
-+              if (duplex == DUPLEX_FULL)
-+                      reg |= QCA8K_PORT_STATUS_DUPLEX;
-+
-+              if (rx_pause || dsa_is_cpu_port(ds, port))
-+                      reg |= QCA8K_PORT_STATUS_RXFLOW;
-+
-+              if (tx_pause || dsa_is_cpu_port(ds, port))
-+                      reg |= QCA8K_PORT_STATUS_TXFLOW;
-+      }
-+
-+      reg |= QCA8K_PORT_STATUS_TXMAC | QCA8K_PORT_STATUS_RXMAC;
-+
-+      qca8k_write(priv, QCA8K_REG_PORT_STATUS(port), reg);
-+}
-+
-+static void
-+qca8k_get_strings(struct dsa_switch *ds, int port, u32 stringset, uint8_t *data)
-+{
-+      struct qca8k_priv *priv = ds->priv;
-+      int i;
-+
-+      if (stringset != ETH_SS_STATS)
-+              return;
-+
-+      for (i = 0; i < priv->info->mib_count; i++)
-+              strncpy(data + i * ETH_GSTRING_LEN, ar8327_mib[i].name,
-+                      ETH_GSTRING_LEN);
-+}
-+
-+static void qca8k_mib_autocast_handler(struct dsa_switch *ds, struct sk_buff *skb)
-+{
-+      struct qca8k_mib_eth_data *mib_eth_data;
-+      struct qca8k_priv *priv = ds->priv;
-+      const struct qca8k_mib_desc *mib;
-+      struct mib_ethhdr *mib_ethhdr;
-+      int i, mib_len, offset = 0;
-+      u64 *data;
-+      u8 port;
-+
-+      mib_ethhdr = (struct mib_ethhdr *)skb_mac_header(skb);
-+      mib_eth_data = &priv->mib_eth_data;
-+
-+      /* The switch autocast every port. Ignore other packet and
-+       * parse only the requested one.
-+       */
-+      port = FIELD_GET(QCA_HDR_RECV_SOURCE_PORT, ntohs(mib_ethhdr->hdr));
-+      if (port != mib_eth_data->req_port)
-+              goto exit;
-+
-+      data = mib_eth_data->data;
-+
-+      for (i = 0; i < priv->info->mib_count; i++) {
-+              mib = &ar8327_mib[i];
-+
-+              /* First 3 mib are present in the skb head */
-+              if (i < 3) {
-+                      data[i] = mib_ethhdr->data[i];
-+                      continue;
-+              }
-+
-+              mib_len = sizeof(uint32_t);
-+
-+              /* Some mib are 64 bit wide */
-+              if (mib->size == 2)
-+                      mib_len = sizeof(uint64_t);
-+
-+              /* Copy the mib value from packet to the */
-+              memcpy(data + i, skb->data + offset, mib_len);
-+
-+              /* Set the offset for the next mib */
-+              offset += mib_len;
-+      }
-+
-+exit:
-+      /* Complete on receiving all the mib packet */
-+      if (refcount_dec_and_test(&mib_eth_data->port_parsed))
-+              complete(&mib_eth_data->rw_done);
-+}
-+
-+static int
-+qca8k_get_ethtool_stats_eth(struct dsa_switch *ds, int port, u64 *data)
-+{
-+      struct dsa_port *dp = dsa_to_port(ds, port);
-+      struct qca8k_mib_eth_data *mib_eth_data;
-+      struct qca8k_priv *priv = ds->priv;
-+      int ret;
-+
-+      mib_eth_data = &priv->mib_eth_data;
-+
-+      mutex_lock(&mib_eth_data->mutex);
-+
-+      reinit_completion(&mib_eth_data->rw_done);
-+
-+      mib_eth_data->req_port = dp->index;
-+      mib_eth_data->data = data;
-+      refcount_set(&mib_eth_data->port_parsed, QCA8K_NUM_PORTS);
-+
-+      mutex_lock(&priv->reg_mutex);
-+
-+      /* Send mib autocast request */
-+      ret = regmap_update_bits(priv->regmap, QCA8K_REG_MIB,
-+                               QCA8K_MIB_FUNC | QCA8K_MIB_BUSY,
-+                               FIELD_PREP(QCA8K_MIB_FUNC, QCA8K_MIB_CAST) |
-+                               QCA8K_MIB_BUSY);
-+
-+      mutex_unlock(&priv->reg_mutex);
-+
-+      if (ret)
-+              goto exit;
-+
-+      ret = wait_for_completion_timeout(&mib_eth_data->rw_done, QCA8K_ETHERNET_TIMEOUT);
-+
-+exit:
-+      mutex_unlock(&mib_eth_data->mutex);
-+
-+      return ret;
-+}
-+
-+static void
-+qca8k_get_ethtool_stats(struct dsa_switch *ds, int port,
-+                      uint64_t *data)
-+{
-+      struct qca8k_priv *priv = (struct qca8k_priv *)ds->priv;
-+      const struct qca8k_mib_desc *mib;
-+      u32 reg, i, val;
-+      u32 hi = 0;
-+      int ret;
-+
-+      if (priv->mgmt_master && priv->info->ops->autocast_mib &&
-+          priv->info->ops->autocast_mib(ds, port, data) > 0)
-+              return;
-+
-+      for (i = 0; i < priv->info->mib_count; i++) {
-+              mib = &ar8327_mib[i];
-+              reg = QCA8K_PORT_MIB_COUNTER(port) + mib->offset;
-+
-+              ret = qca8k_read(priv, reg, &val);
-+              if (ret < 0)
-+                      continue;
-+
-+              if (mib->size == 2) {
-+                      ret = qca8k_read(priv, reg + 4, &hi);
-+                      if (ret < 0)
-+                              continue;
-+              }
-+
-+              data[i] = val;
-+              if (mib->size == 2)
-+                      data[i] |= (u64)hi << 32;
-+      }
-+}
-+
-+static int
-+qca8k_get_sset_count(struct dsa_switch *ds, int port, int sset)
-+{
-+      struct qca8k_priv *priv = ds->priv;
-+
-+      if (sset != ETH_SS_STATS)
-+              return 0;
-+
-+      return priv->info->mib_count;
-+}
-+
-+static int
-+qca8k_set_mac_eee(struct dsa_switch *ds, int port, struct ethtool_eee *eee)
-+{
-+      struct qca8k_priv *priv = (struct qca8k_priv *)ds->priv;
-+      u32 lpi_en = QCA8K_REG_EEE_CTRL_LPI_EN(port);
-+      u32 reg;
-+      int ret;
-+
-+      mutex_lock(&priv->reg_mutex);
-+      ret = qca8k_read(priv, QCA8K_REG_EEE_CTRL, &reg);
-+      if (ret < 0)
-+              goto exit;
-+
-+      if (eee->eee_enabled)
-+              reg |= lpi_en;
-+      else
-+              reg &= ~lpi_en;
-+      ret = qca8k_write(priv, QCA8K_REG_EEE_CTRL, reg);
-+
-+exit:
-+      mutex_unlock(&priv->reg_mutex);
-+      return ret;
-+}
-+
-+static int
-+qca8k_get_mac_eee(struct dsa_switch *ds, int port, struct ethtool_eee *e)
-+{
-+      /* Nothing to do on the port's MAC */
-+      return 0;
-+}
-+
-+static void
-+qca8k_port_stp_state_set(struct dsa_switch *ds, int port, u8 state)
-+{
-+      struct qca8k_priv *priv = (struct qca8k_priv *)ds->priv;
-+      u32 stp_state;
-+
-+      switch (state) {
-+      case BR_STATE_DISABLED:
-+              stp_state = QCA8K_PORT_LOOKUP_STATE_DISABLED;
-+              break;
-+      case BR_STATE_BLOCKING:
-+              stp_state = QCA8K_PORT_LOOKUP_STATE_BLOCKING;
-+              break;
-+      case BR_STATE_LISTENING:
-+              stp_state = QCA8K_PORT_LOOKUP_STATE_LISTENING;
-+              break;
-+      case BR_STATE_LEARNING:
-+              stp_state = QCA8K_PORT_LOOKUP_STATE_LEARNING;
-+              break;
-+      case BR_STATE_FORWARDING:
-+      default:
-+              stp_state = QCA8K_PORT_LOOKUP_STATE_FORWARD;
-+              break;
-+      }
-+
-+      qca8k_rmw(priv, QCA8K_PORT_LOOKUP_CTRL(port),
-+                QCA8K_PORT_LOOKUP_STATE_MASK, stp_state);
-+}
-+
-+static int
-+qca8k_port_bridge_join(struct dsa_switch *ds, int port, struct net_device *br)
-+{
-+      struct qca8k_priv *priv = (struct qca8k_priv *)ds->priv;
-+      int port_mask, cpu_port;
-+      int i, ret;
-+
-+      cpu_port = dsa_to_port(ds, port)->cpu_dp->index;
-+      port_mask = BIT(cpu_port);
-+
-+      for (i = 0; i < QCA8K_NUM_PORTS; i++) {
-+              if (dsa_is_cpu_port(ds, i))
-+                      continue;
-+              if (dsa_to_port(ds, i)->bridge_dev != br)
-+                      continue;
-+              /* Add this port to the portvlan mask of the other ports
-+               * in the bridge
-+               */
-+              ret = regmap_set_bits(priv->regmap,
-+                                    QCA8K_PORT_LOOKUP_CTRL(i),
-+                                    BIT(port));
-+              if (ret)
-+                      return ret;
-+              if (i != port)
-+                      port_mask |= BIT(i);
-+      }
-+
-+      /* Add all other ports to this ports portvlan mask */
-+      ret = qca8k_rmw(priv, QCA8K_PORT_LOOKUP_CTRL(port),
-+                      QCA8K_PORT_LOOKUP_MEMBER, port_mask);
-+
-+      return ret;
-+}
-+
-+static void
-+qca8k_port_bridge_leave(struct dsa_switch *ds, int port, struct net_device *br)
-+{
-+      struct qca8k_priv *priv = (struct qca8k_priv *)ds->priv;
-+      int cpu_port, i;
-+
-+      cpu_port = dsa_to_port(ds, port)->cpu_dp->index;
-+
-+      for (i = 0; i < QCA8K_NUM_PORTS; i++) {
-+              if (dsa_is_cpu_port(ds, i))
-+                      continue;
-+              if (dsa_to_port(ds, i)->bridge_dev != br)
-+                      continue;
-+              /* Remove this port to the portvlan mask of the other ports
-+               * in the bridge
-+               */
-+              regmap_clear_bits(priv->regmap,
-+                                QCA8K_PORT_LOOKUP_CTRL(i),
-+                                BIT(port));
-+      }
-+
-+      /* Set the cpu port to be the only one in the portvlan mask of
-+       * this port
-+       */
-+      qca8k_rmw(priv, QCA8K_PORT_LOOKUP_CTRL(port),
-+                QCA8K_PORT_LOOKUP_MEMBER, BIT(cpu_port));
-+}
-+
-+static void
-+qca8k_port_fast_age(struct dsa_switch *ds, int port)
-+{
-+      struct qca8k_priv *priv = ds->priv;
-+
-+      mutex_lock(&priv->reg_mutex);
-+      qca8k_fdb_access(priv, QCA8K_FDB_FLUSH_PORT, port);
-+      mutex_unlock(&priv->reg_mutex);
-+}
-+
-+static int
-+qca8k_set_ageing_time(struct dsa_switch *ds, unsigned int msecs)
-+{
-+      struct qca8k_priv *priv = ds->priv;
-+      unsigned int secs = msecs / 1000;
-+      u32 val;
-+
-+      /* AGE_TIME reg is set in 7s step */
-+      val = secs / 7;
-+
-+      /* Handle case with 0 as val to NOT disable
-+       * learning
-+       */
-+      if (!val)
-+              val = 1;
-+
-+      return regmap_update_bits(priv->regmap, QCA8K_REG_ATU_CTRL, QCA8K_ATU_AGE_TIME_MASK,
-+                                QCA8K_ATU_AGE_TIME(val));
-+}
-+
-+static int
-+qca8k_port_enable(struct dsa_switch *ds, int port,
-+                struct phy_device *phy)
-+{
-+      struct qca8k_priv *priv = (struct qca8k_priv *)ds->priv;
-+
-+      qca8k_port_set_status(priv, port, 1);
-+      priv->port_enabled_map |= BIT(port);
-+
-+      if (dsa_is_user_port(ds, port))
-+              phy_support_asym_pause(phy);
-+
-+      return 0;
-+}
-+
-+static void
-+qca8k_port_disable(struct dsa_switch *ds, int port)
-+{
-+      struct qca8k_priv *priv = (struct qca8k_priv *)ds->priv;
-+
-+      qca8k_port_set_status(priv, port, 0);
-+      priv->port_enabled_map &= ~BIT(port);
-+}
-+
-+static int
-+qca8k_port_change_mtu(struct dsa_switch *ds, int port, int new_mtu)
-+{
-+      struct qca8k_priv *priv = ds->priv;
-+      int ret;
-+
-+      /* We have only have a general MTU setting.
-+       * DSA always set the CPU port's MTU to the largest MTU of the slave
-+       * ports.
-+       * Setting MTU just for the CPU port is sufficient to correctly set a
-+       * value for every port.
-+       */
-+      if (!dsa_is_cpu_port(ds, port))
-+              return 0;
-+
-+      /* To change the MAX_FRAME_SIZE the cpu ports must be off or
-+       * the switch panics.
-+       * Turn off both cpu ports before applying the new value to prevent
-+       * this.
-+       */
-+      if (priv->port_enabled_map & BIT(0))
-+              qca8k_port_set_status(priv, 0, 0);
-+
-+      if (priv->port_enabled_map & BIT(6))
-+              qca8k_port_set_status(priv, 6, 0);
-+
-+      /* Include L2 header / FCS length */
-+      ret = qca8k_write(priv, QCA8K_MAX_FRAME_SIZE, new_mtu + ETH_HLEN + ETH_FCS_LEN);
-+
-+      if (priv->port_enabled_map & BIT(0))
-+              qca8k_port_set_status(priv, 0, 1);
-+
-+      if (priv->port_enabled_map & BIT(6))
-+              qca8k_port_set_status(priv, 6, 1);
-+
-+      return ret;
-+}
-+
-+static int
-+qca8k_port_max_mtu(struct dsa_switch *ds, int port)
-+{
-+      return QCA8K_MAX_MTU;
-+}
-+
-+static int
-+qca8k_port_fdb_insert(struct qca8k_priv *priv, const u8 *addr,
-+                    u16 port_mask, u16 vid)
-+{
-+      /* Set the vid to the port vlan id if no vid is set */
-+      if (!vid)
-+              vid = QCA8K_PORT_VID_DEF;
-+
-+      return qca8k_fdb_add(priv, addr, port_mask, vid,
-+                           QCA8K_ATU_STATUS_STATIC);
-+}
-+
-+static int
-+qca8k_port_fdb_add(struct dsa_switch *ds, int port,
-+                 const unsigned char *addr, u16 vid)
-+{
-+      struct qca8k_priv *priv = (struct qca8k_priv *)ds->priv;
-+      u16 port_mask = BIT(port);
-+
-+      return qca8k_port_fdb_insert(priv, addr, port_mask, vid);
-+}
-+
-+static int
-+qca8k_port_fdb_del(struct dsa_switch *ds, int port,
-+                 const unsigned char *addr, u16 vid)
-+{
-+      struct qca8k_priv *priv = (struct qca8k_priv *)ds->priv;
-+      u16 port_mask = BIT(port);
-+
-+      if (!vid)
-+              vid = QCA8K_PORT_VID_DEF;
-+
-+      return qca8k_fdb_del(priv, addr, port_mask, vid);
-+}
-+
-+static int
-+qca8k_port_fdb_dump(struct dsa_switch *ds, int port,
-+                  dsa_fdb_dump_cb_t *cb, void *data)
-+{
-+      struct qca8k_priv *priv = (struct qca8k_priv *)ds->priv;
-+      struct qca8k_fdb _fdb = { 0 };
-+      int cnt = QCA8K_NUM_FDB_RECORDS;
-+      bool is_static;
-+      int ret = 0;
-+
-+      mutex_lock(&priv->reg_mutex);
-+      while (cnt-- && !qca8k_fdb_next(priv, &_fdb, port)) {
-+              if (!_fdb.aging)
-+                      break;
-+              is_static = (_fdb.aging == QCA8K_ATU_STATUS_STATIC);
-+              ret = cb(_fdb.mac, _fdb.vid, is_static, data);
-+              if (ret)
-+                      break;
-+      }
-+      mutex_unlock(&priv->reg_mutex);
-+
-+      return 0;
-+}
-+
-+static int
-+qca8k_port_mdb_add(struct dsa_switch *ds, int port,
-+                 const struct switchdev_obj_port_mdb *mdb)
-+{
-+      struct qca8k_priv *priv = ds->priv;
-+      const u8 *addr = mdb->addr;
-+      u16 vid = mdb->vid;
-+
-+      return qca8k_fdb_search_and_insert(priv, BIT(port), addr, vid);
-+}
-+
-+static int
-+qca8k_port_mdb_del(struct dsa_switch *ds, int port,
-+                 const struct switchdev_obj_port_mdb *mdb)
-+{
-+      struct qca8k_priv *priv = ds->priv;
-+      const u8 *addr = mdb->addr;
-+      u16 vid = mdb->vid;
-+
-+      return qca8k_fdb_search_and_del(priv, BIT(port), addr, vid);
-+}
-+
-+static int
-+qca8k_port_mirror_add(struct dsa_switch *ds, int port,
-+                    struct dsa_mall_mirror_tc_entry *mirror,
-+                    bool ingress)
-+{
-+      struct qca8k_priv *priv = ds->priv;
-+      int monitor_port, ret;
-+      u32 reg, val;
-+
-+      /* Check for existent entry */
-+      if ((ingress ? priv->mirror_rx : priv->mirror_tx) & BIT(port))
-+              return -EEXIST;
-+
-+      ret = regmap_read(priv->regmap, QCA8K_REG_GLOBAL_FW_CTRL0, &val);
-+      if (ret)
-+              return ret;
-+
-+      /* QCA83xx can have only one port set to mirror mode.
-+       * Check that the correct port is requested and return error otherwise.
-+       * When no mirror port is set, the values is set to 0xF
-+       */
-+      monitor_port = FIELD_GET(QCA8K_GLOBAL_FW_CTRL0_MIRROR_PORT_NUM, val);
-+      if (monitor_port != 0xF && monitor_port != mirror->to_local_port)
-+              return -EEXIST;
-+
-+      /* Set the monitor port */
-+      val = FIELD_PREP(QCA8K_GLOBAL_FW_CTRL0_MIRROR_PORT_NUM,
-+                       mirror->to_local_port);
-+      ret = regmap_update_bits(priv->regmap, QCA8K_REG_GLOBAL_FW_CTRL0,
-+                               QCA8K_GLOBAL_FW_CTRL0_MIRROR_PORT_NUM, val);
-+      if (ret)
-+              return ret;
-+
-+      if (ingress) {
-+              reg = QCA8K_PORT_LOOKUP_CTRL(port);
-+              val = QCA8K_PORT_LOOKUP_ING_MIRROR_EN;
-+      } else {
-+              reg = QCA8K_REG_PORT_HOL_CTRL1(port);
-+              val = QCA8K_PORT_HOL_CTRL1_EG_MIRROR_EN;
-+      }
-+
-+      ret = regmap_update_bits(priv->regmap, reg, val, val);
-+      if (ret)
-+              return ret;
-+
-+      /* Track mirror port for tx and rx to decide when the
-+       * mirror port has to be disabled.
-+       */
-+      if (ingress)
-+              priv->mirror_rx |= BIT(port);
-+      else
-+              priv->mirror_tx |= BIT(port);
-+
-+      return 0;
-+}
-+
-+static void
-+qca8k_port_mirror_del(struct dsa_switch *ds, int port,
-+                    struct dsa_mall_mirror_tc_entry *mirror)
-+{
-+      struct qca8k_priv *priv = ds->priv;
-+      u32 reg, val;
-+      int ret;
-+
-+      if (mirror->ingress) {
-+              reg = QCA8K_PORT_LOOKUP_CTRL(port);
-+              val = QCA8K_PORT_LOOKUP_ING_MIRROR_EN;
-+      } else {
-+              reg = QCA8K_REG_PORT_HOL_CTRL1(port);
-+              val = QCA8K_PORT_HOL_CTRL1_EG_MIRROR_EN;
-+      }
-+
-+      ret = regmap_clear_bits(priv->regmap, reg, val);
-+      if (ret)
-+              goto err;
-+
-+      if (mirror->ingress)
-+              priv->mirror_rx &= ~BIT(port);
-+      else
-+              priv->mirror_tx &= ~BIT(port);
-+
-+      /* No port set to send packet to mirror port. Disable mirror port */
-+      if (!priv->mirror_rx && !priv->mirror_tx) {
-+              val = FIELD_PREP(QCA8K_GLOBAL_FW_CTRL0_MIRROR_PORT_NUM, 0xF);
-+              ret = regmap_update_bits(priv->regmap, QCA8K_REG_GLOBAL_FW_CTRL0,
-+                                       QCA8K_GLOBAL_FW_CTRL0_MIRROR_PORT_NUM, val);
-+              if (ret)
-+                      goto err;
-+      }
-+err:
-+      dev_err(priv->dev, "Failed to del mirror port from %d", port);
-+}
-+
-+static int
-+qca8k_port_vlan_filtering(struct dsa_switch *ds, int port, bool vlan_filtering,
-+                        struct netlink_ext_ack *extack)
-+{
-+      struct qca8k_priv *priv = ds->priv;
-+      int ret;
-+
-+      if (vlan_filtering) {
-+              ret = qca8k_rmw(priv, QCA8K_PORT_LOOKUP_CTRL(port),
-+                              QCA8K_PORT_LOOKUP_VLAN_MODE_MASK,
-+                              QCA8K_PORT_LOOKUP_VLAN_MODE_SECURE);
-+      } else {
-+              ret = qca8k_rmw(priv, QCA8K_PORT_LOOKUP_CTRL(port),
-+                              QCA8K_PORT_LOOKUP_VLAN_MODE_MASK,
-+                              QCA8K_PORT_LOOKUP_VLAN_MODE_NONE);
-+      }
-+
-+      return ret;
-+}
-+
-+static int
-+qca8k_port_vlan_add(struct dsa_switch *ds, int port,
-+                  const struct switchdev_obj_port_vlan *vlan,
-+                  struct netlink_ext_ack *extack)
-+{
-+      bool untagged = vlan->flags & BRIDGE_VLAN_INFO_UNTAGGED;
-+      bool pvid = vlan->flags & BRIDGE_VLAN_INFO_PVID;
-+      struct qca8k_priv *priv = ds->priv;
-+      int ret;
-+
-+      ret = qca8k_vlan_add(priv, port, vlan->vid, untagged);
-+      if (ret) {
-+              dev_err(priv->dev, "Failed to add VLAN to port %d (%d)", port, ret);
-+              return ret;
-+      }
-+
-+      if (pvid) {
-+              ret = qca8k_rmw(priv, QCA8K_EGRESS_VLAN(port),
-+                              QCA8K_EGREES_VLAN_PORT_MASK(port),
-+                              QCA8K_EGREES_VLAN_PORT(port, vlan->vid));
-+              if (ret)
-+                      return ret;
-+
-+              ret = qca8k_write(priv, QCA8K_REG_PORT_VLAN_CTRL0(port),
-+                                QCA8K_PORT_VLAN_CVID(vlan->vid) |
-+                                QCA8K_PORT_VLAN_SVID(vlan->vid));
-+      }
-+
-+      return ret;
-+}
-+
-+static int
-+qca8k_port_vlan_del(struct dsa_switch *ds, int port,
-+                  const struct switchdev_obj_port_vlan *vlan)
-+{
-+      struct qca8k_priv *priv = ds->priv;
-+      int ret;
-+
-+      ret = qca8k_vlan_del(priv, port, vlan->vid);
-+      if (ret)
-+              dev_err(priv->dev, "Failed to delete VLAN from port %d (%d)", port, ret);
-+
-+      return ret;
-+}
-+
-+static u32 qca8k_get_phy_flags(struct dsa_switch *ds, int port)
-+{
-+      struct qca8k_priv *priv = ds->priv;
-+
-+      /* Communicate to the phy internal driver the switch revision.
-+       * Based on the switch revision different values needs to be
-+       * set to the dbg and mmd reg on the phy.
-+       * The first 2 bit are used to communicate the switch revision
-+       * to the phy driver.
-+       */
-+      if (port > 0 && port < 6)
-+              return priv->switch_revision;
-+
-+      return 0;
-+}
-+
-+static enum dsa_tag_protocol
-+qca8k_get_tag_protocol(struct dsa_switch *ds, int port,
-+                     enum dsa_tag_protocol mp)
-+{
-+      return DSA_TAG_PROTO_QCA;
-+}
-+
-+static bool
-+qca8k_lag_can_offload(struct dsa_switch *ds,
-+                    struct net_device *lag,
-+                    struct netdev_lag_upper_info *info)
-+{
-+      struct dsa_port *dp;
-+      int id, members = 0;
-+
-+      id = dsa_lag_id(ds->dst, lag);
-+      if (id < 0 || id >= ds->num_lag_ids)
-+              return false;
-+
-+      dsa_lag_foreach_port(dp, ds->dst, lag)
-+              /* Includes the port joining the LAG */
-+              members++;
-+
-+      if (members > QCA8K_NUM_PORTS_FOR_LAG)
-+              return false;
-+
-+      if (info->tx_type != NETDEV_LAG_TX_TYPE_HASH)
-+              return false;
-+
-+      if (info->hash_type != NETDEV_LAG_HASH_L2 &&
-+          info->hash_type != NETDEV_LAG_HASH_L23)
-+              return false;
-+
-+      return true;
-+}
-+
-+static int
-+qca8k_lag_setup_hash(struct dsa_switch *ds,
-+                   struct net_device *lag,
-+                   struct netdev_lag_upper_info *info)
-+{
-+      struct qca8k_priv *priv = ds->priv;
-+      bool unique_lag = true;
-+      u32 hash = 0;
-+      int i, id;
-+
-+      id = dsa_lag_id(ds->dst, lag);
-+
-+      switch (info->hash_type) {
-+      case NETDEV_LAG_HASH_L23:
-+              hash |= QCA8K_TRUNK_HASH_SIP_EN;
-+              hash |= QCA8K_TRUNK_HASH_DIP_EN;
-+              fallthrough;
-+      case NETDEV_LAG_HASH_L2:
-+              hash |= QCA8K_TRUNK_HASH_SA_EN;
-+              hash |= QCA8K_TRUNK_HASH_DA_EN;
-+              break;
-+      default: /* We should NEVER reach this */
-+              return -EOPNOTSUPP;
-+      }
-+
-+      /* Check if we are the unique configured LAG */
-+      dsa_lags_foreach_id(i, ds->dst)
-+              if (i != id && dsa_lag_dev(ds->dst, i)) {
-+                      unique_lag = false;
-+                      break;
-+              }
-+
-+      /* Hash Mode is global. Make sure the same Hash Mode
-+       * is set to all the 4 possible lag.
-+       * If we are the unique LAG we can set whatever hash
-+       * mode we want.
-+       * To change hash mode it's needed to remove all LAG
-+       * and change the mode with the latest.
-+       */
-+      if (unique_lag) {
-+              priv->lag_hash_mode = hash;
-+      } else if (priv->lag_hash_mode != hash) {
-+              netdev_err(lag, "Error: Mismateched Hash Mode across different lag is not supported\n");
-+              return -EOPNOTSUPP;
-+      }
-+
-+      return regmap_update_bits(priv->regmap, QCA8K_TRUNK_HASH_EN_CTRL,
-+                                QCA8K_TRUNK_HASH_MASK, hash);
-+}
-+
-+static int
-+qca8k_lag_refresh_portmap(struct dsa_switch *ds, int port,
-+                        struct net_device *lag, bool delete)
-+{
-+      struct qca8k_priv *priv = ds->priv;
-+      int ret, id, i;
-+      u32 val;
-+
-+      id = dsa_lag_id(ds->dst, lag);
-+
-+      /* Read current port member */
-+      ret = regmap_read(priv->regmap, QCA8K_REG_GOL_TRUNK_CTRL0, &val);
-+      if (ret)
-+              return ret;
-+
-+      /* Shift val to the correct trunk */
-+      val >>= QCA8K_REG_GOL_TRUNK_SHIFT(id);
-+      val &= QCA8K_REG_GOL_TRUNK_MEMBER_MASK;
-+      if (delete)
-+              val &= ~BIT(port);
-+      else
-+              val |= BIT(port);
-+
-+      /* Update port member. With empty portmap disable trunk */
-+      ret = regmap_update_bits(priv->regmap, QCA8K_REG_GOL_TRUNK_CTRL0,
-+                               QCA8K_REG_GOL_TRUNK_MEMBER(id) |
-+                               QCA8K_REG_GOL_TRUNK_EN(id),
-+                               !val << QCA8K_REG_GOL_TRUNK_SHIFT(id) |
-+                               val << QCA8K_REG_GOL_TRUNK_SHIFT(id));
-+
-+      /* Search empty member if adding or port on deleting */
-+      for (i = 0; i < QCA8K_NUM_PORTS_FOR_LAG; i++) {
-+              ret = regmap_read(priv->regmap, QCA8K_REG_GOL_TRUNK_CTRL(id), &val);
-+              if (ret)
-+                      return ret;
-+
-+              val >>= QCA8K_REG_GOL_TRUNK_ID_MEM_ID_SHIFT(id, i);
-+              val &= QCA8K_REG_GOL_TRUNK_ID_MEM_ID_MASK;
-+
-+              if (delete) {
-+                      /* If port flagged to be disabled assume this member is
-+                       * empty
-+                       */
-+                      if (val != QCA8K_REG_GOL_TRUNK_ID_MEM_ID_EN_MASK)
-+                              continue;
-+
-+                      val &= QCA8K_REG_GOL_TRUNK_ID_MEM_ID_PORT_MASK;
-+                      if (val != port)
-+                              continue;
-+              } else {
-+                      /* If port flagged to be enabled assume this member is
-+                       * already set
-+                       */
-+                      if (val == QCA8K_REG_GOL_TRUNK_ID_MEM_ID_EN_MASK)
-+                              continue;
-+              }
-+
-+              /* We have found the member to add/remove */
-+              break;
-+      }
-+
-+      /* Set port in the correct port mask or disable port if in delete mode */
-+      return regmap_update_bits(priv->regmap, QCA8K_REG_GOL_TRUNK_CTRL(id),
-+                                QCA8K_REG_GOL_TRUNK_ID_MEM_ID_EN(id, i) |
-+                                QCA8K_REG_GOL_TRUNK_ID_MEM_ID_PORT(id, i),
-+                                !delete << QCA8K_REG_GOL_TRUNK_ID_MEM_ID_SHIFT(id, i) |
-+                                port << QCA8K_REG_GOL_TRUNK_ID_MEM_ID_SHIFT(id, i));
-+}
-+
-+static int
-+qca8k_port_lag_join(struct dsa_switch *ds, int port,
-+                  struct net_device *lag,
-+                  struct netdev_lag_upper_info *info)
-+{
-+      int ret;
-+
-+      if (!qca8k_lag_can_offload(ds, lag, info))
-+              return -EOPNOTSUPP;
-+
-+      ret = qca8k_lag_setup_hash(ds, lag, info);
-+      if (ret)
-+              return ret;
-+
-+      return qca8k_lag_refresh_portmap(ds, port, lag, false);
-+}
-+
-+static int
-+qca8k_port_lag_leave(struct dsa_switch *ds, int port,
-+                   struct net_device *lag)
-+{
-+      return qca8k_lag_refresh_portmap(ds, port, lag, true);
-+}
-+
-+static void
-+qca8k_master_change(struct dsa_switch *ds, const struct net_device *master,
-+                  bool operational)
-+{
-+      struct dsa_port *dp = master->dsa_ptr;
-+      struct qca8k_priv *priv = ds->priv;
-+
-+      /* Ethernet MIB/MDIO is only supported for CPU port 0 */
-+      if (dp->index != 0)
-+              return;
-+
-+      mutex_lock(&priv->mgmt_eth_data.mutex);
-+      mutex_lock(&priv->mib_eth_data.mutex);
-+
-+      priv->mgmt_master = operational ? (struct net_device *)master : NULL;
-+
-+      mutex_unlock(&priv->mib_eth_data.mutex);
-+      mutex_unlock(&priv->mgmt_eth_data.mutex);
-+}
-+
-+static int qca8k_connect_tag_protocol(struct dsa_switch *ds,
-+                                    enum dsa_tag_protocol proto)
-+{
-+      struct qca_tagger_data *tagger_data;
-+
-+      switch (proto) {
-+      case DSA_TAG_PROTO_QCA:
-+              tagger_data = ds->tagger_data;
-+
-+              tagger_data->rw_reg_ack_handler = qca8k_rw_reg_ack_handler;
-+              tagger_data->mib_autocast_handler = qca8k_mib_autocast_handler;
-+
-+              break;
-+      default:
-+              return -EOPNOTSUPP;
-+      }
-+
-+      return 0;
-+}
-+
-+static const struct dsa_switch_ops qca8k_switch_ops = {
-+      .get_tag_protocol       = qca8k_get_tag_protocol,
-+      .setup                  = qca8k_setup,
-+      .get_strings            = qca8k_get_strings,
-+      .get_ethtool_stats      = qca8k_get_ethtool_stats,
-+      .get_sset_count         = qca8k_get_sset_count,
-+      .set_ageing_time        = qca8k_set_ageing_time,
-+      .get_mac_eee            = qca8k_get_mac_eee,
-+      .set_mac_eee            = qca8k_set_mac_eee,
-+      .port_enable            = qca8k_port_enable,
-+      .port_disable           = qca8k_port_disable,
-+      .port_change_mtu        = qca8k_port_change_mtu,
-+      .port_max_mtu           = qca8k_port_max_mtu,
-+      .port_stp_state_set     = qca8k_port_stp_state_set,
-+      .port_bridge_join       = qca8k_port_bridge_join,
-+      .port_bridge_leave      = qca8k_port_bridge_leave,
-+      .port_fast_age          = qca8k_port_fast_age,
-+      .port_fdb_add           = qca8k_port_fdb_add,
-+      .port_fdb_del           = qca8k_port_fdb_del,
-+      .port_fdb_dump          = qca8k_port_fdb_dump,
-+      .port_mdb_add           = qca8k_port_mdb_add,
-+      .port_mdb_del           = qca8k_port_mdb_del,
-+      .port_mirror_add        = qca8k_port_mirror_add,
-+      .port_mirror_del        = qca8k_port_mirror_del,
-+      .port_vlan_filtering    = qca8k_port_vlan_filtering,
-+      .port_vlan_add          = qca8k_port_vlan_add,
-+      .port_vlan_del          = qca8k_port_vlan_del,
-+      .phylink_validate       = qca8k_phylink_validate,
-+      .phylink_mac_link_state = qca8k_phylink_mac_link_state,
-+      .phylink_mac_config     = qca8k_phylink_mac_config,
-+      .phylink_mac_link_down  = qca8k_phylink_mac_link_down,
-+      .phylink_mac_link_up    = qca8k_phylink_mac_link_up,
-+      .get_phy_flags          = qca8k_get_phy_flags,
-+      .port_lag_join          = qca8k_port_lag_join,
-+      .port_lag_leave         = qca8k_port_lag_leave,
-+      .master_state_change    = qca8k_master_change,
-+      .connect_tag_protocol   = qca8k_connect_tag_protocol,
-+};
-+
-+static int qca8k_read_switch_id(struct qca8k_priv *priv)
-+{
-+      u32 val;
-+      u8 id;
-+      int ret;
-+
-+      if (!priv->info)
-+              return -ENODEV;
-+
-+      ret = qca8k_read(priv, QCA8K_REG_MASK_CTRL, &val);
-+      if (ret < 0)
-+              return -ENODEV;
-+
-+      id = QCA8K_MASK_CTRL_DEVICE_ID(val);
-+      if (id != priv->info->id) {
-+              dev_err(priv->dev,
-+                      "Switch id detected %x but expected %x",
-+                      id, priv->info->id);
-+              return -ENODEV;
-+      }
-+
-+      priv->switch_id = id;
-+
-+      /* Save revision to communicate to the internal PHY driver */
-+      priv->switch_revision = QCA8K_MASK_CTRL_REV_ID(val);
-+
-+      return 0;
-+}
-+
-+static int
-+qca8k_sw_probe(struct mdio_device *mdiodev)
-+{
-+      struct qca8k_priv *priv;
-+      int ret;
-+
-+      /* allocate the private data struct so that we can probe the switches
-+       * ID register
-+       */
-+      priv = devm_kzalloc(&mdiodev->dev, sizeof(*priv), GFP_KERNEL);
-+      if (!priv)
-+              return -ENOMEM;
-+
-+      priv->info = of_device_get_match_data(priv->dev);
-+      priv->bus = mdiodev->bus;
-+      priv->dev = &mdiodev->dev;
-+
-+      priv->reset_gpio = devm_gpiod_get_optional(priv->dev, "reset",
-+                                                 GPIOD_ASIS);
-+      if (IS_ERR(priv->reset_gpio))
-+              return PTR_ERR(priv->reset_gpio);
-+
-+      if (priv->reset_gpio) {
-+              gpiod_set_value_cansleep(priv->reset_gpio, 1);
-+              /* The active low duration must be greater than 10 ms
-+               * and checkpatch.pl wants 20 ms.
-+               */
-+              msleep(20);
-+              gpiod_set_value_cansleep(priv->reset_gpio, 0);
-+      }
-+
-+      /* Start by setting up the register mapping */
-+      priv->regmap = devm_regmap_init(&mdiodev->dev, NULL, priv,
-+                                      &qca8k_regmap_config);
-+      if (IS_ERR(priv->regmap)) {
-+              dev_err(priv->dev, "regmap initialization failed");
-+              return PTR_ERR(priv->regmap);
-+      }
-+
-+      priv->mdio_cache.page = 0xffff;
-+      priv->mdio_cache.lo = 0xffff;
-+      priv->mdio_cache.hi = 0xffff;
-+
-+      /* Check the detected switch id */
-+      ret = qca8k_read_switch_id(priv);
-+      if (ret)
-+              return ret;
-+
-+      priv->ds = devm_kzalloc(&mdiodev->dev, sizeof(*priv->ds), GFP_KERNEL);
-+      if (!priv->ds)
-+              return -ENOMEM;
-+
-+      mutex_init(&priv->mgmt_eth_data.mutex);
-+      init_completion(&priv->mgmt_eth_data.rw_done);
-+
-+      mutex_init(&priv->mib_eth_data.mutex);
-+      init_completion(&priv->mib_eth_data.rw_done);
-+
-+      priv->ds->dev = &mdiodev->dev;
-+      priv->ds->num_ports = QCA8K_NUM_PORTS;
-+      priv->ds->priv = priv;
-+      priv->ds->ops = &qca8k_switch_ops;
-+      mutex_init(&priv->reg_mutex);
-+      dev_set_drvdata(&mdiodev->dev, priv);
-+
-+      return dsa_register_switch(priv->ds);
-+}
-+
-+static void
-+qca8k_sw_remove(struct mdio_device *mdiodev)
-+{
-+      struct qca8k_priv *priv = dev_get_drvdata(&mdiodev->dev);
-+      int i;
-+
-+      if (!priv)
-+              return;
-+
-+      for (i = 0; i < QCA8K_NUM_PORTS; i++)
-+              qca8k_port_set_status(priv, i, 0);
-+
-+      dsa_unregister_switch(priv->ds);
-+
-+      dev_set_drvdata(&mdiodev->dev, NULL);
-+}
-+
-+static void qca8k_sw_shutdown(struct mdio_device *mdiodev)
-+{
-+      struct qca8k_priv *priv = dev_get_drvdata(&mdiodev->dev);
-+
-+      if (!priv)
-+              return;
-+
-+      dsa_switch_shutdown(priv->ds);
-+
-+      dev_set_drvdata(&mdiodev->dev, NULL);
-+}
-+
-+#ifdef CONFIG_PM_SLEEP
-+static void
-+qca8k_set_pm(struct qca8k_priv *priv, int enable)
-+{
-+      int port;
-+
-+      for (port = 0; port < QCA8K_NUM_PORTS; port++) {
-+              /* Do not enable on resume if the port was
-+               * disabled before.
-+               */
-+              if (!(priv->port_enabled_map & BIT(port)))
-+                      continue;
-+
-+              qca8k_port_set_status(priv, port, enable);
-+      }
-+}
-+
-+static int qca8k_suspend(struct device *dev)
-+{
-+      struct qca8k_priv *priv = dev_get_drvdata(dev);
-+
-+      qca8k_set_pm(priv, 0);
-+
-+      return dsa_switch_suspend(priv->ds);
-+}
-+
-+static int qca8k_resume(struct device *dev)
-+{
-+      struct qca8k_priv *priv = dev_get_drvdata(dev);
-+
-+      qca8k_set_pm(priv, 1);
-+
-+      return dsa_switch_resume(priv->ds);
-+}
-+#endif /* CONFIG_PM_SLEEP */
-+
-+static SIMPLE_DEV_PM_OPS(qca8k_pm_ops,
-+                       qca8k_suspend, qca8k_resume);
-+
-+static const struct qca8k_info_ops qca8xxx_ops = {
-+      .autocast_mib = qca8k_get_ethtool_stats_eth,
-+};
-+
-+static const struct qca8k_match_data qca8327 = {
-+      .id = QCA8K_ID_QCA8327,
-+      .reduced_package = true,
-+      .mib_count = QCA8K_QCA832X_MIB_COUNT,
-+      .ops = &qca8xxx_ops,
-+};
-+
-+static const struct qca8k_match_data qca8328 = {
-+      .id = QCA8K_ID_QCA8327,
-+      .mib_count = QCA8K_QCA832X_MIB_COUNT,
-+      .ops = &qca8xxx_ops,
-+};
-+
-+static const struct qca8k_match_data qca833x = {
-+      .id = QCA8K_ID_QCA8337,
-+      .mib_count = QCA8K_QCA833X_MIB_COUNT,
-+      .ops = &qca8xxx_ops,
-+};
-+
-+static const struct of_device_id qca8k_of_match[] = {
-+      { .compatible = "qca,qca8327", .data = &qca8327 },
-+      { .compatible = "qca,qca8328", .data = &qca8328 },
-+      { .compatible = "qca,qca8334", .data = &qca833x },
-+      { .compatible = "qca,qca8337", .data = &qca833x },
-+      { /* sentinel */ },
-+};
-+
-+static struct mdio_driver qca8kmdio_driver = {
-+      .probe  = qca8k_sw_probe,
-+      .remove = qca8k_sw_remove,
-+      .shutdown = qca8k_sw_shutdown,
-+      .mdiodrv.driver = {
-+              .name = "qca8k",
-+              .of_match_table = qca8k_of_match,
-+              .pm = &qca8k_pm_ops,
-+      },
-+};
-+
-+mdio_module_driver(qca8kmdio_driver);
-+
-+MODULE_AUTHOR("Mathieu Olivari, John Crispin <[email protected]>");
-+MODULE_DESCRIPTION("Driver for QCA8K ethernet switch family");
-+MODULE_LICENSE("GPL v2");
-+MODULE_ALIAS("platform:qca8k");
---- /dev/null
-+++ b/drivers/net/dsa/qca/qca8k-common.c
-@@ -0,0 +1,63 @@
-+// SPDX-License-Identifier: GPL-2.0
-+/*
-+ * Copyright (C) 2009 Felix Fietkau <[email protected]>
-+ * Copyright (C) 2011-2012 Gabor Juhos <[email protected]>
-+ * Copyright (c) 2015, 2019, The Linux Foundation. All rights reserved.
-+ * Copyright (c) 2016 John Crispin <[email protected]>
-+ */
-+
-+#include <linux/netdevice.h>
-+#include <net/dsa.h>
-+
-+#include "qca8k.h"
-+
-+#define MIB_DESC(_s, _o, _n)  \
-+      {                       \
-+              .size = (_s),   \
-+              .offset = (_o), \
-+              .name = (_n),   \
-+      }
-+
-+const struct qca8k_mib_desc ar8327_mib[] = {
-+      MIB_DESC(1, 0x00, "RxBroad"),
-+      MIB_DESC(1, 0x04, "RxPause"),
-+      MIB_DESC(1, 0x08, "RxMulti"),
-+      MIB_DESC(1, 0x0c, "RxFcsErr"),
-+      MIB_DESC(1, 0x10, "RxAlignErr"),
-+      MIB_DESC(1, 0x14, "RxRunt"),
-+      MIB_DESC(1, 0x18, "RxFragment"),
-+      MIB_DESC(1, 0x1c, "Rx64Byte"),
-+      MIB_DESC(1, 0x20, "Rx128Byte"),
-+      MIB_DESC(1, 0x24, "Rx256Byte"),
-+      MIB_DESC(1, 0x28, "Rx512Byte"),
-+      MIB_DESC(1, 0x2c, "Rx1024Byte"),
-+      MIB_DESC(1, 0x30, "Rx1518Byte"),
-+      MIB_DESC(1, 0x34, "RxMaxByte"),
-+      MIB_DESC(1, 0x38, "RxTooLong"),
-+      MIB_DESC(2, 0x3c, "RxGoodByte"),
-+      MIB_DESC(2, 0x44, "RxBadByte"),
-+      MIB_DESC(1, 0x4c, "RxOverFlow"),
-+      MIB_DESC(1, 0x50, "Filtered"),
-+      MIB_DESC(1, 0x54, "TxBroad"),
-+      MIB_DESC(1, 0x58, "TxPause"),
-+      MIB_DESC(1, 0x5c, "TxMulti"),
-+      MIB_DESC(1, 0x60, "TxUnderRun"),
-+      MIB_DESC(1, 0x64, "Tx64Byte"),
-+      MIB_DESC(1, 0x68, "Tx128Byte"),
-+      MIB_DESC(1, 0x6c, "Tx256Byte"),
-+      MIB_DESC(1, 0x70, "Tx512Byte"),
-+      MIB_DESC(1, 0x74, "Tx1024Byte"),
-+      MIB_DESC(1, 0x78, "Tx1518Byte"),
-+      MIB_DESC(1, 0x7c, "TxMaxByte"),
-+      MIB_DESC(1, 0x80, "TxOverSize"),
-+      MIB_DESC(2, 0x84, "TxByte"),
-+      MIB_DESC(1, 0x8c, "TxCollision"),
-+      MIB_DESC(1, 0x90, "TxAbortCol"),
-+      MIB_DESC(1, 0x94, "TxMultiCol"),
-+      MIB_DESC(1, 0x98, "TxSingleCol"),
-+      MIB_DESC(1, 0x9c, "TxExcDefer"),
-+      MIB_DESC(1, 0xa0, "TxDefer"),
-+      MIB_DESC(1, 0xa4, "TxLateCol"),
-+      MIB_DESC(1, 0xa8, "RXUnicast"),
-+      MIB_DESC(1, 0xac, "TXUnicast"),
-+};
---- a/drivers/net/dsa/qca/qca8k.h
-+++ b/drivers/net/dsa/qca/qca8k.h
-@@ -414,4 +414,7 @@ struct qca8k_fdb {
-       u8 mac[6];
- };
-+/* Common setup function */
-+extern const struct qca8k_mib_desc ar8327_mib[];
-+
- #endif /* __QCA8K_H */
diff --git a/target/linux/generic/backport-5.15/771-v6.0-04-net-dsa-qca8k-move-qca8k-read-write-rmw-and-reg-tabl.patch b/target/linux/generic/backport-5.15/771-v6.0-04-net-dsa-qca8k-move-qca8k-read-write-rmw-and-reg-tabl.patch
deleted file mode 100644 (file)
index 012ab85..0000000
+++ /dev/null
@@ -1,135 +0,0 @@
-From d5f901eab2e9dfed1095995dfc98f231f4fd2971 Mon Sep 17 00:00:00 2001
-From: Christian Marangi <[email protected]>
-Date: Wed, 27 Jul 2022 13:35:13 +0200
-Subject: [PATCH 04/14] net: dsa: qca8k: move qca8k read/write/rmw and reg
- table to common code
-
-The same reg table and read/write/rmw function are used by drivers
-based on qca8k family switch.
-Move them to common code to make it accessible also by other drivers.
-
-Signed-off-by: Christian Marangi <[email protected]>
-Reviewed-by: Vladimir Oltean <[email protected]>
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- drivers/net/dsa/qca/qca8k-8xxx.c   | 42 ------------------------------
- drivers/net/dsa/qca/qca8k-common.c | 38 +++++++++++++++++++++++++++
- drivers/net/dsa/qca/qca8k.h        |  6 +++++
- 3 files changed, 44 insertions(+), 42 deletions(-)
-
---- a/drivers/net/dsa/qca/qca8k-8xxx.c
-+++ b/drivers/net/dsa/qca/qca8k-8xxx.c
-@@ -133,24 +133,6 @@ qca8k_set_page(struct qca8k_priv *priv,
-       return 0;
- }
--static int
--qca8k_read(struct qca8k_priv *priv, u32 reg, u32 *val)
--{
--      return regmap_read(priv->regmap, reg, val);
--}
--
--static int
--qca8k_write(struct qca8k_priv *priv, u32 reg, u32 val)
--{
--      return regmap_write(priv->regmap, reg, val);
--}
--
--static int
--qca8k_rmw(struct qca8k_priv *priv, u32 reg, u32 mask, u32 write_val)
--{
--      return regmap_update_bits(priv->regmap, reg, mask, write_val);
--}
--
- static void qca8k_rw_reg_ack_handler(struct dsa_switch *ds, struct sk_buff *skb)
- {
-       struct qca8k_mgmt_eth_data *mgmt_eth_data;
-@@ -483,30 +465,6 @@ exit:
-       return ret;
- }
--static const struct regmap_range qca8k_readable_ranges[] = {
--      regmap_reg_range(0x0000, 0x00e4), /* Global control */
--      regmap_reg_range(0x0100, 0x0168), /* EEE control */
--      regmap_reg_range(0x0200, 0x0270), /* Parser control */
--      regmap_reg_range(0x0400, 0x0454), /* ACL */
--      regmap_reg_range(0x0600, 0x0718), /* Lookup */
--      regmap_reg_range(0x0800, 0x0b70), /* QM */
--      regmap_reg_range(0x0c00, 0x0c80), /* PKT */
--      regmap_reg_range(0x0e00, 0x0e98), /* L3 */
--      regmap_reg_range(0x1000, 0x10ac), /* MIB - Port0 */
--      regmap_reg_range(0x1100, 0x11ac), /* MIB - Port1 */
--      regmap_reg_range(0x1200, 0x12ac), /* MIB - Port2 */
--      regmap_reg_range(0x1300, 0x13ac), /* MIB - Port3 */
--      regmap_reg_range(0x1400, 0x14ac), /* MIB - Port4 */
--      regmap_reg_range(0x1500, 0x15ac), /* MIB - Port5 */
--      regmap_reg_range(0x1600, 0x16ac), /* MIB - Port6 */
--
--};
--
--static const struct regmap_access_table qca8k_readable_table = {
--      .yes_ranges = qca8k_readable_ranges,
--      .n_yes_ranges = ARRAY_SIZE(qca8k_readable_ranges),
--};
--
- static struct regmap_config qca8k_regmap_config = {
-       .reg_bits = 16,
-       .val_bits = 32,
---- a/drivers/net/dsa/qca/qca8k-common.c
-+++ b/drivers/net/dsa/qca/qca8k-common.c
-@@ -61,3 +61,41 @@ const struct qca8k_mib_desc ar8327_mib[]
-       MIB_DESC(1, 0xa8, "RXUnicast"),
-       MIB_DESC(1, 0xac, "TXUnicast"),
- };
-+
-+int qca8k_read(struct qca8k_priv *priv, u32 reg, u32 *val)
-+{
-+      return regmap_read(priv->regmap, reg, val);
-+}
-+
-+int qca8k_write(struct qca8k_priv *priv, u32 reg, u32 val)
-+{
-+      return regmap_write(priv->regmap, reg, val);
-+}
-+
-+int qca8k_rmw(struct qca8k_priv *priv, u32 reg, u32 mask, u32 write_val)
-+{
-+      return regmap_update_bits(priv->regmap, reg, mask, write_val);
-+}
-+
-+static const struct regmap_range qca8k_readable_ranges[] = {
-+      regmap_reg_range(0x0000, 0x00e4), /* Global control */
-+      regmap_reg_range(0x0100, 0x0168), /* EEE control */
-+      regmap_reg_range(0x0200, 0x0270), /* Parser control */
-+      regmap_reg_range(0x0400, 0x0454), /* ACL */
-+      regmap_reg_range(0x0600, 0x0718), /* Lookup */
-+      regmap_reg_range(0x0800, 0x0b70), /* QM */
-+      regmap_reg_range(0x0c00, 0x0c80), /* PKT */
-+      regmap_reg_range(0x0e00, 0x0e98), /* L3 */
-+      regmap_reg_range(0x1000, 0x10ac), /* MIB - Port0 */
-+      regmap_reg_range(0x1100, 0x11ac), /* MIB - Port1 */
-+      regmap_reg_range(0x1200, 0x12ac), /* MIB - Port2 */
-+      regmap_reg_range(0x1300, 0x13ac), /* MIB - Port3 */
-+      regmap_reg_range(0x1400, 0x14ac), /* MIB - Port4 */
-+      regmap_reg_range(0x1500, 0x15ac), /* MIB - Port5 */
-+      regmap_reg_range(0x1600, 0x16ac), /* MIB - Port6 */
-+};
-+
-+const struct regmap_access_table qca8k_readable_table = {
-+      .yes_ranges = qca8k_readable_ranges,
-+      .n_yes_ranges = ARRAY_SIZE(qca8k_readable_ranges),
-+};
---- a/drivers/net/dsa/qca/qca8k.h
-+++ b/drivers/net/dsa/qca/qca8k.h
-@@ -416,5 +416,11 @@ struct qca8k_fdb {
- /* Common setup function */
- extern const struct qca8k_mib_desc ar8327_mib[];
-+extern const struct regmap_access_table qca8k_readable_table;
-+
-+/* Common read/write/rmw function */
-+int qca8k_read(struct qca8k_priv *priv, u32 reg, u32 *val);
-+int qca8k_write(struct qca8k_priv *priv, u32 reg, u32 val);
-+int qca8k_rmw(struct qca8k_priv *priv, u32 reg, u32 mask, u32 write_val);
- #endif /* __QCA8K_H */
diff --git a/target/linux/generic/backport-5.15/771-v6.0-05-net-dsa-qca8k-move-qca8k-bulk-read-write-helper-to-c.patch b/target/linux/generic/backport-5.15/771-v6.0-05-net-dsa-qca8k-move-qca8k-bulk-read-write-helper-to-c.patch
deleted file mode 100644 (file)
index 0ed7ed4..0000000
+++ /dev/null
@@ -1,145 +0,0 @@
-From 910746444313dc463396cd63024cdf54ef04ef39 Mon Sep 17 00:00:00 2001
-From: Christian Marangi <[email protected]>
-Date: Wed, 27 Jul 2022 13:35:14 +0200
-Subject: [PATCH 05/14] net: dsa: qca8k: move qca8k bulk read/write helper to
- common code
-
-The same ATU function are used by drivers based on qca8k family switch.
-Move the bulk read/write helper to common code to declare these shared
-ATU functions in common code.
-These helper will be dropped when regmap correctly support bulk
-read/write.
-
-Signed-off-by: Christian Marangi <[email protected]>
-Reviewed-by: Vladimir Oltean <[email protected]>
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- drivers/net/dsa/qca/qca8k-8xxx.c   | 39 ++----------------------------
- drivers/net/dsa/qca/qca8k-common.c | 39 ++++++++++++++++++++++++++++++
- drivers/net/dsa/qca/qca8k.h        |  8 ++++++
- 3 files changed, 49 insertions(+), 37 deletions(-)
-
---- a/drivers/net/dsa/qca/qca8k-8xxx.c
-+++ b/drivers/net/dsa/qca/qca8k-8xxx.c
-@@ -343,43 +343,6 @@ qca8k_regmap_update_bits_eth(struct qca8
- }
- static int
--qca8k_bulk_read(struct qca8k_priv *priv, u32 reg, u32 *val, int len)
--{
--      int i, count = len / sizeof(u32), ret;
--
--      if (priv->mgmt_master && !qca8k_read_eth(priv, reg, val, len))
--              return 0;
--
--      for (i = 0; i < count; i++) {
--              ret = regmap_read(priv->regmap, reg + (i * 4), val + i);
--              if (ret < 0)
--                      return ret;
--      }
--
--      return 0;
--}
--
--static int
--qca8k_bulk_write(struct qca8k_priv *priv, u32 reg, u32 *val, int len)
--{
--      int i, count = len / sizeof(u32), ret;
--      u32 tmp;
--
--      if (priv->mgmt_master && !qca8k_write_eth(priv, reg, val, len))
--              return 0;
--
--      for (i = 0; i < count; i++) {
--              tmp = val[i];
--
--              ret = regmap_write(priv->regmap, reg + (i * 4), tmp);
--              if (ret < 0)
--                      return ret;
--      }
--
--      return 0;
--}
--
--static int
- qca8k_regmap_read(void *ctx, uint32_t reg, uint32_t *val)
- {
-       struct qca8k_priv *priv = (struct qca8k_priv *)ctx;
-@@ -3096,6 +3059,8 @@ static SIMPLE_DEV_PM_OPS(qca8k_pm_ops,
- static const struct qca8k_info_ops qca8xxx_ops = {
-       .autocast_mib = qca8k_get_ethtool_stats_eth,
-+      .read_eth = qca8k_read_eth,
-+      .write_eth = qca8k_write_eth,
- };
- static const struct qca8k_match_data qca8327 = {
---- a/drivers/net/dsa/qca/qca8k-common.c
-+++ b/drivers/net/dsa/qca/qca8k-common.c
-@@ -99,3 +99,42 @@ const struct regmap_access_table qca8k_r
-       .yes_ranges = qca8k_readable_ranges,
-       .n_yes_ranges = ARRAY_SIZE(qca8k_readable_ranges),
- };
-+
-+/* TODO: remove these extra ops when we can support regmap bulk read/write */
-+int qca8k_bulk_read(struct qca8k_priv *priv, u32 reg, u32 *val, int len)
-+{
-+      int i, count = len / sizeof(u32), ret;
-+
-+      if (priv->mgmt_master && priv->info->ops->read_eth &&
-+          !priv->info->ops->read_eth(priv, reg, val, len))
-+              return 0;
-+
-+      for (i = 0; i < count; i++) {
-+              ret = regmap_read(priv->regmap, reg + (i * 4), val + i);
-+              if (ret < 0)
-+                      return ret;
-+      }
-+
-+      return 0;
-+}
-+
-+/* TODO: remove these extra ops when we can support regmap bulk read/write */
-+int qca8k_bulk_write(struct qca8k_priv *priv, u32 reg, u32 *val, int len)
-+{
-+      int i, count = len / sizeof(u32), ret;
-+      u32 tmp;
-+
-+      if (priv->mgmt_master && priv->info->ops->write_eth &&
-+          !priv->info->ops->write_eth(priv, reg, val, len))
-+              return 0;
-+
-+      for (i = 0; i < count; i++) {
-+              tmp = val[i];
-+
-+              ret = regmap_write(priv->regmap, reg + (i * 4), tmp);
-+              if (ret < 0)
-+                      return ret;
-+      }
-+
-+      return 0;
-+}
---- a/drivers/net/dsa/qca/qca8k.h
-+++ b/drivers/net/dsa/qca/qca8k.h
-@@ -324,8 +324,13 @@ enum qca8k_mid_cmd {
-       QCA8K_MIB_CAST = 3,
- };
-+struct qca8k_priv;
-+
- struct qca8k_info_ops {
-       int (*autocast_mib)(struct dsa_switch *ds, int port, u64 *data);
-+      /* TODO: remove these extra ops when we can support regmap bulk read/write */
-+      int (*read_eth)(struct qca8k_priv *priv, u32 reg, u32 *val, int len);
-+      int (*write_eth)(struct qca8k_priv *priv, u32 reg, u32 *val, int len);
- };
- struct qca8k_match_data {
-@@ -423,4 +428,7 @@ int qca8k_read(struct qca8k_priv *priv,
- int qca8k_write(struct qca8k_priv *priv, u32 reg, u32 val);
- int qca8k_rmw(struct qca8k_priv *priv, u32 reg, u32 mask, u32 write_val);
-+int qca8k_bulk_read(struct qca8k_priv *priv, u32 reg, u32 *val, int len);
-+int qca8k_bulk_write(struct qca8k_priv *priv, u32 reg, u32 *val, int len);
-+
- #endif /* __QCA8K_H */
diff --git a/target/linux/generic/backport-5.15/771-v6.0-06-net-dsa-qca8k-move-mib-init-function-to-common-code.patch b/target/linux/generic/backport-5.15/771-v6.0-06-net-dsa-qca8k-move-mib-init-function-to-common-code.patch
deleted file mode 100644 (file)
index a39a55b..0000000
+++ /dev/null
@@ -1,137 +0,0 @@
-From fce1ec0c4e2d03d9c62ffc615a42bdba78eb4c14 Mon Sep 17 00:00:00 2001
-From: Christian Marangi <[email protected]>
-Date: Wed, 27 Jul 2022 13:35:15 +0200
-Subject: [PATCH 06/14] net: dsa: qca8k: move mib init function to common code
-
-The same mib function is used by drivers based on qca8k family switch.
-Move it to common code to make it accessible also by other drivers.
-
-Signed-off-by: Christian Marangi <[email protected]>
-Reviewed-by: Vladimir Oltean <[email protected]>
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- drivers/net/dsa/qca/qca8k-8xxx.c   | 37 ------------------------------
- drivers/net/dsa/qca/qca8k-common.c | 35 ++++++++++++++++++++++++++++
- drivers/net/dsa/qca/qca8k.h        |  4 ++++
- 3 files changed, 39 insertions(+), 37 deletions(-)
-
---- a/drivers/net/dsa/qca/qca8k-8xxx.c
-+++ b/drivers/net/dsa/qca/qca8k-8xxx.c
-@@ -442,15 +442,6 @@ static struct regmap_config qca8k_regmap
- };
- static int
--qca8k_busy_wait(struct qca8k_priv *priv, u32 reg, u32 mask)
--{
--      u32 val;
--
--      return regmap_read_poll_timeout(priv->regmap, reg, val, !(val & mask), 0,
--                                     QCA8K_BUSY_WAIT_TIMEOUT * USEC_PER_MSEC);
--}
--
--static int
- qca8k_fdb_read(struct qca8k_priv *priv, struct qca8k_fdb *fdb)
- {
-       u32 reg[3];
-@@ -777,34 +768,6 @@ out:
-       return ret;
- }
--static int
--qca8k_mib_init(struct qca8k_priv *priv)
--{
--      int ret;
--
--      mutex_lock(&priv->reg_mutex);
--      ret = regmap_update_bits(priv->regmap, QCA8K_REG_MIB,
--                               QCA8K_MIB_FUNC | QCA8K_MIB_BUSY,
--                               FIELD_PREP(QCA8K_MIB_FUNC, QCA8K_MIB_FLUSH) |
--                               QCA8K_MIB_BUSY);
--      if (ret)
--              goto exit;
--
--      ret = qca8k_busy_wait(priv, QCA8K_REG_MIB, QCA8K_MIB_BUSY);
--      if (ret)
--              goto exit;
--
--      ret = regmap_set_bits(priv->regmap, QCA8K_REG_MIB, QCA8K_MIB_CPU_KEEP);
--      if (ret)
--              goto exit;
--
--      ret = qca8k_write(priv, QCA8K_REG_MODULE_EN, QCA8K_MODULE_EN_MIB);
--
--exit:
--      mutex_unlock(&priv->reg_mutex);
--      return ret;
--}
--
- static void
- qca8k_port_set_status(struct qca8k_priv *priv, int port, int enable)
- {
---- a/drivers/net/dsa/qca/qca8k-common.c
-+++ b/drivers/net/dsa/qca/qca8k-common.c
-@@ -7,6 +7,7 @@
-  */
- #include <linux/netdevice.h>
-+#include <linux/bitfield.h>
- #include <net/dsa.h>
- #include "qca8k.h"
-@@ -138,3 +139,38 @@ int qca8k_bulk_write(struct qca8k_priv *
-       return 0;
- }
-+
-+int qca8k_busy_wait(struct qca8k_priv *priv, u32 reg, u32 mask)
-+{
-+      u32 val;
-+
-+      return regmap_read_poll_timeout(priv->regmap, reg, val, !(val & mask), 0,
-+                                     QCA8K_BUSY_WAIT_TIMEOUT * USEC_PER_MSEC);
-+}
-+
-+int qca8k_mib_init(struct qca8k_priv *priv)
-+{
-+      int ret;
-+
-+      mutex_lock(&priv->reg_mutex);
-+      ret = regmap_update_bits(priv->regmap, QCA8K_REG_MIB,
-+                               QCA8K_MIB_FUNC | QCA8K_MIB_BUSY,
-+                               FIELD_PREP(QCA8K_MIB_FUNC, QCA8K_MIB_FLUSH) |
-+                               QCA8K_MIB_BUSY);
-+      if (ret)
-+              goto exit;
-+
-+      ret = qca8k_busy_wait(priv, QCA8K_REG_MIB, QCA8K_MIB_BUSY);
-+      if (ret)
-+              goto exit;
-+
-+      ret = regmap_set_bits(priv->regmap, QCA8K_REG_MIB, QCA8K_MIB_CPU_KEEP);
-+      if (ret)
-+              goto exit;
-+
-+      ret = qca8k_write(priv, QCA8K_REG_MODULE_EN, QCA8K_MODULE_EN_MIB);
-+
-+exit:
-+      mutex_unlock(&priv->reg_mutex);
-+      return ret;
-+}
---- a/drivers/net/dsa/qca/qca8k.h
-+++ b/drivers/net/dsa/qca/qca8k.h
-@@ -422,6 +422,7 @@ struct qca8k_fdb {
- /* Common setup function */
- extern const struct qca8k_mib_desc ar8327_mib[];
- extern const struct regmap_access_table qca8k_readable_table;
-+int qca8k_mib_init(struct qca8k_priv *priv);
- /* Common read/write/rmw function */
- int qca8k_read(struct qca8k_priv *priv, u32 reg, u32 *val);
-@@ -431,4 +432,7 @@ int qca8k_rmw(struct qca8k_priv *priv, u
- int qca8k_bulk_read(struct qca8k_priv *priv, u32 reg, u32 *val, int len);
- int qca8k_bulk_write(struct qca8k_priv *priv, u32 reg, u32 *val, int len);
-+/* Common ops function */
-+int qca8k_busy_wait(struct qca8k_priv *priv, u32 reg, u32 mask);
-+
- #endif /* __QCA8K_H */
diff --git a/target/linux/generic/backport-5.15/771-v6.0-07-net-dsa-qca8k-move-port-set-status-eee-ethtool-stats.patch b/target/linux/generic/backport-5.15/771-v6.0-07-net-dsa-qca8k-move-port-set-status-eee-ethtool-stats.patch
deleted file mode 100644 (file)
index 6fd1c66..0000000
+++ /dev/null
@@ -1,281 +0,0 @@
-From 472fcea160f27a5d9b7526093d9d8d89ba0b6137 Mon Sep 17 00:00:00 2001
-From: Christian Marangi <[email protected]>
-Date: Wed, 27 Jul 2022 13:35:16 +0200
-Subject: [PATCH 07/14] net: dsa: qca8k: move port set status/eee/ethtool stats
- function to common code
-
-The same logic to disable/enable port, set eee and get ethtool stats is
-used by drivers based on qca8k family switch.
-Move it to common code to make it accessible also by other drivers.
-While at it also drop unnecessary qca8k_priv cast for void pointers.
-
-Signed-off-by: Christian Marangi <[email protected]>
-Reviewed-by: Vladimir Oltean <[email protected]>
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- drivers/net/dsa/qca/qca8k-8xxx.c   | 105 -----------------------------
- drivers/net/dsa/qca/qca8k-common.c | 102 ++++++++++++++++++++++++++++
- drivers/net/dsa/qca/qca8k.h        |  11 +++
- 3 files changed, 113 insertions(+), 105 deletions(-)
-
---- a/drivers/net/dsa/qca/qca8k-8xxx.c
-+++ b/drivers/net/dsa/qca/qca8k-8xxx.c
-@@ -768,21 +768,6 @@ out:
-       return ret;
- }
--static void
--qca8k_port_set_status(struct qca8k_priv *priv, int port, int enable)
--{
--      u32 mask = QCA8K_PORT_STATUS_TXMAC | QCA8K_PORT_STATUS_RXMAC;
--
--      /* Port 0 and 6 have no internal PHY */
--      if (port > 0 && port < 6)
--              mask |= QCA8K_PORT_STATUS_LINK_AUTO;
--
--      if (enable)
--              regmap_set_bits(priv->regmap, QCA8K_REG_PORT_STATUS(port), mask);
--      else
--              regmap_clear_bits(priv->regmap, QCA8K_REG_PORT_STATUS(port), mask);
--}
--
- static int
- qca8k_phy_eth_busy_wait(struct qca8k_mgmt_eth_data *mgmt_eth_data,
-                       struct sk_buff *read_skb, u32 *val)
-@@ -1974,20 +1959,6 @@ qca8k_phylink_mac_link_up(struct dsa_swi
-       qca8k_write(priv, QCA8K_REG_PORT_STATUS(port), reg);
- }
--static void
--qca8k_get_strings(struct dsa_switch *ds, int port, u32 stringset, uint8_t *data)
--{
--      struct qca8k_priv *priv = ds->priv;
--      int i;
--
--      if (stringset != ETH_SS_STATS)
--              return;
--
--      for (i = 0; i < priv->info->mib_count; i++)
--              strncpy(data + i * ETH_GSTRING_LEN, ar8327_mib[i].name,
--                      ETH_GSTRING_LEN);
--}
--
- static void qca8k_mib_autocast_handler(struct dsa_switch *ds, struct sk_buff *skb)
- {
-       struct qca8k_mib_eth_data *mib_eth_data;
-@@ -2078,82 +2049,6 @@ exit:
- }
- static void
--qca8k_get_ethtool_stats(struct dsa_switch *ds, int port,
--                      uint64_t *data)
--{
--      struct qca8k_priv *priv = (struct qca8k_priv *)ds->priv;
--      const struct qca8k_mib_desc *mib;
--      u32 reg, i, val;
--      u32 hi = 0;
--      int ret;
--
--      if (priv->mgmt_master && priv->info->ops->autocast_mib &&
--          priv->info->ops->autocast_mib(ds, port, data) > 0)
--              return;
--
--      for (i = 0; i < priv->info->mib_count; i++) {
--              mib = &ar8327_mib[i];
--              reg = QCA8K_PORT_MIB_COUNTER(port) + mib->offset;
--
--              ret = qca8k_read(priv, reg, &val);
--              if (ret < 0)
--                      continue;
--
--              if (mib->size == 2) {
--                      ret = qca8k_read(priv, reg + 4, &hi);
--                      if (ret < 0)
--                              continue;
--              }
--
--              data[i] = val;
--              if (mib->size == 2)
--                      data[i] |= (u64)hi << 32;
--      }
--}
--
--static int
--qca8k_get_sset_count(struct dsa_switch *ds, int port, int sset)
--{
--      struct qca8k_priv *priv = ds->priv;
--
--      if (sset != ETH_SS_STATS)
--              return 0;
--
--      return priv->info->mib_count;
--}
--
--static int
--qca8k_set_mac_eee(struct dsa_switch *ds, int port, struct ethtool_eee *eee)
--{
--      struct qca8k_priv *priv = (struct qca8k_priv *)ds->priv;
--      u32 lpi_en = QCA8K_REG_EEE_CTRL_LPI_EN(port);
--      u32 reg;
--      int ret;
--
--      mutex_lock(&priv->reg_mutex);
--      ret = qca8k_read(priv, QCA8K_REG_EEE_CTRL, &reg);
--      if (ret < 0)
--              goto exit;
--
--      if (eee->eee_enabled)
--              reg |= lpi_en;
--      else
--              reg &= ~lpi_en;
--      ret = qca8k_write(priv, QCA8K_REG_EEE_CTRL, reg);
--
--exit:
--      mutex_unlock(&priv->reg_mutex);
--      return ret;
--}
--
--static int
--qca8k_get_mac_eee(struct dsa_switch *ds, int port, struct ethtool_eee *e)
--{
--      /* Nothing to do on the port's MAC */
--      return 0;
--}
--
--static void
- qca8k_port_stp_state_set(struct dsa_switch *ds, int port, u8 state)
- {
-       struct qca8k_priv *priv = (struct qca8k_priv *)ds->priv;
---- a/drivers/net/dsa/qca/qca8k-common.c
-+++ b/drivers/net/dsa/qca/qca8k-common.c
-@@ -174,3 +174,105 @@ exit:
-       mutex_unlock(&priv->reg_mutex);
-       return ret;
- }
-+
-+void qca8k_port_set_status(struct qca8k_priv *priv, int port, int enable)
-+{
-+      u32 mask = QCA8K_PORT_STATUS_TXMAC | QCA8K_PORT_STATUS_RXMAC;
-+
-+      /* Port 0 and 6 have no internal PHY */
-+      if (port > 0 && port < 6)
-+              mask |= QCA8K_PORT_STATUS_LINK_AUTO;
-+
-+      if (enable)
-+              regmap_set_bits(priv->regmap, QCA8K_REG_PORT_STATUS(port), mask);
-+      else
-+              regmap_clear_bits(priv->regmap, QCA8K_REG_PORT_STATUS(port), mask);
-+}
-+
-+void qca8k_get_strings(struct dsa_switch *ds, int port, u32 stringset,
-+                     uint8_t *data)
-+{
-+      struct qca8k_priv *priv = ds->priv;
-+      int i;
-+
-+      if (stringset != ETH_SS_STATS)
-+              return;
-+
-+      for (i = 0; i < priv->info->mib_count; i++)
-+              strncpy(data + i * ETH_GSTRING_LEN, ar8327_mib[i].name,
-+                      ETH_GSTRING_LEN);
-+}
-+
-+void qca8k_get_ethtool_stats(struct dsa_switch *ds, int port,
-+                           uint64_t *data)
-+{
-+      struct qca8k_priv *priv = ds->priv;
-+      const struct qca8k_mib_desc *mib;
-+      u32 reg, i, val;
-+      u32 hi = 0;
-+      int ret;
-+
-+      if (priv->mgmt_master && priv->info->ops->autocast_mib &&
-+          priv->info->ops->autocast_mib(ds, port, data) > 0)
-+              return;
-+
-+      for (i = 0; i < priv->info->mib_count; i++) {
-+              mib = &ar8327_mib[i];
-+              reg = QCA8K_PORT_MIB_COUNTER(port) + mib->offset;
-+
-+              ret = qca8k_read(priv, reg, &val);
-+              if (ret < 0)
-+                      continue;
-+
-+              if (mib->size == 2) {
-+                      ret = qca8k_read(priv, reg + 4, &hi);
-+                      if (ret < 0)
-+                              continue;
-+              }
-+
-+              data[i] = val;
-+              if (mib->size == 2)
-+                      data[i] |= (u64)hi << 32;
-+      }
-+}
-+
-+int qca8k_get_sset_count(struct dsa_switch *ds, int port, int sset)
-+{
-+      struct qca8k_priv *priv = ds->priv;
-+
-+      if (sset != ETH_SS_STATS)
-+              return 0;
-+
-+      return priv->info->mib_count;
-+}
-+
-+int qca8k_set_mac_eee(struct dsa_switch *ds, int port,
-+                    struct ethtool_eee *eee)
-+{
-+      u32 lpi_en = QCA8K_REG_EEE_CTRL_LPI_EN(port);
-+      struct qca8k_priv *priv = ds->priv;
-+      u32 reg;
-+      int ret;
-+
-+      mutex_lock(&priv->reg_mutex);
-+      ret = qca8k_read(priv, QCA8K_REG_EEE_CTRL, &reg);
-+      if (ret < 0)
-+              goto exit;
-+
-+      if (eee->eee_enabled)
-+              reg |= lpi_en;
-+      else
-+              reg &= ~lpi_en;
-+      ret = qca8k_write(priv, QCA8K_REG_EEE_CTRL, reg);
-+
-+exit:
-+      mutex_unlock(&priv->reg_mutex);
-+      return ret;
-+}
-+
-+int qca8k_get_mac_eee(struct dsa_switch *ds, int port,
-+                    struct ethtool_eee *e)
-+{
-+      /* Nothing to do on the port's MAC */
-+      return 0;
-+}
---- a/drivers/net/dsa/qca/qca8k.h
-+++ b/drivers/net/dsa/qca/qca8k.h
-@@ -423,6 +423,7 @@ struct qca8k_fdb {
- extern const struct qca8k_mib_desc ar8327_mib[];
- extern const struct regmap_access_table qca8k_readable_table;
- int qca8k_mib_init(struct qca8k_priv *priv);
-+void qca8k_port_set_status(struct qca8k_priv *priv, int port, int enable);
- /* Common read/write/rmw function */
- int qca8k_read(struct qca8k_priv *priv, u32 reg, u32 *val);
-@@ -435,4 +436,14 @@ int qca8k_bulk_write(struct qca8k_priv *
- /* Common ops function */
- int qca8k_busy_wait(struct qca8k_priv *priv, u32 reg, u32 mask);
-+/* Common ethtool stats function */
-+void qca8k_get_strings(struct dsa_switch *ds, int port, u32 stringset, uint8_t *data);
-+void qca8k_get_ethtool_stats(struct dsa_switch *ds, int port,
-+                           uint64_t *data);
-+int qca8k_get_sset_count(struct dsa_switch *ds, int port, int sset);
-+
-+/* Common eee function */
-+int qca8k_set_mac_eee(struct dsa_switch *ds, int port, struct ethtool_eee *eee);
-+int qca8k_get_mac_eee(struct dsa_switch *ds, int port, struct ethtool_eee *e);
-+
- #endif /* __QCA8K_H */
diff --git a/target/linux/generic/backport-5.15/771-v6.0-08-net-dsa-qca8k-move-bridge-functions-to-common-code.patch b/target/linux/generic/backport-5.15/771-v6.0-08-net-dsa-qca8k-move-bridge-functions-to-common-code.patch
deleted file mode 100644 (file)
index 3ca682d..0000000
+++ /dev/null
@@ -1,237 +0,0 @@
-From fd3cae2f3ac190d06e48f43739237e02f9dc51ff Mon Sep 17 00:00:00 2001
-From: Christian Marangi <[email protected]>
-Date: Wed, 27 Jul 2022 13:35:17 +0200
-Subject: [PATCH 08/14] net: dsa: qca8k: move bridge functions to common code
-
-The same bridge functions are used by drivers based on qca8k family
-switch. Move them to common code to make them accessible also by other
-drivers.
-While at it also drop unnecessary qca8k_priv cast for void pointers.
-
-Signed-off-by: Christian Marangi <[email protected]>
-Reviewed-by: Vladimir Oltean <[email protected]>
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- drivers/net/dsa/qca/qca8k-8xxx.c   | 93 ------------------------------
- drivers/net/dsa/qca/qca8k-common.c | 93 ++++++++++++++++++++++++++++++
- drivers/net/dsa/qca/qca8k.h        |  9 +++
- 3 files changed, 102 insertions(+), 93 deletions(-)
-
---- a/drivers/net/dsa/qca/qca8k-8xxx.c
-+++ b/drivers/net/dsa/qca/qca8k-8xxx.c
-@@ -2049,97 +2049,6 @@ exit:
- }
- static void
--qca8k_port_stp_state_set(struct dsa_switch *ds, int port, u8 state)
--{
--      struct qca8k_priv *priv = (struct qca8k_priv *)ds->priv;
--      u32 stp_state;
--
--      switch (state) {
--      case BR_STATE_DISABLED:
--              stp_state = QCA8K_PORT_LOOKUP_STATE_DISABLED;
--              break;
--      case BR_STATE_BLOCKING:
--              stp_state = QCA8K_PORT_LOOKUP_STATE_BLOCKING;
--              break;
--      case BR_STATE_LISTENING:
--              stp_state = QCA8K_PORT_LOOKUP_STATE_LISTENING;
--              break;
--      case BR_STATE_LEARNING:
--              stp_state = QCA8K_PORT_LOOKUP_STATE_LEARNING;
--              break;
--      case BR_STATE_FORWARDING:
--      default:
--              stp_state = QCA8K_PORT_LOOKUP_STATE_FORWARD;
--              break;
--      }
--
--      qca8k_rmw(priv, QCA8K_PORT_LOOKUP_CTRL(port),
--                QCA8K_PORT_LOOKUP_STATE_MASK, stp_state);
--}
--
--static int
--qca8k_port_bridge_join(struct dsa_switch *ds, int port, struct net_device *br)
--{
--      struct qca8k_priv *priv = (struct qca8k_priv *)ds->priv;
--      int port_mask, cpu_port;
--      int i, ret;
--
--      cpu_port = dsa_to_port(ds, port)->cpu_dp->index;
--      port_mask = BIT(cpu_port);
--
--      for (i = 0; i < QCA8K_NUM_PORTS; i++) {
--              if (dsa_is_cpu_port(ds, i))
--                      continue;
--              if (dsa_to_port(ds, i)->bridge_dev != br)
--                      continue;
--              /* Add this port to the portvlan mask of the other ports
--               * in the bridge
--               */
--              ret = regmap_set_bits(priv->regmap,
--                                    QCA8K_PORT_LOOKUP_CTRL(i),
--                                    BIT(port));
--              if (ret)
--                      return ret;
--              if (i != port)
--                      port_mask |= BIT(i);
--      }
--
--      /* Add all other ports to this ports portvlan mask */
--      ret = qca8k_rmw(priv, QCA8K_PORT_LOOKUP_CTRL(port),
--                      QCA8K_PORT_LOOKUP_MEMBER, port_mask);
--
--      return ret;
--}
--
--static void
--qca8k_port_bridge_leave(struct dsa_switch *ds, int port, struct net_device *br)
--{
--      struct qca8k_priv *priv = (struct qca8k_priv *)ds->priv;
--      int cpu_port, i;
--
--      cpu_port = dsa_to_port(ds, port)->cpu_dp->index;
--
--      for (i = 0; i < QCA8K_NUM_PORTS; i++) {
--              if (dsa_is_cpu_port(ds, i))
--                      continue;
--              if (dsa_to_port(ds, i)->bridge_dev != br)
--                      continue;
--              /* Remove this port to the portvlan mask of the other ports
--               * in the bridge
--               */
--              regmap_clear_bits(priv->regmap,
--                                QCA8K_PORT_LOOKUP_CTRL(i),
--                                BIT(port));
--      }
--
--      /* Set the cpu port to be the only one in the portvlan mask of
--       * this port
--       */
--      qca8k_rmw(priv, QCA8K_PORT_LOOKUP_CTRL(port),
--                QCA8K_PORT_LOOKUP_MEMBER, BIT(cpu_port));
--}
--
--static void
- qca8k_port_fast_age(struct dsa_switch *ds, int port)
- {
-       struct qca8k_priv *priv = ds->priv;
---- a/drivers/net/dsa/qca/qca8k-common.c
-+++ b/drivers/net/dsa/qca/qca8k-common.c
-@@ -9,6 +9,7 @@
- #include <linux/netdevice.h>
- #include <linux/bitfield.h>
- #include <net/dsa.h>
-+#include <linux/if_bridge.h>
- #include "qca8k.h"
-@@ -276,3 +277,93 @@ int qca8k_get_mac_eee(struct dsa_switch
-       /* Nothing to do on the port's MAC */
-       return 0;
- }
-+
-+void qca8k_port_stp_state_set(struct dsa_switch *ds, int port, u8 state)
-+{
-+      struct qca8k_priv *priv = ds->priv;
-+      u32 stp_state;
-+
-+      switch (state) {
-+      case BR_STATE_DISABLED:
-+              stp_state = QCA8K_PORT_LOOKUP_STATE_DISABLED;
-+              break;
-+      case BR_STATE_BLOCKING:
-+              stp_state = QCA8K_PORT_LOOKUP_STATE_BLOCKING;
-+              break;
-+      case BR_STATE_LISTENING:
-+              stp_state = QCA8K_PORT_LOOKUP_STATE_LISTENING;
-+              break;
-+      case BR_STATE_LEARNING:
-+              stp_state = QCA8K_PORT_LOOKUP_STATE_LEARNING;
-+              break;
-+      case BR_STATE_FORWARDING:
-+      default:
-+              stp_state = QCA8K_PORT_LOOKUP_STATE_FORWARD;
-+              break;
-+      }
-+
-+      qca8k_rmw(priv, QCA8K_PORT_LOOKUP_CTRL(port),
-+                QCA8K_PORT_LOOKUP_STATE_MASK, stp_state);
-+}
-+
-+int qca8k_port_bridge_join(struct dsa_switch *ds, int port,
-+                         struct net_device *br)
-+{
-+      struct qca8k_priv *priv = ds->priv;
-+      int port_mask, cpu_port;
-+      int i, ret;
-+
-+      cpu_port = dsa_to_port(ds, port)->cpu_dp->index;
-+      port_mask = BIT(cpu_port);
-+
-+      for (i = 0; i < QCA8K_NUM_PORTS; i++) {
-+              if (dsa_is_cpu_port(ds, i))
-+                      continue;
-+              if (dsa_to_port(ds, i)->bridge_dev != br)
-+                      continue;
-+              /* Add this port to the portvlan mask of the other ports
-+               * in the bridge
-+               */
-+              ret = regmap_set_bits(priv->regmap,
-+                                    QCA8K_PORT_LOOKUP_CTRL(i),
-+                                    BIT(port));
-+              if (ret)
-+                      return ret;
-+              if (i != port)
-+                      port_mask |= BIT(i);
-+      }
-+
-+      /* Add all other ports to this ports portvlan mask */
-+      ret = qca8k_rmw(priv, QCA8K_PORT_LOOKUP_CTRL(port),
-+                      QCA8K_PORT_LOOKUP_MEMBER, port_mask);
-+
-+      return ret;
-+}
-+
-+void qca8k_port_bridge_leave(struct dsa_switch *ds, int port,
-+                           struct net_device *br)
-+{
-+      struct qca8k_priv *priv = ds->priv;
-+      int cpu_port, i;
-+
-+      cpu_port = dsa_to_port(ds, port)->cpu_dp->index;
-+
-+      for (i = 0; i < QCA8K_NUM_PORTS; i++) {
-+              if (dsa_is_cpu_port(ds, i))
-+                      continue;
-+              if (dsa_to_port(ds, i)->bridge_dev != br)
-+                      continue;
-+              /* Remove this port to the portvlan mask of the other ports
-+               * in the bridge
-+               */
-+              regmap_clear_bits(priv->regmap,
-+                                QCA8K_PORT_LOOKUP_CTRL(i),
-+                                BIT(port));
-+      }
-+
-+      /* Set the cpu port to be the only one in the portvlan mask of
-+       * this port
-+       */
-+      qca8k_rmw(priv, QCA8K_PORT_LOOKUP_CTRL(port),
-+                QCA8K_PORT_LOOKUP_MEMBER, BIT(cpu_port));
-+}
---- a/drivers/net/dsa/qca/qca8k.h
-+++ b/drivers/net/dsa/qca/qca8k.h
-@@ -446,4 +446,11 @@ int qca8k_get_sset_count(struct dsa_swit
- int qca8k_set_mac_eee(struct dsa_switch *ds, int port, struct ethtool_eee *eee);
- int qca8k_get_mac_eee(struct dsa_switch *ds, int port, struct ethtool_eee *e);
-+/* Common bridge function */
-+void qca8k_port_stp_state_set(struct dsa_switch *ds, int port, u8 state);
-+int qca8k_port_bridge_join(struct dsa_switch *ds, int port,
-+                         struct net_device *br);
-+void qca8k_port_bridge_leave(struct dsa_switch *ds, int port,
-+                           struct net_device *br);
-+
- #endif /* __QCA8K_H */
diff --git a/target/linux/generic/backport-5.15/771-v6.0-09-net-dsa-qca8k-move-set-age-MTU-port-enable-disable-f.patch b/target/linux/generic/backport-5.15/771-v6.0-09-net-dsa-qca8k-move-set-age-MTU-port-enable-disable-f.patch
deleted file mode 100644 (file)
index e341440..0000000
+++ /dev/null
@@ -1,227 +0,0 @@
-From b3a302b171f73425b41de8d3357fae3fa7057322 Mon Sep 17 00:00:00 2001
-From: Christian Marangi <[email protected]>
-Date: Wed, 27 Jul 2022 13:35:18 +0200
-Subject: [PATCH 09/14] net: dsa: qca8k: move set age/MTU/port enable/disable
- functions to common code
-
-The same set age, MTU and port enable/disable function are used by
-driver based on qca8k family switch.
-Move them to common code to make them accessible also by other drivers.
-While at it also drop unnecessary qca8k_priv cast for void pointers.
-
-Signed-off-by: Christian Marangi <[email protected]>
-Reviewed-by: Vladimir Oltean <[email protected]>
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- drivers/net/dsa/qca/qca8k-8xxx.c   | 88 ------------------------------
- drivers/net/dsa/qca/qca8k-common.c | 85 +++++++++++++++++++++++++++++
- drivers/net/dsa/qca/qca8k.h        | 12 ++++
- 3 files changed, 97 insertions(+), 88 deletions(-)
-
---- a/drivers/net/dsa/qca/qca8k-8xxx.c
-+++ b/drivers/net/dsa/qca/qca8k-8xxx.c
-@@ -2059,94 +2059,6 @@ qca8k_port_fast_age(struct dsa_switch *d
- }
- static int
--qca8k_set_ageing_time(struct dsa_switch *ds, unsigned int msecs)
--{
--      struct qca8k_priv *priv = ds->priv;
--      unsigned int secs = msecs / 1000;
--      u32 val;
--
--      /* AGE_TIME reg is set in 7s step */
--      val = secs / 7;
--
--      /* Handle case with 0 as val to NOT disable
--       * learning
--       */
--      if (!val)
--              val = 1;
--
--      return regmap_update_bits(priv->regmap, QCA8K_REG_ATU_CTRL, QCA8K_ATU_AGE_TIME_MASK,
--                                QCA8K_ATU_AGE_TIME(val));
--}
--
--static int
--qca8k_port_enable(struct dsa_switch *ds, int port,
--                struct phy_device *phy)
--{
--      struct qca8k_priv *priv = (struct qca8k_priv *)ds->priv;
--
--      qca8k_port_set_status(priv, port, 1);
--      priv->port_enabled_map |= BIT(port);
--
--      if (dsa_is_user_port(ds, port))
--              phy_support_asym_pause(phy);
--
--      return 0;
--}
--
--static void
--qca8k_port_disable(struct dsa_switch *ds, int port)
--{
--      struct qca8k_priv *priv = (struct qca8k_priv *)ds->priv;
--
--      qca8k_port_set_status(priv, port, 0);
--      priv->port_enabled_map &= ~BIT(port);
--}
--
--static int
--qca8k_port_change_mtu(struct dsa_switch *ds, int port, int new_mtu)
--{
--      struct qca8k_priv *priv = ds->priv;
--      int ret;
--
--      /* We have only have a general MTU setting.
--       * DSA always set the CPU port's MTU to the largest MTU of the slave
--       * ports.
--       * Setting MTU just for the CPU port is sufficient to correctly set a
--       * value for every port.
--       */
--      if (!dsa_is_cpu_port(ds, port))
--              return 0;
--
--      /* To change the MAX_FRAME_SIZE the cpu ports must be off or
--       * the switch panics.
--       * Turn off both cpu ports before applying the new value to prevent
--       * this.
--       */
--      if (priv->port_enabled_map & BIT(0))
--              qca8k_port_set_status(priv, 0, 0);
--
--      if (priv->port_enabled_map & BIT(6))
--              qca8k_port_set_status(priv, 6, 0);
--
--      /* Include L2 header / FCS length */
--      ret = qca8k_write(priv, QCA8K_MAX_FRAME_SIZE, new_mtu + ETH_HLEN + ETH_FCS_LEN);
--
--      if (priv->port_enabled_map & BIT(0))
--              qca8k_port_set_status(priv, 0, 1);
--
--      if (priv->port_enabled_map & BIT(6))
--              qca8k_port_set_status(priv, 6, 1);
--
--      return ret;
--}
--
--static int
--qca8k_port_max_mtu(struct dsa_switch *ds, int port)
--{
--      return QCA8K_MAX_MTU;
--}
--
--static int
- qca8k_port_fdb_insert(struct qca8k_priv *priv, const u8 *addr,
-                     u16 port_mask, u16 vid)
- {
---- a/drivers/net/dsa/qca/qca8k-common.c
-+++ b/drivers/net/dsa/qca/qca8k-common.c
-@@ -367,3 +367,88 @@ void qca8k_port_bridge_leave(struct dsa_
-       qca8k_rmw(priv, QCA8K_PORT_LOOKUP_CTRL(port),
-                 QCA8K_PORT_LOOKUP_MEMBER, BIT(cpu_port));
- }
-+
-+int qca8k_set_ageing_time(struct dsa_switch *ds, unsigned int msecs)
-+{
-+      struct qca8k_priv *priv = ds->priv;
-+      unsigned int secs = msecs / 1000;
-+      u32 val;
-+
-+      /* AGE_TIME reg is set in 7s step */
-+      val = secs / 7;
-+
-+      /* Handle case with 0 as val to NOT disable
-+       * learning
-+       */
-+      if (!val)
-+              val = 1;
-+
-+      return regmap_update_bits(priv->regmap, QCA8K_REG_ATU_CTRL,
-+                                QCA8K_ATU_AGE_TIME_MASK,
-+                                QCA8K_ATU_AGE_TIME(val));
-+}
-+
-+int qca8k_port_enable(struct dsa_switch *ds, int port,
-+                    struct phy_device *phy)
-+{
-+      struct qca8k_priv *priv = ds->priv;
-+
-+      qca8k_port_set_status(priv, port, 1);
-+      priv->port_enabled_map |= BIT(port);
-+
-+      if (dsa_is_user_port(ds, port))
-+              phy_support_asym_pause(phy);
-+
-+      return 0;
-+}
-+
-+void qca8k_port_disable(struct dsa_switch *ds, int port)
-+{
-+      struct qca8k_priv *priv = ds->priv;
-+
-+      qca8k_port_set_status(priv, port, 0);
-+      priv->port_enabled_map &= ~BIT(port);
-+}
-+
-+int qca8k_port_change_mtu(struct dsa_switch *ds, int port, int new_mtu)
-+{
-+      struct qca8k_priv *priv = ds->priv;
-+      int ret;
-+
-+      /* We have only have a general MTU setting.
-+       * DSA always set the CPU port's MTU to the largest MTU of the slave
-+       * ports.
-+       * Setting MTU just for the CPU port is sufficient to correctly set a
-+       * value for every port.
-+       */
-+      if (!dsa_is_cpu_port(ds, port))
-+              return 0;
-+
-+      /* To change the MAX_FRAME_SIZE the cpu ports must be off or
-+       * the switch panics.
-+       * Turn off both cpu ports before applying the new value to prevent
-+       * this.
-+       */
-+      if (priv->port_enabled_map & BIT(0))
-+              qca8k_port_set_status(priv, 0, 0);
-+
-+      if (priv->port_enabled_map & BIT(6))
-+              qca8k_port_set_status(priv, 6, 0);
-+
-+      /* Include L2 header / FCS length */
-+      ret = qca8k_write(priv, QCA8K_MAX_FRAME_SIZE, new_mtu +
-+                        ETH_HLEN + ETH_FCS_LEN);
-+
-+      if (priv->port_enabled_map & BIT(0))
-+              qca8k_port_set_status(priv, 0, 1);
-+
-+      if (priv->port_enabled_map & BIT(6))
-+              qca8k_port_set_status(priv, 6, 1);
-+
-+      return ret;
-+}
-+
-+int qca8k_port_max_mtu(struct dsa_switch *ds, int port)
-+{
-+      return QCA8K_MAX_MTU;
-+}
---- a/drivers/net/dsa/qca/qca8k.h
-+++ b/drivers/net/dsa/qca/qca8k.h
-@@ -453,4 +453,16 @@ int qca8k_port_bridge_join(struct dsa_sw
- void qca8k_port_bridge_leave(struct dsa_switch *ds, int port,
-                            struct net_device *br);
-+/* Common port enable/disable function */
-+int qca8k_port_enable(struct dsa_switch *ds, int port,
-+                    struct phy_device *phy);
-+void qca8k_port_disable(struct dsa_switch *ds, int port);
-+
-+/* Common MTU function */
-+int qca8k_port_change_mtu(struct dsa_switch *ds, int port, int new_mtu);
-+int qca8k_port_max_mtu(struct dsa_switch *ds, int port);
-+
-+/* Common fast age function */
-+int qca8k_set_ageing_time(struct dsa_switch *ds, unsigned int msecs);
-+
- #endif /* __QCA8K_H */
diff --git a/target/linux/generic/backport-5.15/771-v6.0-10-net-dsa-qca8k-move-port-FDB-MDB-function-to-common-c.patch b/target/linux/generic/backport-5.15/771-v6.0-10-net-dsa-qca8k-move-port-FDB-MDB-function-to-common-c.patch
deleted file mode 100644 (file)
index 96468ae..0000000
+++ /dev/null
@@ -1,704 +0,0 @@
-From 2e5bd96eea86a246b4de3bf756f7a11b43e6187d Mon Sep 17 00:00:00 2001
-From: Christian Marangi <[email protected]>
-Date: Wed, 27 Jul 2022 13:35:19 +0200
-Subject: [PATCH 10/14] net: dsa: qca8k: move port FDB/MDB function to common
- code
-
-The same port FDB/MDB function are used by drivers based on qca8k family
-switch. Move them to common code to make them accessible also by other
-drivers.
-Also drop bulk read/write functions and make them static
-
-Signed-off-by: Christian Marangi <[email protected]>
-Reviewed-by: Vladimir Oltean <[email protected]>
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- drivers/net/dsa/qca/qca8k-8xxx.c   | 306 -----------------------------
- drivers/net/dsa/qca/qca8k-common.c | 297 +++++++++++++++++++++++++++-
- drivers/net/dsa/qca/qca8k.h        |  25 ++-
- 3 files changed, 317 insertions(+), 311 deletions(-)
-
---- a/drivers/net/dsa/qca/qca8k-8xxx.c
-+++ b/drivers/net/dsa/qca/qca8k-8xxx.c
-@@ -442,217 +442,6 @@ static struct regmap_config qca8k_regmap
- };
- static int
--qca8k_fdb_read(struct qca8k_priv *priv, struct qca8k_fdb *fdb)
--{
--      u32 reg[3];
--      int ret;
--
--      /* load the ARL table into an array */
--      ret = qca8k_bulk_read(priv, QCA8K_REG_ATU_DATA0, reg, sizeof(reg));
--      if (ret)
--              return ret;
--
--      /* vid - 83:72 */
--      fdb->vid = FIELD_GET(QCA8K_ATU_VID_MASK, reg[2]);
--      /* aging - 67:64 */
--      fdb->aging = FIELD_GET(QCA8K_ATU_STATUS_MASK, reg[2]);
--      /* portmask - 54:48 */
--      fdb->port_mask = FIELD_GET(QCA8K_ATU_PORT_MASK, reg[1]);
--      /* mac - 47:0 */
--      fdb->mac[0] = FIELD_GET(QCA8K_ATU_ADDR0_MASK, reg[1]);
--      fdb->mac[1] = FIELD_GET(QCA8K_ATU_ADDR1_MASK, reg[1]);
--      fdb->mac[2] = FIELD_GET(QCA8K_ATU_ADDR2_MASK, reg[0]);
--      fdb->mac[3] = FIELD_GET(QCA8K_ATU_ADDR3_MASK, reg[0]);
--      fdb->mac[4] = FIELD_GET(QCA8K_ATU_ADDR4_MASK, reg[0]);
--      fdb->mac[5] = FIELD_GET(QCA8K_ATU_ADDR5_MASK, reg[0]);
--
--      return 0;
--}
--
--static void
--qca8k_fdb_write(struct qca8k_priv *priv, u16 vid, u8 port_mask, const u8 *mac,
--              u8 aging)
--{
--      u32 reg[3] = { 0 };
--
--      /* vid - 83:72 */
--      reg[2] = FIELD_PREP(QCA8K_ATU_VID_MASK, vid);
--      /* aging - 67:64 */
--      reg[2] |= FIELD_PREP(QCA8K_ATU_STATUS_MASK, aging);
--      /* portmask - 54:48 */
--      reg[1] = FIELD_PREP(QCA8K_ATU_PORT_MASK, port_mask);
--      /* mac - 47:0 */
--      reg[1] |= FIELD_PREP(QCA8K_ATU_ADDR0_MASK, mac[0]);
--      reg[1] |= FIELD_PREP(QCA8K_ATU_ADDR1_MASK, mac[1]);
--      reg[0] |= FIELD_PREP(QCA8K_ATU_ADDR2_MASK, mac[2]);
--      reg[0] |= FIELD_PREP(QCA8K_ATU_ADDR3_MASK, mac[3]);
--      reg[0] |= FIELD_PREP(QCA8K_ATU_ADDR4_MASK, mac[4]);
--      reg[0] |= FIELD_PREP(QCA8K_ATU_ADDR5_MASK, mac[5]);
--
--      /* load the array into the ARL table */
--      qca8k_bulk_write(priv, QCA8K_REG_ATU_DATA0, reg, sizeof(reg));
--}
--
--static int
--qca8k_fdb_access(struct qca8k_priv *priv, enum qca8k_fdb_cmd cmd, int port)
--{
--      u32 reg;
--      int ret;
--
--      /* Set the command and FDB index */
--      reg = QCA8K_ATU_FUNC_BUSY;
--      reg |= cmd;
--      if (port >= 0) {
--              reg |= QCA8K_ATU_FUNC_PORT_EN;
--              reg |= FIELD_PREP(QCA8K_ATU_FUNC_PORT_MASK, port);
--      }
--
--      /* Write the function register triggering the table access */
--      ret = qca8k_write(priv, QCA8K_REG_ATU_FUNC, reg);
--      if (ret)
--              return ret;
--
--      /* wait for completion */
--      ret = qca8k_busy_wait(priv, QCA8K_REG_ATU_FUNC, QCA8K_ATU_FUNC_BUSY);
--      if (ret)
--              return ret;
--
--      /* Check for table full violation when adding an entry */
--      if (cmd == QCA8K_FDB_LOAD) {
--              ret = qca8k_read(priv, QCA8K_REG_ATU_FUNC, &reg);
--              if (ret < 0)
--                      return ret;
--              if (reg & QCA8K_ATU_FUNC_FULL)
--                      return -1;
--      }
--
--      return 0;
--}
--
--static int
--qca8k_fdb_next(struct qca8k_priv *priv, struct qca8k_fdb *fdb, int port)
--{
--      int ret;
--
--      qca8k_fdb_write(priv, fdb->vid, fdb->port_mask, fdb->mac, fdb->aging);
--      ret = qca8k_fdb_access(priv, QCA8K_FDB_NEXT, port);
--      if (ret < 0)
--              return ret;
--
--      return qca8k_fdb_read(priv, fdb);
--}
--
--static int
--qca8k_fdb_add(struct qca8k_priv *priv, const u8 *mac, u16 port_mask,
--            u16 vid, u8 aging)
--{
--      int ret;
--
--      mutex_lock(&priv->reg_mutex);
--      qca8k_fdb_write(priv, vid, port_mask, mac, aging);
--      ret = qca8k_fdb_access(priv, QCA8K_FDB_LOAD, -1);
--      mutex_unlock(&priv->reg_mutex);
--
--      return ret;
--}
--
--static int
--qca8k_fdb_del(struct qca8k_priv *priv, const u8 *mac, u16 port_mask, u16 vid)
--{
--      int ret;
--
--      mutex_lock(&priv->reg_mutex);
--      qca8k_fdb_write(priv, vid, port_mask, mac, 0);
--      ret = qca8k_fdb_access(priv, QCA8K_FDB_PURGE, -1);
--      mutex_unlock(&priv->reg_mutex);
--
--      return ret;
--}
--
--static void
--qca8k_fdb_flush(struct qca8k_priv *priv)
--{
--      mutex_lock(&priv->reg_mutex);
--      qca8k_fdb_access(priv, QCA8K_FDB_FLUSH, -1);
--      mutex_unlock(&priv->reg_mutex);
--}
--
--static int
--qca8k_fdb_search_and_insert(struct qca8k_priv *priv, u8 port_mask,
--                          const u8 *mac, u16 vid)
--{
--      struct qca8k_fdb fdb = { 0 };
--      int ret;
--
--      mutex_lock(&priv->reg_mutex);
--
--      qca8k_fdb_write(priv, vid, 0, mac, 0);
--      ret = qca8k_fdb_access(priv, QCA8K_FDB_SEARCH, -1);
--      if (ret < 0)
--              goto exit;
--
--      ret = qca8k_fdb_read(priv, &fdb);
--      if (ret < 0)
--              goto exit;
--
--      /* Rule exist. Delete first */
--      if (!fdb.aging) {
--              ret = qca8k_fdb_access(priv, QCA8K_FDB_PURGE, -1);
--              if (ret)
--                      goto exit;
--      }
--
--      /* Add port to fdb portmask */
--      fdb.port_mask |= port_mask;
--
--      qca8k_fdb_write(priv, vid, fdb.port_mask, mac, fdb.aging);
--      ret = qca8k_fdb_access(priv, QCA8K_FDB_LOAD, -1);
--
--exit:
--      mutex_unlock(&priv->reg_mutex);
--      return ret;
--}
--
--static int
--qca8k_fdb_search_and_del(struct qca8k_priv *priv, u8 port_mask,
--                       const u8 *mac, u16 vid)
--{
--      struct qca8k_fdb fdb = { 0 };
--      int ret;
--
--      mutex_lock(&priv->reg_mutex);
--
--      qca8k_fdb_write(priv, vid, 0, mac, 0);
--      ret = qca8k_fdb_access(priv, QCA8K_FDB_SEARCH, -1);
--      if (ret < 0)
--              goto exit;
--
--      /* Rule doesn't exist. Why delete? */
--      if (!fdb.aging) {
--              ret = -EINVAL;
--              goto exit;
--      }
--
--      ret = qca8k_fdb_access(priv, QCA8K_FDB_PURGE, -1);
--      if (ret)
--              goto exit;
--
--      /* Only port in the rule is this port. Don't re insert */
--      if (fdb.port_mask == port_mask)
--              goto exit;
--
--      /* Remove port from port mask */
--      fdb.port_mask &= ~port_mask;
--
--      qca8k_fdb_write(priv, vid, fdb.port_mask, mac, fdb.aging);
--      ret = qca8k_fdb_access(priv, QCA8K_FDB_LOAD, -1);
--
--exit:
--      mutex_unlock(&priv->reg_mutex);
--      return ret;
--}
--
--static int
- qca8k_vlan_access(struct qca8k_priv *priv, enum qca8k_vlan_cmd cmd, u16 vid)
- {
-       u32 reg;
-@@ -2048,97 +1837,6 @@ exit:
-       return ret;
- }
--static void
--qca8k_port_fast_age(struct dsa_switch *ds, int port)
--{
--      struct qca8k_priv *priv = ds->priv;
--
--      mutex_lock(&priv->reg_mutex);
--      qca8k_fdb_access(priv, QCA8K_FDB_FLUSH_PORT, port);
--      mutex_unlock(&priv->reg_mutex);
--}
--
--static int
--qca8k_port_fdb_insert(struct qca8k_priv *priv, const u8 *addr,
--                    u16 port_mask, u16 vid)
--{
--      /* Set the vid to the port vlan id if no vid is set */
--      if (!vid)
--              vid = QCA8K_PORT_VID_DEF;
--
--      return qca8k_fdb_add(priv, addr, port_mask, vid,
--                           QCA8K_ATU_STATUS_STATIC);
--}
--
--static int
--qca8k_port_fdb_add(struct dsa_switch *ds, int port,
--                 const unsigned char *addr, u16 vid)
--{
--      struct qca8k_priv *priv = (struct qca8k_priv *)ds->priv;
--      u16 port_mask = BIT(port);
--
--      return qca8k_port_fdb_insert(priv, addr, port_mask, vid);
--}
--
--static int
--qca8k_port_fdb_del(struct dsa_switch *ds, int port,
--                 const unsigned char *addr, u16 vid)
--{
--      struct qca8k_priv *priv = (struct qca8k_priv *)ds->priv;
--      u16 port_mask = BIT(port);
--
--      if (!vid)
--              vid = QCA8K_PORT_VID_DEF;
--
--      return qca8k_fdb_del(priv, addr, port_mask, vid);
--}
--
--static int
--qca8k_port_fdb_dump(struct dsa_switch *ds, int port,
--                  dsa_fdb_dump_cb_t *cb, void *data)
--{
--      struct qca8k_priv *priv = (struct qca8k_priv *)ds->priv;
--      struct qca8k_fdb _fdb = { 0 };
--      int cnt = QCA8K_NUM_FDB_RECORDS;
--      bool is_static;
--      int ret = 0;
--
--      mutex_lock(&priv->reg_mutex);
--      while (cnt-- && !qca8k_fdb_next(priv, &_fdb, port)) {
--              if (!_fdb.aging)
--                      break;
--              is_static = (_fdb.aging == QCA8K_ATU_STATUS_STATIC);
--              ret = cb(_fdb.mac, _fdb.vid, is_static, data);
--              if (ret)
--                      break;
--      }
--      mutex_unlock(&priv->reg_mutex);
--
--      return 0;
--}
--
--static int
--qca8k_port_mdb_add(struct dsa_switch *ds, int port,
--                 const struct switchdev_obj_port_mdb *mdb)
--{
--      struct qca8k_priv *priv = ds->priv;
--      const u8 *addr = mdb->addr;
--      u16 vid = mdb->vid;
--
--      return qca8k_fdb_search_and_insert(priv, BIT(port), addr, vid);
--}
--
--static int
--qca8k_port_mdb_del(struct dsa_switch *ds, int port,
--                 const struct switchdev_obj_port_mdb *mdb)
--{
--      struct qca8k_priv *priv = ds->priv;
--      const u8 *addr = mdb->addr;
--      u16 vid = mdb->vid;
--
--      return qca8k_fdb_search_and_del(priv, BIT(port), addr, vid);
--}
--
- static int
- qca8k_port_mirror_add(struct dsa_switch *ds, int port,
-                     struct dsa_mall_mirror_tc_entry *mirror,
---- a/drivers/net/dsa/qca/qca8k-common.c
-+++ b/drivers/net/dsa/qca/qca8k-common.c
-@@ -103,7 +103,7 @@ const struct regmap_access_table qca8k_r
- };
- /* TODO: remove these extra ops when we can support regmap bulk read/write */
--int qca8k_bulk_read(struct qca8k_priv *priv, u32 reg, u32 *val, int len)
-+static int qca8k_bulk_read(struct qca8k_priv *priv, u32 reg, u32 *val, int len)
- {
-       int i, count = len / sizeof(u32), ret;
-@@ -121,7 +121,7 @@ int qca8k_bulk_read(struct qca8k_priv *p
- }
- /* TODO: remove these extra ops when we can support regmap bulk read/write */
--int qca8k_bulk_write(struct qca8k_priv *priv, u32 reg, u32 *val, int len)
-+static int qca8k_bulk_write(struct qca8k_priv *priv, u32 reg, u32 *val, int len)
- {
-       int i, count = len / sizeof(u32), ret;
-       u32 tmp;
-@@ -149,6 +149,211 @@ int qca8k_busy_wait(struct qca8k_priv *p
-                                      QCA8K_BUSY_WAIT_TIMEOUT * USEC_PER_MSEC);
- }
-+static int qca8k_fdb_read(struct qca8k_priv *priv, struct qca8k_fdb *fdb)
-+{
-+      u32 reg[3];
-+      int ret;
-+
-+      /* load the ARL table into an array */
-+      ret = qca8k_bulk_read(priv, QCA8K_REG_ATU_DATA0, reg, sizeof(reg));
-+      if (ret)
-+              return ret;
-+
-+      /* vid - 83:72 */
-+      fdb->vid = FIELD_GET(QCA8K_ATU_VID_MASK, reg[2]);
-+      /* aging - 67:64 */
-+      fdb->aging = FIELD_GET(QCA8K_ATU_STATUS_MASK, reg[2]);
-+      /* portmask - 54:48 */
-+      fdb->port_mask = FIELD_GET(QCA8K_ATU_PORT_MASK, reg[1]);
-+      /* mac - 47:0 */
-+      fdb->mac[0] = FIELD_GET(QCA8K_ATU_ADDR0_MASK, reg[1]);
-+      fdb->mac[1] = FIELD_GET(QCA8K_ATU_ADDR1_MASK, reg[1]);
-+      fdb->mac[2] = FIELD_GET(QCA8K_ATU_ADDR2_MASK, reg[0]);
-+      fdb->mac[3] = FIELD_GET(QCA8K_ATU_ADDR3_MASK, reg[0]);
-+      fdb->mac[4] = FIELD_GET(QCA8K_ATU_ADDR4_MASK, reg[0]);
-+      fdb->mac[5] = FIELD_GET(QCA8K_ATU_ADDR5_MASK, reg[0]);
-+
-+      return 0;
-+}
-+
-+static void qca8k_fdb_write(struct qca8k_priv *priv, u16 vid, u8 port_mask,
-+                          const u8 *mac, u8 aging)
-+{
-+      u32 reg[3] = { 0 };
-+
-+      /* vid - 83:72 */
-+      reg[2] = FIELD_PREP(QCA8K_ATU_VID_MASK, vid);
-+      /* aging - 67:64 */
-+      reg[2] |= FIELD_PREP(QCA8K_ATU_STATUS_MASK, aging);
-+      /* portmask - 54:48 */
-+      reg[1] = FIELD_PREP(QCA8K_ATU_PORT_MASK, port_mask);
-+      /* mac - 47:0 */
-+      reg[1] |= FIELD_PREP(QCA8K_ATU_ADDR0_MASK, mac[0]);
-+      reg[1] |= FIELD_PREP(QCA8K_ATU_ADDR1_MASK, mac[1]);
-+      reg[0] |= FIELD_PREP(QCA8K_ATU_ADDR2_MASK, mac[2]);
-+      reg[0] |= FIELD_PREP(QCA8K_ATU_ADDR3_MASK, mac[3]);
-+      reg[0] |= FIELD_PREP(QCA8K_ATU_ADDR4_MASK, mac[4]);
-+      reg[0] |= FIELD_PREP(QCA8K_ATU_ADDR5_MASK, mac[5]);
-+
-+      /* load the array into the ARL table */
-+      qca8k_bulk_write(priv, QCA8K_REG_ATU_DATA0, reg, sizeof(reg));
-+}
-+
-+static int qca8k_fdb_access(struct qca8k_priv *priv, enum qca8k_fdb_cmd cmd,
-+                          int port)
-+{
-+      u32 reg;
-+      int ret;
-+
-+      /* Set the command and FDB index */
-+      reg = QCA8K_ATU_FUNC_BUSY;
-+      reg |= cmd;
-+      if (port >= 0) {
-+              reg |= QCA8K_ATU_FUNC_PORT_EN;
-+              reg |= FIELD_PREP(QCA8K_ATU_FUNC_PORT_MASK, port);
-+      }
-+
-+      /* Write the function register triggering the table access */
-+      ret = qca8k_write(priv, QCA8K_REG_ATU_FUNC, reg);
-+      if (ret)
-+              return ret;
-+
-+      /* wait for completion */
-+      ret = qca8k_busy_wait(priv, QCA8K_REG_ATU_FUNC, QCA8K_ATU_FUNC_BUSY);
-+      if (ret)
-+              return ret;
-+
-+      /* Check for table full violation when adding an entry */
-+      if (cmd == QCA8K_FDB_LOAD) {
-+              ret = qca8k_read(priv, QCA8K_REG_ATU_FUNC, &reg);
-+              if (ret < 0)
-+                      return ret;
-+              if (reg & QCA8K_ATU_FUNC_FULL)
-+                      return -1;
-+      }
-+
-+      return 0;
-+}
-+
-+static int qca8k_fdb_next(struct qca8k_priv *priv, struct qca8k_fdb *fdb,
-+                        int port)
-+{
-+      int ret;
-+
-+      qca8k_fdb_write(priv, fdb->vid, fdb->port_mask, fdb->mac, fdb->aging);
-+      ret = qca8k_fdb_access(priv, QCA8K_FDB_NEXT, port);
-+      if (ret < 0)
-+              return ret;
-+
-+      return qca8k_fdb_read(priv, fdb);
-+}
-+
-+static int qca8k_fdb_add(struct qca8k_priv *priv, const u8 *mac,
-+                       u16 port_mask, u16 vid, u8 aging)
-+{
-+      int ret;
-+
-+      mutex_lock(&priv->reg_mutex);
-+      qca8k_fdb_write(priv, vid, port_mask, mac, aging);
-+      ret = qca8k_fdb_access(priv, QCA8K_FDB_LOAD, -1);
-+      mutex_unlock(&priv->reg_mutex);
-+
-+      return ret;
-+}
-+
-+static int qca8k_fdb_del(struct qca8k_priv *priv, const u8 *mac,
-+                       u16 port_mask, u16 vid)
-+{
-+      int ret;
-+
-+      mutex_lock(&priv->reg_mutex);
-+      qca8k_fdb_write(priv, vid, port_mask, mac, 0);
-+      ret = qca8k_fdb_access(priv, QCA8K_FDB_PURGE, -1);
-+      mutex_unlock(&priv->reg_mutex);
-+
-+      return ret;
-+}
-+
-+void qca8k_fdb_flush(struct qca8k_priv *priv)
-+{
-+      mutex_lock(&priv->reg_mutex);
-+      qca8k_fdb_access(priv, QCA8K_FDB_FLUSH, -1);
-+      mutex_unlock(&priv->reg_mutex);
-+}
-+
-+static int qca8k_fdb_search_and_insert(struct qca8k_priv *priv, u8 port_mask,
-+                                     const u8 *mac, u16 vid)
-+{
-+      struct qca8k_fdb fdb = { 0 };
-+      int ret;
-+
-+      mutex_lock(&priv->reg_mutex);
-+
-+      qca8k_fdb_write(priv, vid, 0, mac, 0);
-+      ret = qca8k_fdb_access(priv, QCA8K_FDB_SEARCH, -1);
-+      if (ret < 0)
-+              goto exit;
-+
-+      ret = qca8k_fdb_read(priv, &fdb);
-+      if (ret < 0)
-+              goto exit;
-+
-+      /* Rule exist. Delete first */
-+      if (!fdb.aging) {
-+              ret = qca8k_fdb_access(priv, QCA8K_FDB_PURGE, -1);
-+              if (ret)
-+                      goto exit;
-+      }
-+
-+      /* Add port to fdb portmask */
-+      fdb.port_mask |= port_mask;
-+
-+      qca8k_fdb_write(priv, vid, fdb.port_mask, mac, fdb.aging);
-+      ret = qca8k_fdb_access(priv, QCA8K_FDB_LOAD, -1);
-+
-+exit:
-+      mutex_unlock(&priv->reg_mutex);
-+      return ret;
-+}
-+
-+static int qca8k_fdb_search_and_del(struct qca8k_priv *priv, u8 port_mask,
-+                                  const u8 *mac, u16 vid)
-+{
-+      struct qca8k_fdb fdb = { 0 };
-+      int ret;
-+
-+      mutex_lock(&priv->reg_mutex);
-+
-+      qca8k_fdb_write(priv, vid, 0, mac, 0);
-+      ret = qca8k_fdb_access(priv, QCA8K_FDB_SEARCH, -1);
-+      if (ret < 0)
-+              goto exit;
-+
-+      /* Rule doesn't exist. Why delete? */
-+      if (!fdb.aging) {
-+              ret = -EINVAL;
-+              goto exit;
-+      }
-+
-+      ret = qca8k_fdb_access(priv, QCA8K_FDB_PURGE, -1);
-+      if (ret)
-+              goto exit;
-+
-+      /* Only port in the rule is this port. Don't re insert */
-+      if (fdb.port_mask == port_mask)
-+              goto exit;
-+
-+      /* Remove port from port mask */
-+      fdb.port_mask &= ~port_mask;
-+
-+      qca8k_fdb_write(priv, vid, fdb.port_mask, mac, fdb.aging);
-+      ret = qca8k_fdb_access(priv, QCA8K_FDB_LOAD, -1);
-+
-+exit:
-+      mutex_unlock(&priv->reg_mutex);
-+      return ret;
-+}
-+
- int qca8k_mib_init(struct qca8k_priv *priv)
- {
-       int ret;
-@@ -368,6 +573,15 @@ void qca8k_port_bridge_leave(struct dsa_
-                 QCA8K_PORT_LOOKUP_MEMBER, BIT(cpu_port));
- }
-+void qca8k_port_fast_age(struct dsa_switch *ds, int port)
-+{
-+      struct qca8k_priv *priv = ds->priv;
-+
-+      mutex_lock(&priv->reg_mutex);
-+      qca8k_fdb_access(priv, QCA8K_FDB_FLUSH_PORT, port);
-+      mutex_unlock(&priv->reg_mutex);
-+}
-+
- int qca8k_set_ageing_time(struct dsa_switch *ds, unsigned int msecs)
- {
-       struct qca8k_priv *priv = ds->priv;
-@@ -452,3 +666,78 @@ int qca8k_port_max_mtu(struct dsa_switch
- {
-       return QCA8K_MAX_MTU;
- }
-+
-+int qca8k_port_fdb_insert(struct qca8k_priv *priv, const u8 *addr,
-+                        u16 port_mask, u16 vid)
-+{
-+      /* Set the vid to the port vlan id if no vid is set */
-+      if (!vid)
-+              vid = QCA8K_PORT_VID_DEF;
-+
-+      return qca8k_fdb_add(priv, addr, port_mask, vid,
-+                           QCA8K_ATU_STATUS_STATIC);
-+}
-+
-+int qca8k_port_fdb_add(struct dsa_switch *ds, int port,
-+                     const unsigned char *addr, u16 vid)
-+{
-+      struct qca8k_priv *priv = (struct qca8k_priv *)ds->priv;
-+      u16 port_mask = BIT(port);
-+
-+      return qca8k_port_fdb_insert(priv, addr, port_mask, vid);
-+}
-+
-+int qca8k_port_fdb_del(struct dsa_switch *ds, int port,
-+                     const unsigned char *addr, u16 vid)
-+{
-+      struct qca8k_priv *priv = (struct qca8k_priv *)ds->priv;
-+      u16 port_mask = BIT(port);
-+
-+      if (!vid)
-+              vid = QCA8K_PORT_VID_DEF;
-+
-+      return qca8k_fdb_del(priv, addr, port_mask, vid);
-+}
-+
-+int qca8k_port_fdb_dump(struct dsa_switch *ds, int port,
-+                      dsa_fdb_dump_cb_t *cb, void *data)
-+{
-+      struct qca8k_priv *priv = (struct qca8k_priv *)ds->priv;
-+      struct qca8k_fdb _fdb = { 0 };
-+      int cnt = QCA8K_NUM_FDB_RECORDS;
-+      bool is_static;
-+      int ret = 0;
-+
-+      mutex_lock(&priv->reg_mutex);
-+      while (cnt-- && !qca8k_fdb_next(priv, &_fdb, port)) {
-+              if (!_fdb.aging)
-+                      break;
-+              is_static = (_fdb.aging == QCA8K_ATU_STATUS_STATIC);
-+              ret = cb(_fdb.mac, _fdb.vid, is_static, data);
-+              if (ret)
-+                      break;
-+      }
-+      mutex_unlock(&priv->reg_mutex);
-+
-+      return 0;
-+}
-+
-+int qca8k_port_mdb_add(struct dsa_switch *ds, int port,
-+                     const struct switchdev_obj_port_mdb *mdb)
-+{
-+      struct qca8k_priv *priv = ds->priv;
-+      const u8 *addr = mdb->addr;
-+      u16 vid = mdb->vid;
-+
-+      return qca8k_fdb_search_and_insert(priv, BIT(port), addr, vid);
-+}
-+
-+int qca8k_port_mdb_del(struct dsa_switch *ds, int port,
-+                     const struct switchdev_obj_port_mdb *mdb)
-+{
-+      struct qca8k_priv *priv = ds->priv;
-+      const u8 *addr = mdb->addr;
-+      u16 vid = mdb->vid;
-+
-+      return qca8k_fdb_search_and_del(priv, BIT(port), addr, vid);
-+}
---- a/drivers/net/dsa/qca/qca8k.h
-+++ b/drivers/net/dsa/qca/qca8k.h
-@@ -430,11 +430,9 @@ int qca8k_read(struct qca8k_priv *priv,
- int qca8k_write(struct qca8k_priv *priv, u32 reg, u32 val);
- int qca8k_rmw(struct qca8k_priv *priv, u32 reg, u32 mask, u32 write_val);
--int qca8k_bulk_read(struct qca8k_priv *priv, u32 reg, u32 *val, int len);
--int qca8k_bulk_write(struct qca8k_priv *priv, u32 reg, u32 *val, int len);
--
- /* Common ops function */
- int qca8k_busy_wait(struct qca8k_priv *priv, u32 reg, u32 mask);
-+void qca8k_fdb_flush(struct qca8k_priv *priv);
- /* Common ethtool stats function */
- void qca8k_get_strings(struct dsa_switch *ds, int port, u32 stringset, uint8_t *data);
-@@ -463,6 +461,23 @@ int qca8k_port_change_mtu(struct dsa_swi
- int qca8k_port_max_mtu(struct dsa_switch *ds, int port);
- /* Common fast age function */
-+void qca8k_port_fast_age(struct dsa_switch *ds, int port);
- int qca8k_set_ageing_time(struct dsa_switch *ds, unsigned int msecs);
-+/* Common FDB function */
-+int qca8k_port_fdb_insert(struct qca8k_priv *priv, const u8 *addr,
-+                        u16 port_mask, u16 vid);
-+int qca8k_port_fdb_add(struct dsa_switch *ds, int port,
-+                     const unsigned char *addr, u16 vid);
-+int qca8k_port_fdb_del(struct dsa_switch *ds, int port,
-+                     const unsigned char *addr, u16 vid);
-+int qca8k_port_fdb_dump(struct dsa_switch *ds, int port,
-+                      dsa_fdb_dump_cb_t *cb, void *data);
-+
-+/* Common MDB function */
-+int qca8k_port_mdb_add(struct dsa_switch *ds, int port,
-+                     const struct switchdev_obj_port_mdb *mdb);
-+int qca8k_port_mdb_del(struct dsa_switch *ds, int port,
-+                     const struct switchdev_obj_port_mdb *mdb);
-+
- #endif /* __QCA8K_H */
diff --git a/target/linux/generic/backport-5.15/771-v6.0-11-net-dsa-qca8k-move-port-mirror-functions-to-common-c.patch b/target/linux/generic/backport-5.15/771-v6.0-11-net-dsa-qca8k-move-port-mirror-functions-to-common-c.patch
deleted file mode 100644 (file)
index c1336d4..0000000
+++ /dev/null
@@ -1,232 +0,0 @@
-From 742d37a84d3f7bb60d9b2d9ada9ad4e599f65ebf Mon Sep 17 00:00:00 2001
-From: Christian Marangi <[email protected]>
-Date: Wed, 27 Jul 2022 13:35:20 +0200
-Subject: [PATCH 11/14] net: dsa: qca8k: move port mirror functions to common
- code
-
-The same port mirror functions are used by drivers based on qca8k family
-switch. Move them to common code to make them accessible also by other
-drivers.
-
-Signed-off-by: Christian Marangi <[email protected]>
-Reviewed-by: Vladimir Oltean <[email protected]>
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- drivers/net/dsa/qca/qca8k-8xxx.c   | 93 ------------------------------
- drivers/net/dsa/qca/qca8k-common.c | 91 +++++++++++++++++++++++++++++
- drivers/net/dsa/qca/qca8k.h        |  7 +++
- 3 files changed, 98 insertions(+), 93 deletions(-)
-
---- a/drivers/net/dsa/qca/qca8k-8xxx.c
-+++ b/drivers/net/dsa/qca/qca8k-8xxx.c
-@@ -1838,99 +1838,6 @@ exit:
- }
- static int
--qca8k_port_mirror_add(struct dsa_switch *ds, int port,
--                    struct dsa_mall_mirror_tc_entry *mirror,
--                    bool ingress)
--{
--      struct qca8k_priv *priv = ds->priv;
--      int monitor_port, ret;
--      u32 reg, val;
--
--      /* Check for existent entry */
--      if ((ingress ? priv->mirror_rx : priv->mirror_tx) & BIT(port))
--              return -EEXIST;
--
--      ret = regmap_read(priv->regmap, QCA8K_REG_GLOBAL_FW_CTRL0, &val);
--      if (ret)
--              return ret;
--
--      /* QCA83xx can have only one port set to mirror mode.
--       * Check that the correct port is requested and return error otherwise.
--       * When no mirror port is set, the values is set to 0xF
--       */
--      monitor_port = FIELD_GET(QCA8K_GLOBAL_FW_CTRL0_MIRROR_PORT_NUM, val);
--      if (monitor_port != 0xF && monitor_port != mirror->to_local_port)
--              return -EEXIST;
--
--      /* Set the monitor port */
--      val = FIELD_PREP(QCA8K_GLOBAL_FW_CTRL0_MIRROR_PORT_NUM,
--                       mirror->to_local_port);
--      ret = regmap_update_bits(priv->regmap, QCA8K_REG_GLOBAL_FW_CTRL0,
--                               QCA8K_GLOBAL_FW_CTRL0_MIRROR_PORT_NUM, val);
--      if (ret)
--              return ret;
--
--      if (ingress) {
--              reg = QCA8K_PORT_LOOKUP_CTRL(port);
--              val = QCA8K_PORT_LOOKUP_ING_MIRROR_EN;
--      } else {
--              reg = QCA8K_REG_PORT_HOL_CTRL1(port);
--              val = QCA8K_PORT_HOL_CTRL1_EG_MIRROR_EN;
--      }
--
--      ret = regmap_update_bits(priv->regmap, reg, val, val);
--      if (ret)
--              return ret;
--
--      /* Track mirror port for tx and rx to decide when the
--       * mirror port has to be disabled.
--       */
--      if (ingress)
--              priv->mirror_rx |= BIT(port);
--      else
--              priv->mirror_tx |= BIT(port);
--
--      return 0;
--}
--
--static void
--qca8k_port_mirror_del(struct dsa_switch *ds, int port,
--                    struct dsa_mall_mirror_tc_entry *mirror)
--{
--      struct qca8k_priv *priv = ds->priv;
--      u32 reg, val;
--      int ret;
--
--      if (mirror->ingress) {
--              reg = QCA8K_PORT_LOOKUP_CTRL(port);
--              val = QCA8K_PORT_LOOKUP_ING_MIRROR_EN;
--      } else {
--              reg = QCA8K_REG_PORT_HOL_CTRL1(port);
--              val = QCA8K_PORT_HOL_CTRL1_EG_MIRROR_EN;
--      }
--
--      ret = regmap_clear_bits(priv->regmap, reg, val);
--      if (ret)
--              goto err;
--
--      if (mirror->ingress)
--              priv->mirror_rx &= ~BIT(port);
--      else
--              priv->mirror_tx &= ~BIT(port);
--
--      /* No port set to send packet to mirror port. Disable mirror port */
--      if (!priv->mirror_rx && !priv->mirror_tx) {
--              val = FIELD_PREP(QCA8K_GLOBAL_FW_CTRL0_MIRROR_PORT_NUM, 0xF);
--              ret = regmap_update_bits(priv->regmap, QCA8K_REG_GLOBAL_FW_CTRL0,
--                                       QCA8K_GLOBAL_FW_CTRL0_MIRROR_PORT_NUM, val);
--              if (ret)
--                      goto err;
--      }
--err:
--      dev_err(priv->dev, "Failed to del mirror port from %d", port);
--}
--
--static int
- qca8k_port_vlan_filtering(struct dsa_switch *ds, int port, bool vlan_filtering,
-                         struct netlink_ext_ack *extack)
- {
---- a/drivers/net/dsa/qca/qca8k-common.c
-+++ b/drivers/net/dsa/qca/qca8k-common.c
-@@ -741,3 +741,94 @@ int qca8k_port_mdb_del(struct dsa_switch
-       return qca8k_fdb_search_and_del(priv, BIT(port), addr, vid);
- }
-+
-+int qca8k_port_mirror_add(struct dsa_switch *ds, int port,
-+                        struct dsa_mall_mirror_tc_entry *mirror,
-+                        bool ingress)
-+{
-+      struct qca8k_priv *priv = ds->priv;
-+      int monitor_port, ret;
-+      u32 reg, val;
-+
-+      /* Check for existent entry */
-+      if ((ingress ? priv->mirror_rx : priv->mirror_tx) & BIT(port))
-+              return -EEXIST;
-+
-+      ret = regmap_read(priv->regmap, QCA8K_REG_GLOBAL_FW_CTRL0, &val);
-+      if (ret)
-+              return ret;
-+
-+      /* QCA83xx can have only one port set to mirror mode.
-+       * Check that the correct port is requested and return error otherwise.
-+       * When no mirror port is set, the values is set to 0xF
-+       */
-+      monitor_port = FIELD_GET(QCA8K_GLOBAL_FW_CTRL0_MIRROR_PORT_NUM, val);
-+      if (monitor_port != 0xF && monitor_port != mirror->to_local_port)
-+              return -EEXIST;
-+
-+      /* Set the monitor port */
-+      val = FIELD_PREP(QCA8K_GLOBAL_FW_CTRL0_MIRROR_PORT_NUM,
-+                       mirror->to_local_port);
-+      ret = regmap_update_bits(priv->regmap, QCA8K_REG_GLOBAL_FW_CTRL0,
-+                               QCA8K_GLOBAL_FW_CTRL0_MIRROR_PORT_NUM, val);
-+      if (ret)
-+              return ret;
-+
-+      if (ingress) {
-+              reg = QCA8K_PORT_LOOKUP_CTRL(port);
-+              val = QCA8K_PORT_LOOKUP_ING_MIRROR_EN;
-+      } else {
-+              reg = QCA8K_REG_PORT_HOL_CTRL1(port);
-+              val = QCA8K_PORT_HOL_CTRL1_EG_MIRROR_EN;
-+      }
-+
-+      ret = regmap_update_bits(priv->regmap, reg, val, val);
-+      if (ret)
-+              return ret;
-+
-+      /* Track mirror port for tx and rx to decide when the
-+       * mirror port has to be disabled.
-+       */
-+      if (ingress)
-+              priv->mirror_rx |= BIT(port);
-+      else
-+              priv->mirror_tx |= BIT(port);
-+
-+      return 0;
-+}
-+
-+void qca8k_port_mirror_del(struct dsa_switch *ds, int port,
-+                         struct dsa_mall_mirror_tc_entry *mirror)
-+{
-+      struct qca8k_priv *priv = ds->priv;
-+      u32 reg, val;
-+      int ret;
-+
-+      if (mirror->ingress) {
-+              reg = QCA8K_PORT_LOOKUP_CTRL(port);
-+              val = QCA8K_PORT_LOOKUP_ING_MIRROR_EN;
-+      } else {
-+              reg = QCA8K_REG_PORT_HOL_CTRL1(port);
-+              val = QCA8K_PORT_HOL_CTRL1_EG_MIRROR_EN;
-+      }
-+
-+      ret = regmap_clear_bits(priv->regmap, reg, val);
-+      if (ret)
-+              goto err;
-+
-+      if (mirror->ingress)
-+              priv->mirror_rx &= ~BIT(port);
-+      else
-+              priv->mirror_tx &= ~BIT(port);
-+
-+      /* No port set to send packet to mirror port. Disable mirror port */
-+      if (!priv->mirror_rx && !priv->mirror_tx) {
-+              val = FIELD_PREP(QCA8K_GLOBAL_FW_CTRL0_MIRROR_PORT_NUM, 0xF);
-+              ret = regmap_update_bits(priv->regmap, QCA8K_REG_GLOBAL_FW_CTRL0,
-+                                       QCA8K_GLOBAL_FW_CTRL0_MIRROR_PORT_NUM, val);
-+              if (ret)
-+                      goto err;
-+      }
-+err:
-+      dev_err(priv->dev, "Failed to del mirror port from %d", port);
-+}
---- a/drivers/net/dsa/qca/qca8k.h
-+++ b/drivers/net/dsa/qca/qca8k.h
-@@ -480,4 +480,11 @@ int qca8k_port_mdb_add(struct dsa_switch
- int qca8k_port_mdb_del(struct dsa_switch *ds, int port,
-                      const struct switchdev_obj_port_mdb *mdb);
-+/* Common port mirror function */
-+int qca8k_port_mirror_add(struct dsa_switch *ds, int port,
-+                        struct dsa_mall_mirror_tc_entry *mirror,
-+                        bool ingress);
-+void qca8k_port_mirror_del(struct dsa_switch *ds, int port,
-+                         struct dsa_mall_mirror_tc_entry *mirror);
-+
- #endif /* __QCA8K_H */
diff --git a/target/linux/generic/backport-5.15/771-v6.0-12-net-dsa-qca8k-move-port-VLAN-functions-to-common-cod.patch b/target/linux/generic/backport-5.15/771-v6.0-12-net-dsa-qca8k-move-port-VLAN-functions-to-common-cod.patch
deleted file mode 100644 (file)
index 898010f..0000000
+++ /dev/null
@@ -1,448 +0,0 @@
-From c5290f636624b98e76a82bd63ffec0a8a9daa620 Mon Sep 17 00:00:00 2001
-From: Christian Marangi <[email protected]>
-Date: Wed, 27 Jul 2022 13:35:21 +0200
-Subject: [PATCH 12/14] net: dsa: qca8k: move port VLAN functions to common
- code
-
-The same port VLAN functions are used by drivers based on qca8k family
-switch. Move them to common code to make them accessible also by other
-drivers.
-Also drop exposing busy_wait and make it static.
-
-Signed-off-by: Christian Marangi <[email protected]>
-Reviewed-by: Vladimir Oltean <[email protected]>
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- drivers/net/dsa/qca/qca8k-8xxx.c   | 182 -----------------------------
- drivers/net/dsa/qca/qca8k-common.c | 179 +++++++++++++++++++++++++++-
- drivers/net/dsa/qca/qca8k.h        |  10 +-
- 3 files changed, 187 insertions(+), 184 deletions(-)
-
---- a/drivers/net/dsa/qca/qca8k-8xxx.c
-+++ b/drivers/net/dsa/qca/qca8k-8xxx.c
-@@ -15,7 +15,6 @@
- #include <linux/of_net.h>
- #include <linux/of_mdio.h>
- #include <linux/of_platform.h>
--#include <linux/if_bridge.h>
- #include <linux/mdio.h>
- #include <linux/phylink.h>
- #include <linux/gpio/consumer.h>
-@@ -442,122 +441,6 @@ static struct regmap_config qca8k_regmap
- };
- static int
--qca8k_vlan_access(struct qca8k_priv *priv, enum qca8k_vlan_cmd cmd, u16 vid)
--{
--      u32 reg;
--      int ret;
--
--      /* Set the command and VLAN index */
--      reg = QCA8K_VTU_FUNC1_BUSY;
--      reg |= cmd;
--      reg |= FIELD_PREP(QCA8K_VTU_FUNC1_VID_MASK, vid);
--
--      /* Write the function register triggering the table access */
--      ret = qca8k_write(priv, QCA8K_REG_VTU_FUNC1, reg);
--      if (ret)
--              return ret;
--
--      /* wait for completion */
--      ret = qca8k_busy_wait(priv, QCA8K_REG_VTU_FUNC1, QCA8K_VTU_FUNC1_BUSY);
--      if (ret)
--              return ret;
--
--      /* Check for table full violation when adding an entry */
--      if (cmd == QCA8K_VLAN_LOAD) {
--              ret = qca8k_read(priv, QCA8K_REG_VTU_FUNC1, &reg);
--              if (ret < 0)
--                      return ret;
--              if (reg & QCA8K_VTU_FUNC1_FULL)
--                      return -ENOMEM;
--      }
--
--      return 0;
--}
--
--static int
--qca8k_vlan_add(struct qca8k_priv *priv, u8 port, u16 vid, bool untagged)
--{
--      u32 reg;
--      int ret;
--
--      /*
--         We do the right thing with VLAN 0 and treat it as untagged while
--         preserving the tag on egress.
--       */
--      if (vid == 0)
--              return 0;
--
--      mutex_lock(&priv->reg_mutex);
--      ret = qca8k_vlan_access(priv, QCA8K_VLAN_READ, vid);
--      if (ret < 0)
--              goto out;
--
--      ret = qca8k_read(priv, QCA8K_REG_VTU_FUNC0, &reg);
--      if (ret < 0)
--              goto out;
--      reg |= QCA8K_VTU_FUNC0_VALID | QCA8K_VTU_FUNC0_IVL_EN;
--      reg &= ~QCA8K_VTU_FUNC0_EG_MODE_PORT_MASK(port);
--      if (untagged)
--              reg |= QCA8K_VTU_FUNC0_EG_MODE_PORT_UNTAG(port);
--      else
--              reg |= QCA8K_VTU_FUNC0_EG_MODE_PORT_TAG(port);
--
--      ret = qca8k_write(priv, QCA8K_REG_VTU_FUNC0, reg);
--      if (ret)
--              goto out;
--      ret = qca8k_vlan_access(priv, QCA8K_VLAN_LOAD, vid);
--
--out:
--      mutex_unlock(&priv->reg_mutex);
--
--      return ret;
--}
--
--static int
--qca8k_vlan_del(struct qca8k_priv *priv, u8 port, u16 vid)
--{
--      u32 reg, mask;
--      int ret, i;
--      bool del;
--
--      mutex_lock(&priv->reg_mutex);
--      ret = qca8k_vlan_access(priv, QCA8K_VLAN_READ, vid);
--      if (ret < 0)
--              goto out;
--
--      ret = qca8k_read(priv, QCA8K_REG_VTU_FUNC0, &reg);
--      if (ret < 0)
--              goto out;
--      reg &= ~QCA8K_VTU_FUNC0_EG_MODE_PORT_MASK(port);
--      reg |= QCA8K_VTU_FUNC0_EG_MODE_PORT_NOT(port);
--
--      /* Check if we're the last member to be removed */
--      del = true;
--      for (i = 0; i < QCA8K_NUM_PORTS; i++) {
--              mask = QCA8K_VTU_FUNC0_EG_MODE_PORT_NOT(i);
--
--              if ((reg & mask) != mask) {
--                      del = false;
--                      break;
--              }
--      }
--
--      if (del) {
--              ret = qca8k_vlan_access(priv, QCA8K_VLAN_PURGE, vid);
--      } else {
--              ret = qca8k_write(priv, QCA8K_REG_VTU_FUNC0, reg);
--              if (ret)
--                      goto out;
--              ret = qca8k_vlan_access(priv, QCA8K_VLAN_LOAD, vid);
--      }
--
--out:
--      mutex_unlock(&priv->reg_mutex);
--
--      return ret;
--}
--
--static int
- qca8k_phy_eth_busy_wait(struct qca8k_mgmt_eth_data *mgmt_eth_data,
-                       struct sk_buff *read_skb, u32 *val)
- {
-@@ -1836,71 +1719,6 @@ exit:
-       return ret;
- }
--
--static int
--qca8k_port_vlan_filtering(struct dsa_switch *ds, int port, bool vlan_filtering,
--                        struct netlink_ext_ack *extack)
--{
--      struct qca8k_priv *priv = ds->priv;
--      int ret;
--
--      if (vlan_filtering) {
--              ret = qca8k_rmw(priv, QCA8K_PORT_LOOKUP_CTRL(port),
--                              QCA8K_PORT_LOOKUP_VLAN_MODE_MASK,
--                              QCA8K_PORT_LOOKUP_VLAN_MODE_SECURE);
--      } else {
--              ret = qca8k_rmw(priv, QCA8K_PORT_LOOKUP_CTRL(port),
--                              QCA8K_PORT_LOOKUP_VLAN_MODE_MASK,
--                              QCA8K_PORT_LOOKUP_VLAN_MODE_NONE);
--      }
--
--      return ret;
--}
--
--static int
--qca8k_port_vlan_add(struct dsa_switch *ds, int port,
--                  const struct switchdev_obj_port_vlan *vlan,
--                  struct netlink_ext_ack *extack)
--{
--      bool untagged = vlan->flags & BRIDGE_VLAN_INFO_UNTAGGED;
--      bool pvid = vlan->flags & BRIDGE_VLAN_INFO_PVID;
--      struct qca8k_priv *priv = ds->priv;
--      int ret;
--
--      ret = qca8k_vlan_add(priv, port, vlan->vid, untagged);
--      if (ret) {
--              dev_err(priv->dev, "Failed to add VLAN to port %d (%d)", port, ret);
--              return ret;
--      }
--
--      if (pvid) {
--              ret = qca8k_rmw(priv, QCA8K_EGRESS_VLAN(port),
--                              QCA8K_EGREES_VLAN_PORT_MASK(port),
--                              QCA8K_EGREES_VLAN_PORT(port, vlan->vid));
--              if (ret)
--                      return ret;
--
--              ret = qca8k_write(priv, QCA8K_REG_PORT_VLAN_CTRL0(port),
--                                QCA8K_PORT_VLAN_CVID(vlan->vid) |
--                                QCA8K_PORT_VLAN_SVID(vlan->vid));
--      }
--
--      return ret;
--}
--
--static int
--qca8k_port_vlan_del(struct dsa_switch *ds, int port,
--                  const struct switchdev_obj_port_vlan *vlan)
--{
--      struct qca8k_priv *priv = ds->priv;
--      int ret;
--
--      ret = qca8k_vlan_del(priv, port, vlan->vid);
--      if (ret)
--              dev_err(priv->dev, "Failed to delete VLAN from port %d (%d)", port, ret);
--
--      return ret;
--}
- static u32 qca8k_get_phy_flags(struct dsa_switch *ds, int port)
- {
---- a/drivers/net/dsa/qca/qca8k-common.c
-+++ b/drivers/net/dsa/qca/qca8k-common.c
-@@ -141,7 +141,7 @@ static int qca8k_bulk_write(struct qca8k
-       return 0;
- }
--int qca8k_busy_wait(struct qca8k_priv *priv, u32 reg, u32 mask)
-+static int qca8k_busy_wait(struct qca8k_priv *priv, u32 reg, u32 mask)
- {
-       u32 val;
-@@ -354,6 +354,120 @@ exit:
-       return ret;
- }
-+static int qca8k_vlan_access(struct qca8k_priv *priv,
-+                           enum qca8k_vlan_cmd cmd, u16 vid)
-+{
-+      u32 reg;
-+      int ret;
-+
-+      /* Set the command and VLAN index */
-+      reg = QCA8K_VTU_FUNC1_BUSY;
-+      reg |= cmd;
-+      reg |= FIELD_PREP(QCA8K_VTU_FUNC1_VID_MASK, vid);
-+
-+      /* Write the function register triggering the table access */
-+      ret = qca8k_write(priv, QCA8K_REG_VTU_FUNC1, reg);
-+      if (ret)
-+              return ret;
-+
-+      /* wait for completion */
-+      ret = qca8k_busy_wait(priv, QCA8K_REG_VTU_FUNC1, QCA8K_VTU_FUNC1_BUSY);
-+      if (ret)
-+              return ret;
-+
-+      /* Check for table full violation when adding an entry */
-+      if (cmd == QCA8K_VLAN_LOAD) {
-+              ret = qca8k_read(priv, QCA8K_REG_VTU_FUNC1, &reg);
-+              if (ret < 0)
-+                      return ret;
-+              if (reg & QCA8K_VTU_FUNC1_FULL)
-+                      return -ENOMEM;
-+      }
-+
-+      return 0;
-+}
-+
-+static int qca8k_vlan_add(struct qca8k_priv *priv, u8 port, u16 vid,
-+                        bool untagged)
-+{
-+      u32 reg;
-+      int ret;
-+
-+      /* We do the right thing with VLAN 0 and treat it as untagged while
-+       * preserving the tag on egress.
-+       */
-+      if (vid == 0)
-+              return 0;
-+
-+      mutex_lock(&priv->reg_mutex);
-+      ret = qca8k_vlan_access(priv, QCA8K_VLAN_READ, vid);
-+      if (ret < 0)
-+              goto out;
-+
-+      ret = qca8k_read(priv, QCA8K_REG_VTU_FUNC0, &reg);
-+      if (ret < 0)
-+              goto out;
-+      reg |= QCA8K_VTU_FUNC0_VALID | QCA8K_VTU_FUNC0_IVL_EN;
-+      reg &= ~QCA8K_VTU_FUNC0_EG_MODE_PORT_MASK(port);
-+      if (untagged)
-+              reg |= QCA8K_VTU_FUNC0_EG_MODE_PORT_UNTAG(port);
-+      else
-+              reg |= QCA8K_VTU_FUNC0_EG_MODE_PORT_TAG(port);
-+
-+      ret = qca8k_write(priv, QCA8K_REG_VTU_FUNC0, reg);
-+      if (ret)
-+              goto out;
-+      ret = qca8k_vlan_access(priv, QCA8K_VLAN_LOAD, vid);
-+
-+out:
-+      mutex_unlock(&priv->reg_mutex);
-+
-+      return ret;
-+}
-+
-+static int qca8k_vlan_del(struct qca8k_priv *priv, u8 port, u16 vid)
-+{
-+      u32 reg, mask;
-+      int ret, i;
-+      bool del;
-+
-+      mutex_lock(&priv->reg_mutex);
-+      ret = qca8k_vlan_access(priv, QCA8K_VLAN_READ, vid);
-+      if (ret < 0)
-+              goto out;
-+
-+      ret = qca8k_read(priv, QCA8K_REG_VTU_FUNC0, &reg);
-+      if (ret < 0)
-+              goto out;
-+      reg &= ~QCA8K_VTU_FUNC0_EG_MODE_PORT_MASK(port);
-+      reg |= QCA8K_VTU_FUNC0_EG_MODE_PORT_NOT(port);
-+
-+      /* Check if we're the last member to be removed */
-+      del = true;
-+      for (i = 0; i < QCA8K_NUM_PORTS; i++) {
-+              mask = QCA8K_VTU_FUNC0_EG_MODE_PORT_NOT(i);
-+
-+              if ((reg & mask) != mask) {
-+                      del = false;
-+                      break;
-+              }
-+      }
-+
-+      if (del) {
-+              ret = qca8k_vlan_access(priv, QCA8K_VLAN_PURGE, vid);
-+      } else {
-+              ret = qca8k_write(priv, QCA8K_REG_VTU_FUNC0, reg);
-+              if (ret)
-+                      goto out;
-+              ret = qca8k_vlan_access(priv, QCA8K_VLAN_LOAD, vid);
-+      }
-+
-+out:
-+      mutex_unlock(&priv->reg_mutex);
-+
-+      return ret;
-+}
-+
- int qca8k_mib_init(struct qca8k_priv *priv)
- {
-       int ret;
-@@ -832,3 +946,66 @@ void qca8k_port_mirror_del(struct dsa_sw
- err:
-       dev_err(priv->dev, "Failed to del mirror port from %d", port);
- }
-+
-+int qca8k_port_vlan_filtering(struct dsa_switch *ds, int port,
-+                            bool vlan_filtering,
-+                            struct netlink_ext_ack *extack)
-+{
-+      struct qca8k_priv *priv = ds->priv;
-+      int ret;
-+
-+      if (vlan_filtering) {
-+              ret = qca8k_rmw(priv, QCA8K_PORT_LOOKUP_CTRL(port),
-+                              QCA8K_PORT_LOOKUP_VLAN_MODE_MASK,
-+                              QCA8K_PORT_LOOKUP_VLAN_MODE_SECURE);
-+      } else {
-+              ret = qca8k_rmw(priv, QCA8K_PORT_LOOKUP_CTRL(port),
-+                              QCA8K_PORT_LOOKUP_VLAN_MODE_MASK,
-+                              QCA8K_PORT_LOOKUP_VLAN_MODE_NONE);
-+      }
-+
-+      return ret;
-+}
-+
-+int qca8k_port_vlan_add(struct dsa_switch *ds, int port,
-+                      const struct switchdev_obj_port_vlan *vlan,
-+                      struct netlink_ext_ack *extack)
-+{
-+      bool untagged = vlan->flags & BRIDGE_VLAN_INFO_UNTAGGED;
-+      bool pvid = vlan->flags & BRIDGE_VLAN_INFO_PVID;
-+      struct qca8k_priv *priv = ds->priv;
-+      int ret;
-+
-+      ret = qca8k_vlan_add(priv, port, vlan->vid, untagged);
-+      if (ret) {
-+              dev_err(priv->dev, "Failed to add VLAN to port %d (%d)", port, ret);
-+              return ret;
-+      }
-+
-+      if (pvid) {
-+              ret = qca8k_rmw(priv, QCA8K_EGRESS_VLAN(port),
-+                              QCA8K_EGREES_VLAN_PORT_MASK(port),
-+                              QCA8K_EGREES_VLAN_PORT(port, vlan->vid));
-+              if (ret)
-+                      return ret;
-+
-+              ret = qca8k_write(priv, QCA8K_REG_PORT_VLAN_CTRL0(port),
-+                                QCA8K_PORT_VLAN_CVID(vlan->vid) |
-+                                QCA8K_PORT_VLAN_SVID(vlan->vid));
-+      }
-+
-+      return ret;
-+}
-+
-+int qca8k_port_vlan_del(struct dsa_switch *ds, int port,
-+                      const struct switchdev_obj_port_vlan *vlan)
-+{
-+      struct qca8k_priv *priv = ds->priv;
-+      int ret;
-+
-+      ret = qca8k_vlan_del(priv, port, vlan->vid);
-+      if (ret)
-+              dev_err(priv->dev, "Failed to delete VLAN from port %d (%d)", port, ret);
-+
-+      return ret;
-+}
---- a/drivers/net/dsa/qca/qca8k.h
-+++ b/drivers/net/dsa/qca/qca8k.h
-@@ -431,7 +431,6 @@ int qca8k_write(struct qca8k_priv *priv,
- int qca8k_rmw(struct qca8k_priv *priv, u32 reg, u32 mask, u32 write_val);
- /* Common ops function */
--int qca8k_busy_wait(struct qca8k_priv *priv, u32 reg, u32 mask);
- void qca8k_fdb_flush(struct qca8k_priv *priv);
- /* Common ethtool stats function */
-@@ -487,4 +486,13 @@ int qca8k_port_mirror_add(struct dsa_swi
- void qca8k_port_mirror_del(struct dsa_switch *ds, int port,
-                          struct dsa_mall_mirror_tc_entry *mirror);
-+/* Common port VLAN function */
-+int qca8k_port_vlan_filtering(struct dsa_switch *ds, int port, bool vlan_filtering,
-+                            struct netlink_ext_ack *extack);
-+int qca8k_port_vlan_add(struct dsa_switch *ds, int port,
-+                      const struct switchdev_obj_port_vlan *vlan,
-+                      struct netlink_ext_ack *extack);
-+int qca8k_port_vlan_del(struct dsa_switch *ds, int port,
-+                      const struct switchdev_obj_port_vlan *vlan);
-+
- #endif /* __QCA8K_H */
diff --git a/target/linux/generic/backport-5.15/771-v6.0-13-net-dsa-qca8k-move-port-LAG-functions-to-common-code.patch b/target/linux/generic/backport-5.15/771-v6.0-13-net-dsa-qca8k-move-port-LAG-functions-to-common-code.patch
deleted file mode 100644 (file)
index 1802b17..0000000
+++ /dev/null
@@ -1,384 +0,0 @@
-From e9bbf019af44b204b71ef8edf224002550aab641 Mon Sep 17 00:00:00 2001
-From: Christian Marangi <[email protected]>
-Date: Wed, 27 Jul 2022 13:35:22 +0200
-Subject: [PATCH 13/14] net: dsa: qca8k: move port LAG functions to common code
-
-The same port LAG functions are used by drivers based on qca8k family
-switch. Move them to common code to make them accessible also by other
-drivers.
-
-Signed-off-by: Christian Marangi <[email protected]>
-Reviewed-by: Vladimir Oltean <[email protected]>
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- drivers/net/dsa/qca/qca8k-8xxx.c   | 168 -----------------------------
- drivers/net/dsa/qca/qca8k-common.c | 165 ++++++++++++++++++++++++++++
- drivers/net/dsa/qca/qca8k.h        |   6 ++
- 3 files changed, 171 insertions(+), 168 deletions(-)
-
---- a/drivers/net/dsa/qca/qca8k-8xxx.c
-+++ b/drivers/net/dsa/qca/qca8k-8xxx.c
-@@ -1743,178 +1743,6 @@ qca8k_get_tag_protocol(struct dsa_switch
-       return DSA_TAG_PROTO_QCA;
- }
--static bool
--qca8k_lag_can_offload(struct dsa_switch *ds,
--                    struct net_device *lag,
--                    struct netdev_lag_upper_info *info)
--{
--      struct dsa_port *dp;
--      int id, members = 0;
--
--      id = dsa_lag_id(ds->dst, lag);
--      if (id < 0 || id >= ds->num_lag_ids)
--              return false;
--
--      dsa_lag_foreach_port(dp, ds->dst, lag)
--              /* Includes the port joining the LAG */
--              members++;
--
--      if (members > QCA8K_NUM_PORTS_FOR_LAG)
--              return false;
--
--      if (info->tx_type != NETDEV_LAG_TX_TYPE_HASH)
--              return false;
--
--      if (info->hash_type != NETDEV_LAG_HASH_L2 &&
--          info->hash_type != NETDEV_LAG_HASH_L23)
--              return false;
--
--      return true;
--}
--
--static int
--qca8k_lag_setup_hash(struct dsa_switch *ds,
--                   struct net_device *lag,
--                   struct netdev_lag_upper_info *info)
--{
--      struct qca8k_priv *priv = ds->priv;
--      bool unique_lag = true;
--      u32 hash = 0;
--      int i, id;
--
--      id = dsa_lag_id(ds->dst, lag);
--
--      switch (info->hash_type) {
--      case NETDEV_LAG_HASH_L23:
--              hash |= QCA8K_TRUNK_HASH_SIP_EN;
--              hash |= QCA8K_TRUNK_HASH_DIP_EN;
--              fallthrough;
--      case NETDEV_LAG_HASH_L2:
--              hash |= QCA8K_TRUNK_HASH_SA_EN;
--              hash |= QCA8K_TRUNK_HASH_DA_EN;
--              break;
--      default: /* We should NEVER reach this */
--              return -EOPNOTSUPP;
--      }
--
--      /* Check if we are the unique configured LAG */
--      dsa_lags_foreach_id(i, ds->dst)
--              if (i != id && dsa_lag_dev(ds->dst, i)) {
--                      unique_lag = false;
--                      break;
--              }
--
--      /* Hash Mode is global. Make sure the same Hash Mode
--       * is set to all the 4 possible lag.
--       * If we are the unique LAG we can set whatever hash
--       * mode we want.
--       * To change hash mode it's needed to remove all LAG
--       * and change the mode with the latest.
--       */
--      if (unique_lag) {
--              priv->lag_hash_mode = hash;
--      } else if (priv->lag_hash_mode != hash) {
--              netdev_err(lag, "Error: Mismateched Hash Mode across different lag is not supported\n");
--              return -EOPNOTSUPP;
--      }
--
--      return regmap_update_bits(priv->regmap, QCA8K_TRUNK_HASH_EN_CTRL,
--                                QCA8K_TRUNK_HASH_MASK, hash);
--}
--
--static int
--qca8k_lag_refresh_portmap(struct dsa_switch *ds, int port,
--                        struct net_device *lag, bool delete)
--{
--      struct qca8k_priv *priv = ds->priv;
--      int ret, id, i;
--      u32 val;
--
--      id = dsa_lag_id(ds->dst, lag);
--
--      /* Read current port member */
--      ret = regmap_read(priv->regmap, QCA8K_REG_GOL_TRUNK_CTRL0, &val);
--      if (ret)
--              return ret;
--
--      /* Shift val to the correct trunk */
--      val >>= QCA8K_REG_GOL_TRUNK_SHIFT(id);
--      val &= QCA8K_REG_GOL_TRUNK_MEMBER_MASK;
--      if (delete)
--              val &= ~BIT(port);
--      else
--              val |= BIT(port);
--
--      /* Update port member. With empty portmap disable trunk */
--      ret = regmap_update_bits(priv->regmap, QCA8K_REG_GOL_TRUNK_CTRL0,
--                               QCA8K_REG_GOL_TRUNK_MEMBER(id) |
--                               QCA8K_REG_GOL_TRUNK_EN(id),
--                               !val << QCA8K_REG_GOL_TRUNK_SHIFT(id) |
--                               val << QCA8K_REG_GOL_TRUNK_SHIFT(id));
--
--      /* Search empty member if adding or port on deleting */
--      for (i = 0; i < QCA8K_NUM_PORTS_FOR_LAG; i++) {
--              ret = regmap_read(priv->regmap, QCA8K_REG_GOL_TRUNK_CTRL(id), &val);
--              if (ret)
--                      return ret;
--
--              val >>= QCA8K_REG_GOL_TRUNK_ID_MEM_ID_SHIFT(id, i);
--              val &= QCA8K_REG_GOL_TRUNK_ID_MEM_ID_MASK;
--
--              if (delete) {
--                      /* If port flagged to be disabled assume this member is
--                       * empty
--                       */
--                      if (val != QCA8K_REG_GOL_TRUNK_ID_MEM_ID_EN_MASK)
--                              continue;
--
--                      val &= QCA8K_REG_GOL_TRUNK_ID_MEM_ID_PORT_MASK;
--                      if (val != port)
--                              continue;
--              } else {
--                      /* If port flagged to be enabled assume this member is
--                       * already set
--                       */
--                      if (val == QCA8K_REG_GOL_TRUNK_ID_MEM_ID_EN_MASK)
--                              continue;
--              }
--
--              /* We have found the member to add/remove */
--              break;
--      }
--
--      /* Set port in the correct port mask or disable port if in delete mode */
--      return regmap_update_bits(priv->regmap, QCA8K_REG_GOL_TRUNK_CTRL(id),
--                                QCA8K_REG_GOL_TRUNK_ID_MEM_ID_EN(id, i) |
--                                QCA8K_REG_GOL_TRUNK_ID_MEM_ID_PORT(id, i),
--                                !delete << QCA8K_REG_GOL_TRUNK_ID_MEM_ID_SHIFT(id, i) |
--                                port << QCA8K_REG_GOL_TRUNK_ID_MEM_ID_SHIFT(id, i));
--}
--
--static int
--qca8k_port_lag_join(struct dsa_switch *ds, int port,
--                  struct net_device *lag,
--                  struct netdev_lag_upper_info *info)
--{
--      int ret;
--
--      if (!qca8k_lag_can_offload(ds, lag, info))
--              return -EOPNOTSUPP;
--
--      ret = qca8k_lag_setup_hash(ds, lag, info);
--      if (ret)
--              return ret;
--
--      return qca8k_lag_refresh_portmap(ds, port, lag, false);
--}
--
--static int
--qca8k_port_lag_leave(struct dsa_switch *ds, int port,
--                   struct net_device *lag)
--{
--      return qca8k_lag_refresh_portmap(ds, port, lag, true);
--}
--
- static void
- qca8k_master_change(struct dsa_switch *ds, const struct net_device *master,
-                   bool operational)
---- a/drivers/net/dsa/qca/qca8k-common.c
-+++ b/drivers/net/dsa/qca/qca8k-common.c
-@@ -1009,3 +1009,169 @@ int qca8k_port_vlan_del(struct dsa_switc
-       return ret;
- }
-+
-+static bool qca8k_lag_can_offload(struct dsa_switch *ds,
-+                                struct net_device *lag,
-+                                struct netdev_lag_upper_info *info)
-+{
-+      struct dsa_port *dp;
-+      int id, members = 0;
-+
-+      id = dsa_lag_id(ds->dst, lag);
-+      if (id < 0 || id >= ds->num_lag_ids)
-+              return false;
-+
-+      dsa_lag_foreach_port(dp, ds->dst, lag)
-+              /* Includes the port joining the LAG */
-+              members++;
-+
-+      if (members > QCA8K_NUM_PORTS_FOR_LAG)
-+              return false;
-+
-+      if (info->tx_type != NETDEV_LAG_TX_TYPE_HASH)
-+              return false;
-+
-+      if (info->hash_type != NETDEV_LAG_HASH_L2 &&
-+          info->hash_type != NETDEV_LAG_HASH_L23)
-+              return false;
-+
-+      return true;
-+}
-+
-+static int qca8k_lag_setup_hash(struct dsa_switch *ds,
-+                              struct net_device *lag,
-+                              struct netdev_lag_upper_info *info)
-+{
-+      struct qca8k_priv *priv = ds->priv;
-+      bool unique_lag = true;
-+      u32 hash = 0;
-+      int i, id;
-+
-+      id = dsa_lag_id(ds->dst, lag);
-+
-+      switch (info->hash_type) {
-+      case NETDEV_LAG_HASH_L23:
-+              hash |= QCA8K_TRUNK_HASH_SIP_EN;
-+              hash |= QCA8K_TRUNK_HASH_DIP_EN;
-+              fallthrough;
-+      case NETDEV_LAG_HASH_L2:
-+              hash |= QCA8K_TRUNK_HASH_SA_EN;
-+              hash |= QCA8K_TRUNK_HASH_DA_EN;
-+              break;
-+      default: /* We should NEVER reach this */
-+              return -EOPNOTSUPP;
-+      }
-+
-+      /* Check if we are the unique configured LAG */
-+      dsa_lags_foreach_id(i, ds->dst)
-+              if (i != id && dsa_lag_dev(ds->dst, i)) {
-+                      unique_lag = false;
-+                      break;
-+              }
-+
-+      /* Hash Mode is global. Make sure the same Hash Mode
-+       * is set to all the 4 possible lag.
-+       * If we are the unique LAG we can set whatever hash
-+       * mode we want.
-+       * To change hash mode it's needed to remove all LAG
-+       * and change the mode with the latest.
-+       */
-+      if (unique_lag) {
-+              priv->lag_hash_mode = hash;
-+      } else if (priv->lag_hash_mode != hash) {
-+              netdev_err(lag, "Error: Mismatched Hash Mode across different lag is not supported\n");
-+              return -EOPNOTSUPP;
-+      }
-+
-+      return regmap_update_bits(priv->regmap, QCA8K_TRUNK_HASH_EN_CTRL,
-+                                QCA8K_TRUNK_HASH_MASK, hash);
-+}
-+
-+static int qca8k_lag_refresh_portmap(struct dsa_switch *ds, int port,
-+                                   struct net_device *lag, bool delete)
-+{
-+      struct qca8k_priv *priv = ds->priv;
-+      int ret, id, i;
-+      u32 val;
-+
-+      id = dsa_lag_id(ds->dst, lag);
-+
-+      /* Read current port member */
-+      ret = regmap_read(priv->regmap, QCA8K_REG_GOL_TRUNK_CTRL0, &val);
-+      if (ret)
-+              return ret;
-+
-+      /* Shift val to the correct trunk */
-+      val >>= QCA8K_REG_GOL_TRUNK_SHIFT(id);
-+      val &= QCA8K_REG_GOL_TRUNK_MEMBER_MASK;
-+      if (delete)
-+              val &= ~BIT(port);
-+      else
-+              val |= BIT(port);
-+
-+      /* Update port member. With empty portmap disable trunk */
-+      ret = regmap_update_bits(priv->regmap, QCA8K_REG_GOL_TRUNK_CTRL0,
-+                               QCA8K_REG_GOL_TRUNK_MEMBER(id) |
-+                               QCA8K_REG_GOL_TRUNK_EN(id),
-+                               !val << QCA8K_REG_GOL_TRUNK_SHIFT(id) |
-+                               val << QCA8K_REG_GOL_TRUNK_SHIFT(id));
-+
-+      /* Search empty member if adding or port on deleting */
-+      for (i = 0; i < QCA8K_NUM_PORTS_FOR_LAG; i++) {
-+              ret = regmap_read(priv->regmap, QCA8K_REG_GOL_TRUNK_CTRL(id), &val);
-+              if (ret)
-+                      return ret;
-+
-+              val >>= QCA8K_REG_GOL_TRUNK_ID_MEM_ID_SHIFT(id, i);
-+              val &= QCA8K_REG_GOL_TRUNK_ID_MEM_ID_MASK;
-+
-+              if (delete) {
-+                      /* If port flagged to be disabled assume this member is
-+                       * empty
-+                       */
-+                      if (val != QCA8K_REG_GOL_TRUNK_ID_MEM_ID_EN_MASK)
-+                              continue;
-+
-+                      val &= QCA8K_REG_GOL_TRUNK_ID_MEM_ID_PORT_MASK;
-+                      if (val != port)
-+                              continue;
-+              } else {
-+                      /* If port flagged to be enabled assume this member is
-+                       * already set
-+                       */
-+                      if (val == QCA8K_REG_GOL_TRUNK_ID_MEM_ID_EN_MASK)
-+                              continue;
-+              }
-+
-+              /* We have found the member to add/remove */
-+              break;
-+      }
-+
-+      /* Set port in the correct port mask or disable port if in delete mode */
-+      return regmap_update_bits(priv->regmap, QCA8K_REG_GOL_TRUNK_CTRL(id),
-+                                QCA8K_REG_GOL_TRUNK_ID_MEM_ID_EN(id, i) |
-+                                QCA8K_REG_GOL_TRUNK_ID_MEM_ID_PORT(id, i),
-+                                !delete << QCA8K_REG_GOL_TRUNK_ID_MEM_ID_SHIFT(id, i) |
-+                                port << QCA8K_REG_GOL_TRUNK_ID_MEM_ID_SHIFT(id, i));
-+}
-+
-+int qca8k_port_lag_join(struct dsa_switch *ds, int port, struct net_device *lag,
-+                      struct netdev_lag_upper_info *info)
-+{
-+      int ret;
-+
-+      if (!qca8k_lag_can_offload(ds, lag, info))
-+              return -EOPNOTSUPP;
-+
-+      ret = qca8k_lag_setup_hash(ds, lag, info);
-+      if (ret)
-+              return ret;
-+
-+      return qca8k_lag_refresh_portmap(ds, port, lag, false);
-+}
-+
-+int qca8k_port_lag_leave(struct dsa_switch *ds, int port,
-+                       struct net_device *lag)
-+{
-+      return qca8k_lag_refresh_portmap(ds, port, lag, true);
-+}
---- a/drivers/net/dsa/qca/qca8k.h
-+++ b/drivers/net/dsa/qca/qca8k.h
-@@ -495,4 +495,10 @@ int qca8k_port_vlan_add(struct dsa_switc
- int qca8k_port_vlan_del(struct dsa_switch *ds, int port,
-                       const struct switchdev_obj_port_vlan *vlan);
-+/* Common port LAG function */
-+int qca8k_port_lag_join(struct dsa_switch *ds, int port, struct net_device *lag,
-+                      struct netdev_lag_upper_info *info);
-+int qca8k_port_lag_leave(struct dsa_switch *ds, int port,
-+                       struct net_device *lag);
-+
- #endif /* __QCA8K_H */
diff --git a/target/linux/generic/backport-5.15/771-v6.0-14-net-dsa-qca8k-move-read_switch_id-function-to-common.patch b/target/linux/generic/backport-5.15/771-v6.0-14-net-dsa-qca8k-move-read_switch_id-function-to-common.patch
deleted file mode 100644 (file)
index d6ec8b7..0000000
+++ /dev/null
@@ -1,102 +0,0 @@
-From 9d1bcb1f293f1391302a109c9819c3705c804700 Mon Sep 17 00:00:00 2001
-From: Christian Marangi <[email protected]>
-Date: Wed, 27 Jul 2022 13:35:23 +0200
-Subject: [PATCH 14/14] net: dsa: qca8k: move read_switch_id function to common
- code
-
-The same function to read the switch id is used by drivers based on
-qca8k family switch. Move them to common code to make them accessible
-also by other drivers.
-
-Signed-off-by: Christian Marangi <[email protected]>
-Reviewed-by: Vladimir Oltean <[email protected]>
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- drivers/net/dsa/qca/qca8k-8xxx.c   | 29 -----------------------------
- drivers/net/dsa/qca/qca8k-common.c | 29 +++++++++++++++++++++++++++++
- drivers/net/dsa/qca/qca8k.h        |  1 +
- 3 files changed, 30 insertions(+), 29 deletions(-)
-
---- a/drivers/net/dsa/qca/qca8k-8xxx.c
-+++ b/drivers/net/dsa/qca/qca8k-8xxx.c
-@@ -1822,35 +1822,6 @@ static const struct dsa_switch_ops qca8k
-       .connect_tag_protocol   = qca8k_connect_tag_protocol,
- };
--static int qca8k_read_switch_id(struct qca8k_priv *priv)
--{
--      u32 val;
--      u8 id;
--      int ret;
--
--      if (!priv->info)
--              return -ENODEV;
--
--      ret = qca8k_read(priv, QCA8K_REG_MASK_CTRL, &val);
--      if (ret < 0)
--              return -ENODEV;
--
--      id = QCA8K_MASK_CTRL_DEVICE_ID(val);
--      if (id != priv->info->id) {
--              dev_err(priv->dev,
--                      "Switch id detected %x but expected %x",
--                      id, priv->info->id);
--              return -ENODEV;
--      }
--
--      priv->switch_id = id;
--
--      /* Save revision to communicate to the internal PHY driver */
--      priv->switch_revision = QCA8K_MASK_CTRL_REV_ID(val);
--
--      return 0;
--}
--
- static int
- qca8k_sw_probe(struct mdio_device *mdiodev)
- {
---- a/drivers/net/dsa/qca/qca8k-common.c
-+++ b/drivers/net/dsa/qca/qca8k-common.c
-@@ -1175,3 +1175,32 @@ int qca8k_port_lag_leave(struct dsa_swit
- {
-       return qca8k_lag_refresh_portmap(ds, port, lag, true);
- }
-+
-+int qca8k_read_switch_id(struct qca8k_priv *priv)
-+{
-+      u32 val;
-+      u8 id;
-+      int ret;
-+
-+      if (!priv->info)
-+              return -ENODEV;
-+
-+      ret = qca8k_read(priv, QCA8K_REG_MASK_CTRL, &val);
-+      if (ret < 0)
-+              return -ENODEV;
-+
-+      id = QCA8K_MASK_CTRL_DEVICE_ID(val);
-+      if (id != priv->info->id) {
-+              dev_err(priv->dev,
-+                      "Switch id detected %x but expected %x",
-+                      id, priv->info->id);
-+              return -ENODEV;
-+      }
-+
-+      priv->switch_id = id;
-+
-+      /* Save revision to communicate to the internal PHY driver */
-+      priv->switch_revision = QCA8K_MASK_CTRL_REV_ID(val);
-+
-+      return 0;
-+}
---- a/drivers/net/dsa/qca/qca8k.h
-+++ b/drivers/net/dsa/qca/qca8k.h
-@@ -424,6 +424,7 @@ extern const struct qca8k_mib_desc ar832
- extern const struct regmap_access_table qca8k_readable_table;
- int qca8k_mib_init(struct qca8k_priv *priv);
- void qca8k_port_set_status(struct qca8k_priv *priv, int port, int enable);
-+int qca8k_read_switch_id(struct qca8k_priv *priv);
- /* Common read/write/rmw function */
- int qca8k_read(struct qca8k_priv *priv, u32 reg, u32 *val);
diff --git a/target/linux/generic/backport-5.15/772-v6.0-net-dsa-qca8k-fix-NULL-pointer-dereference-for-of_de.patch b/target/linux/generic/backport-5.15/772-v6.0-net-dsa-qca8k-fix-NULL-pointer-dereference-for-of_de.patch
deleted file mode 100644 (file)
index 0cca278..0000000
+++ /dev/null
@@ -1,29 +0,0 @@
-From 057bcf15db8e625276ddf02b2b7c668a3cb43f81 Mon Sep 17 00:00:00 2001
-From: Christian Marangi <[email protected]>
-Date: Sun, 4 Sep 2022 23:46:24 +0200
-Subject: [net PATCH] net: dsa: qca8k: fix NULL pointer dereference for
- of_device_get_match_data
-
-of_device_get_match_data is called on priv->dev before priv->dev is
-actually set. Move of_device_get_match_data after priv->dev is correctly
-set to fix this kernel panic.
-
-Fixes: 3bb0844e7bcd ("net: dsa: qca8k: cache match data to speed up access")
-Signed-off-by: Christian Marangi <[email protected]>
----
- drivers/net/dsa/qca/qca8k-8xxx.c | 2 +-
- 1 file changed, 1 insertion(+), 1 deletion(-)
-
---- a/drivers/net/dsa/qca/qca8k-8xxx.c
-+++ b/drivers/net/dsa/qca/qca8k-8xxx.c
-@@ -1835,9 +1835,9 @@ qca8k_sw_probe(struct mdio_device *mdiod
-       if (!priv)
-               return -ENOMEM;
--      priv->info = of_device_get_match_data(priv->dev);
-       priv->bus = mdiodev->bus;
-       priv->dev = &mdiodev->dev;
-+      priv->info = of_device_get_match_data(priv->dev);
-       priv->reset_gpio = devm_gpiod_get_optional(priv->dev, "reset",
-                                                  GPIOD_ASIS);
diff --git a/target/linux/generic/backport-5.15/773-v5.18-1-net-dsa-Move-VLAN-filtering-syncing-out-of-dsa_switc.patch b/target/linux/generic/backport-5.15/773-v5.18-1-net-dsa-Move-VLAN-filtering-syncing-out-of-dsa_switc.patch
deleted file mode 100644 (file)
index 44093ea..0000000
+++ /dev/null
@@ -1,77 +0,0 @@
-From 381a730182f1d174e1950cd4e63e885b1c302051 Mon Sep 17 00:00:00 2001
-From: Tobias Waldekranz <[email protected]>
-Date: Mon, 24 Jan 2022 22:09:43 +0100
-Subject: net: dsa: Move VLAN filtering syncing out of dsa_switch_bridge_leave
-
-Most of dsa_switch_bridge_leave was, in fact, dealing with the syncing
-of VLAN filtering for switches on which that is a global
-setting. Separate the two phases to prepare for the cross-chip related
-bugfix in the following commit.
-
-Signed-off-by: Tobias Waldekranz <[email protected]>
-Reviewed-by: Vladimir Oltean <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- net/dsa/switch.c | 38 +++++++++++++++++++++++++-------------
- 1 file changed, 25 insertions(+), 13 deletions(-)
-
---- a/net/dsa/switch.c
-+++ b/net/dsa/switch.c
-@@ -113,25 +113,14 @@ static int dsa_switch_bridge_join(struct
-       return dsa_tag_8021q_bridge_join(ds, info);
- }
--static int dsa_switch_bridge_leave(struct dsa_switch *ds,
--                                 struct dsa_notifier_bridge_info *info)
-+static int dsa_switch_sync_vlan_filtering(struct dsa_switch *ds,
-+                                        struct dsa_notifier_bridge_info *info)
- {
--      struct dsa_switch_tree *dst = ds->dst;
-       struct netlink_ext_ack extack = {0};
-       bool change_vlan_filtering = false;
-       bool vlan_filtering;
-       int err, port;
--      if (dst->index == info->tree_index && ds->index == info->sw_index &&
--          ds->ops->port_bridge_leave)
--              ds->ops->port_bridge_leave(ds, info->port, info->br);
--
--      if ((dst->index != info->tree_index || ds->index != info->sw_index) &&
--          ds->ops->crosschip_bridge_leave)
--              ds->ops->crosschip_bridge_leave(ds, info->tree_index,
--                                              info->sw_index, info->port,
--                                              info->br);
--
-       if (ds->needs_standalone_vlan_filtering && !br_vlan_enabled(info->br)) {
-               change_vlan_filtering = true;
-               vlan_filtering = true;
-@@ -172,6 +161,29 @@ static int dsa_switch_bridge_leave(struc
-                       return err;
-       }
-+      return 0;
-+}
-+
-+static int dsa_switch_bridge_leave(struct dsa_switch *ds,
-+                                 struct dsa_notifier_bridge_info *info)
-+{
-+      struct dsa_switch_tree *dst = ds->dst;
-+      int err;
-+
-+      if (dst->index == info->tree_index && ds->index == info->sw_index &&
-+          ds->ops->port_bridge_leave)
-+              ds->ops->port_bridge_leave(ds, info->port, info->br);
-+
-+      if ((dst->index != info->tree_index || ds->index != info->sw_index) &&
-+          ds->ops->crosschip_bridge_leave)
-+              ds->ops->crosschip_bridge_leave(ds, info->tree_index,
-+                                              info->sw_index, info->port,
-+                                              info->br);
-+
-+      err = dsa_switch_sync_vlan_filtering(ds, info);
-+      if (err)
-+              return err;
-+
-       return dsa_tag_8021q_bridge_leave(ds, info);
- }
diff --git a/target/linux/generic/backport-5.15/773-v5.18-2-net-dsa-Avoid-cross-chip-syncing-of-VLAN-filtering.patch b/target/linux/generic/backport-5.15/773-v5.18-2-net-dsa-Avoid-cross-chip-syncing-of-VLAN-filtering.patch
deleted file mode 100644 (file)
index cdddbcf..0000000
+++ /dev/null
@@ -1,52 +0,0 @@
-From 108dc8741c203e9d6ce4e973367f1bac20c7192b Mon Sep 17 00:00:00 2001
-From: Tobias Waldekranz <[email protected]>
-Date: Mon, 24 Jan 2022 22:09:44 +0100
-Subject: net: dsa: Avoid cross-chip syncing of VLAN filtering
-
-Changes to VLAN filtering are not applicable to cross-chip
-notifications.
-
-On a system like this:
-
-.-----.   .-----.   .-----.
-| sw1 +---+ sw2 +---+ sw3 |
-'-1-2-'   '-1-2-'   '-1-2-'
-
-Before this change, upon sw1p1 leaving a bridge, a call to
-dsa_port_vlan_filtering would also be made to sw2p1 and sw3p1.
-
-In this scenario:
-
-.---------.   .-----.   .-----.
-|   sw1   +---+ sw2 +---+ sw3 |
-'-1-2-3-4-'   '-1-2-'   '-1-2-'
-
-When sw1p4 would leave a bridge, dsa_port_vlan_filtering would be
-called for sw2 and sw3 with a non-existing port - leading to array
-out-of-bounds accesses and crashes on mv88e6xxx.
-
-Fixes: d371b7c92d19 ("net: dsa: Unset vlan_filtering when ports leave the bridge")
-Signed-off-by: Tobias Waldekranz <[email protected]>
-Reviewed-by: Vladimir Oltean <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- net/dsa/switch.c | 8 +++++---
- 1 file changed, 5 insertions(+), 3 deletions(-)
-
---- a/net/dsa/switch.c
-+++ b/net/dsa/switch.c
-@@ -180,9 +180,11 @@ static int dsa_switch_bridge_leave(struc
-                                               info->sw_index, info->port,
-                                               info->br);
--      err = dsa_switch_sync_vlan_filtering(ds, info);
--      if (err)
--              return err;
-+      if (ds->dst->index == info->tree_index && ds->index == info->sw_index) {
-+              err = dsa_switch_sync_vlan_filtering(ds, info);
-+              if (err)
-+                      return err;
-+      }
-       return dsa_tag_8021q_bridge_leave(ds, info);
- }
diff --git a/target/linux/generic/backport-5.15/774-v5.16-01-net-dsa-rtl8366rb-Support-bridge-offloading.patch b/target/linux/generic/backport-5.15/774-v5.16-01-net-dsa-rtl8366rb-Support-bridge-offloading.patch
deleted file mode 100644 (file)
index 78570c5..0000000
+++ /dev/null
@@ -1,141 +0,0 @@
-From c9111895fd38dadf125e07be627778a9950d8d77 Mon Sep 17 00:00:00 2001
-From: DENG Qingfang <[email protected]>
-Date: Sun, 26 Sep 2021 00:59:24 +0200
-Subject: [PATCH 01/11] net: dsa: rtl8366rb: Support bridge offloading
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-Use port isolation registers to configure bridge offloading.
-
-Tested on the D-Link DIR-685, switching between ports and
-sniffing ports to make sure no packets leak.
-
-Cc: Vladimir Oltean <[email protected]>
-Cc: Mauri Sandberg <[email protected]>
-Reviewed-by: Vladimir Oltean <[email protected]>
-Reviewed-by: Alvin Šipraga <[email protected]>
-Reviewed-by: Florian Fainelli <[email protected]>
-Signed-off-by: DENG Qingfang <[email protected]>
-Signed-off-by: Linus Walleij <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/dsa/rtl8366rb.c | 86 +++++++++++++++++++++++++++++++++++++
- 1 file changed, 86 insertions(+)
-
---- a/drivers/net/dsa/rtl8366rb.c
-+++ b/drivers/net/dsa/rtl8366rb.c
-@@ -300,6 +300,13 @@
- #define RTL8366RB_INTERRUPT_STATUS_REG        0x0442
- #define RTL8366RB_NUM_INTERRUPT               14 /* 0..13 */
-+/* Port isolation registers */
-+#define RTL8366RB_PORT_ISO_BASE               0x0F08
-+#define RTL8366RB_PORT_ISO(pnum)      (RTL8366RB_PORT_ISO_BASE + (pnum))
-+#define RTL8366RB_PORT_ISO_EN         BIT(0)
-+#define RTL8366RB_PORT_ISO_PORTS_MASK GENMASK(7, 1)
-+#define RTL8366RB_PORT_ISO_PORTS(pmask)       ((pmask) << 1)
-+
- /* bits 0..5 enable force when cleared */
- #define RTL8366RB_MAC_FORCE_CTRL_REG  0x0F11
-@@ -835,6 +842,21 @@ static int rtl8366rb_setup(struct dsa_sw
-       if (ret)
-               return ret;
-+      /* Isolate all user ports so they can only send packets to itself and the CPU port */
-+      for (i = 0; i < RTL8366RB_PORT_NUM_CPU; i++) {
-+              ret = regmap_write(smi->map, RTL8366RB_PORT_ISO(i),
-+                                 RTL8366RB_PORT_ISO_PORTS(BIT(RTL8366RB_PORT_NUM_CPU)) |
-+                                 RTL8366RB_PORT_ISO_EN);
-+              if (ret)
-+                      return ret;
-+      }
-+      /* CPU port can send packets to all ports */
-+      ret = regmap_write(smi->map, RTL8366RB_PORT_ISO(RTL8366RB_PORT_NUM_CPU),
-+                         RTL8366RB_PORT_ISO_PORTS(dsa_user_ports(ds)) |
-+                         RTL8366RB_PORT_ISO_EN);
-+      if (ret)
-+              return ret;
-+
-       /* Set up the "green ethernet" feature */
-       ret = rtl8366rb_jam_table(rtl8366rb_green_jam,
-                                 ARRAY_SIZE(rtl8366rb_green_jam), smi, false);
-@@ -1127,6 +1149,68 @@ rtl8366rb_port_disable(struct dsa_switch
-       rb8366rb_set_port_led(smi, port, false);
- }
-+static int
-+rtl8366rb_port_bridge_join(struct dsa_switch *ds, int port,
-+                         struct net_device *bridge)
-+{
-+      struct realtek_smi *smi = ds->priv;
-+      unsigned int port_bitmap = 0;
-+      int ret, i;
-+
-+      /* Loop over all other ports than the current one */
-+      for (i = 0; i < RTL8366RB_PORT_NUM_CPU; i++) {
-+              /* Current port handled last */
-+              if (i == port)
-+                      continue;
-+              /* Not on this bridge */
-+              if (dsa_to_port(ds, i)->bridge_dev != bridge)
-+                      continue;
-+              /* Join this port to each other port on the bridge */
-+              ret = regmap_update_bits(smi->map, RTL8366RB_PORT_ISO(i),
-+                                       RTL8366RB_PORT_ISO_PORTS(BIT(port)),
-+                                       RTL8366RB_PORT_ISO_PORTS(BIT(port)));
-+              if (ret)
-+                      dev_err(smi->dev, "failed to join port %d\n", port);
-+
-+              port_bitmap |= BIT(i);
-+      }
-+
-+      /* Set the bits for the ports we can access */
-+      return regmap_update_bits(smi->map, RTL8366RB_PORT_ISO(port),
-+                                RTL8366RB_PORT_ISO_PORTS(port_bitmap),
-+                                RTL8366RB_PORT_ISO_PORTS(port_bitmap));
-+}
-+
-+static void
-+rtl8366rb_port_bridge_leave(struct dsa_switch *ds, int port,
-+                          struct net_device *bridge)
-+{
-+      struct realtek_smi *smi = ds->priv;
-+      unsigned int port_bitmap = 0;
-+      int ret, i;
-+
-+      /* Loop over all other ports than this one */
-+      for (i = 0; i < RTL8366RB_PORT_NUM_CPU; i++) {
-+              /* Current port handled last */
-+              if (i == port)
-+                      continue;
-+              /* Not on this bridge */
-+              if (dsa_to_port(ds, i)->bridge_dev != bridge)
-+                      continue;
-+              /* Remove this port from any other port on the bridge */
-+              ret = regmap_update_bits(smi->map, RTL8366RB_PORT_ISO(i),
-+                                       RTL8366RB_PORT_ISO_PORTS(BIT(port)), 0);
-+              if (ret)
-+                      dev_err(smi->dev, "failed to leave port %d\n", port);
-+
-+              port_bitmap |= BIT(i);
-+      }
-+
-+      /* Clear the bits for the ports we can not access, leave ourselves */
-+      regmap_update_bits(smi->map, RTL8366RB_PORT_ISO(port),
-+                         RTL8366RB_PORT_ISO_PORTS(port_bitmap), 0);
-+}
-+
- static int rtl8366rb_change_mtu(struct dsa_switch *ds, int port, int new_mtu)
- {
-       struct realtek_smi *smi = ds->priv;
-@@ -1510,6 +1594,8 @@ static const struct dsa_switch_ops rtl83
-       .get_strings = rtl8366_get_strings,
-       .get_ethtool_stats = rtl8366_get_ethtool_stats,
-       .get_sset_count = rtl8366_get_sset_count,
-+      .port_bridge_join = rtl8366rb_port_bridge_join,
-+      .port_bridge_leave = rtl8366rb_port_bridge_leave,
-       .port_vlan_filtering = rtl8366_vlan_filtering,
-       .port_vlan_add = rtl8366_vlan_add,
-       .port_vlan_del = rtl8366_vlan_del,
diff --git a/target/linux/generic/backport-5.15/774-v5.16-02-net-dsa-rtl8366-Drop-custom-VLAN-set-up.patch b/target/linux/generic/backport-5.15/774-v5.16-02-net-dsa-rtl8366-Drop-custom-VLAN-set-up.patch
deleted file mode 100644 (file)
index e61349a..0000000
+++ /dev/null
@@ -1,118 +0,0 @@
-From 96cf10a8e7297065459473c081a6fb6432a22312 Mon Sep 17 00:00:00 2001
-From: Linus Walleij <[email protected]>
-Date: Sun, 26 Sep 2021 00:59:25 +0200
-Subject: [PATCH 02/11] net: dsa: rtl8366: Drop custom VLAN set-up
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-This hacky default VLAN setup was done in order to direct
-packets to the right ports and provide port isolation, both
-which we now support properly using custom tags and proper
-bridge port isolation.
-
-We can drop the custom VLAN code and leave all VLAN handling
-alone, as users expect things to be. We can also drop
-ds->configure_vlan_while_not_filtering = false; and let
-the core deal with any VLANs it wants.
-
-Cc: Mauri Sandberg <[email protected]>
-Cc: DENG Qingfang <[email protected]>
-Reviewed-by: Vladimir Oltean <[email protected]>
-Reviewed-by: Alvin Šipraga <[email protected]>
-Reviewed-by: Florian Fainelli <[email protected]>
-Signed-off-by: Linus Walleij <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/dsa/realtek-smi-core.h |  1 -
- drivers/net/dsa/rtl8366.c          | 48 ------------------------------
- drivers/net/dsa/rtl8366rb.c        |  4 +--
- 3 files changed, 1 insertion(+), 52 deletions(-)
-
---- a/drivers/net/dsa/realtek-smi-core.h
-+++ b/drivers/net/dsa/realtek-smi-core.h
-@@ -129,7 +129,6 @@ int rtl8366_set_pvid(struct realtek_smi
- int rtl8366_enable_vlan4k(struct realtek_smi *smi, bool enable);
- int rtl8366_enable_vlan(struct realtek_smi *smi, bool enable);
- int rtl8366_reset_vlan(struct realtek_smi *smi);
--int rtl8366_init_vlan(struct realtek_smi *smi);
- int rtl8366_vlan_filtering(struct dsa_switch *ds, int port, bool vlan_filtering,
-                          struct netlink_ext_ack *extack);
- int rtl8366_vlan_add(struct dsa_switch *ds, int port,
---- a/drivers/net/dsa/rtl8366.c
-+++ b/drivers/net/dsa/rtl8366.c
-@@ -292,54 +292,6 @@ int rtl8366_reset_vlan(struct realtek_sm
- }
- EXPORT_SYMBOL_GPL(rtl8366_reset_vlan);
--int rtl8366_init_vlan(struct realtek_smi *smi)
--{
--      int port;
--      int ret;
--
--      ret = rtl8366_reset_vlan(smi);
--      if (ret)
--              return ret;
--
--      /* Loop over the available ports, for each port, associate
--       * it with the VLAN (port+1)
--       */
--      for (port = 0; port < smi->num_ports; port++) {
--              u32 mask;
--
--              if (port == smi->cpu_port)
--                      /* For the CPU port, make all ports members of this
--                       * VLAN.
--                       */
--                      mask = GENMASK((int)smi->num_ports - 1, 0);
--              else
--                      /* For all other ports, enable itself plus the
--                       * CPU port.
--                       */
--                      mask = BIT(port) | BIT(smi->cpu_port);
--
--              /* For each port, set the port as member of VLAN (port+1)
--               * and untagged, except for the CPU port: the CPU port (5) is
--               * member of VLAN 6 and so are ALL the other ports as well.
--               * Use filter 0 (no filter).
--               */
--              dev_info(smi->dev, "VLAN%d port mask for port %d, %08x\n",
--                       (port + 1), port, mask);
--              ret = rtl8366_set_vlan(smi, (port + 1), mask, mask, 0);
--              if (ret)
--                      return ret;
--
--              dev_info(smi->dev, "VLAN%d port %d, PVID set to %d\n",
--                       (port + 1), port, (port + 1));
--              ret = rtl8366_set_pvid(smi, port, (port + 1));
--              if (ret)
--                      return ret;
--      }
--
--      return rtl8366_enable_vlan(smi, true);
--}
--EXPORT_SYMBOL_GPL(rtl8366_init_vlan);
--
- int rtl8366_vlan_filtering(struct dsa_switch *ds, int port, bool vlan_filtering,
-                          struct netlink_ext_ack *extack)
- {
---- a/drivers/net/dsa/rtl8366rb.c
-+++ b/drivers/net/dsa/rtl8366rb.c
-@@ -985,7 +985,7 @@ static int rtl8366rb_setup(struct dsa_sw
-                       return ret;
-       }
--      ret = rtl8366_init_vlan(smi);
-+      ret = rtl8366_reset_vlan(smi);
-       if (ret)
-               return ret;
-@@ -999,8 +999,6 @@ static int rtl8366rb_setup(struct dsa_sw
-               return -ENODEV;
-       }
--      ds->configure_vlan_while_not_filtering = false;
--
-       return 0;
- }
diff --git a/target/linux/generic/backport-5.15/774-v5.16-03-net-dsa-rtl8366rb-Rewrite-weird-VLAN-filering-enable.patch b/target/linux/generic/backport-5.15/774-v5.16-03-net-dsa-rtl8366rb-Rewrite-weird-VLAN-filering-enable.patch
deleted file mode 100644 (file)
index 2b19752..0000000
+++ /dev/null
@@ -1,270 +0,0 @@
-From 7028f54b620f8df344b18e46e4a78e266091ab45 Mon Sep 17 00:00:00 2001
-From: Linus Walleij <[email protected]>
-Date: Sun, 26 Sep 2021 00:59:26 +0200
-Subject: [PATCH 03/11] net: dsa: rtl8366rb: Rewrite weird VLAN filering
- enablement
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-While we were defining one VLAN per port for isolating the ports
-the port_vlan_filtering() callback was implemented to enable a
-VLAN on the port + 1. This function makes no sense, not only is
-it incomplete as it only enables the VLAN, it doesn't do what
-the callback is supposed to do, which is to selectively enable
-and disable filtering on a certain port.
-
-Implement the correct callback: we have two registers dealing
-with filtering on the RTL9366RB, so we implement an ASIC-specific
-callback and implement filering using the register bit that makes
-the switch drop frames if the port is not in the VLAN member set.
-
-The DSA documentation Documentation/networking/switchdev.rst states:
-
-  When the bridge has VLAN filtering enabled and a PVID is not
-  configured on the ingress port, untagged and 802.1p tagged
-  packets must be dropped. When the bridge has VLAN filtering
-  enabled and a PVID exists on the ingress port, untagged and
-  priority-tagged packets must be accepted and forwarded according
-  to the bridge's port membership of the PVID VLAN. When the
-  bridge has VLAN filtering disabled, the presence/lack of a
-  PVID should not influence the packet forwarding decision.
-
-To comply with this, we add two arrays of bool in the RTL8366RB
-state that keeps track of if filtering and PVID is enabled or
-not for each port. We then add code such that whenever filtering
-or PVID changes, we update the filter according to the
-specification.
-
-Cc: Vladimir Oltean <[email protected]>
-Cc: Mauri Sandberg <[email protected]>
-Cc: Alvin Šipraga <[email protected]>
-Cc: Florian Fainelli <[email protected]>
-Cc: DENG Qingfang <[email protected]>
-Signed-off-by: Linus Walleij <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/dsa/realtek-smi-core.h |   2 -
- drivers/net/dsa/rtl8366.c          |  35 ----------
- drivers/net/dsa/rtl8366rb.c        | 102 +++++++++++++++++++++++++++--
- 3 files changed, 95 insertions(+), 44 deletions(-)
-
---- a/drivers/net/dsa/realtek-smi-core.h
-+++ b/drivers/net/dsa/realtek-smi-core.h
-@@ -129,8 +129,6 @@ int rtl8366_set_pvid(struct realtek_smi
- int rtl8366_enable_vlan4k(struct realtek_smi *smi, bool enable);
- int rtl8366_enable_vlan(struct realtek_smi *smi, bool enable);
- int rtl8366_reset_vlan(struct realtek_smi *smi);
--int rtl8366_vlan_filtering(struct dsa_switch *ds, int port, bool vlan_filtering,
--                         struct netlink_ext_ack *extack);
- int rtl8366_vlan_add(struct dsa_switch *ds, int port,
-                    const struct switchdev_obj_port_vlan *vlan,
-                    struct netlink_ext_ack *extack);
---- a/drivers/net/dsa/rtl8366.c
-+++ b/drivers/net/dsa/rtl8366.c
-@@ -292,41 +292,6 @@ int rtl8366_reset_vlan(struct realtek_sm
- }
- EXPORT_SYMBOL_GPL(rtl8366_reset_vlan);
--int rtl8366_vlan_filtering(struct dsa_switch *ds, int port, bool vlan_filtering,
--                         struct netlink_ext_ack *extack)
--{
--      struct realtek_smi *smi = ds->priv;
--      struct rtl8366_vlan_4k vlan4k;
--      int ret;
--
--      /* Use VLAN nr port + 1 since VLAN0 is not valid */
--      if (!smi->ops->is_vlan_valid(smi, port + 1))
--              return -EINVAL;
--
--      dev_info(smi->dev, "%s filtering on port %d\n",
--               vlan_filtering ? "enable" : "disable",
--               port);
--
--      /* TODO:
--       * The hardware support filter ID (FID) 0..7, I have no clue how to
--       * support this in the driver when the callback only says on/off.
--       */
--      ret = smi->ops->get_vlan_4k(smi, port + 1, &vlan4k);
--      if (ret)
--              return ret;
--
--      /* Just set the filter to FID 1 for now then */
--      ret = rtl8366_set_vlan(smi, port + 1,
--                             vlan4k.member,
--                             vlan4k.untag,
--                             1);
--      if (ret)
--              return ret;
--
--      return 0;
--}
--EXPORT_SYMBOL_GPL(rtl8366_vlan_filtering);
--
- int rtl8366_vlan_add(struct dsa_switch *ds, int port,
-                    const struct switchdev_obj_port_vlan *vlan,
-                    struct netlink_ext_ack *extack)
---- a/drivers/net/dsa/rtl8366rb.c
-+++ b/drivers/net/dsa/rtl8366rb.c
-@@ -143,6 +143,21 @@
- #define RTL8366RB_PHY_NO_OFFSET                       9
- #define RTL8366RB_PHY_NO_MASK                 (0x1f << 9)
-+/* VLAN Ingress Control Register 1, one bit per port.
-+ * bit 0 .. 5 will make the switch drop ingress frames without
-+ * VID such as untagged or priority-tagged frames for respective
-+ * port.
-+ * bit 6 .. 11 will make the switch drop ingress frames carrying
-+ * a C-tag with VID != 0 for respective port.
-+ */
-+#define RTL8366RB_VLAN_INGRESS_CTRL1_REG      0x037E
-+#define RTL8366RB_VLAN_INGRESS_CTRL1_DROP(port)       (BIT((port)) | BIT((port) + 6))
-+
-+/* VLAN Ingress Control Register 2, one bit per port.
-+ * bit0 .. bit5 will make the switch drop all ingress frames with
-+ * a VLAN classification that does not include the port is in its
-+ * member set.
-+ */
- #define RTL8366RB_VLAN_INGRESS_CTRL2_REG      0x037f
- /* LED control registers */
-@@ -321,9 +336,13 @@
- /**
-  * struct rtl8366rb - RTL8366RB-specific data
-  * @max_mtu: per-port max MTU setting
-+ * @pvid_enabled: if PVID is set for respective port
-+ * @vlan_filtering: if VLAN filtering is enabled for respective port
-  */
- struct rtl8366rb {
-       unsigned int max_mtu[RTL8366RB_NUM_PORTS];
-+      bool pvid_enabled[RTL8366RB_NUM_PORTS];
-+      bool vlan_filtering[RTL8366RB_NUM_PORTS];
- };
- static struct rtl8366_mib_counter rtl8366rb_mib_counters[] = {
-@@ -933,11 +952,13 @@ static int rtl8366rb_setup(struct dsa_sw
-       if (ret)
-               return ret;
--      /* Discard VLAN tagged packets if the port is not a member of
--       * the VLAN with which the packets is associated.
--       */
-+      /* Accept all packets by default, we enable filtering on-demand */
-+      ret = regmap_write(smi->map, RTL8366RB_VLAN_INGRESS_CTRL1_REG,
-+                         0);
-+      if (ret)
-+              return ret;
-       ret = regmap_write(smi->map, RTL8366RB_VLAN_INGRESS_CTRL2_REG,
--                         RTL8366RB_PORT_ALL);
-+                         0);
-       if (ret)
-               return ret;
-@@ -1209,6 +1230,53 @@ rtl8366rb_port_bridge_leave(struct dsa_s
-                          RTL8366RB_PORT_ISO_PORTS(port_bitmap), 0);
- }
-+/**
-+ * rtl8366rb_drop_untagged() - make the switch drop untagged and C-tagged frames
-+ * @smi: SMI state container
-+ * @port: the port to drop untagged and C-tagged frames on
-+ * @drop: whether to drop or pass untagged and C-tagged frames
-+ */
-+static int rtl8366rb_drop_untagged(struct realtek_smi *smi, int port, bool drop)
-+{
-+      return regmap_update_bits(smi->map, RTL8366RB_VLAN_INGRESS_CTRL1_REG,
-+                                RTL8366RB_VLAN_INGRESS_CTRL1_DROP(port),
-+                                drop ? RTL8366RB_VLAN_INGRESS_CTRL1_DROP(port) : 0);
-+}
-+
-+static int rtl8366rb_vlan_filtering(struct dsa_switch *ds, int port,
-+                                  bool vlan_filtering,
-+                                  struct netlink_ext_ack *extack)
-+{
-+      struct realtek_smi *smi = ds->priv;
-+      struct rtl8366rb *rb;
-+      int ret;
-+
-+      rb = smi->chip_data;
-+
-+      dev_dbg(smi->dev, "port %d: %s VLAN filtering\n", port,
-+              vlan_filtering ? "enable" : "disable");
-+
-+      /* If the port is not in the member set, the frame will be dropped */
-+      ret = regmap_update_bits(smi->map, RTL8366RB_VLAN_INGRESS_CTRL2_REG,
-+                               BIT(port), vlan_filtering ? BIT(port) : 0);
-+      if (ret)
-+              return ret;
-+
-+      /* Keep track if filtering is enabled on each port */
-+      rb->vlan_filtering[port] = vlan_filtering;
-+
-+      /* If VLAN filtering is enabled and PVID is also enabled, we must
-+       * not drop any untagged or C-tagged frames. If we turn off VLAN
-+       * filtering on a port, we need ti accept any frames.
-+       */
-+      if (vlan_filtering)
-+              ret = rtl8366rb_drop_untagged(smi, port, !rb->pvid_enabled[port]);
-+      else
-+              ret = rtl8366rb_drop_untagged(smi, port, false);
-+
-+      return ret;
-+}
-+
- static int rtl8366rb_change_mtu(struct dsa_switch *ds, int port, int new_mtu)
- {
-       struct realtek_smi *smi = ds->priv;
-@@ -1420,14 +1488,34 @@ static int rtl8366rb_get_mc_index(struct
- static int rtl8366rb_set_mc_index(struct realtek_smi *smi, int port, int index)
- {
-+      struct rtl8366rb *rb;
-+      bool pvid_enabled;
-+      int ret;
-+
-+      rb = smi->chip_data;
-+      pvid_enabled = !!index;
-+
-       if (port >= smi->num_ports || index >= RTL8366RB_NUM_VLANS)
-               return -EINVAL;
--      return regmap_update_bits(smi->map, RTL8366RB_PORT_VLAN_CTRL_REG(port),
-+      ret = regmap_update_bits(smi->map, RTL8366RB_PORT_VLAN_CTRL_REG(port),
-                               RTL8366RB_PORT_VLAN_CTRL_MASK <<
-                                       RTL8366RB_PORT_VLAN_CTRL_SHIFT(port),
-                               (index & RTL8366RB_PORT_VLAN_CTRL_MASK) <<
-                                       RTL8366RB_PORT_VLAN_CTRL_SHIFT(port));
-+      if (ret)
-+              return ret;
-+
-+      rb->pvid_enabled[port] = pvid_enabled;
-+
-+      /* If VLAN filtering is enabled and PVID is also enabled, we must
-+       * not drop any untagged or C-tagged frames. Make sure to update the
-+       * filtering setting.
-+       */
-+      if (rb->vlan_filtering[port])
-+              ret = rtl8366rb_drop_untagged(smi, port, !pvid_enabled);
-+
-+      return ret;
- }
- static bool rtl8366rb_is_vlan_valid(struct realtek_smi *smi, unsigned int vlan)
-@@ -1437,7 +1525,7 @@ static bool rtl8366rb_is_vlan_valid(stru
-       if (smi->vlan4k_enabled)
-               max = RTL8366RB_NUM_VIDS - 1;
--      if (vlan == 0 || vlan > max)
-+      if (vlan > max)
-               return false;
-       return true;
-@@ -1594,7 +1682,7 @@ static const struct dsa_switch_ops rtl83
-       .get_sset_count = rtl8366_get_sset_count,
-       .port_bridge_join = rtl8366rb_port_bridge_join,
-       .port_bridge_leave = rtl8366rb_port_bridge_leave,
--      .port_vlan_filtering = rtl8366_vlan_filtering,
-+      .port_vlan_filtering = rtl8366rb_vlan_filtering,
-       .port_vlan_add = rtl8366_vlan_add,
-       .port_vlan_del = rtl8366_vlan_del,
-       .port_enable = rtl8366rb_port_enable,
diff --git a/target/linux/generic/backport-5.15/774-v5.16-06-net-dsa-rtl8366-Drop-and-depromote-pointless-prints.patch b/target/linux/generic/backport-5.15/774-v5.16-06-net-dsa-rtl8366-Drop-and-depromote-pointless-prints.patch
deleted file mode 100644 (file)
index b56032c..0000000
+++ /dev/null
@@ -1,51 +0,0 @@
-From ddb59a5dc42714999c335dab4bf256125ba3120c Mon Sep 17 00:00:00 2001
-From: Linus Walleij <[email protected]>
-Date: Sun, 26 Sep 2021 00:59:29 +0200
-Subject: [PATCH 06/11] net: dsa: rtl8366: Drop and depromote pointless prints
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-We don't need a message for every VLAN association, dbg
-is fine. The message about adding the DSA or CPU
-port to a VLAN is directly misleading, this is perfectly
-fine.
-
-Cc: Vladimir Oltean <[email protected]>
-Cc: Mauri Sandberg <[email protected]>
-Cc: DENG Qingfang <[email protected]>
-Reviewed-by: Alvin Šipraga <[email protected]>
-Reviewed-by: Florian Fainelli <[email protected]>
-Signed-off-by: Linus Walleij <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/dsa/rtl8366.c | 11 ++++-------
- 1 file changed, 4 insertions(+), 7 deletions(-)
-
---- a/drivers/net/dsa/rtl8366.c
-+++ b/drivers/net/dsa/rtl8366.c
-@@ -318,12 +318,9 @@ int rtl8366_vlan_add(struct dsa_switch *
-               return ret;
-       }
--      dev_info(smi->dev, "add VLAN %d on port %d, %s, %s\n",
--               vlan->vid, port, untagged ? "untagged" : "tagged",
--               pvid ? " PVID" : "no PVID");
--
--      if (dsa_is_dsa_port(ds, port) || dsa_is_cpu_port(ds, port))
--              dev_err(smi->dev, "port is DSA or CPU port\n");
-+      dev_dbg(smi->dev, "add VLAN %d on port %d, %s, %s\n",
-+              vlan->vid, port, untagged ? "untagged" : "tagged",
-+              pvid ? "PVID" : "no PVID");
-       member |= BIT(port);
-@@ -356,7 +353,7 @@ int rtl8366_vlan_del(struct dsa_switch *
-       struct realtek_smi *smi = ds->priv;
-       int ret, i;
--      dev_info(smi->dev, "del VLAN %04x on port %d\n", vlan->vid, port);
-+      dev_dbg(smi->dev, "del VLAN %d on port %d\n", vlan->vid, port);
-       for (i = 0; i < smi->num_vlan_mc; i++) {
-               struct rtl8366_vlan_mc vlanmc;
diff --git a/target/linux/generic/backport-5.15/774-v5.16-07-net-dsa-rtl8366rb-Use-core-filtering-tracking.patch b/target/linux/generic/backport-5.15/774-v5.16-07-net-dsa-rtl8366rb-Use-core-filtering-tracking.patch
deleted file mode 100644 (file)
index 8cd1df9..0000000
+++ /dev/null
@@ -1,61 +0,0 @@
-From 5c9b66f3c8a3f72fa2a58e89a57c6d7afd550bf0 Mon Sep 17 00:00:00 2001
-From: Linus Walleij <[email protected]>
-Date: Wed, 29 Sep 2021 13:23:22 +0200
-Subject: [PATCH 07/11] net: dsa: rtl8366rb: Use core filtering tracking
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-We added a state variable to track whether a certain port
-was VLAN filtering or not, but we can just inquire the DSA
-core about this.
-
-Cc: Vladimir Oltean <[email protected]>
-Cc: Mauri Sandberg <[email protected]>
-Cc: DENG Qingfang <[email protected]>
-Cc: Alvin Šipraga <[email protected]>
-Cc: Reviewed-by: Florian Fainelli <[email protected]>
-Signed-off-by: Linus Walleij <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/dsa/rtl8366rb.c | 9 ++-------
- 1 file changed, 2 insertions(+), 7 deletions(-)
-
---- a/drivers/net/dsa/rtl8366rb.c
-+++ b/drivers/net/dsa/rtl8366rb.c
-@@ -337,12 +337,10 @@
-  * struct rtl8366rb - RTL8366RB-specific data
-  * @max_mtu: per-port max MTU setting
-  * @pvid_enabled: if PVID is set for respective port
-- * @vlan_filtering: if VLAN filtering is enabled for respective port
-  */
- struct rtl8366rb {
-       unsigned int max_mtu[RTL8366RB_NUM_PORTS];
-       bool pvid_enabled[RTL8366RB_NUM_PORTS];
--      bool vlan_filtering[RTL8366RB_NUM_PORTS];
- };
- static struct rtl8366_mib_counter rtl8366rb_mib_counters[] = {
-@@ -1262,12 +1260,9 @@ static int rtl8366rb_vlan_filtering(stru
-       if (ret)
-               return ret;
--      /* Keep track if filtering is enabled on each port */
--      rb->vlan_filtering[port] = vlan_filtering;
--
-       /* If VLAN filtering is enabled and PVID is also enabled, we must
-        * not drop any untagged or C-tagged frames. If we turn off VLAN
--       * filtering on a port, we need ti accept any frames.
-+       * filtering on a port, we need to accept any frames.
-        */
-       if (vlan_filtering)
-               ret = rtl8366rb_drop_untagged(smi, port, !rb->pvid_enabled[port]);
-@@ -1512,7 +1507,7 @@ static int rtl8366rb_set_mc_index(struct
-        * not drop any untagged or C-tagged frames. Make sure to update the
-        * filtering setting.
-        */
--      if (rb->vlan_filtering[port])
-+      if (dsa_port_is_vlan_filtering(dsa_to_port(smi->ds, port)))
-               ret = rtl8366rb_drop_untagged(smi, port, !pvid_enabled);
-       return ret;
diff --git a/target/linux/generic/backport-5.15/774-v5.16-08-net-dsa-rtl8366rb-Support-disabling-learning.patch b/target/linux/generic/backport-5.15/774-v5.16-08-net-dsa-rtl8366rb-Support-disabling-learning.patch
deleted file mode 100644 (file)
index 8306eb5..0000000
+++ /dev/null
@@ -1,115 +0,0 @@
-From 831a3d26bea0d14f8563eecf96def660a74a3000 Mon Sep 17 00:00:00 2001
-From: Linus Walleij <[email protected]>
-Date: Tue, 5 Oct 2021 21:47:02 +0200
-Subject: [PATCH 08/11] net: dsa: rtl8366rb: Support disabling learning
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-The RTL8366RB hardware supports disabling learning per-port
-so let's make use of this feature. Rename some unfortunately
-named registers in the process.
-
-Suggested-by: Vladimir Oltean <[email protected]>
-Cc: Alvin Šipraga <[email protected]>
-Cc: Mauri Sandberg <[email protected]>
-Cc: Florian Fainelli <[email protected]>
-Cc: DENG Qingfang <[email protected]>
-Reviewed-by: Vladimir Oltean <[email protected]>
-Signed-off-by: Linus Walleij <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/dsa/rtl8366rb.c | 50 ++++++++++++++++++++++++++++++++-----
- 1 file changed, 44 insertions(+), 6 deletions(-)
-
---- a/drivers/net/dsa/rtl8366rb.c
-+++ b/drivers/net/dsa/rtl8366rb.c
-@@ -14,6 +14,7 @@
- #include <linux/bitops.h>
- #include <linux/etherdevice.h>
-+#include <linux/if_bridge.h>
- #include <linux/interrupt.h>
- #include <linux/irqdomain.h>
- #include <linux/irqchip/chained_irq.h>
-@@ -42,9 +43,12 @@
- /* Port Enable Control register */
- #define RTL8366RB_PECR                                0x0001
--/* Switch Security Control registers */
--#define RTL8366RB_SSCR0                               0x0002
--#define RTL8366RB_SSCR1                               0x0003
-+/* Switch per-port learning disablement register */
-+#define RTL8366RB_PORT_LEARNDIS_CTRL          0x0002
-+
-+/* Security control, actually aging register */
-+#define RTL8366RB_SECURITY_CTRL                       0x0003
-+
- #define RTL8366RB_SSCR2                               0x0004
- #define RTL8366RB_SSCR2_DROP_UNKNOWN_DA               BIT(0)
-@@ -927,13 +931,14 @@ static int rtl8366rb_setup(struct dsa_sw
-               /* layer 2 size, see rtl8366rb_change_mtu() */
-               rb->max_mtu[i] = 1532;
--      /* Enable learning for all ports */
--      ret = regmap_write(smi->map, RTL8366RB_SSCR0, 0);
-+      /* Disable learning for all ports */
-+      ret = regmap_write(smi->map, RTL8366RB_PORT_LEARNDIS_CTRL,
-+                         RTL8366RB_PORT_ALL);
-       if (ret)
-               return ret;
-       /* Enable auto ageing for all ports */
--      ret = regmap_write(smi->map, RTL8366RB_SSCR1, 0);
-+      ret = regmap_write(smi->map, RTL8366RB_SECURITY_CTRL, 0);
-       if (ret)
-               return ret;
-@@ -1272,6 +1277,37 @@ static int rtl8366rb_vlan_filtering(stru
-       return ret;
- }
-+static int
-+rtl8366rb_port_pre_bridge_flags(struct dsa_switch *ds, int port,
-+                              struct switchdev_brport_flags flags,
-+                              struct netlink_ext_ack *extack)
-+{
-+      /* We support enabling/disabling learning */
-+      if (flags.mask & ~(BR_LEARNING))
-+              return -EINVAL;
-+
-+      return 0;
-+}
-+
-+static int
-+rtl8366rb_port_bridge_flags(struct dsa_switch *ds, int port,
-+                          struct switchdev_brport_flags flags,
-+                          struct netlink_ext_ack *extack)
-+{
-+      struct realtek_smi *smi = ds->priv;
-+      int ret;
-+
-+      if (flags.mask & BR_LEARNING) {
-+              ret = regmap_update_bits(smi->map, RTL8366RB_PORT_LEARNDIS_CTRL,
-+                                       BIT(port),
-+                                       (flags.val & BR_LEARNING) ? 0 : BIT(port));
-+              if (ret)
-+                      return ret;
-+      }
-+
-+      return 0;
-+}
-+
- static int rtl8366rb_change_mtu(struct dsa_switch *ds, int port, int new_mtu)
- {
-       struct realtek_smi *smi = ds->priv;
-@@ -1682,6 +1718,8 @@ static const struct dsa_switch_ops rtl83
-       .port_vlan_del = rtl8366_vlan_del,
-       .port_enable = rtl8366rb_port_enable,
-       .port_disable = rtl8366rb_port_disable,
-+      .port_pre_bridge_flags = rtl8366rb_port_pre_bridge_flags,
-+      .port_bridge_flags = rtl8366rb_port_bridge_flags,
-       .port_change_mtu = rtl8366rb_change_mtu,
-       .port_max_mtu = rtl8366rb_max_mtu,
- };
diff --git a/target/linux/generic/backport-5.15/774-v5.16-09-net-dsa-rtl8366rb-Support-fast-aging.patch b/target/linux/generic/backport-5.15/774-v5.16-09-net-dsa-rtl8366rb-Support-fast-aging.patch
deleted file mode 100644 (file)
index a74108e..0000000
+++ /dev/null
@@ -1,57 +0,0 @@
-From 8eb13420eb9ab4a4e2ebd612bf5dc9dba0039236 Mon Sep 17 00:00:00 2001
-From: Linus Walleij <[email protected]>
-Date: Tue, 5 Oct 2021 21:47:03 +0200
-Subject: [PATCH 09/11] net: dsa: rtl8366rb: Support fast aging
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-This implements fast aging per-port using the special "security"
-register, which will flush any learned L2 LUT entries on a port.
-
-The vendor API just enabled setting and clearing this bit, so
-we set it to age out any entries on the port and then we clear
-it again.
-
-Suggested-by: Vladimir Oltean <[email protected]>
-Cc: Mauri Sandberg <[email protected]>
-Cc: DENG Qingfang <[email protected]>
-Cc: Florian Fainelli <[email protected]>
-Reviewed-by: Alvin Šipraga <[email protected]>
-Signed-off-by: Linus Walleij <[email protected]>
-Reviewed-by: Vladimir Oltean <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/dsa/rtl8366rb.c | 14 ++++++++++++++
- 1 file changed, 14 insertions(+)
-
---- a/drivers/net/dsa/rtl8366rb.c
-+++ b/drivers/net/dsa/rtl8366rb.c
-@@ -1308,6 +1308,19 @@ rtl8366rb_port_bridge_flags(struct dsa_s
-       return 0;
- }
-+static void
-+rtl8366rb_port_fast_age(struct dsa_switch *ds, int port)
-+{
-+      struct realtek_smi *smi = ds->priv;
-+
-+      /* This will age out any learned L2 entries */
-+      regmap_update_bits(smi->map, RTL8366RB_SECURITY_CTRL,
-+                         BIT(port), BIT(port));
-+      /* Restore the normal state of things */
-+      regmap_update_bits(smi->map, RTL8366RB_SECURITY_CTRL,
-+                         BIT(port), 0);
-+}
-+
- static int rtl8366rb_change_mtu(struct dsa_switch *ds, int port, int new_mtu)
- {
-       struct realtek_smi *smi = ds->priv;
-@@ -1720,6 +1733,7 @@ static const struct dsa_switch_ops rtl83
-       .port_disable = rtl8366rb_port_disable,
-       .port_pre_bridge_flags = rtl8366rb_port_pre_bridge_flags,
-       .port_bridge_flags = rtl8366rb_port_bridge_flags,
-+      .port_fast_age = rtl8366rb_port_fast_age,
-       .port_change_mtu = rtl8366rb_change_mtu,
-       .port_max_mtu = rtl8366rb_max_mtu,
- };
diff --git a/target/linux/generic/backport-5.15/774-v5.16-10-net-dsa-rtl8366rb-Support-setting-STP-state.patch b/target/linux/generic/backport-5.15/774-v5.16-10-net-dsa-rtl8366rb-Support-setting-STP-state.patch
deleted file mode 100644 (file)
index e787ce9..0000000
+++ /dev/null
@@ -1,107 +0,0 @@
-From 90c855471a89d3e05ecf5b6464bd04abf2c83b70 Mon Sep 17 00:00:00 2001
-From: Linus Walleij <[email protected]>
-Date: Tue, 5 Oct 2021 21:47:04 +0200
-Subject: [PATCH 10/11] net: dsa: rtl8366rb: Support setting STP state
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-This adds support for setting the STP state to the RTL8366RB
-DSA switch. This rids the following message from the kernel on
-e.g. OpenWrt:
-
-DSA: failed to set STP state 3 (-95)
-
-Since the RTL8366RB has one STP state register per FID with
-two bit per port in each, we simply loop over all the FIDs
-and set the state on all of them.
-
-Cc: Vladimir Oltean <[email protected]>
-Cc: Alvin Šipraga <[email protected]>
-Cc: Mauri Sandberg <[email protected]>
-Cc: DENG Qingfang <[email protected]>
-Signed-off-by: Linus Walleij <[email protected]>
-Reviewed-by: Vladimir Oltean <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/dsa/rtl8366rb.c | 48 +++++++++++++++++++++++++++++++++++++
- 1 file changed, 48 insertions(+)
-
---- a/drivers/net/dsa/rtl8366rb.c
-+++ b/drivers/net/dsa/rtl8366rb.c
-@@ -110,6 +110,18 @@
- #define RTL8366RB_POWER_SAVING_REG    0x0021
-+/* Spanning tree status (STP) control, two bits per port per FID */
-+#define RTL8366RB_STP_STATE_BASE      0x0050 /* 0x0050..0x0057 */
-+#define RTL8366RB_STP_STATE_DISABLED  0x0
-+#define RTL8366RB_STP_STATE_BLOCKING  0x1
-+#define RTL8366RB_STP_STATE_LEARNING  0x2
-+#define RTL8366RB_STP_STATE_FORWARDING        0x3
-+#define RTL8366RB_STP_MASK            GENMASK(1, 0)
-+#define RTL8366RB_STP_STATE(port, state) \
-+      ((state) << ((port) * 2))
-+#define RTL8366RB_STP_STATE_MASK(port) \
-+      RTL8366RB_STP_STATE((port), RTL8366RB_STP_MASK)
-+
- /* CPU port control reg */
- #define RTL8368RB_CPU_CTRL_REG                0x0061
- #define RTL8368RB_CPU_PORTS_MSK               0x00FF
-@@ -234,6 +246,7 @@
- #define RTL8366RB_NUM_LEDGROUPS               4
- #define RTL8366RB_NUM_VIDS            4096
- #define RTL8366RB_PRIORITYMAX         7
-+#define RTL8366RB_NUM_FIDS            8
- #define RTL8366RB_FIDMAX              7
- #define RTL8366RB_PORT_1              BIT(0) /* In userspace port 0 */
-@@ -1309,6 +1322,40 @@ rtl8366rb_port_bridge_flags(struct dsa_s
- }
- static void
-+rtl8366rb_port_stp_state_set(struct dsa_switch *ds, int port, u8 state)
-+{
-+      struct realtek_smi *smi = ds->priv;
-+      u32 val;
-+      int i;
-+
-+      switch (state) {
-+      case BR_STATE_DISABLED:
-+              val = RTL8366RB_STP_STATE_DISABLED;
-+              break;
-+      case BR_STATE_BLOCKING:
-+      case BR_STATE_LISTENING:
-+              val = RTL8366RB_STP_STATE_BLOCKING;
-+              break;
-+      case BR_STATE_LEARNING:
-+              val = RTL8366RB_STP_STATE_LEARNING;
-+              break;
-+      case BR_STATE_FORWARDING:
-+              val = RTL8366RB_STP_STATE_FORWARDING;
-+              break;
-+      default:
-+              dev_err(smi->dev, "unknown bridge state requested\n");
-+              return;
-+      };
-+
-+      /* Set the same status for the port on all the FIDs */
-+      for (i = 0; i < RTL8366RB_NUM_FIDS; i++) {
-+              regmap_update_bits(smi->map, RTL8366RB_STP_STATE_BASE + i,
-+                                 RTL8366RB_STP_STATE_MASK(port),
-+                                 RTL8366RB_STP_STATE(port, val));
-+      }
-+}
-+
-+static void
- rtl8366rb_port_fast_age(struct dsa_switch *ds, int port)
- {
-       struct realtek_smi *smi = ds->priv;
-@@ -1733,6 +1780,7 @@ static const struct dsa_switch_ops rtl83
-       .port_disable = rtl8366rb_port_disable,
-       .port_pre_bridge_flags = rtl8366rb_port_pre_bridge_flags,
-       .port_bridge_flags = rtl8366rb_port_bridge_flags,
-+      .port_stp_state_set = rtl8366rb_port_stp_state_set,
-       .port_fast_age = rtl8366rb_port_fast_age,
-       .port_change_mtu = rtl8366rb_change_mtu,
-       .port_max_mtu = rtl8366rb_max_mtu,
diff --git a/target/linux/generic/backport-5.15/775-v6.0-01-net-ethernet-stmicro-stmmac-move-queue-reset-to-dedi.patch b/target/linux/generic/backport-5.15/775-v6.0-01-net-ethernet-stmicro-stmmac-move-queue-reset-to-dedi.patch
deleted file mode 100644 (file)
index 43fc3b1..0000000
+++ /dev/null
@@ -1,142 +0,0 @@
-From f9ec5723c3dbfcede9c7b0dcdf85e401ce16316c Mon Sep 17 00:00:00 2001
-From: Christian Marangi <[email protected]>
-Date: Sat, 23 Jul 2022 16:29:29 +0200
-Subject: [PATCH 1/5] net: ethernet: stmicro: stmmac: move queue reset to
- dedicated functions
-
-Move queue reset to dedicated functions. This aside from a simple
-cleanup is also required to allocate a dma conf without resetting the tx
-queue while the device is temporarily detached as now the reset is not
-part of the dma init function and can be done later in the code flow.
-
-Signed-off-by: Christian Marangi <[email protected]>
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- .../net/ethernet/stmicro/stmmac/stmmac_main.c | 59 ++++++++++---------
- 1 file changed, 31 insertions(+), 28 deletions(-)
-
---- a/drivers/net/ethernet/stmicro/stmmac/stmmac_main.c
-+++ b/drivers/net/ethernet/stmicro/stmmac/stmmac_main.c
-@@ -130,6 +130,9 @@ static irqreturn_t stmmac_mac_interrupt(
- static irqreturn_t stmmac_safety_interrupt(int irq, void *dev_id);
- static irqreturn_t stmmac_msi_intr_tx(int irq, void *data);
- static irqreturn_t stmmac_msi_intr_rx(int irq, void *data);
-+static void stmmac_reset_rx_queue(struct stmmac_priv *priv, u32 queue);
-+static void stmmac_reset_tx_queue(struct stmmac_priv *priv, u32 queue);
-+static void stmmac_reset_queues_param(struct stmmac_priv *priv);
- static void stmmac_tx_timer_arm(struct stmmac_priv *priv, u32 queue);
- static void stmmac_flush_tx_descriptors(struct stmmac_priv *priv, int queue);
-@@ -1713,9 +1716,6 @@ static int __init_dma_rx_desc_rings(stru
-                       return -ENOMEM;
-       }
--      rx_q->cur_rx = 0;
--      rx_q->dirty_rx = 0;
--
-       /* Setup the chained descriptor addresses */
-       if (priv->mode == STMMAC_CHAIN_MODE) {
-               if (priv->extend_desc)
-@@ -1821,12 +1821,6 @@ static int __init_dma_tx_desc_rings(stru
-               tx_q->tx_skbuff[i] = NULL;
-       }
--      tx_q->dirty_tx = 0;
--      tx_q->cur_tx = 0;
--      tx_q->mss = 0;
--
--      netdev_tx_reset_queue(netdev_get_tx_queue(priv->dev, queue));
--
-       return 0;
- }
-@@ -2695,10 +2689,7 @@ static void stmmac_tx_err(struct stmmac_
-       stmmac_stop_tx_dma(priv, chan);
-       dma_free_tx_skbufs(priv, chan);
-       stmmac_clear_tx_descriptors(priv, chan);
--      tx_q->dirty_tx = 0;
--      tx_q->cur_tx = 0;
--      tx_q->mss = 0;
--      netdev_tx_reset_queue(netdev_get_tx_queue(priv->dev, chan));
-+      stmmac_reset_tx_queue(priv, chan);
-       stmmac_init_tx_chan(priv, priv->ioaddr, priv->plat->dma_cfg,
-                           tx_q->dma_tx_phy, chan);
-       stmmac_start_tx_dma(priv, chan);
-@@ -3783,6 +3774,8 @@ static int stmmac_open(struct net_device
-               }
-       }
-+      stmmac_reset_queues_param(priv);
-+
-       ret = stmmac_hw_setup(dev, true);
-       if (ret < 0) {
-               netdev_err(priv->dev, "%s: Hw setup failed\n", __func__);
-@@ -6412,6 +6405,7 @@ void stmmac_enable_rx_queue(struct stmma
-               return;
-       }
-+      stmmac_reset_rx_queue(priv, queue);
-       stmmac_clear_rx_descriptors(priv, queue);
-       stmmac_init_rx_chan(priv, priv->ioaddr, priv->plat->dma_cfg,
-@@ -6473,6 +6467,7 @@ void stmmac_enable_tx_queue(struct stmma
-               return;
-       }
-+      stmmac_reset_tx_queue(priv, queue);
-       stmmac_clear_tx_descriptors(priv, queue);
-       stmmac_init_tx_chan(priv, priv->ioaddr, priv->plat->dma_cfg,
-@@ -7400,6 +7395,25 @@ int stmmac_suspend(struct device *dev)
- }
- EXPORT_SYMBOL_GPL(stmmac_suspend);
-+static void stmmac_reset_rx_queue(struct stmmac_priv *priv, u32 queue)
-+{
-+      struct stmmac_rx_queue *rx_q = &priv->rx_queue[queue];
-+
-+      rx_q->cur_rx = 0;
-+      rx_q->dirty_rx = 0;
-+}
-+
-+static void stmmac_reset_tx_queue(struct stmmac_priv *priv, u32 queue)
-+{
-+      struct stmmac_tx_queue *tx_q = &priv->tx_queue[queue];
-+
-+      tx_q->cur_tx = 0;
-+      tx_q->dirty_tx = 0;
-+      tx_q->mss = 0;
-+
-+      netdev_tx_reset_queue(netdev_get_tx_queue(priv->dev, queue));
-+}
-+
- /**
-  * stmmac_reset_queues_param - reset queue parameters
-  * @priv: device pointer
-@@ -7410,22 +7424,11 @@ static void stmmac_reset_queues_param(st
-       u32 tx_cnt = priv->plat->tx_queues_to_use;
-       u32 queue;
--      for (queue = 0; queue < rx_cnt; queue++) {
--              struct stmmac_rx_queue *rx_q = &priv->rx_queue[queue];
-+      for (queue = 0; queue < rx_cnt; queue++)
-+              stmmac_reset_rx_queue(priv, queue);
--              rx_q->cur_rx = 0;
--              rx_q->dirty_rx = 0;
--      }
--
--      for (queue = 0; queue < tx_cnt; queue++) {
--              struct stmmac_tx_queue *tx_q = &priv->tx_queue[queue];
--
--              tx_q->cur_tx = 0;
--              tx_q->dirty_tx = 0;
--              tx_q->mss = 0;
--
--              netdev_tx_reset_queue(netdev_get_tx_queue(priv->dev, queue));
--      }
-+      for (queue = 0; queue < tx_cnt; queue++)
-+              stmmac_reset_tx_queue(priv, queue);
- }
- /**
diff --git a/target/linux/generic/backport-5.15/775-v6.0-02-net-ethernet-stmicro-stmmac-first-disable-all-queues.patch b/target/linux/generic/backport-5.15/775-v6.0-02-net-ethernet-stmicro-stmmac-first-disable-all-queues.patch
deleted file mode 100644 (file)
index 0940d3d..0000000
+++ /dev/null
@@ -1,37 +0,0 @@
-From 7028471edb646bfc532fec0973e50e784cdcb7c6 Mon Sep 17 00:00:00 2001
-From: Christian Marangi <[email protected]>
-Date: Sat, 23 Jul 2022 16:29:30 +0200
-Subject: [PATCH 2/5] net: ethernet: stmicro: stmmac: first disable all queues
- and disconnect in release
-
-Disable all queues and disconnect before tx_disable in stmmac_release to
-prevent a corner case where packet may be still queued at the same time
-tx_disable is called resulting in kernel panic if some packet still has
-to be processed.
-
-Signed-off-by: Christian Marangi <[email protected]>
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- drivers/net/ethernet/stmicro/stmmac/stmmac_main.c | 4 ++--
- 1 file changed, 2 insertions(+), 2 deletions(-)
-
---- a/drivers/net/ethernet/stmicro/stmmac/stmmac_main.c
-+++ b/drivers/net/ethernet/stmicro/stmmac/stmmac_main.c
-@@ -3837,8 +3837,6 @@ static int stmmac_release(struct net_dev
-       struct stmmac_priv *priv = netdev_priv(dev);
-       u32 chan;
--      netif_tx_disable(dev);
--
-       if (device_may_wakeup(priv->device))
-               phylink_speed_down(priv->phylink, false);
-       /* Stop and disconnect the PHY */
-@@ -3850,6 +3848,8 @@ static int stmmac_release(struct net_dev
-       for (chan = 0; chan < priv->plat->tx_queues_to_use; chan++)
-               hrtimer_cancel(&priv->tx_queue[chan].txtimer);
-+      netif_tx_disable(dev);
-+
-       /* Free the IRQ lines */
-       stmmac_free_irq(dev, REQ_IRQ_ERR_ALL, 0);
diff --git a/target/linux/generic/backport-5.15/775-v6.0-03-net-ethernet-stmicro-stmmac-move-dma-conf-to-dedicat.patch b/target/linux/generic/backport-5.15/775-v6.0-03-net-ethernet-stmicro-stmmac-move-dma-conf-to-dedicat.patch
deleted file mode 100644 (file)
index 1b5a8a7..0000000
+++ /dev/null
@@ -1,1289 +0,0 @@
-From 8531c80800c10e8ef7952022326c2f983e1314bf Mon Sep 17 00:00:00 2001
-From: Christian Marangi <[email protected]>
-Date: Sat, 23 Jul 2022 16:29:31 +0200
-Subject: [PATCH 3/5] net: ethernet: stmicro: stmmac: move dma conf to
- dedicated struct
-
-Move dma buf conf to dedicated struct. This in preparation for code
-rework that will permit to allocate separate dma_conf without affecting
-the priv struct.
-
-Signed-off-by: Christian Marangi <[email protected]>
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- .../net/ethernet/stmicro/stmmac/chain_mode.c  |   6 +-
- .../net/ethernet/stmicro/stmmac/ring_mode.c   |   4 +-
- drivers/net/ethernet/stmicro/stmmac/stmmac.h  |  21 +-
- .../ethernet/stmicro/stmmac/stmmac_ethtool.c  |   4 +-
- .../net/ethernet/stmicro/stmmac/stmmac_main.c | 286 +++++++++---------
- .../stmicro/stmmac/stmmac_selftests.c         |   8 +-
- .../net/ethernet/stmicro/stmmac/stmmac_tc.c   |   6 +-
- 7 files changed, 172 insertions(+), 163 deletions(-)
-
---- a/drivers/net/ethernet/stmicro/stmmac/chain_mode.c
-+++ b/drivers/net/ethernet/stmicro/stmmac/chain_mode.c
-@@ -46,7 +46,7 @@ static int jumbo_frm(void *p, struct sk_
-       while (len != 0) {
-               tx_q->tx_skbuff[entry] = NULL;
--              entry = STMMAC_GET_ENTRY(entry, priv->dma_tx_size);
-+              entry = STMMAC_GET_ENTRY(entry, priv->dma_conf.dma_tx_size);
-               desc = tx_q->dma_tx + entry;
-               if (len > bmax) {
-@@ -137,7 +137,7 @@ static void refill_desc3(void *priv_ptr,
-                */
-               p->des3 = cpu_to_le32((unsigned int)(rx_q->dma_rx_phy +
-                                     (((rx_q->dirty_rx) + 1) %
--                                     priv->dma_rx_size) *
-+                                     priv->dma_conf.dma_rx_size) *
-                                     sizeof(struct dma_desc)));
- }
-@@ -155,7 +155,7 @@ static void clean_desc3(void *priv_ptr,
-                */
-               p->des3 = cpu_to_le32((unsigned int)((tx_q->dma_tx_phy +
-                                     ((tx_q->dirty_tx + 1) %
--                                     priv->dma_tx_size))
-+                                     priv->dma_conf.dma_tx_size))
-                                     * sizeof(struct dma_desc)));
- }
---- a/drivers/net/ethernet/stmicro/stmmac/ring_mode.c
-+++ b/drivers/net/ethernet/stmicro/stmmac/ring_mode.c
-@@ -51,7 +51,7 @@ static int jumbo_frm(void *p, struct sk_
-               stmmac_prepare_tx_desc(priv, desc, 1, bmax, csum,
-                               STMMAC_RING_MODE, 0, false, skb->len);
-               tx_q->tx_skbuff[entry] = NULL;
--              entry = STMMAC_GET_ENTRY(entry, priv->dma_tx_size);
-+              entry = STMMAC_GET_ENTRY(entry, priv->dma_conf.dma_tx_size);
-               if (priv->extend_desc)
-                       desc = (struct dma_desc *)(tx_q->dma_etx + entry);
-@@ -107,7 +107,7 @@ static void refill_desc3(void *priv_ptr,
-       struct stmmac_priv *priv = rx_q->priv_data;
-       /* Fill DES3 in case of RING mode */
--      if (priv->dma_buf_sz == BUF_SIZE_16KiB)
-+      if (priv->dma_conf.dma_buf_sz == BUF_SIZE_16KiB)
-               p->des3 = cpu_to_le32(le32_to_cpu(p->des2) + BUF_SIZE_8KiB);
- }
---- a/drivers/net/ethernet/stmicro/stmmac/stmmac.h
-+++ b/drivers/net/ethernet/stmicro/stmmac/stmmac.h
-@@ -185,6 +185,18 @@ struct stmmac_rfs_entry {
-       int tc;
- };
-+struct stmmac_dma_conf {
-+      unsigned int dma_buf_sz;
-+
-+      /* RX Queue */
-+      struct stmmac_rx_queue rx_queue[MTL_MAX_RX_QUEUES];
-+      unsigned int dma_rx_size;
-+
-+      /* TX Queue */
-+      struct stmmac_tx_queue tx_queue[MTL_MAX_TX_QUEUES];
-+      unsigned int dma_tx_size;
-+};
-+
- struct stmmac_priv {
-       /* Frequently used values are kept adjacent for cache effect */
-       u32 tx_coal_frames[MTL_MAX_TX_QUEUES];
-@@ -199,7 +211,6 @@ struct stmmac_priv {
-       int sph_cap;
-       u32 sarc_type;
--      unsigned int dma_buf_sz;
-       unsigned int rx_copybreak;
-       u32 rx_riwt[MTL_MAX_TX_QUEUES];
-       int hwts_rx_en;
-@@ -211,13 +222,7 @@ struct stmmac_priv {
-       int (*hwif_quirks)(struct stmmac_priv *priv);
-       struct mutex lock;
--      /* RX Queue */
--      struct stmmac_rx_queue rx_queue[MTL_MAX_RX_QUEUES];
--      unsigned int dma_rx_size;
--
--      /* TX Queue */
--      struct stmmac_tx_queue tx_queue[MTL_MAX_TX_QUEUES];
--      unsigned int dma_tx_size;
-+      struct stmmac_dma_conf dma_conf;
-       /* Generic channel for NAPI */
-       struct stmmac_channel channel[STMMAC_CH_MAX];
---- a/drivers/net/ethernet/stmicro/stmmac/stmmac_ethtool.c
-+++ b/drivers/net/ethernet/stmicro/stmmac/stmmac_ethtool.c
-@@ -484,8 +484,8 @@ static void stmmac_get_ringparam(struct
-       ring->rx_max_pending = DMA_MAX_RX_SIZE;
-       ring->tx_max_pending = DMA_MAX_TX_SIZE;
--      ring->rx_pending = priv->dma_rx_size;
--      ring->tx_pending = priv->dma_tx_size;
-+      ring->rx_pending = priv->dma_conf.dma_rx_size;
-+      ring->tx_pending = priv->dma_conf.dma_tx_size;
- }
- static int stmmac_set_ringparam(struct net_device *netdev,
---- a/drivers/net/ethernet/stmicro/stmmac/stmmac_main.c
-+++ b/drivers/net/ethernet/stmicro/stmmac/stmmac_main.c
-@@ -74,8 +74,8 @@ static int phyaddr = -1;
- module_param(phyaddr, int, 0444);
- MODULE_PARM_DESC(phyaddr, "Physical device address");
--#define STMMAC_TX_THRESH(x)   ((x)->dma_tx_size / 4)
--#define STMMAC_RX_THRESH(x)   ((x)->dma_rx_size / 4)
-+#define STMMAC_TX_THRESH(x)   ((x)->dma_conf.dma_tx_size / 4)
-+#define STMMAC_RX_THRESH(x)   ((x)->dma_conf.dma_rx_size / 4)
- /* Limit to make sure XDP TX and slow path can coexist */
- #define STMMAC_XSK_TX_BUDGET_MAX      256
-@@ -232,7 +232,7 @@ static void stmmac_disable_all_queues(st
-       /* synchronize_rcu() needed for pending XDP buffers to drain */
-       for (queue = 0; queue < rx_queues_cnt; queue++) {
--              rx_q = &priv->rx_queue[queue];
-+              rx_q = &priv->dma_conf.rx_queue[queue];
-               if (rx_q->xsk_pool) {
-                       synchronize_rcu();
-                       break;
-@@ -358,13 +358,13 @@ static void print_pkt(unsigned char *buf
- static inline u32 stmmac_tx_avail(struct stmmac_priv *priv, u32 queue)
- {
--      struct stmmac_tx_queue *tx_q = &priv->tx_queue[queue];
-+      struct stmmac_tx_queue *tx_q = &priv->dma_conf.tx_queue[queue];
-       u32 avail;
-       if (tx_q->dirty_tx > tx_q->cur_tx)
-               avail = tx_q->dirty_tx - tx_q->cur_tx - 1;
-       else
--              avail = priv->dma_tx_size - tx_q->cur_tx + tx_q->dirty_tx - 1;
-+              avail = priv->dma_conf.dma_tx_size - tx_q->cur_tx + tx_q->dirty_tx - 1;
-       return avail;
- }
-@@ -376,13 +376,13 @@ static inline u32 stmmac_tx_avail(struct
-  */
- static inline u32 stmmac_rx_dirty(struct stmmac_priv *priv, u32 queue)
- {
--      struct stmmac_rx_queue *rx_q = &priv->rx_queue[queue];
-+      struct stmmac_rx_queue *rx_q = &priv->dma_conf.rx_queue[queue];
-       u32 dirty;
-       if (rx_q->dirty_rx <= rx_q->cur_rx)
-               dirty = rx_q->cur_rx - rx_q->dirty_rx;
-       else
--              dirty = priv->dma_rx_size - rx_q->dirty_rx + rx_q->cur_rx;
-+              dirty = priv->dma_conf.dma_rx_size - rx_q->dirty_rx + rx_q->cur_rx;
-       return dirty;
- }
-@@ -410,7 +410,7 @@ static int stmmac_enable_eee_mode(struct
-       /* check if all TX queues have the work finished */
-       for (queue = 0; queue < tx_cnt; queue++) {
--              struct stmmac_tx_queue *tx_q = &priv->tx_queue[queue];
-+              struct stmmac_tx_queue *tx_q = &priv->dma_conf.tx_queue[queue];
-               if (tx_q->dirty_tx != tx_q->cur_tx)
-                       return -EBUSY; /* still unfinished work */
-@@ -1310,7 +1310,7 @@ static void stmmac_display_rx_rings(stru
-       /* Display RX rings */
-       for (queue = 0; queue < rx_cnt; queue++) {
--              struct stmmac_rx_queue *rx_q = &priv->rx_queue[queue];
-+              struct stmmac_rx_queue *rx_q = &priv->dma_conf.rx_queue[queue];
-               pr_info("\tRX Queue %u rings\n", queue);
-@@ -1323,7 +1323,7 @@ static void stmmac_display_rx_rings(stru
-               }
-               /* Display RX ring */
--              stmmac_display_ring(priv, head_rx, priv->dma_rx_size, true,
-+              stmmac_display_ring(priv, head_rx, priv->dma_conf.dma_rx_size, true,
-                                   rx_q->dma_rx_phy, desc_size);
-       }
- }
-@@ -1337,7 +1337,7 @@ static void stmmac_display_tx_rings(stru
-       /* Display TX rings */
-       for (queue = 0; queue < tx_cnt; queue++) {
--              struct stmmac_tx_queue *tx_q = &priv->tx_queue[queue];
-+              struct stmmac_tx_queue *tx_q = &priv->dma_conf.tx_queue[queue];
-               pr_info("\tTX Queue %d rings\n", queue);
-@@ -1352,7 +1352,7 @@ static void stmmac_display_tx_rings(stru
-                       desc_size = sizeof(struct dma_desc);
-               }
--              stmmac_display_ring(priv, head_tx, priv->dma_tx_size, false,
-+              stmmac_display_ring(priv, head_tx, priv->dma_conf.dma_tx_size, false,
-                                   tx_q->dma_tx_phy, desc_size);
-       }
- }
-@@ -1393,21 +1393,21 @@ static int stmmac_set_bfsize(int mtu, in
-  */
- static void stmmac_clear_rx_descriptors(struct stmmac_priv *priv, u32 queue)
- {
--      struct stmmac_rx_queue *rx_q = &priv->rx_queue[queue];
-+      struct stmmac_rx_queue *rx_q = &priv->dma_conf.rx_queue[queue];
-       int i;
-       /* Clear the RX descriptors */
--      for (i = 0; i < priv->dma_rx_size; i++)
-+      for (i = 0; i < priv->dma_conf.dma_rx_size; i++)
-               if (priv->extend_desc)
-                       stmmac_init_rx_desc(priv, &rx_q->dma_erx[i].basic,
-                                       priv->use_riwt, priv->mode,
--                                      (i == priv->dma_rx_size - 1),
--                                      priv->dma_buf_sz);
-+                                      (i == priv->dma_conf.dma_rx_size - 1),
-+                                      priv->dma_conf.dma_buf_sz);
-               else
-                       stmmac_init_rx_desc(priv, &rx_q->dma_rx[i],
-                                       priv->use_riwt, priv->mode,
--                                      (i == priv->dma_rx_size - 1),
--                                      priv->dma_buf_sz);
-+                                      (i == priv->dma_conf.dma_rx_size - 1),
-+                                      priv->dma_conf.dma_buf_sz);
- }
- /**
-@@ -1419,12 +1419,12 @@ static void stmmac_clear_rx_descriptors(
-  */
- static void stmmac_clear_tx_descriptors(struct stmmac_priv *priv, u32 queue)
- {
--      struct stmmac_tx_queue *tx_q = &priv->tx_queue[queue];
-+      struct stmmac_tx_queue *tx_q = &priv->dma_conf.tx_queue[queue];
-       int i;
-       /* Clear the TX descriptors */
--      for (i = 0; i < priv->dma_tx_size; i++) {
--              int last = (i == (priv->dma_tx_size - 1));
-+      for (i = 0; i < priv->dma_conf.dma_tx_size; i++) {
-+              int last = (i == (priv->dma_conf.dma_tx_size - 1));
-               struct dma_desc *p;
-               if (priv->extend_desc)
-@@ -1472,7 +1472,7 @@ static void stmmac_clear_descriptors(str
- static int stmmac_init_rx_buffers(struct stmmac_priv *priv, struct dma_desc *p,
-                                 int i, gfp_t flags, u32 queue)
- {
--      struct stmmac_rx_queue *rx_q = &priv->rx_queue[queue];
-+      struct stmmac_rx_queue *rx_q = &priv->dma_conf.rx_queue[queue];
-       struct stmmac_rx_buffer *buf = &rx_q->buf_pool[i];
-       if (!buf->page) {
-@@ -1497,7 +1497,7 @@ static int stmmac_init_rx_buffers(struct
-       buf->addr = page_pool_get_dma_addr(buf->page) + buf->page_offset;
-       stmmac_set_desc_addr(priv, p, buf->addr);
--      if (priv->dma_buf_sz == BUF_SIZE_16KiB)
-+      if (priv->dma_conf.dma_buf_sz == BUF_SIZE_16KiB)
-               stmmac_init_desc3(priv, p);
-       return 0;
-@@ -1511,7 +1511,7 @@ static int stmmac_init_rx_buffers(struct
-  */
- static void stmmac_free_rx_buffer(struct stmmac_priv *priv, u32 queue, int i)
- {
--      struct stmmac_rx_queue *rx_q = &priv->rx_queue[queue];
-+      struct stmmac_rx_queue *rx_q = &priv->dma_conf.rx_queue[queue];
-       struct stmmac_rx_buffer *buf = &rx_q->buf_pool[i];
-       if (buf->page)
-@@ -1531,7 +1531,7 @@ static void stmmac_free_rx_buffer(struct
-  */
- static void stmmac_free_tx_buffer(struct stmmac_priv *priv, u32 queue, int i)
- {
--      struct stmmac_tx_queue *tx_q = &priv->tx_queue[queue];
-+      struct stmmac_tx_queue *tx_q = &priv->dma_conf.tx_queue[queue];
-       if (tx_q->tx_skbuff_dma[i].buf &&
-           tx_q->tx_skbuff_dma[i].buf_type != STMMAC_TXBUF_T_XDP_TX) {
-@@ -1576,17 +1576,17 @@ static void dma_free_rx_skbufs(struct st
- {
-       int i;
--      for (i = 0; i < priv->dma_rx_size; i++)
-+      for (i = 0; i < priv->dma_conf.dma_rx_size; i++)
-               stmmac_free_rx_buffer(priv, queue, i);
- }
- static int stmmac_alloc_rx_buffers(struct stmmac_priv *priv, u32 queue,
-                                  gfp_t flags)
- {
--      struct stmmac_rx_queue *rx_q = &priv->rx_queue[queue];
-+      struct stmmac_rx_queue *rx_q = &priv->dma_conf.rx_queue[queue];
-       int i;
--      for (i = 0; i < priv->dma_rx_size; i++) {
-+      for (i = 0; i < priv->dma_conf.dma_rx_size; i++) {
-               struct dma_desc *p;
-               int ret;
-@@ -1613,10 +1613,10 @@ static int stmmac_alloc_rx_buffers(struc
-  */
- static void dma_free_rx_xskbufs(struct stmmac_priv *priv, u32 queue)
- {
--      struct stmmac_rx_queue *rx_q = &priv->rx_queue[queue];
-+      struct stmmac_rx_queue *rx_q = &priv->dma_conf.rx_queue[queue];
-       int i;
--      for (i = 0; i < priv->dma_rx_size; i++) {
-+      for (i = 0; i < priv->dma_conf.dma_rx_size; i++) {
-               struct stmmac_rx_buffer *buf = &rx_q->buf_pool[i];
-               if (!buf->xdp)
-@@ -1629,10 +1629,10 @@ static void dma_free_rx_xskbufs(struct s
- static int stmmac_alloc_rx_buffers_zc(struct stmmac_priv *priv, u32 queue)
- {
--      struct stmmac_rx_queue *rx_q = &priv->rx_queue[queue];
-+      struct stmmac_rx_queue *rx_q = &priv->dma_conf.rx_queue[queue];
-       int i;
--      for (i = 0; i < priv->dma_rx_size; i++) {
-+      for (i = 0; i < priv->dma_conf.dma_rx_size; i++) {
-               struct stmmac_rx_buffer *buf;
-               dma_addr_t dma_addr;
-               struct dma_desc *p;
-@@ -1675,7 +1675,7 @@ static struct xsk_buff_pool *stmmac_get_
-  */
- static int __init_dma_rx_desc_rings(struct stmmac_priv *priv, u32 queue, gfp_t flags)
- {
--      struct stmmac_rx_queue *rx_q = &priv->rx_queue[queue];
-+      struct stmmac_rx_queue *rx_q = &priv->dma_conf.rx_queue[queue];
-       int ret;
-       netif_dbg(priv, probe, priv->dev,
-@@ -1721,11 +1721,11 @@ static int __init_dma_rx_desc_rings(stru
-               if (priv->extend_desc)
-                       stmmac_mode_init(priv, rx_q->dma_erx,
-                                        rx_q->dma_rx_phy,
--                                       priv->dma_rx_size, 1);
-+                                       priv->dma_conf.dma_rx_size, 1);
-               else
-                       stmmac_mode_init(priv, rx_q->dma_rx,
-                                        rx_q->dma_rx_phy,
--                                       priv->dma_rx_size, 0);
-+                                       priv->dma_conf.dma_rx_size, 0);
-       }
-       return 0;
-@@ -1752,7 +1752,7 @@ static int init_dma_rx_desc_rings(struct
- err_init_rx_buffers:
-       while (queue >= 0) {
--              struct stmmac_rx_queue *rx_q = &priv->rx_queue[queue];
-+              struct stmmac_rx_queue *rx_q = &priv->dma_conf.rx_queue[queue];
-               if (rx_q->xsk_pool)
-                       dma_free_rx_xskbufs(priv, queue);
-@@ -1781,7 +1781,7 @@ err_init_rx_buffers:
-  */
- static int __init_dma_tx_desc_rings(struct stmmac_priv *priv, u32 queue)
- {
--      struct stmmac_tx_queue *tx_q = &priv->tx_queue[queue];
-+      struct stmmac_tx_queue *tx_q = &priv->dma_conf.tx_queue[queue];
-       int i;
-       netif_dbg(priv, probe, priv->dev,
-@@ -1793,16 +1793,16 @@ static int __init_dma_tx_desc_rings(stru
-               if (priv->extend_desc)
-                       stmmac_mode_init(priv, tx_q->dma_etx,
-                                        tx_q->dma_tx_phy,
--                                       priv->dma_tx_size, 1);
-+                                       priv->dma_conf.dma_tx_size, 1);
-               else if (!(tx_q->tbs & STMMAC_TBS_AVAIL))
-                       stmmac_mode_init(priv, tx_q->dma_tx,
-                                        tx_q->dma_tx_phy,
--                                       priv->dma_tx_size, 0);
-+                                       priv->dma_conf.dma_tx_size, 0);
-       }
-       tx_q->xsk_pool = stmmac_get_xsk_pool(priv, queue);
--      for (i = 0; i < priv->dma_tx_size; i++) {
-+      for (i = 0; i < priv->dma_conf.dma_tx_size; i++) {
-               struct dma_desc *p;
-               if (priv->extend_desc)
-@@ -1872,12 +1872,12 @@ static int init_dma_desc_rings(struct ne
-  */
- static void dma_free_tx_skbufs(struct stmmac_priv *priv, u32 queue)
- {
--      struct stmmac_tx_queue *tx_q = &priv->tx_queue[queue];
-+      struct stmmac_tx_queue *tx_q = &priv->dma_conf.tx_queue[queue];
-       int i;
-       tx_q->xsk_frames_done = 0;
--      for (i = 0; i < priv->dma_tx_size; i++)
-+      for (i = 0; i < priv->dma_conf.dma_tx_size; i++)
-               stmmac_free_tx_buffer(priv, queue, i);
-       if (tx_q->xsk_pool && tx_q->xsk_frames_done) {
-@@ -1907,7 +1907,7 @@ static void stmmac_free_tx_skbufs(struct
-  */
- static void __free_dma_rx_desc_resources(struct stmmac_priv *priv, u32 queue)
- {
--      struct stmmac_rx_queue *rx_q = &priv->rx_queue[queue];
-+      struct stmmac_rx_queue *rx_q = &priv->dma_conf.rx_queue[queue];
-       /* Release the DMA RX socket buffers */
-       if (rx_q->xsk_pool)
-@@ -1920,11 +1920,11 @@ static void __free_dma_rx_desc_resources
-       /* Free DMA regions of consistent memory previously allocated */
-       if (!priv->extend_desc)
--              dma_free_coherent(priv->device, priv->dma_rx_size *
-+              dma_free_coherent(priv->device, priv->dma_conf.dma_rx_size *
-                                 sizeof(struct dma_desc),
-                                 rx_q->dma_rx, rx_q->dma_rx_phy);
-       else
--              dma_free_coherent(priv->device, priv->dma_rx_size *
-+              dma_free_coherent(priv->device, priv->dma_conf.dma_rx_size *
-                                 sizeof(struct dma_extended_desc),
-                                 rx_q->dma_erx, rx_q->dma_rx_phy);
-@@ -1953,7 +1953,7 @@ static void free_dma_rx_desc_resources(s
-  */
- static void __free_dma_tx_desc_resources(struct stmmac_priv *priv, u32 queue)
- {
--      struct stmmac_tx_queue *tx_q = &priv->tx_queue[queue];
-+      struct stmmac_tx_queue *tx_q = &priv->dma_conf.tx_queue[queue];
-       size_t size;
-       void *addr;
-@@ -1971,7 +1971,7 @@ static void __free_dma_tx_desc_resources
-               addr = tx_q->dma_tx;
-       }
--      size *= priv->dma_tx_size;
-+      size *= priv->dma_conf.dma_tx_size;
-       dma_free_coherent(priv->device, size, addr, tx_q->dma_tx_phy);
-@@ -2000,7 +2000,7 @@ static void free_dma_tx_desc_resources(s
-  */
- static int __alloc_dma_rx_desc_resources(struct stmmac_priv *priv, u32 queue)
- {
--      struct stmmac_rx_queue *rx_q = &priv->rx_queue[queue];
-+      struct stmmac_rx_queue *rx_q = &priv->dma_conf.rx_queue[queue];
-       struct stmmac_channel *ch = &priv->channel[queue];
-       bool xdp_prog = stmmac_xdp_is_enabled(priv);
-       struct page_pool_params pp_params = { 0 };
-@@ -2012,8 +2012,8 @@ static int __alloc_dma_rx_desc_resources
-       rx_q->priv_data = priv;
-       pp_params.flags = PP_FLAG_DMA_MAP | PP_FLAG_DMA_SYNC_DEV;
--      pp_params.pool_size = priv->dma_rx_size;
--      num_pages = DIV_ROUND_UP(priv->dma_buf_sz, PAGE_SIZE);
-+      pp_params.pool_size = priv->dma_conf.dma_rx_size;
-+      num_pages = DIV_ROUND_UP(priv->dma_conf.dma_buf_sz, PAGE_SIZE);
-       pp_params.order = ilog2(num_pages);
-       pp_params.nid = dev_to_node(priv->device);
-       pp_params.dev = priv->device;
-@@ -2028,7 +2028,7 @@ static int __alloc_dma_rx_desc_resources
-               return ret;
-       }
--      rx_q->buf_pool = kcalloc(priv->dma_rx_size,
-+      rx_q->buf_pool = kcalloc(priv->dma_conf.dma_rx_size,
-                                sizeof(*rx_q->buf_pool),
-                                GFP_KERNEL);
-       if (!rx_q->buf_pool)
-@@ -2036,7 +2036,7 @@ static int __alloc_dma_rx_desc_resources
-       if (priv->extend_desc) {
-               rx_q->dma_erx = dma_alloc_coherent(priv->device,
--                                                 priv->dma_rx_size *
-+                                                 priv->dma_conf.dma_rx_size *
-                                                  sizeof(struct dma_extended_desc),
-                                                  &rx_q->dma_rx_phy,
-                                                  GFP_KERNEL);
-@@ -2045,7 +2045,7 @@ static int __alloc_dma_rx_desc_resources
-       } else {
-               rx_q->dma_rx = dma_alloc_coherent(priv->device,
--                                                priv->dma_rx_size *
-+                                                priv->dma_conf.dma_rx_size *
-                                                 sizeof(struct dma_desc),
-                                                 &rx_q->dma_rx_phy,
-                                                 GFP_KERNEL);
-@@ -2102,20 +2102,20 @@ err_dma:
-  */
- static int __alloc_dma_tx_desc_resources(struct stmmac_priv *priv, u32 queue)
- {
--      struct stmmac_tx_queue *tx_q = &priv->tx_queue[queue];
-+      struct stmmac_tx_queue *tx_q = &priv->dma_conf.tx_queue[queue];
-       size_t size;
-       void *addr;
-       tx_q->queue_index = queue;
-       tx_q->priv_data = priv;
--      tx_q->tx_skbuff_dma = kcalloc(priv->dma_tx_size,
-+      tx_q->tx_skbuff_dma = kcalloc(priv->dma_conf.dma_tx_size,
-                                     sizeof(*tx_q->tx_skbuff_dma),
-                                     GFP_KERNEL);
-       if (!tx_q->tx_skbuff_dma)
-               return -ENOMEM;
--      tx_q->tx_skbuff = kcalloc(priv->dma_tx_size,
-+      tx_q->tx_skbuff = kcalloc(priv->dma_conf.dma_tx_size,
-                                 sizeof(struct sk_buff *),
-                                 GFP_KERNEL);
-       if (!tx_q->tx_skbuff)
-@@ -2128,7 +2128,7 @@ static int __alloc_dma_tx_desc_resources
-       else
-               size = sizeof(struct dma_desc);
--      size *= priv->dma_tx_size;
-+      size *= priv->dma_conf.dma_tx_size;
-       addr = dma_alloc_coherent(priv->device, size,
-                                 &tx_q->dma_tx_phy, GFP_KERNEL);
-@@ -2372,7 +2372,7 @@ static void stmmac_dma_operation_mode(st
-       /* configure all channels */
-       for (chan = 0; chan < rx_channels_count; chan++) {
--              struct stmmac_rx_queue *rx_q = &priv->rx_queue[chan];
-+              struct stmmac_rx_queue *rx_q = &priv->dma_conf.rx_queue[chan];
-               u32 buf_size;
-               qmode = priv->plat->rx_queues_cfg[chan].mode_to_use;
-@@ -2387,7 +2387,7 @@ static void stmmac_dma_operation_mode(st
-                                             chan);
-               } else {
-                       stmmac_set_dma_bfsize(priv, priv->ioaddr,
--                                            priv->dma_buf_sz,
-+                                            priv->dma_conf.dma_buf_sz,
-                                             chan);
-               }
-       }
-@@ -2403,7 +2403,7 @@ static void stmmac_dma_operation_mode(st
- static bool stmmac_xdp_xmit_zc(struct stmmac_priv *priv, u32 queue, u32 budget)
- {
-       struct netdev_queue *nq = netdev_get_tx_queue(priv->dev, queue);
--      struct stmmac_tx_queue *tx_q = &priv->tx_queue[queue];
-+      struct stmmac_tx_queue *tx_q = &priv->dma_conf.tx_queue[queue];
-       struct xsk_buff_pool *pool = tx_q->xsk_pool;
-       unsigned int entry = tx_q->cur_tx;
-       struct dma_desc *tx_desc = NULL;
-@@ -2478,7 +2478,7 @@ static bool stmmac_xdp_xmit_zc(struct st
-               stmmac_enable_dma_transmission(priv, priv->ioaddr);
--              tx_q->cur_tx = STMMAC_GET_ENTRY(tx_q->cur_tx, priv->dma_tx_size);
-+              tx_q->cur_tx = STMMAC_GET_ENTRY(tx_q->cur_tx, priv->dma_conf.dma_tx_size);
-               entry = tx_q->cur_tx;
-       }
-@@ -2504,7 +2504,7 @@ static bool stmmac_xdp_xmit_zc(struct st
-  */
- static int stmmac_tx_clean(struct stmmac_priv *priv, int budget, u32 queue)
- {
--      struct stmmac_tx_queue *tx_q = &priv->tx_queue[queue];
-+      struct stmmac_tx_queue *tx_q = &priv->dma_conf.tx_queue[queue];
-       unsigned int bytes_compl = 0, pkts_compl = 0;
-       unsigned int entry, xmits = 0, count = 0;
-@@ -2517,7 +2517,7 @@ static int stmmac_tx_clean(struct stmmac
-       entry = tx_q->dirty_tx;
-       /* Try to clean all TX complete frame in 1 shot */
--      while ((entry != tx_q->cur_tx) && count < priv->dma_tx_size) {
-+      while ((entry != tx_q->cur_tx) && count < priv->dma_conf.dma_tx_size) {
-               struct xdp_frame *xdpf;
-               struct sk_buff *skb;
-               struct dma_desc *p;
-@@ -2617,7 +2617,7 @@ static int stmmac_tx_clean(struct stmmac
-               stmmac_release_tx_desc(priv, p, priv->mode);
--              entry = STMMAC_GET_ENTRY(entry, priv->dma_tx_size);
-+              entry = STMMAC_GET_ENTRY(entry, priv->dma_conf.dma_tx_size);
-       }
-       tx_q->dirty_tx = entry;
-@@ -2682,7 +2682,7 @@ static int stmmac_tx_clean(struct stmmac
-  */
- static void stmmac_tx_err(struct stmmac_priv *priv, u32 chan)
- {
--      struct stmmac_tx_queue *tx_q = &priv->tx_queue[chan];
-+      struct stmmac_tx_queue *tx_q = &priv->dma_conf.tx_queue[chan];
-       netif_tx_stop_queue(netdev_get_tx_queue(priv->dev, chan));
-@@ -2749,8 +2749,8 @@ static int stmmac_napi_check(struct stmm
- {
-       int status = stmmac_dma_interrupt_status(priv, priv->ioaddr,
-                                                &priv->xstats, chan, dir);
--      struct stmmac_rx_queue *rx_q = &priv->rx_queue[chan];
--      struct stmmac_tx_queue *tx_q = &priv->tx_queue[chan];
-+      struct stmmac_rx_queue *rx_q = &priv->dma_conf.rx_queue[chan];
-+      struct stmmac_tx_queue *tx_q = &priv->dma_conf.tx_queue[chan];
-       struct stmmac_channel *ch = &priv->channel[chan];
-       struct napi_struct *rx_napi;
-       struct napi_struct *tx_napi;
-@@ -2926,7 +2926,7 @@ static int stmmac_init_dma_engine(struct
-       /* DMA RX Channel Configuration */
-       for (chan = 0; chan < rx_channels_count; chan++) {
--              rx_q = &priv->rx_queue[chan];
-+              rx_q = &priv->dma_conf.rx_queue[chan];
-               stmmac_init_rx_chan(priv, priv->ioaddr, priv->plat->dma_cfg,
-                                   rx_q->dma_rx_phy, chan);
-@@ -2940,7 +2940,7 @@ static int stmmac_init_dma_engine(struct
-       /* DMA TX Channel Configuration */
-       for (chan = 0; chan < tx_channels_count; chan++) {
--              tx_q = &priv->tx_queue[chan];
-+              tx_q = &priv->dma_conf.tx_queue[chan];
-               stmmac_init_tx_chan(priv, priv->ioaddr, priv->plat->dma_cfg,
-                                   tx_q->dma_tx_phy, chan);
-@@ -2955,7 +2955,7 @@ static int stmmac_init_dma_engine(struct
- static void stmmac_tx_timer_arm(struct stmmac_priv *priv, u32 queue)
- {
--      struct stmmac_tx_queue *tx_q = &priv->tx_queue[queue];
-+      struct stmmac_tx_queue *tx_q = &priv->dma_conf.tx_queue[queue];
-       hrtimer_start(&tx_q->txtimer,
-                     STMMAC_COAL_TIMER(priv->tx_coal_timer[queue]),
-@@ -3005,7 +3005,7 @@ static void stmmac_init_coalesce(struct
-       u32 chan;
-       for (chan = 0; chan < tx_channel_count; chan++) {
--              struct stmmac_tx_queue *tx_q = &priv->tx_queue[chan];
-+              struct stmmac_tx_queue *tx_q = &priv->dma_conf.tx_queue[chan];
-               priv->tx_coal_frames[chan] = STMMAC_TX_FRAMES;
-               priv->tx_coal_timer[chan] = STMMAC_COAL_TX_TIMER;
-@@ -3027,12 +3027,12 @@ static void stmmac_set_rings_length(stru
-       /* set TX ring length */
-       for (chan = 0; chan < tx_channels_count; chan++)
-               stmmac_set_tx_ring_len(priv, priv->ioaddr,
--                                     (priv->dma_tx_size - 1), chan);
-+                                     (priv->dma_conf.dma_tx_size - 1), chan);
-       /* set RX ring length */
-       for (chan = 0; chan < rx_channels_count; chan++)
-               stmmac_set_rx_ring_len(priv, priv->ioaddr,
--                                     (priv->dma_rx_size - 1), chan);
-+                                     (priv->dma_conf.dma_rx_size - 1), chan);
- }
- /**
-@@ -3367,7 +3367,7 @@ static int stmmac_hw_setup(struct net_de
-       /* Enable TSO */
-       if (priv->tso) {
-               for (chan = 0; chan < tx_cnt; chan++) {
--                      struct stmmac_tx_queue *tx_q = &priv->tx_queue[chan];
-+                      struct stmmac_tx_queue *tx_q = &priv->dma_conf.tx_queue[chan];
-                       /* TSO and TBS cannot co-exist */
-                       if (tx_q->tbs & STMMAC_TBS_AVAIL)
-@@ -3389,7 +3389,7 @@ static int stmmac_hw_setup(struct net_de
-       /* TBS */
-       for (chan = 0; chan < tx_cnt; chan++) {
--              struct stmmac_tx_queue *tx_q = &priv->tx_queue[chan];
-+              struct stmmac_tx_queue *tx_q = &priv->dma_conf.tx_queue[chan];
-               int enable = tx_q->tbs & STMMAC_TBS_AVAIL;
-               stmmac_enable_tbs(priv, priv->ioaddr, enable, chan);
-@@ -3433,7 +3433,7 @@ static void stmmac_free_irq(struct net_d
-               for (j = irq_idx - 1; j >= 0; j--) {
-                       if (priv->tx_irq[j] > 0) {
-                               irq_set_affinity_hint(priv->tx_irq[j], NULL);
--                              free_irq(priv->tx_irq[j], &priv->tx_queue[j]);
-+                              free_irq(priv->tx_irq[j], &priv->dma_conf.tx_queue[j]);
-                       }
-               }
-               irq_idx = priv->plat->rx_queues_to_use;
-@@ -3442,7 +3442,7 @@ static void stmmac_free_irq(struct net_d
-               for (j = irq_idx - 1; j >= 0; j--) {
-                       if (priv->rx_irq[j] > 0) {
-                               irq_set_affinity_hint(priv->rx_irq[j], NULL);
--                              free_irq(priv->rx_irq[j], &priv->rx_queue[j]);
-+                              free_irq(priv->rx_irq[j], &priv->dma_conf.rx_queue[j]);
-                       }
-               }
-@@ -3576,7 +3576,7 @@ static int stmmac_request_irq_multi_msi(
-               sprintf(int_name, "%s:%s-%d", dev->name, "rx", i);
-               ret = request_irq(priv->rx_irq[i],
-                                 stmmac_msi_intr_rx,
--                                0, int_name, &priv->rx_queue[i]);
-+                                0, int_name, &priv->dma_conf.rx_queue[i]);
-               if (unlikely(ret < 0)) {
-                       netdev_err(priv->dev,
-                                  "%s: alloc rx-%d  MSI %d (error: %d)\n",
-@@ -3599,7 +3599,7 @@ static int stmmac_request_irq_multi_msi(
-               sprintf(int_name, "%s:%s-%d", dev->name, "tx", i);
-               ret = request_irq(priv->tx_irq[i],
-                                 stmmac_msi_intr_tx,
--                                0, int_name, &priv->tx_queue[i]);
-+                                0, int_name, &priv->dma_conf.tx_queue[i]);
-               if (unlikely(ret < 0)) {
-                       netdev_err(priv->dev,
-                                  "%s: alloc tx-%d  MSI %d (error: %d)\n",
-@@ -3730,21 +3730,21 @@ static int stmmac_open(struct net_device
-               bfsize = 0;
-       if (bfsize < BUF_SIZE_16KiB)
--              bfsize = stmmac_set_bfsize(dev->mtu, priv->dma_buf_sz);
-+              bfsize = stmmac_set_bfsize(dev->mtu, priv->dma_conf.dma_buf_sz);
--      priv->dma_buf_sz = bfsize;
-+      priv->dma_conf.dma_buf_sz = bfsize;
-       buf_sz = bfsize;
-       priv->rx_copybreak = STMMAC_RX_COPYBREAK;
--      if (!priv->dma_tx_size)
--              priv->dma_tx_size = DMA_DEFAULT_TX_SIZE;
--      if (!priv->dma_rx_size)
--              priv->dma_rx_size = DMA_DEFAULT_RX_SIZE;
-+      if (!priv->dma_conf.dma_tx_size)
-+              priv->dma_conf.dma_tx_size = DMA_DEFAULT_TX_SIZE;
-+      if (!priv->dma_conf.dma_rx_size)
-+              priv->dma_conf.dma_rx_size = DMA_DEFAULT_RX_SIZE;
-       /* Earlier check for TBS */
-       for (chan = 0; chan < priv->plat->tx_queues_to_use; chan++) {
--              struct stmmac_tx_queue *tx_q = &priv->tx_queue[chan];
-+              struct stmmac_tx_queue *tx_q = &priv->dma_conf.tx_queue[chan];
-               int tbs_en = priv->plat->tx_queues_cfg[chan].tbs_en;
-               /* Setup per-TXQ tbs flag before TX descriptor alloc */
-@@ -3802,7 +3802,7 @@ irq_error:
-       phylink_stop(priv->phylink);
-       for (chan = 0; chan < priv->plat->tx_queues_to_use; chan++)
--              hrtimer_cancel(&priv->tx_queue[chan].txtimer);
-+              hrtimer_cancel(&priv->dma_conf.tx_queue[chan].txtimer);
-       stmmac_hw_teardown(dev);
- init_error:
-@@ -3846,7 +3846,7 @@ static int stmmac_release(struct net_dev
-       stmmac_disable_all_queues(priv);
-       for (chan = 0; chan < priv->plat->tx_queues_to_use; chan++)
--              hrtimer_cancel(&priv->tx_queue[chan].txtimer);
-+              hrtimer_cancel(&priv->dma_conf.tx_queue[chan].txtimer);
-       netif_tx_disable(dev);
-@@ -3910,7 +3910,7 @@ static bool stmmac_vlan_insert(struct st
-               return false;
-       stmmac_set_tx_owner(priv, p);
--      tx_q->cur_tx = STMMAC_GET_ENTRY(tx_q->cur_tx, priv->dma_tx_size);
-+      tx_q->cur_tx = STMMAC_GET_ENTRY(tx_q->cur_tx, priv->dma_conf.dma_tx_size);
-       return true;
- }
-@@ -3928,7 +3928,7 @@ static bool stmmac_vlan_insert(struct st
- static void stmmac_tso_allocator(struct stmmac_priv *priv, dma_addr_t des,
-                                int total_len, bool last_segment, u32 queue)
- {
--      struct stmmac_tx_queue *tx_q = &priv->tx_queue[queue];
-+      struct stmmac_tx_queue *tx_q = &priv->dma_conf.tx_queue[queue];
-       struct dma_desc *desc;
-       u32 buff_size;
-       int tmp_len;
-@@ -3939,7 +3939,7 @@ static void stmmac_tso_allocator(struct
-               dma_addr_t curr_addr;
-               tx_q->cur_tx = STMMAC_GET_ENTRY(tx_q->cur_tx,
--                                              priv->dma_tx_size);
-+                                              priv->dma_conf.dma_tx_size);
-               WARN_ON(tx_q->tx_skbuff[tx_q->cur_tx]);
-               if (tx_q->tbs & STMMAC_TBS_AVAIL)
-@@ -3967,7 +3967,7 @@ static void stmmac_tso_allocator(struct
- static void stmmac_flush_tx_descriptors(struct stmmac_priv *priv, int queue)
- {
--      struct stmmac_tx_queue *tx_q = &priv->tx_queue[queue];
-+      struct stmmac_tx_queue *tx_q = &priv->dma_conf.tx_queue[queue];
-       int desc_size;
-       if (likely(priv->extend_desc))
-@@ -4029,7 +4029,7 @@ static netdev_tx_t stmmac_tso_xmit(struc
-       dma_addr_t des;
-       int i;
--      tx_q = &priv->tx_queue[queue];
-+      tx_q = &priv->dma_conf.tx_queue[queue];
-       first_tx = tx_q->cur_tx;
-       /* Compute header lengths */
-@@ -4069,7 +4069,7 @@ static netdev_tx_t stmmac_tso_xmit(struc
-               stmmac_set_mss(priv, mss_desc, mss);
-               tx_q->mss = mss;
-               tx_q->cur_tx = STMMAC_GET_ENTRY(tx_q->cur_tx,
--                                              priv->dma_tx_size);
-+                                              priv->dma_conf.dma_tx_size);
-               WARN_ON(tx_q->tx_skbuff[tx_q->cur_tx]);
-       }
-@@ -4181,7 +4181,7 @@ static netdev_tx_t stmmac_tso_xmit(struc
-        * ndo_start_xmit will fill this descriptor the next time it's
-        * called and stmmac_tx_clean may clean up to this descriptor.
-        */
--      tx_q->cur_tx = STMMAC_GET_ENTRY(tx_q->cur_tx, priv->dma_tx_size);
-+      tx_q->cur_tx = STMMAC_GET_ENTRY(tx_q->cur_tx, priv->dma_conf.dma_tx_size);
-       if (unlikely(stmmac_tx_avail(priv, queue) <= (MAX_SKB_FRAGS + 1))) {
-               netif_dbg(priv, hw, priv->dev, "%s: stop transmitted packets\n",
-@@ -4269,7 +4269,7 @@ static netdev_tx_t stmmac_xmit(struct sk
-       int entry, first_tx;
-       dma_addr_t des;
--      tx_q = &priv->tx_queue[queue];
-+      tx_q = &priv->dma_conf.tx_queue[queue];
-       first_tx = tx_q->cur_tx;
-       if (priv->tx_path_in_lpi_mode && priv->eee_sw_timer_en)
-@@ -4332,7 +4332,7 @@ static netdev_tx_t stmmac_xmit(struct sk
-               int len = skb_frag_size(frag);
-               bool last_segment = (i == (nfrags - 1));
--              entry = STMMAC_GET_ENTRY(entry, priv->dma_tx_size);
-+              entry = STMMAC_GET_ENTRY(entry, priv->dma_conf.dma_tx_size);
-               WARN_ON(tx_q->tx_skbuff[entry]);
-               if (likely(priv->extend_desc))
-@@ -4403,7 +4403,7 @@ static netdev_tx_t stmmac_xmit(struct sk
-        * ndo_start_xmit will fill this descriptor the next time it's
-        * called and stmmac_tx_clean may clean up to this descriptor.
-        */
--      entry = STMMAC_GET_ENTRY(entry, priv->dma_tx_size);
-+      entry = STMMAC_GET_ENTRY(entry, priv->dma_conf.dma_tx_size);
-       tx_q->cur_tx = entry;
-       if (netif_msg_pktdata(priv)) {
-@@ -4515,7 +4515,7 @@ static void stmmac_rx_vlan(struct net_de
-  */
- static inline void stmmac_rx_refill(struct stmmac_priv *priv, u32 queue)
- {
--      struct stmmac_rx_queue *rx_q = &priv->rx_queue[queue];
-+      struct stmmac_rx_queue *rx_q = &priv->dma_conf.rx_queue[queue];
-       int dirty = stmmac_rx_dirty(priv, queue);
-       unsigned int entry = rx_q->dirty_rx;
-@@ -4565,7 +4565,7 @@ static inline void stmmac_rx_refill(stru
-               dma_wmb();
-               stmmac_set_rx_owner(priv, p, use_rx_wd);
--              entry = STMMAC_GET_ENTRY(entry, priv->dma_rx_size);
-+              entry = STMMAC_GET_ENTRY(entry, priv->dma_conf.dma_rx_size);
-       }
-       rx_q->dirty_rx = entry;
-       rx_q->rx_tail_addr = rx_q->dma_rx_phy +
-@@ -4593,12 +4593,12 @@ static unsigned int stmmac_rx_buf1_len(s
-       /* First descriptor, not last descriptor and not split header */
-       if (status & rx_not_ls)
--              return priv->dma_buf_sz;
-+              return priv->dma_conf.dma_buf_sz;
-       plen = stmmac_get_rx_frame_len(priv, p, coe);
-       /* First descriptor and last descriptor and not split header */
--      return min_t(unsigned int, priv->dma_buf_sz, plen);
-+      return min_t(unsigned int, priv->dma_conf.dma_buf_sz, plen);
- }
- static unsigned int stmmac_rx_buf2_len(struct stmmac_priv *priv,
-@@ -4614,7 +4614,7 @@ static unsigned int stmmac_rx_buf2_len(s
-       /* Not last descriptor */
-       if (status & rx_not_ls)
--              return priv->dma_buf_sz;
-+              return priv->dma_conf.dma_buf_sz;
-       plen = stmmac_get_rx_frame_len(priv, p, coe);
-@@ -4625,7 +4625,7 @@ static unsigned int stmmac_rx_buf2_len(s
- static int stmmac_xdp_xmit_xdpf(struct stmmac_priv *priv, int queue,
-                               struct xdp_frame *xdpf, bool dma_map)
- {
--      struct stmmac_tx_queue *tx_q = &priv->tx_queue[queue];
-+      struct stmmac_tx_queue *tx_q = &priv->dma_conf.tx_queue[queue];
-       unsigned int entry = tx_q->cur_tx;
-       struct dma_desc *tx_desc;
-       dma_addr_t dma_addr;
-@@ -4688,7 +4688,7 @@ static int stmmac_xdp_xmit_xdpf(struct s
-       stmmac_enable_dma_transmission(priv, priv->ioaddr);
--      entry = STMMAC_GET_ENTRY(entry, priv->dma_tx_size);
-+      entry = STMMAC_GET_ENTRY(entry, priv->dma_conf.dma_tx_size);
-       tx_q->cur_tx = entry;
-       return STMMAC_XDP_TX;
-@@ -4862,7 +4862,7 @@ static void stmmac_dispatch_skb_zc(struc
- static bool stmmac_rx_refill_zc(struct stmmac_priv *priv, u32 queue, u32 budget)
- {
--      struct stmmac_rx_queue *rx_q = &priv->rx_queue[queue];
-+      struct stmmac_rx_queue *rx_q = &priv->dma_conf.rx_queue[queue];
-       unsigned int entry = rx_q->dirty_rx;
-       struct dma_desc *rx_desc = NULL;
-       bool ret = true;
-@@ -4905,7 +4905,7 @@ static bool stmmac_rx_refill_zc(struct s
-               dma_wmb();
-               stmmac_set_rx_owner(priv, rx_desc, use_rx_wd);
--              entry = STMMAC_GET_ENTRY(entry, priv->dma_rx_size);
-+              entry = STMMAC_GET_ENTRY(entry, priv->dma_conf.dma_rx_size);
-       }
-       if (rx_desc) {
-@@ -4920,7 +4920,7 @@ static bool stmmac_rx_refill_zc(struct s
- static int stmmac_rx_zc(struct stmmac_priv *priv, int limit, u32 queue)
- {
--      struct stmmac_rx_queue *rx_q = &priv->rx_queue[queue];
-+      struct stmmac_rx_queue *rx_q = &priv->dma_conf.rx_queue[queue];
-       unsigned int count = 0, error = 0, len = 0;
-       int dirty = stmmac_rx_dirty(priv, queue);
-       unsigned int next_entry = rx_q->cur_rx;
-@@ -4942,7 +4942,7 @@ static int stmmac_rx_zc(struct stmmac_pr
-                       desc_size = sizeof(struct dma_desc);
-               }
--              stmmac_display_ring(priv, rx_head, priv->dma_rx_size, true,
-+              stmmac_display_ring(priv, rx_head, priv->dma_conf.dma_rx_size, true,
-                                   rx_q->dma_rx_phy, desc_size);
-       }
-       while (count < limit) {
-@@ -4989,7 +4989,7 @@ read_again:
-               /* Prefetch the next RX descriptor */
-               rx_q->cur_rx = STMMAC_GET_ENTRY(rx_q->cur_rx,
--                                              priv->dma_rx_size);
-+                                              priv->dma_conf.dma_rx_size);
-               next_entry = rx_q->cur_rx;
-               if (priv->extend_desc)
-@@ -5110,7 +5110,7 @@ read_again:
-  */
- static int stmmac_rx(struct stmmac_priv *priv, int limit, u32 queue)
- {
--      struct stmmac_rx_queue *rx_q = &priv->rx_queue[queue];
-+      struct stmmac_rx_queue *rx_q = &priv->dma_conf.rx_queue[queue];
-       struct stmmac_channel *ch = &priv->channel[queue];
-       unsigned int count = 0, error = 0, len = 0;
-       int status = 0, coe = priv->hw->rx_csum;
-@@ -5123,7 +5123,7 @@ static int stmmac_rx(struct stmmac_priv
-       int buf_sz;
-       dma_dir = page_pool_get_dma_dir(rx_q->page_pool);
--      buf_sz = DIV_ROUND_UP(priv->dma_buf_sz, PAGE_SIZE) * PAGE_SIZE;
-+      buf_sz = DIV_ROUND_UP(priv->dma_conf.dma_buf_sz, PAGE_SIZE) * PAGE_SIZE;
-       if (netif_msg_rx_status(priv)) {
-               void *rx_head;
-@@ -5137,7 +5137,7 @@ static int stmmac_rx(struct stmmac_priv
-                       desc_size = sizeof(struct dma_desc);
-               }
--              stmmac_display_ring(priv, rx_head, priv->dma_rx_size, true,
-+              stmmac_display_ring(priv, rx_head, priv->dma_conf.dma_rx_size, true,
-                                   rx_q->dma_rx_phy, desc_size);
-       }
-       while (count < limit) {
-@@ -5181,7 +5181,7 @@ read_again:
-                       break;
-               rx_q->cur_rx = STMMAC_GET_ENTRY(rx_q->cur_rx,
--                                              priv->dma_rx_size);
-+                                              priv->dma_conf.dma_rx_size);
-               next_entry = rx_q->cur_rx;
-               if (priv->extend_desc)
-@@ -5315,7 +5315,7 @@ read_again:
-                                               buf1_len, dma_dir);
-                       skb_add_rx_frag(skb, skb_shinfo(skb)->nr_frags,
-                                       buf->page, buf->page_offset, buf1_len,
--                                      priv->dma_buf_sz);
-+                                      priv->dma_conf.dma_buf_sz);
-                       /* Data payload appended into SKB */
-                       page_pool_release_page(rx_q->page_pool, buf->page);
-@@ -5327,7 +5327,7 @@ read_again:
-                                               buf2_len, dma_dir);
-                       skb_add_rx_frag(skb, skb_shinfo(skb)->nr_frags,
-                                       buf->sec_page, 0, buf2_len,
--                                      priv->dma_buf_sz);
-+                                      priv->dma_conf.dma_buf_sz);
-                       /* Data payload appended into SKB */
-                       page_pool_release_page(rx_q->page_pool, buf->sec_page);
-@@ -5760,11 +5760,13 @@ static irqreturn_t stmmac_safety_interru
- static irqreturn_t stmmac_msi_intr_tx(int irq, void *data)
- {
-       struct stmmac_tx_queue *tx_q = (struct stmmac_tx_queue *)data;
-+      struct stmmac_dma_conf *dma_conf;
-       int chan = tx_q->queue_index;
-       struct stmmac_priv *priv;
-       int status;
--      priv = container_of(tx_q, struct stmmac_priv, tx_queue[chan]);
-+      dma_conf = container_of(tx_q, struct stmmac_dma_conf, tx_queue[chan]);
-+      priv = container_of(dma_conf, struct stmmac_priv, dma_conf);
-       /* Check if adapter is up */
-       if (test_bit(STMMAC_DOWN, &priv->state))
-@@ -5799,10 +5801,12 @@ static irqreturn_t stmmac_msi_intr_tx(in
- static irqreturn_t stmmac_msi_intr_rx(int irq, void *data)
- {
-       struct stmmac_rx_queue *rx_q = (struct stmmac_rx_queue *)data;
-+      struct stmmac_dma_conf *dma_conf;
-       int chan = rx_q->queue_index;
-       struct stmmac_priv *priv;
--      priv = container_of(rx_q, struct stmmac_priv, rx_queue[chan]);
-+      dma_conf = container_of(rx_q, struct stmmac_dma_conf, rx_queue[chan]);
-+      priv = container_of(dma_conf, struct stmmac_priv, dma_conf);
-       /* Check if adapter is up */
-       if (test_bit(STMMAC_DOWN, &priv->state))
-@@ -5828,10 +5832,10 @@ static void stmmac_poll_controller(struc
-       if (priv->plat->multi_msi_en) {
-               for (i = 0; i < priv->plat->rx_queues_to_use; i++)
--                      stmmac_msi_intr_rx(0, &priv->rx_queue[i]);
-+                      stmmac_msi_intr_rx(0, &priv->dma_conf.rx_queue[i]);
-               for (i = 0; i < priv->plat->tx_queues_to_use; i++)
--                      stmmac_msi_intr_tx(0, &priv->tx_queue[i]);
-+                      stmmac_msi_intr_tx(0, &priv->dma_conf.tx_queue[i]);
-       } else {
-               disable_irq(dev->irq);
-               stmmac_interrupt(dev->irq, dev);
-@@ -6012,34 +6016,34 @@ static int stmmac_rings_status_show(stru
-               return 0;
-       for (queue = 0; queue < rx_count; queue++) {
--              struct stmmac_rx_queue *rx_q = &priv->rx_queue[queue];
-+              struct stmmac_rx_queue *rx_q = &priv->dma_conf.rx_queue[queue];
-               seq_printf(seq, "RX Queue %d:\n", queue);
-               if (priv->extend_desc) {
-                       seq_printf(seq, "Extended descriptor ring:\n");
-                       sysfs_display_ring((void *)rx_q->dma_erx,
--                                         priv->dma_rx_size, 1, seq, rx_q->dma_rx_phy);
-+                                         priv->dma_conf.dma_rx_size, 1, seq, rx_q->dma_rx_phy);
-               } else {
-                       seq_printf(seq, "Descriptor ring:\n");
-                       sysfs_display_ring((void *)rx_q->dma_rx,
--                                         priv->dma_rx_size, 0, seq, rx_q->dma_rx_phy);
-+                                         priv->dma_conf.dma_rx_size, 0, seq, rx_q->dma_rx_phy);
-               }
-       }
-       for (queue = 0; queue < tx_count; queue++) {
--              struct stmmac_tx_queue *tx_q = &priv->tx_queue[queue];
-+              struct stmmac_tx_queue *tx_q = &priv->dma_conf.tx_queue[queue];
-               seq_printf(seq, "TX Queue %d:\n", queue);
-               if (priv->extend_desc) {
-                       seq_printf(seq, "Extended descriptor ring:\n");
-                       sysfs_display_ring((void *)tx_q->dma_etx,
--                                         priv->dma_tx_size, 1, seq, tx_q->dma_tx_phy);
-+                                         priv->dma_conf.dma_tx_size, 1, seq, tx_q->dma_tx_phy);
-               } else if (!(tx_q->tbs & STMMAC_TBS_AVAIL)) {
-                       seq_printf(seq, "Descriptor ring:\n");
-                       sysfs_display_ring((void *)tx_q->dma_tx,
--                                         priv->dma_tx_size, 0, seq, tx_q->dma_tx_phy);
-+                                         priv->dma_conf.dma_tx_size, 0, seq, tx_q->dma_tx_phy);
-               }
-       }
-@@ -6386,7 +6390,7 @@ void stmmac_disable_rx_queue(struct stmm
- void stmmac_enable_rx_queue(struct stmmac_priv *priv, u32 queue)
- {
--      struct stmmac_rx_queue *rx_q = &priv->rx_queue[queue];
-+      struct stmmac_rx_queue *rx_q = &priv->dma_conf.rx_queue[queue];
-       struct stmmac_channel *ch = &priv->channel[queue];
-       unsigned long flags;
-       u32 buf_size;
-@@ -6423,7 +6427,7 @@ void stmmac_enable_rx_queue(struct stmma
-                                     rx_q->queue_index);
-       } else {
-               stmmac_set_dma_bfsize(priv, priv->ioaddr,
--                                    priv->dma_buf_sz,
-+                                    priv->dma_conf.dma_buf_sz,
-                                     rx_q->queue_index);
-       }
-@@ -6449,7 +6453,7 @@ void stmmac_disable_tx_queue(struct stmm
- void stmmac_enable_tx_queue(struct stmmac_priv *priv, u32 queue)
- {
--      struct stmmac_tx_queue *tx_q = &priv->tx_queue[queue];
-+      struct stmmac_tx_queue *tx_q = &priv->dma_conf.tx_queue[queue];
-       struct stmmac_channel *ch = &priv->channel[queue];
-       unsigned long flags;
-       int ret;
-@@ -6499,7 +6503,7 @@ void stmmac_xdp_release(struct net_devic
-       stmmac_disable_all_queues(priv);
-       for (chan = 0; chan < priv->plat->tx_queues_to_use; chan++)
--              hrtimer_cancel(&priv->tx_queue[chan].txtimer);
-+              hrtimer_cancel(&priv->dma_conf.tx_queue[chan].txtimer);
-       /* Free the IRQ lines */
-       stmmac_free_irq(dev, REQ_IRQ_ERR_ALL, 0);
-@@ -6558,7 +6562,7 @@ int stmmac_xdp_open(struct net_device *d
-       /* DMA RX Channel Configuration */
-       for (chan = 0; chan < rx_cnt; chan++) {
--              rx_q = &priv->rx_queue[chan];
-+              rx_q = &priv->dma_conf.rx_queue[chan];
-               stmmac_init_rx_chan(priv, priv->ioaddr, priv->plat->dma_cfg,
-                                   rx_q->dma_rx_phy, chan);
-@@ -6576,7 +6580,7 @@ int stmmac_xdp_open(struct net_device *d
-                                             rx_q->queue_index);
-               } else {
-                       stmmac_set_dma_bfsize(priv, priv->ioaddr,
--                                            priv->dma_buf_sz,
-+                                            priv->dma_conf.dma_buf_sz,
-                                             rx_q->queue_index);
-               }
-@@ -6585,7 +6589,7 @@ int stmmac_xdp_open(struct net_device *d
-       /* DMA TX Channel Configuration */
-       for (chan = 0; chan < tx_cnt; chan++) {
--              tx_q = &priv->tx_queue[chan];
-+              tx_q = &priv->dma_conf.tx_queue[chan];
-               stmmac_init_tx_chan(priv, priv->ioaddr, priv->plat->dma_cfg,
-                                   tx_q->dma_tx_phy, chan);
-@@ -6618,7 +6622,7 @@ int stmmac_xdp_open(struct net_device *d
- irq_error:
-       for (chan = 0; chan < priv->plat->tx_queues_to_use; chan++)
--              hrtimer_cancel(&priv->tx_queue[chan].txtimer);
-+              hrtimer_cancel(&priv->dma_conf.tx_queue[chan].txtimer);
-       stmmac_hw_teardown(dev);
- init_error:
-@@ -6645,8 +6649,8 @@ int stmmac_xsk_wakeup(struct net_device
-           queue >= priv->plat->tx_queues_to_use)
-               return -EINVAL;
--      rx_q = &priv->rx_queue[queue];
--      tx_q = &priv->tx_queue[queue];
-+      rx_q = &priv->dma_conf.rx_queue[queue];
-+      tx_q = &priv->dma_conf.tx_queue[queue];
-       ch = &priv->channel[queue];
-       if (!rx_q->xsk_pool && !tx_q->xsk_pool)
-@@ -6906,8 +6910,8 @@ int stmmac_reinit_ringparam(struct net_d
-       if (netif_running(dev))
-               stmmac_release(dev);
--      priv->dma_rx_size = rx_size;
--      priv->dma_tx_size = tx_size;
-+      priv->dma_conf.dma_rx_size = rx_size;
-+      priv->dma_conf.dma_tx_size = tx_size;
-       if (netif_running(dev))
-               ret = stmmac_open(dev);
-@@ -7345,7 +7349,7 @@ int stmmac_suspend(struct device *dev)
-       stmmac_disable_all_queues(priv);
-       for (chan = 0; chan < priv->plat->tx_queues_to_use; chan++)
--              hrtimer_cancel(&priv->tx_queue[chan].txtimer);
-+              hrtimer_cancel(&priv->dma_conf.tx_queue[chan].txtimer);
-       if (priv->eee_enabled) {
-               priv->tx_path_in_lpi_mode = false;
-@@ -7397,7 +7401,7 @@ EXPORT_SYMBOL_GPL(stmmac_suspend);
- static void stmmac_reset_rx_queue(struct stmmac_priv *priv, u32 queue)
- {
--      struct stmmac_rx_queue *rx_q = &priv->rx_queue[queue];
-+      struct stmmac_rx_queue *rx_q = &priv->dma_conf.rx_queue[queue];
-       rx_q->cur_rx = 0;
-       rx_q->dirty_rx = 0;
-@@ -7405,7 +7409,7 @@ static void stmmac_reset_rx_queue(struct
- static void stmmac_reset_tx_queue(struct stmmac_priv *priv, u32 queue)
- {
--      struct stmmac_tx_queue *tx_q = &priv->tx_queue[queue];
-+      struct stmmac_tx_queue *tx_q = &priv->dma_conf.tx_queue[queue];
-       tx_q->cur_tx = 0;
-       tx_q->dirty_tx = 0;
---- a/drivers/net/ethernet/stmicro/stmmac/stmmac_selftests.c
-+++ b/drivers/net/ethernet/stmicro/stmmac/stmmac_selftests.c
-@@ -795,8 +795,8 @@ static int stmmac_test_flowctrl(struct s
-               struct stmmac_channel *ch = &priv->channel[i];
-               u32 tail;
--              tail = priv->rx_queue[i].dma_rx_phy +
--                      (priv->dma_rx_size * sizeof(struct dma_desc));
-+              tail = priv->dma_conf.rx_queue[i].dma_rx_phy +
-+                      (priv->dma_conf.dma_rx_size * sizeof(struct dma_desc));
-               stmmac_set_rx_tail_ptr(priv, priv->ioaddr, tail, i);
-               stmmac_start_rx(priv, priv->ioaddr, i);
-@@ -1684,7 +1684,7 @@ cleanup:
- static int __stmmac_test_jumbo(struct stmmac_priv *priv, u16 queue)
- {
-       struct stmmac_packet_attrs attr = { };
--      int size = priv->dma_buf_sz;
-+      int size = priv->dma_conf.dma_buf_sz;
-       attr.dst = priv->dev->dev_addr;
-       attr.max_size = size - ETH_FCS_LEN;
-@@ -1767,7 +1767,7 @@ static int stmmac_test_tbs(struct stmmac
-       /* Find first TBS enabled Queue, if any */
-       for (i = 0; i < priv->plat->tx_queues_to_use; i++)
--              if (priv->tx_queue[i].tbs & STMMAC_TBS_AVAIL)
-+              if (priv->dma_conf.tx_queue[i].tbs & STMMAC_TBS_AVAIL)
-                       break;
-       if (i >= priv->plat->tx_queues_to_use)
---- a/drivers/net/ethernet/stmicro/stmmac/stmmac_tc.c
-+++ b/drivers/net/ethernet/stmicro/stmmac/stmmac_tc.c
-@@ -971,13 +971,13 @@ static int tc_setup_etf(struct stmmac_pr
-               return -EOPNOTSUPP;
-       if (qopt->queue >= priv->plat->tx_queues_to_use)
-               return -EINVAL;
--      if (!(priv->tx_queue[qopt->queue].tbs & STMMAC_TBS_AVAIL))
-+      if (!(priv->dma_conf.tx_queue[qopt->queue].tbs & STMMAC_TBS_AVAIL))
-               return -EINVAL;
-       if (qopt->enable)
--              priv->tx_queue[qopt->queue].tbs |= STMMAC_TBS_EN;
-+              priv->dma_conf.tx_queue[qopt->queue].tbs |= STMMAC_TBS_EN;
-       else
--              priv->tx_queue[qopt->queue].tbs &= ~STMMAC_TBS_EN;
-+              priv->dma_conf.tx_queue[qopt->queue].tbs &= ~STMMAC_TBS_EN;
-       netdev_info(priv->dev, "%s ETF for Queue %d\n",
-                   qopt->enable ? "enabled" : "disabled", qopt->queue);
diff --git a/target/linux/generic/backport-5.15/775-v6.0-04-net-ethernet-stmicro-stmmac-generate-stmmac-dma-conf.patch b/target/linux/generic/backport-5.15/775-v6.0-04-net-ethernet-stmicro-stmmac-generate-stmmac-dma-conf.patch
deleted file mode 100644 (file)
index 87da2af..0000000
+++ /dev/null
@@ -1,1161 +0,0 @@
-From ba39b344e9240a4a5fd4ab8178200b85cd1809da Mon Sep 17 00:00:00 2001
-From: Christian Marangi <[email protected]>
-Date: Sat, 23 Jul 2022 16:29:32 +0200
-Subject: [PATCH 4/5] net: ethernet: stmicro: stmmac: generate stmmac dma conf
- before open
-
-Rework the driver to generate the stmmac dma_conf before stmmac_open.
-This permits a function to first check if it's possible to allocate a
-new dma_config and then pass it directly to __stmmac_open and "open" the
-interface with the new configuration.
-
-Signed-off-by: Christian Marangi <[email protected]>
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- .../net/ethernet/stmicro/stmmac/stmmac_main.c | 462 +++++++++++-------
- 1 file changed, 289 insertions(+), 173 deletions(-)
-
---- a/drivers/net/ethernet/stmicro/stmmac/stmmac_main.c
-+++ b/drivers/net/ethernet/stmicro/stmmac/stmmac_main.c
-@@ -1301,7 +1301,8 @@ static int stmmac_phy_setup(struct stmma
-       return 0;
- }
--static void stmmac_display_rx_rings(struct stmmac_priv *priv)
-+static void stmmac_display_rx_rings(struct stmmac_priv *priv,
-+                                  struct stmmac_dma_conf *dma_conf)
- {
-       u32 rx_cnt = priv->plat->rx_queues_to_use;
-       unsigned int desc_size;
-@@ -1310,7 +1311,7 @@ static void stmmac_display_rx_rings(stru
-       /* Display RX rings */
-       for (queue = 0; queue < rx_cnt; queue++) {
--              struct stmmac_rx_queue *rx_q = &priv->dma_conf.rx_queue[queue];
-+              struct stmmac_rx_queue *rx_q = &dma_conf->rx_queue[queue];
-               pr_info("\tRX Queue %u rings\n", queue);
-@@ -1323,12 +1324,13 @@ static void stmmac_display_rx_rings(stru
-               }
-               /* Display RX ring */
--              stmmac_display_ring(priv, head_rx, priv->dma_conf.dma_rx_size, true,
-+              stmmac_display_ring(priv, head_rx, dma_conf->dma_rx_size, true,
-                                   rx_q->dma_rx_phy, desc_size);
-       }
- }
--static void stmmac_display_tx_rings(struct stmmac_priv *priv)
-+static void stmmac_display_tx_rings(struct stmmac_priv *priv,
-+                                  struct stmmac_dma_conf *dma_conf)
- {
-       u32 tx_cnt = priv->plat->tx_queues_to_use;
-       unsigned int desc_size;
-@@ -1337,7 +1339,7 @@ static void stmmac_display_tx_rings(stru
-       /* Display TX rings */
-       for (queue = 0; queue < tx_cnt; queue++) {
--              struct stmmac_tx_queue *tx_q = &priv->dma_conf.tx_queue[queue];
-+              struct stmmac_tx_queue *tx_q = &dma_conf->tx_queue[queue];
-               pr_info("\tTX Queue %d rings\n", queue);
-@@ -1352,18 +1354,19 @@ static void stmmac_display_tx_rings(stru
-                       desc_size = sizeof(struct dma_desc);
-               }
--              stmmac_display_ring(priv, head_tx, priv->dma_conf.dma_tx_size, false,
-+              stmmac_display_ring(priv, head_tx, dma_conf->dma_tx_size, false,
-                                   tx_q->dma_tx_phy, desc_size);
-       }
- }
--static void stmmac_display_rings(struct stmmac_priv *priv)
-+static void stmmac_display_rings(struct stmmac_priv *priv,
-+                               struct stmmac_dma_conf *dma_conf)
- {
-       /* Display RX ring */
--      stmmac_display_rx_rings(priv);
-+      stmmac_display_rx_rings(priv, dma_conf);
-       /* Display TX ring */
--      stmmac_display_tx_rings(priv);
-+      stmmac_display_tx_rings(priv, dma_conf);
- }
- static int stmmac_set_bfsize(int mtu, int bufsize)
-@@ -1387,44 +1390,50 @@ static int stmmac_set_bfsize(int mtu, in
- /**
-  * stmmac_clear_rx_descriptors - clear RX descriptors
-  * @priv: driver private structure
-+ * @dma_conf: structure to take the dma data
-  * @queue: RX queue index
-  * Description: this function is called to clear the RX descriptors
-  * in case of both basic and extended descriptors are used.
-  */
--static void stmmac_clear_rx_descriptors(struct stmmac_priv *priv, u32 queue)
-+static void stmmac_clear_rx_descriptors(struct stmmac_priv *priv,
-+                                      struct stmmac_dma_conf *dma_conf,
-+                                      u32 queue)
- {
--      struct stmmac_rx_queue *rx_q = &priv->dma_conf.rx_queue[queue];
-+      struct stmmac_rx_queue *rx_q = &dma_conf->rx_queue[queue];
-       int i;
-       /* Clear the RX descriptors */
--      for (i = 0; i < priv->dma_conf.dma_rx_size; i++)
-+      for (i = 0; i < dma_conf->dma_rx_size; i++)
-               if (priv->extend_desc)
-                       stmmac_init_rx_desc(priv, &rx_q->dma_erx[i].basic,
-                                       priv->use_riwt, priv->mode,
--                                      (i == priv->dma_conf.dma_rx_size - 1),
--                                      priv->dma_conf.dma_buf_sz);
-+                                      (i == dma_conf->dma_rx_size - 1),
-+                                      dma_conf->dma_buf_sz);
-               else
-                       stmmac_init_rx_desc(priv, &rx_q->dma_rx[i],
-                                       priv->use_riwt, priv->mode,
--                                      (i == priv->dma_conf.dma_rx_size - 1),
--                                      priv->dma_conf.dma_buf_sz);
-+                                      (i == dma_conf->dma_rx_size - 1),
-+                                      dma_conf->dma_buf_sz);
- }
- /**
-  * stmmac_clear_tx_descriptors - clear tx descriptors
-  * @priv: driver private structure
-+ * @dma_conf: structure to take the dma data
-  * @queue: TX queue index.
-  * Description: this function is called to clear the TX descriptors
-  * in case of both basic and extended descriptors are used.
-  */
--static void stmmac_clear_tx_descriptors(struct stmmac_priv *priv, u32 queue)
-+static void stmmac_clear_tx_descriptors(struct stmmac_priv *priv,
-+                                      struct stmmac_dma_conf *dma_conf,
-+                                      u32 queue)
- {
--      struct stmmac_tx_queue *tx_q = &priv->dma_conf.tx_queue[queue];
-+      struct stmmac_tx_queue *tx_q = &dma_conf->tx_queue[queue];
-       int i;
-       /* Clear the TX descriptors */
--      for (i = 0; i < priv->dma_conf.dma_tx_size; i++) {
--              int last = (i == (priv->dma_conf.dma_tx_size - 1));
-+      for (i = 0; i < dma_conf->dma_tx_size; i++) {
-+              int last = (i == (dma_conf->dma_tx_size - 1));
-               struct dma_desc *p;
-               if (priv->extend_desc)
-@@ -1441,10 +1450,12 @@ static void stmmac_clear_tx_descriptors(
- /**
-  * stmmac_clear_descriptors - clear descriptors
-  * @priv: driver private structure
-+ * @dma_conf: structure to take the dma data
-  * Description: this function is called to clear the TX and RX descriptors
-  * in case of both basic and extended descriptors are used.
-  */
--static void stmmac_clear_descriptors(struct stmmac_priv *priv)
-+static void stmmac_clear_descriptors(struct stmmac_priv *priv,
-+                                   struct stmmac_dma_conf *dma_conf)
- {
-       u32 rx_queue_cnt = priv->plat->rx_queues_to_use;
-       u32 tx_queue_cnt = priv->plat->tx_queues_to_use;
-@@ -1452,16 +1463,17 @@ static void stmmac_clear_descriptors(str
-       /* Clear the RX descriptors */
-       for (queue = 0; queue < rx_queue_cnt; queue++)
--              stmmac_clear_rx_descriptors(priv, queue);
-+              stmmac_clear_rx_descriptors(priv, dma_conf, queue);
-       /* Clear the TX descriptors */
-       for (queue = 0; queue < tx_queue_cnt; queue++)
--              stmmac_clear_tx_descriptors(priv, queue);
-+              stmmac_clear_tx_descriptors(priv, dma_conf, queue);
- }
- /**
-  * stmmac_init_rx_buffers - init the RX descriptor buffer.
-  * @priv: driver private structure
-+ * @dma_conf: structure to take the dma data
-  * @p: descriptor pointer
-  * @i: descriptor index
-  * @flags: gfp flag
-@@ -1469,10 +1481,12 @@ static void stmmac_clear_descriptors(str
-  * Description: this function is called to allocate a receive buffer, perform
-  * the DMA mapping and init the descriptor.
-  */
--static int stmmac_init_rx_buffers(struct stmmac_priv *priv, struct dma_desc *p,
-+static int stmmac_init_rx_buffers(struct stmmac_priv *priv,
-+                                struct stmmac_dma_conf *dma_conf,
-+                                struct dma_desc *p,
-                                 int i, gfp_t flags, u32 queue)
- {
--      struct stmmac_rx_queue *rx_q = &priv->dma_conf.rx_queue[queue];
-+      struct stmmac_rx_queue *rx_q = &dma_conf->rx_queue[queue];
-       struct stmmac_rx_buffer *buf = &rx_q->buf_pool[i];
-       if (!buf->page) {
-@@ -1497,7 +1511,7 @@ static int stmmac_init_rx_buffers(struct
-       buf->addr = page_pool_get_dma_addr(buf->page) + buf->page_offset;
-       stmmac_set_desc_addr(priv, p, buf->addr);
--      if (priv->dma_conf.dma_buf_sz == BUF_SIZE_16KiB)
-+      if (dma_conf->dma_buf_sz == BUF_SIZE_16KiB)
-               stmmac_init_desc3(priv, p);
-       return 0;
-@@ -1506,12 +1520,13 @@ static int stmmac_init_rx_buffers(struct
- /**
-  * stmmac_free_rx_buffer - free RX dma buffers
-  * @priv: private structure
-- * @queue: RX queue index
-+ * @rx_q: RX queue
-  * @i: buffer index.
-  */
--static void stmmac_free_rx_buffer(struct stmmac_priv *priv, u32 queue, int i)
-+static void stmmac_free_rx_buffer(struct stmmac_priv *priv,
-+                                struct stmmac_rx_queue *rx_q,
-+                                int i)
- {
--      struct stmmac_rx_queue *rx_q = &priv->dma_conf.rx_queue[queue];
-       struct stmmac_rx_buffer *buf = &rx_q->buf_pool[i];
-       if (buf->page)
-@@ -1526,12 +1541,15 @@ static void stmmac_free_rx_buffer(struct
- /**
-  * stmmac_free_tx_buffer - free RX dma buffers
-  * @priv: private structure
-+ * @dma_conf: structure to take the dma data
-  * @queue: RX queue index
-  * @i: buffer index.
-  */
--static void stmmac_free_tx_buffer(struct stmmac_priv *priv, u32 queue, int i)
-+static void stmmac_free_tx_buffer(struct stmmac_priv *priv,
-+                                struct stmmac_dma_conf *dma_conf,
-+                                u32 queue, int i)
- {
--      struct stmmac_tx_queue *tx_q = &priv->dma_conf.tx_queue[queue];
-+      struct stmmac_tx_queue *tx_q = &dma_conf->tx_queue[queue];
-       if (tx_q->tx_skbuff_dma[i].buf &&
-           tx_q->tx_skbuff_dma[i].buf_type != STMMAC_TXBUF_T_XDP_TX) {
-@@ -1570,23 +1588,28 @@ static void stmmac_free_tx_buffer(struct
- /**
-  * dma_free_rx_skbufs - free RX dma buffers
-  * @priv: private structure
-+ * @dma_conf: structure to take the dma data
-  * @queue: RX queue index
-  */
--static void dma_free_rx_skbufs(struct stmmac_priv *priv, u32 queue)
-+static void dma_free_rx_skbufs(struct stmmac_priv *priv,
-+                             struct stmmac_dma_conf *dma_conf,
-+                             u32 queue)
- {
-+      struct stmmac_rx_queue *rx_q = &dma_conf->rx_queue[queue];
-       int i;
--      for (i = 0; i < priv->dma_conf.dma_rx_size; i++)
--              stmmac_free_rx_buffer(priv, queue, i);
-+      for (i = 0; i < dma_conf->dma_rx_size; i++)
-+              stmmac_free_rx_buffer(priv, rx_q, i);
- }
--static int stmmac_alloc_rx_buffers(struct stmmac_priv *priv, u32 queue,
--                                 gfp_t flags)
-+static int stmmac_alloc_rx_buffers(struct stmmac_priv *priv,
-+                                 struct stmmac_dma_conf *dma_conf,
-+                                 u32 queue, gfp_t flags)
- {
--      struct stmmac_rx_queue *rx_q = &priv->dma_conf.rx_queue[queue];
-+      struct stmmac_rx_queue *rx_q = &dma_conf->rx_queue[queue];
-       int i;
--      for (i = 0; i < priv->dma_conf.dma_rx_size; i++) {
-+      for (i = 0; i < dma_conf->dma_rx_size; i++) {
-               struct dma_desc *p;
-               int ret;
-@@ -1595,7 +1618,7 @@ static int stmmac_alloc_rx_buffers(struc
-               else
-                       p = rx_q->dma_rx + i;
--              ret = stmmac_init_rx_buffers(priv, p, i, flags,
-+              ret = stmmac_init_rx_buffers(priv, dma_conf, p, i, flags,
-                                            queue);
-               if (ret)
-                       return ret;
-@@ -1609,14 +1632,17 @@ static int stmmac_alloc_rx_buffers(struc
- /**
-  * dma_free_rx_xskbufs - free RX dma buffers from XSK pool
-  * @priv: private structure
-+ * @dma_conf: structure to take the dma data
-  * @queue: RX queue index
-  */
--static void dma_free_rx_xskbufs(struct stmmac_priv *priv, u32 queue)
-+static void dma_free_rx_xskbufs(struct stmmac_priv *priv,
-+                              struct stmmac_dma_conf *dma_conf,
-+                              u32 queue)
- {
--      struct stmmac_rx_queue *rx_q = &priv->dma_conf.rx_queue[queue];
-+      struct stmmac_rx_queue *rx_q = &dma_conf->rx_queue[queue];
-       int i;
--      for (i = 0; i < priv->dma_conf.dma_rx_size; i++) {
-+      for (i = 0; i < dma_conf->dma_rx_size; i++) {
-               struct stmmac_rx_buffer *buf = &rx_q->buf_pool[i];
-               if (!buf->xdp)
-@@ -1627,12 +1653,14 @@ static void dma_free_rx_xskbufs(struct s
-       }
- }
--static int stmmac_alloc_rx_buffers_zc(struct stmmac_priv *priv, u32 queue)
-+static int stmmac_alloc_rx_buffers_zc(struct stmmac_priv *priv,
-+                                    struct stmmac_dma_conf *dma_conf,
-+                                    u32 queue)
- {
--      struct stmmac_rx_queue *rx_q = &priv->dma_conf.rx_queue[queue];
-+      struct stmmac_rx_queue *rx_q = &dma_conf->rx_queue[queue];
-       int i;
--      for (i = 0; i < priv->dma_conf.dma_rx_size; i++) {
-+      for (i = 0; i < dma_conf->dma_rx_size; i++) {
-               struct stmmac_rx_buffer *buf;
-               dma_addr_t dma_addr;
-               struct dma_desc *p;
-@@ -1667,22 +1695,25 @@ static struct xsk_buff_pool *stmmac_get_
- /**
-  * __init_dma_rx_desc_rings - init the RX descriptor ring (per queue)
-  * @priv: driver private structure
-+ * @dma_conf: structure to take the dma data
-  * @queue: RX queue index
-  * @flags: gfp flag.
-  * Description: this function initializes the DMA RX descriptors
-  * and allocates the socket buffers. It supports the chained and ring
-  * modes.
-  */
--static int __init_dma_rx_desc_rings(struct stmmac_priv *priv, u32 queue, gfp_t flags)
-+static int __init_dma_rx_desc_rings(struct stmmac_priv *priv,
-+                                  struct stmmac_dma_conf *dma_conf,
-+                                  u32 queue, gfp_t flags)
- {
--      struct stmmac_rx_queue *rx_q = &priv->dma_conf.rx_queue[queue];
-+      struct stmmac_rx_queue *rx_q = &dma_conf->rx_queue[queue];
-       int ret;
-       netif_dbg(priv, probe, priv->dev,
-                 "(%s) dma_rx_phy=0x%08x\n", __func__,
-                 (u32)rx_q->dma_rx_phy);
--      stmmac_clear_rx_descriptors(priv, queue);
-+      stmmac_clear_rx_descriptors(priv, dma_conf, queue);
-       xdp_rxq_info_unreg_mem_model(&rx_q->xdp_rxq);
-@@ -1709,9 +1740,9 @@ static int __init_dma_rx_desc_rings(stru
-               /* RX XDP ZC buffer pool may not be populated, e.g.
-                * xdpsock TX-only.
-                */
--              stmmac_alloc_rx_buffers_zc(priv, queue);
-+              stmmac_alloc_rx_buffers_zc(priv, dma_conf, queue);
-       } else {
--              ret = stmmac_alloc_rx_buffers(priv, queue, flags);
-+              ret = stmmac_alloc_rx_buffers(priv, dma_conf, queue, flags);
-               if (ret < 0)
-                       return -ENOMEM;
-       }
-@@ -1721,17 +1752,19 @@ static int __init_dma_rx_desc_rings(stru
-               if (priv->extend_desc)
-                       stmmac_mode_init(priv, rx_q->dma_erx,
-                                        rx_q->dma_rx_phy,
--                                       priv->dma_conf.dma_rx_size, 1);
-+                                       dma_conf->dma_rx_size, 1);
-               else
-                       stmmac_mode_init(priv, rx_q->dma_rx,
-                                        rx_q->dma_rx_phy,
--                                       priv->dma_conf.dma_rx_size, 0);
-+                                       dma_conf->dma_rx_size, 0);
-       }
-       return 0;
- }
--static int init_dma_rx_desc_rings(struct net_device *dev, gfp_t flags)
-+static int init_dma_rx_desc_rings(struct net_device *dev,
-+                                struct stmmac_dma_conf *dma_conf,
-+                                gfp_t flags)
- {
-       struct stmmac_priv *priv = netdev_priv(dev);
-       u32 rx_count = priv->plat->rx_queues_to_use;
-@@ -1743,7 +1776,7 @@ static int init_dma_rx_desc_rings(struct
-                 "SKB addresses:\nskb\t\tskb data\tdma data\n");
-       for (queue = 0; queue < rx_count; queue++) {
--              ret = __init_dma_rx_desc_rings(priv, queue, flags);
-+              ret = __init_dma_rx_desc_rings(priv, dma_conf, queue, flags);
-               if (ret)
-                       goto err_init_rx_buffers;
-       }
-@@ -1752,12 +1785,12 @@ static int init_dma_rx_desc_rings(struct
- err_init_rx_buffers:
-       while (queue >= 0) {
--              struct stmmac_rx_queue *rx_q = &priv->dma_conf.rx_queue[queue];
-+              struct stmmac_rx_queue *rx_q = &dma_conf->rx_queue[queue];
-               if (rx_q->xsk_pool)
--                      dma_free_rx_xskbufs(priv, queue);
-+                      dma_free_rx_xskbufs(priv, dma_conf, queue);
-               else
--                      dma_free_rx_skbufs(priv, queue);
-+                      dma_free_rx_skbufs(priv, dma_conf, queue);
-               rx_q->buf_alloc_num = 0;
-               rx_q->xsk_pool = NULL;
-@@ -1774,14 +1807,17 @@ err_init_rx_buffers:
- /**
-  * __init_dma_tx_desc_rings - init the TX descriptor ring (per queue)
-  * @priv: driver private structure
-- * @queue : TX queue index
-+ * @dma_conf: structure to take the dma data
-+ * @queue: TX queue index
-  * Description: this function initializes the DMA TX descriptors
-  * and allocates the socket buffers. It supports the chained and ring
-  * modes.
-  */
--static int __init_dma_tx_desc_rings(struct stmmac_priv *priv, u32 queue)
-+static int __init_dma_tx_desc_rings(struct stmmac_priv *priv,
-+                                  struct stmmac_dma_conf *dma_conf,
-+                                  u32 queue)
- {
--      struct stmmac_tx_queue *tx_q = &priv->dma_conf.tx_queue[queue];
-+      struct stmmac_tx_queue *tx_q = &dma_conf->tx_queue[queue];
-       int i;
-       netif_dbg(priv, probe, priv->dev,
-@@ -1793,16 +1829,16 @@ static int __init_dma_tx_desc_rings(stru
-               if (priv->extend_desc)
-                       stmmac_mode_init(priv, tx_q->dma_etx,
-                                        tx_q->dma_tx_phy,
--                                       priv->dma_conf.dma_tx_size, 1);
-+                                       dma_conf->dma_tx_size, 1);
-               else if (!(tx_q->tbs & STMMAC_TBS_AVAIL))
-                       stmmac_mode_init(priv, tx_q->dma_tx,
-                                        tx_q->dma_tx_phy,
--                                       priv->dma_conf.dma_tx_size, 0);
-+                                       dma_conf->dma_tx_size, 0);
-       }
-       tx_q->xsk_pool = stmmac_get_xsk_pool(priv, queue);
--      for (i = 0; i < priv->dma_conf.dma_tx_size; i++) {
-+      for (i = 0; i < dma_conf->dma_tx_size; i++) {
-               struct dma_desc *p;
-               if (priv->extend_desc)
-@@ -1824,7 +1860,8 @@ static int __init_dma_tx_desc_rings(stru
-       return 0;
- }
--static int init_dma_tx_desc_rings(struct net_device *dev)
-+static int init_dma_tx_desc_rings(struct net_device *dev,
-+                                struct stmmac_dma_conf *dma_conf)
- {
-       struct stmmac_priv *priv = netdev_priv(dev);
-       u32 tx_queue_cnt;
-@@ -1833,7 +1870,7 @@ static int init_dma_tx_desc_rings(struct
-       tx_queue_cnt = priv->plat->tx_queues_to_use;
-       for (queue = 0; queue < tx_queue_cnt; queue++)
--              __init_dma_tx_desc_rings(priv, queue);
-+              __init_dma_tx_desc_rings(priv, dma_conf, queue);
-       return 0;
- }
-@@ -1841,26 +1878,29 @@ static int init_dma_tx_desc_rings(struct
- /**
-  * init_dma_desc_rings - init the RX/TX descriptor rings
-  * @dev: net device structure
-+ * @dma_conf: structure to take the dma data
-  * @flags: gfp flag.
-  * Description: this function initializes the DMA RX/TX descriptors
-  * and allocates the socket buffers. It supports the chained and ring
-  * modes.
-  */
--static int init_dma_desc_rings(struct net_device *dev, gfp_t flags)
-+static int init_dma_desc_rings(struct net_device *dev,
-+                             struct stmmac_dma_conf *dma_conf,
-+                             gfp_t flags)
- {
-       struct stmmac_priv *priv = netdev_priv(dev);
-       int ret;
--      ret = init_dma_rx_desc_rings(dev, flags);
-+      ret = init_dma_rx_desc_rings(dev, dma_conf, flags);
-       if (ret)
-               return ret;
--      ret = init_dma_tx_desc_rings(dev);
-+      ret = init_dma_tx_desc_rings(dev, dma_conf);
--      stmmac_clear_descriptors(priv);
-+      stmmac_clear_descriptors(priv, dma_conf);
-       if (netif_msg_hw(priv))
--              stmmac_display_rings(priv);
-+              stmmac_display_rings(priv, dma_conf);
-       return ret;
- }
-@@ -1868,17 +1908,20 @@ static int init_dma_desc_rings(struct ne
- /**
-  * dma_free_tx_skbufs - free TX dma buffers
-  * @priv: private structure
-+ * @dma_conf: structure to take the dma data
-  * @queue: TX queue index
-  */
--static void dma_free_tx_skbufs(struct stmmac_priv *priv, u32 queue)
-+static void dma_free_tx_skbufs(struct stmmac_priv *priv,
-+                             struct stmmac_dma_conf *dma_conf,
-+                             u32 queue)
- {
--      struct stmmac_tx_queue *tx_q = &priv->dma_conf.tx_queue[queue];
-+      struct stmmac_tx_queue *tx_q = &dma_conf->tx_queue[queue];
-       int i;
-       tx_q->xsk_frames_done = 0;
--      for (i = 0; i < priv->dma_conf.dma_tx_size; i++)
--              stmmac_free_tx_buffer(priv, queue, i);
-+      for (i = 0; i < dma_conf->dma_tx_size; i++)
-+              stmmac_free_tx_buffer(priv, dma_conf, queue, i);
-       if (tx_q->xsk_pool && tx_q->xsk_frames_done) {
-               xsk_tx_completed(tx_q->xsk_pool, tx_q->xsk_frames_done);
-@@ -1897,34 +1940,37 @@ static void stmmac_free_tx_skbufs(struct
-       u32 queue;
-       for (queue = 0; queue < tx_queue_cnt; queue++)
--              dma_free_tx_skbufs(priv, queue);
-+              dma_free_tx_skbufs(priv, &priv->dma_conf, queue);
- }
- /**
-  * __free_dma_rx_desc_resources - free RX dma desc resources (per queue)
-  * @priv: private structure
-+ * @dma_conf: structure to take the dma data
-  * @queue: RX queue index
-  */
--static void __free_dma_rx_desc_resources(struct stmmac_priv *priv, u32 queue)
-+static void __free_dma_rx_desc_resources(struct stmmac_priv *priv,
-+                                       struct stmmac_dma_conf *dma_conf,
-+                                       u32 queue)
- {
--      struct stmmac_rx_queue *rx_q = &priv->dma_conf.rx_queue[queue];
-+      struct stmmac_rx_queue *rx_q = &dma_conf->rx_queue[queue];
-       /* Release the DMA RX socket buffers */
-       if (rx_q->xsk_pool)
--              dma_free_rx_xskbufs(priv, queue);
-+              dma_free_rx_xskbufs(priv, dma_conf, queue);
-       else
--              dma_free_rx_skbufs(priv, queue);
-+              dma_free_rx_skbufs(priv, dma_conf, queue);
-       rx_q->buf_alloc_num = 0;
-       rx_q->xsk_pool = NULL;
-       /* Free DMA regions of consistent memory previously allocated */
-       if (!priv->extend_desc)
--              dma_free_coherent(priv->device, priv->dma_conf.dma_rx_size *
-+              dma_free_coherent(priv->device, dma_conf->dma_rx_size *
-                                 sizeof(struct dma_desc),
-                                 rx_q->dma_rx, rx_q->dma_rx_phy);
-       else
--              dma_free_coherent(priv->device, priv->dma_conf.dma_rx_size *
-+              dma_free_coherent(priv->device, dma_conf->dma_rx_size *
-                                 sizeof(struct dma_extended_desc),
-                                 rx_q->dma_erx, rx_q->dma_rx_phy);
-@@ -1936,29 +1982,33 @@ static void __free_dma_rx_desc_resources
-               page_pool_destroy(rx_q->page_pool);
- }
--static void free_dma_rx_desc_resources(struct stmmac_priv *priv)
-+static void free_dma_rx_desc_resources(struct stmmac_priv *priv,
-+                                     struct stmmac_dma_conf *dma_conf)
- {
-       u32 rx_count = priv->plat->rx_queues_to_use;
-       u32 queue;
-       /* Free RX queue resources */
-       for (queue = 0; queue < rx_count; queue++)
--              __free_dma_rx_desc_resources(priv, queue);
-+              __free_dma_rx_desc_resources(priv, dma_conf, queue);
- }
- /**
-  * __free_dma_tx_desc_resources - free TX dma desc resources (per queue)
-  * @priv: private structure
-+ * @dma_conf: structure to take the dma data
-  * @queue: TX queue index
-  */
--static void __free_dma_tx_desc_resources(struct stmmac_priv *priv, u32 queue)
-+static void __free_dma_tx_desc_resources(struct stmmac_priv *priv,
-+                                       struct stmmac_dma_conf *dma_conf,
-+                                       u32 queue)
- {
--      struct stmmac_tx_queue *tx_q = &priv->dma_conf.tx_queue[queue];
-+      struct stmmac_tx_queue *tx_q = &dma_conf->tx_queue[queue];
-       size_t size;
-       void *addr;
-       /* Release the DMA TX socket buffers */
--      dma_free_tx_skbufs(priv, queue);
-+      dma_free_tx_skbufs(priv, dma_conf, queue);
-       if (priv->extend_desc) {
-               size = sizeof(struct dma_extended_desc);
-@@ -1971,7 +2021,7 @@ static void __free_dma_tx_desc_resources
-               addr = tx_q->dma_tx;
-       }
--      size *= priv->dma_conf.dma_tx_size;
-+      size *= dma_conf->dma_tx_size;
-       dma_free_coherent(priv->device, size, addr, tx_q->dma_tx_phy);
-@@ -1979,28 +2029,32 @@ static void __free_dma_tx_desc_resources
-       kfree(tx_q->tx_skbuff);
- }
--static void free_dma_tx_desc_resources(struct stmmac_priv *priv)
-+static void free_dma_tx_desc_resources(struct stmmac_priv *priv,
-+                                     struct stmmac_dma_conf *dma_conf)
- {
-       u32 tx_count = priv->plat->tx_queues_to_use;
-       u32 queue;
-       /* Free TX queue resources */
-       for (queue = 0; queue < tx_count; queue++)
--              __free_dma_tx_desc_resources(priv, queue);
-+              __free_dma_tx_desc_resources(priv, dma_conf, queue);
- }
- /**
-  * __alloc_dma_rx_desc_resources - alloc RX resources (per queue).
-  * @priv: private structure
-+ * @dma_conf: structure to take the dma data
-  * @queue: RX queue index
-  * Description: according to which descriptor can be used (extend or basic)
-  * this function allocates the resources for TX and RX paths. In case of
-  * reception, for example, it pre-allocated the RX socket buffer in order to
-  * allow zero-copy mechanism.
-  */
--static int __alloc_dma_rx_desc_resources(struct stmmac_priv *priv, u32 queue)
-+static int __alloc_dma_rx_desc_resources(struct stmmac_priv *priv,
-+                                       struct stmmac_dma_conf *dma_conf,
-+                                       u32 queue)
- {
--      struct stmmac_rx_queue *rx_q = &priv->dma_conf.rx_queue[queue];
-+      struct stmmac_rx_queue *rx_q = &dma_conf->rx_queue[queue];
-       struct stmmac_channel *ch = &priv->channel[queue];
-       bool xdp_prog = stmmac_xdp_is_enabled(priv);
-       struct page_pool_params pp_params = { 0 };
-@@ -2012,8 +2066,8 @@ static int __alloc_dma_rx_desc_resources
-       rx_q->priv_data = priv;
-       pp_params.flags = PP_FLAG_DMA_MAP | PP_FLAG_DMA_SYNC_DEV;
--      pp_params.pool_size = priv->dma_conf.dma_rx_size;
--      num_pages = DIV_ROUND_UP(priv->dma_conf.dma_buf_sz, PAGE_SIZE);
-+      pp_params.pool_size = dma_conf->dma_rx_size;
-+      num_pages = DIV_ROUND_UP(dma_conf->dma_buf_sz, PAGE_SIZE);
-       pp_params.order = ilog2(num_pages);
-       pp_params.nid = dev_to_node(priv->device);
-       pp_params.dev = priv->device;
-@@ -2028,7 +2082,7 @@ static int __alloc_dma_rx_desc_resources
-               return ret;
-       }
--      rx_q->buf_pool = kcalloc(priv->dma_conf.dma_rx_size,
-+      rx_q->buf_pool = kcalloc(dma_conf->dma_rx_size,
-                                sizeof(*rx_q->buf_pool),
-                                GFP_KERNEL);
-       if (!rx_q->buf_pool)
-@@ -2036,7 +2090,7 @@ static int __alloc_dma_rx_desc_resources
-       if (priv->extend_desc) {
-               rx_q->dma_erx = dma_alloc_coherent(priv->device,
--                                                 priv->dma_conf.dma_rx_size *
-+                                                 dma_conf->dma_rx_size *
-                                                  sizeof(struct dma_extended_desc),
-                                                  &rx_q->dma_rx_phy,
-                                                  GFP_KERNEL);
-@@ -2045,7 +2099,7 @@ static int __alloc_dma_rx_desc_resources
-       } else {
-               rx_q->dma_rx = dma_alloc_coherent(priv->device,
--                                                priv->dma_conf.dma_rx_size *
-+                                                dma_conf->dma_rx_size *
-                                                 sizeof(struct dma_desc),
-                                                 &rx_q->dma_rx_phy,
-                                                 GFP_KERNEL);
-@@ -2070,7 +2124,8 @@ static int __alloc_dma_rx_desc_resources
-       return 0;
- }
--static int alloc_dma_rx_desc_resources(struct stmmac_priv *priv)
-+static int alloc_dma_rx_desc_resources(struct stmmac_priv *priv,
-+                                     struct stmmac_dma_conf *dma_conf)
- {
-       u32 rx_count = priv->plat->rx_queues_to_use;
-       u32 queue;
-@@ -2078,7 +2133,7 @@ static int alloc_dma_rx_desc_resources(s
-       /* RX queues buffers and DMA */
-       for (queue = 0; queue < rx_count; queue++) {
--              ret = __alloc_dma_rx_desc_resources(priv, queue);
-+              ret = __alloc_dma_rx_desc_resources(priv, dma_conf, queue);
-               if (ret)
-                       goto err_dma;
-       }
-@@ -2086,7 +2141,7 @@ static int alloc_dma_rx_desc_resources(s
-       return 0;
- err_dma:
--      free_dma_rx_desc_resources(priv);
-+      free_dma_rx_desc_resources(priv, dma_conf);
-       return ret;
- }
-@@ -2094,28 +2149,31 @@ err_dma:
- /**
-  * __alloc_dma_tx_desc_resources - alloc TX resources (per queue).
-  * @priv: private structure
-+ * @dma_conf: structure to take the dma data
-  * @queue: TX queue index
-  * Description: according to which descriptor can be used (extend or basic)
-  * this function allocates the resources for TX and RX paths. In case of
-  * reception, for example, it pre-allocated the RX socket buffer in order to
-  * allow zero-copy mechanism.
-  */
--static int __alloc_dma_tx_desc_resources(struct stmmac_priv *priv, u32 queue)
-+static int __alloc_dma_tx_desc_resources(struct stmmac_priv *priv,
-+                                       struct stmmac_dma_conf *dma_conf,
-+                                       u32 queue)
- {
--      struct stmmac_tx_queue *tx_q = &priv->dma_conf.tx_queue[queue];
-+      struct stmmac_tx_queue *tx_q = &dma_conf->tx_queue[queue];
-       size_t size;
-       void *addr;
-       tx_q->queue_index = queue;
-       tx_q->priv_data = priv;
--      tx_q->tx_skbuff_dma = kcalloc(priv->dma_conf.dma_tx_size,
-+      tx_q->tx_skbuff_dma = kcalloc(dma_conf->dma_tx_size,
-                                     sizeof(*tx_q->tx_skbuff_dma),
-                                     GFP_KERNEL);
-       if (!tx_q->tx_skbuff_dma)
-               return -ENOMEM;
--      tx_q->tx_skbuff = kcalloc(priv->dma_conf.dma_tx_size,
-+      tx_q->tx_skbuff = kcalloc(dma_conf->dma_tx_size,
-                                 sizeof(struct sk_buff *),
-                                 GFP_KERNEL);
-       if (!tx_q->tx_skbuff)
-@@ -2128,7 +2186,7 @@ static int __alloc_dma_tx_desc_resources
-       else
-               size = sizeof(struct dma_desc);
--      size *= priv->dma_conf.dma_tx_size;
-+      size *= dma_conf->dma_tx_size;
-       addr = dma_alloc_coherent(priv->device, size,
-                                 &tx_q->dma_tx_phy, GFP_KERNEL);
-@@ -2145,7 +2203,8 @@ static int __alloc_dma_tx_desc_resources
-       return 0;
- }
--static int alloc_dma_tx_desc_resources(struct stmmac_priv *priv)
-+static int alloc_dma_tx_desc_resources(struct stmmac_priv *priv,
-+                                     struct stmmac_dma_conf *dma_conf)
- {
-       u32 tx_count = priv->plat->tx_queues_to_use;
-       u32 queue;
-@@ -2153,7 +2212,7 @@ static int alloc_dma_tx_desc_resources(s
-       /* TX queues buffers and DMA */
-       for (queue = 0; queue < tx_count; queue++) {
--              ret = __alloc_dma_tx_desc_resources(priv, queue);
-+              ret = __alloc_dma_tx_desc_resources(priv, dma_conf, queue);
-               if (ret)
-                       goto err_dma;
-       }
-@@ -2161,27 +2220,29 @@ static int alloc_dma_tx_desc_resources(s
-       return 0;
- err_dma:
--      free_dma_tx_desc_resources(priv);
-+      free_dma_tx_desc_resources(priv, dma_conf);
-       return ret;
- }
- /**
-  * alloc_dma_desc_resources - alloc TX/RX resources.
-  * @priv: private structure
-+ * @dma_conf: structure to take the dma data
-  * Description: according to which descriptor can be used (extend or basic)
-  * this function allocates the resources for TX and RX paths. In case of
-  * reception, for example, it pre-allocated the RX socket buffer in order to
-  * allow zero-copy mechanism.
-  */
--static int alloc_dma_desc_resources(struct stmmac_priv *priv)
-+static int alloc_dma_desc_resources(struct stmmac_priv *priv,
-+                                  struct stmmac_dma_conf *dma_conf)
- {
-       /* RX Allocation */
--      int ret = alloc_dma_rx_desc_resources(priv);
-+      int ret = alloc_dma_rx_desc_resources(priv, dma_conf);
-       if (ret)
-               return ret;
--      ret = alloc_dma_tx_desc_resources(priv);
-+      ret = alloc_dma_tx_desc_resources(priv, dma_conf);
-       return ret;
- }
-@@ -2189,16 +2250,18 @@ static int alloc_dma_desc_resources(stru
- /**
-  * free_dma_desc_resources - free dma desc resources
-  * @priv: private structure
-+ * @dma_conf: structure to take the dma data
-  */
--static void free_dma_desc_resources(struct stmmac_priv *priv)
-+static void free_dma_desc_resources(struct stmmac_priv *priv,
-+                                  struct stmmac_dma_conf *dma_conf)
- {
-       /* Release the DMA TX socket buffers */
--      free_dma_tx_desc_resources(priv);
-+      free_dma_tx_desc_resources(priv, dma_conf);
-       /* Release the DMA RX socket buffers later
-        * to ensure all pending XDP_TX buffers are returned.
-        */
--      free_dma_rx_desc_resources(priv);
-+      free_dma_rx_desc_resources(priv, dma_conf);
- }
- /**
-@@ -2687,8 +2750,8 @@ static void stmmac_tx_err(struct stmmac_
-       netif_tx_stop_queue(netdev_get_tx_queue(priv->dev, chan));
-       stmmac_stop_tx_dma(priv, chan);
--      dma_free_tx_skbufs(priv, chan);
--      stmmac_clear_tx_descriptors(priv, chan);
-+      dma_free_tx_skbufs(priv, &priv->dma_conf, chan);
-+      stmmac_clear_tx_descriptors(priv, &priv->dma_conf, chan);
-       stmmac_reset_tx_queue(priv, chan);
-       stmmac_init_tx_chan(priv, priv->ioaddr, priv->plat->dma_cfg,
-                           tx_q->dma_tx_phy, chan);
-@@ -3686,19 +3749,93 @@ static int stmmac_request_irq(struct net
- }
- /**
-- *  stmmac_open - open entry point of the driver
-+ *  stmmac_setup_dma_desc - Generate a dma_conf and allocate DMA queue
-+ *  @priv: driver private structure
-+ *  @mtu: MTU to setup the dma queue and buf with
-+ *  Description: Allocate and generate a dma_conf based on the provided MTU.
-+ *  Allocate the Tx/Rx DMA queue and init them.
-+ *  Return value:
-+ *  the dma_conf allocated struct on success and an appropriate ERR_PTR on failure.
-+ */
-+static struct stmmac_dma_conf *
-+stmmac_setup_dma_desc(struct stmmac_priv *priv, unsigned int mtu)
-+{
-+      struct stmmac_dma_conf *dma_conf;
-+      int chan, bfsize, ret;
-+
-+      dma_conf = kzalloc(sizeof(*dma_conf), GFP_KERNEL);
-+      if (!dma_conf) {
-+              netdev_err(priv->dev, "%s: DMA conf allocation failed\n",
-+                         __func__);
-+              return ERR_PTR(-ENOMEM);
-+      }
-+
-+      bfsize = stmmac_set_16kib_bfsize(priv, mtu);
-+      if (bfsize < 0)
-+              bfsize = 0;
-+
-+      if (bfsize < BUF_SIZE_16KiB)
-+              bfsize = stmmac_set_bfsize(mtu, 0);
-+
-+      dma_conf->dma_buf_sz = bfsize;
-+      /* Chose the tx/rx size from the already defined one in the
-+       * priv struct. (if defined)
-+       */
-+      dma_conf->dma_tx_size = priv->dma_conf.dma_tx_size;
-+      dma_conf->dma_rx_size = priv->dma_conf.dma_rx_size;
-+
-+      if (!dma_conf->dma_tx_size)
-+              dma_conf->dma_tx_size = DMA_DEFAULT_TX_SIZE;
-+      if (!dma_conf->dma_rx_size)
-+              dma_conf->dma_rx_size = DMA_DEFAULT_RX_SIZE;
-+
-+      /* Earlier check for TBS */
-+      for (chan = 0; chan < priv->plat->tx_queues_to_use; chan++) {
-+              struct stmmac_tx_queue *tx_q = &dma_conf->tx_queue[chan];
-+              int tbs_en = priv->plat->tx_queues_cfg[chan].tbs_en;
-+
-+              /* Setup per-TXQ tbs flag before TX descriptor alloc */
-+              tx_q->tbs |= tbs_en ? STMMAC_TBS_AVAIL : 0;
-+      }
-+
-+      ret = alloc_dma_desc_resources(priv, dma_conf);
-+      if (ret < 0) {
-+              netdev_err(priv->dev, "%s: DMA descriptors allocation failed\n",
-+                         __func__);
-+              goto alloc_error;
-+      }
-+
-+      ret = init_dma_desc_rings(priv->dev, dma_conf, GFP_KERNEL);
-+      if (ret < 0) {
-+              netdev_err(priv->dev, "%s: DMA descriptors initialization failed\n",
-+                         __func__);
-+              goto init_error;
-+      }
-+
-+      return dma_conf;
-+
-+init_error:
-+      free_dma_desc_resources(priv, dma_conf);
-+alloc_error:
-+      kfree(dma_conf);
-+      return ERR_PTR(ret);
-+}
-+
-+/**
-+ *  __stmmac_open - open entry point of the driver
-  *  @dev : pointer to the device structure.
-+ *  @dma_conf :  structure to take the dma data
-  *  Description:
-  *  This function is the open entry point of the driver.
-  *  Return value:
-  *  0 on success and an appropriate (-)ve integer as defined in errno.h
-  *  file on failure.
-  */
--static int stmmac_open(struct net_device *dev)
-+static int __stmmac_open(struct net_device *dev,
-+                       struct stmmac_dma_conf *dma_conf)
- {
-       struct stmmac_priv *priv = netdev_priv(dev);
-       int mode = priv->plat->phy_interface;
--      int bfsize = 0;
-       u32 chan;
-       int ret;
-@@ -3725,45 +3862,10 @@ static int stmmac_open(struct net_device
-       memset(&priv->xstats, 0, sizeof(struct stmmac_extra_stats));
-       priv->xstats.threshold = tc;
--      bfsize = stmmac_set_16kib_bfsize(priv, dev->mtu);
--      if (bfsize < 0)
--              bfsize = 0;
--
--      if (bfsize < BUF_SIZE_16KiB)
--              bfsize = stmmac_set_bfsize(dev->mtu, priv->dma_conf.dma_buf_sz);
--
--      priv->dma_conf.dma_buf_sz = bfsize;
--      buf_sz = bfsize;
--
-       priv->rx_copybreak = STMMAC_RX_COPYBREAK;
--      if (!priv->dma_conf.dma_tx_size)
--              priv->dma_conf.dma_tx_size = DMA_DEFAULT_TX_SIZE;
--      if (!priv->dma_conf.dma_rx_size)
--              priv->dma_conf.dma_rx_size = DMA_DEFAULT_RX_SIZE;
--
--      /* Earlier check for TBS */
--      for (chan = 0; chan < priv->plat->tx_queues_to_use; chan++) {
--              struct stmmac_tx_queue *tx_q = &priv->dma_conf.tx_queue[chan];
--              int tbs_en = priv->plat->tx_queues_cfg[chan].tbs_en;
--
--              /* Setup per-TXQ tbs flag before TX descriptor alloc */
--              tx_q->tbs |= tbs_en ? STMMAC_TBS_AVAIL : 0;
--      }
--
--      ret = alloc_dma_desc_resources(priv);
--      if (ret < 0) {
--              netdev_err(priv->dev, "%s: DMA descriptors allocation failed\n",
--                         __func__);
--              goto dma_desc_error;
--      }
--
--      ret = init_dma_desc_rings(dev, GFP_KERNEL);
--      if (ret < 0) {
--              netdev_err(priv->dev, "%s: DMA descriptors initialization failed\n",
--                         __func__);
--              goto init_error;
--      }
-+      buf_sz = dma_conf->dma_buf_sz;
-+      memcpy(&priv->dma_conf, dma_conf, sizeof(*dma_conf));
-       if (priv->plat->serdes_powerup) {
-               ret = priv->plat->serdes_powerup(dev, priv->plat->bsp_priv);
-@@ -3806,14 +3908,28 @@ irq_error:
-       stmmac_hw_teardown(dev);
- init_error:
--      free_dma_desc_resources(priv);
--dma_desc_error:
-+      free_dma_desc_resources(priv, &priv->dma_conf);
-       phylink_disconnect_phy(priv->phylink);
- init_phy_error:
-       pm_runtime_put(priv->device);
-       return ret;
- }
-+static int stmmac_open(struct net_device *dev)
-+{
-+      struct stmmac_priv *priv = netdev_priv(dev);
-+      struct stmmac_dma_conf *dma_conf;
-+      int ret;
-+
-+      dma_conf = stmmac_setup_dma_desc(priv, dev->mtu);
-+      if (IS_ERR(dma_conf))
-+              return PTR_ERR(dma_conf);
-+
-+      ret = __stmmac_open(dev, dma_conf);
-+      kfree(dma_conf);
-+      return ret;
-+}
-+
- static void stmmac_fpe_stop_wq(struct stmmac_priv *priv)
- {
-       set_bit(__FPE_REMOVING, &priv->fpe_task_state);
-@@ -3862,7 +3978,7 @@ static int stmmac_release(struct net_dev
-       stmmac_stop_all_dma(priv);
-       /* Release and free the Rx/Tx resources */
--      free_dma_desc_resources(priv);
-+      free_dma_desc_resources(priv, &priv->dma_conf);
-       /* Disable the MAC Rx/Tx */
-       stmmac_mac_set(priv, priv->ioaddr, false);
-@@ -6385,7 +6501,7 @@ void stmmac_disable_rx_queue(struct stmm
-       spin_unlock_irqrestore(&ch->lock, flags);
-       stmmac_stop_rx_dma(priv, queue);
--      __free_dma_rx_desc_resources(priv, queue);
-+      __free_dma_rx_desc_resources(priv, &priv->dma_conf, queue);
- }
- void stmmac_enable_rx_queue(struct stmmac_priv *priv, u32 queue)
-@@ -6396,21 +6512,21 @@ void stmmac_enable_rx_queue(struct stmma
-       u32 buf_size;
-       int ret;
--      ret = __alloc_dma_rx_desc_resources(priv, queue);
-+      ret = __alloc_dma_rx_desc_resources(priv, &priv->dma_conf, queue);
-       if (ret) {
-               netdev_err(priv->dev, "Failed to alloc RX desc.\n");
-               return;
-       }
--      ret = __init_dma_rx_desc_rings(priv, queue, GFP_KERNEL);
-+      ret = __init_dma_rx_desc_rings(priv, &priv->dma_conf, queue, GFP_KERNEL);
-       if (ret) {
--              __free_dma_rx_desc_resources(priv, queue);
-+              __free_dma_rx_desc_resources(priv, &priv->dma_conf, queue);
-               netdev_err(priv->dev, "Failed to init RX desc.\n");
-               return;
-       }
-       stmmac_reset_rx_queue(priv, queue);
--      stmmac_clear_rx_descriptors(priv, queue);
-+      stmmac_clear_rx_descriptors(priv, &priv->dma_conf, queue);
-       stmmac_init_rx_chan(priv, priv->ioaddr, priv->plat->dma_cfg,
-                           rx_q->dma_rx_phy, rx_q->queue_index);
-@@ -6448,7 +6564,7 @@ void stmmac_disable_tx_queue(struct stmm
-       spin_unlock_irqrestore(&ch->lock, flags);
-       stmmac_stop_tx_dma(priv, queue);
--      __free_dma_tx_desc_resources(priv, queue);
-+      __free_dma_tx_desc_resources(priv, &priv->dma_conf, queue);
- }
- void stmmac_enable_tx_queue(struct stmmac_priv *priv, u32 queue)
-@@ -6458,21 +6574,21 @@ void stmmac_enable_tx_queue(struct stmma
-       unsigned long flags;
-       int ret;
--      ret = __alloc_dma_tx_desc_resources(priv, queue);
-+      ret = __alloc_dma_tx_desc_resources(priv, &priv->dma_conf, queue);
-       if (ret) {
-               netdev_err(priv->dev, "Failed to alloc TX desc.\n");
-               return;
-       }
--      ret = __init_dma_tx_desc_rings(priv, queue);
-+      ret = __init_dma_tx_desc_rings(priv,  &priv->dma_conf, queue);
-       if (ret) {
--              __free_dma_tx_desc_resources(priv, queue);
-+              __free_dma_tx_desc_resources(priv, &priv->dma_conf, queue);
-               netdev_err(priv->dev, "Failed to init TX desc.\n");
-               return;
-       }
-       stmmac_reset_tx_queue(priv, queue);
--      stmmac_clear_tx_descriptors(priv, queue);
-+      stmmac_clear_tx_descriptors(priv, &priv->dma_conf, queue);
-       stmmac_init_tx_chan(priv, priv->ioaddr, priv->plat->dma_cfg,
-                           tx_q->dma_tx_phy, tx_q->queue_index);
-@@ -6512,7 +6628,7 @@ void stmmac_xdp_release(struct net_devic
-       stmmac_stop_all_dma(priv);
-       /* Release and free the Rx/Tx resources */
--      free_dma_desc_resources(priv);
-+      free_dma_desc_resources(priv, &priv->dma_conf);
-       /* Disable the MAC Rx/Tx */
-       stmmac_mac_set(priv, priv->ioaddr, false);
-@@ -6537,14 +6653,14 @@ int stmmac_xdp_open(struct net_device *d
-       u32 chan;
-       int ret;
--      ret = alloc_dma_desc_resources(priv);
-+      ret = alloc_dma_desc_resources(priv, &priv->dma_conf);
-       if (ret < 0) {
-               netdev_err(dev, "%s: DMA descriptors allocation failed\n",
-                          __func__);
-               goto dma_desc_error;
-       }
--      ret = init_dma_desc_rings(dev, GFP_KERNEL);
-+      ret = init_dma_desc_rings(dev, &priv->dma_conf, GFP_KERNEL);
-       if (ret < 0) {
-               netdev_err(dev, "%s: DMA descriptors initialization failed\n",
-                          __func__);
-@@ -6626,7 +6742,7 @@ irq_error:
-       stmmac_hw_teardown(dev);
- init_error:
--      free_dma_desc_resources(priv);
-+      free_dma_desc_resources(priv, &priv->dma_conf);
- dma_desc_error:
-       return ret;
- }
-@@ -7492,7 +7608,7 @@ int stmmac_resume(struct device *dev)
-       stmmac_reset_queues_param(priv);
-       stmmac_free_tx_skbufs(priv);
--      stmmac_clear_descriptors(priv);
-+      stmmac_clear_descriptors(priv, &priv->dma_conf);
-       stmmac_hw_setup(ndev, false);
-       stmmac_init_coalesce(priv);
diff --git a/target/linux/generic/backport-5.15/775-v6.0-05-net-ethernet-stmicro-stmmac-permit-MTU-change-with-i.patch b/target/linux/generic/backport-5.15/775-v6.0-05-net-ethernet-stmicro-stmmac-permit-MTU-change-with-i.patch
deleted file mode 100644 (file)
index e1d46f0..0000000
+++ /dev/null
@@ -1,73 +0,0 @@
-From 3470079687448abac42deb62774253be1d6bdef3 Mon Sep 17 00:00:00 2001
-From: Christian Marangi <[email protected]>
-Date: Sat, 23 Jul 2022 16:29:33 +0200
-Subject: [PATCH 5/5] net: ethernet: stmicro: stmmac: permit MTU change with
- interface up
-
-Remove the limitation where the interface needs to be down to change
-MTU by releasing and opening the stmmac driver to set the new MTU.
-Also call the set_filter function to correctly init the port.
-This permits to remove the EBUSY error while the ethernet port is
-running permitting a correct MTU change if for example a DSA request
-a MTU change for a switch CPU port.
-
-Signed-off-by: Christian Marangi <[email protected]>
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- .../net/ethernet/stmicro/stmmac/stmmac_main.c | 30 +++++++++++++++----
- 1 file changed, 24 insertions(+), 6 deletions(-)
-
---- a/drivers/net/ethernet/stmicro/stmmac/stmmac_main.c
-+++ b/drivers/net/ethernet/stmicro/stmmac/stmmac_main.c
-@@ -5627,18 +5627,15 @@ static int stmmac_change_mtu(struct net_
- {
-       struct stmmac_priv *priv = netdev_priv(dev);
-       int txfifosz = priv->plat->tx_fifo_size;
-+      struct stmmac_dma_conf *dma_conf;
-       const int mtu = new_mtu;
-+      int ret;
-       if (txfifosz == 0)
-               txfifosz = priv->dma_cap.tx_fifo_size;
-       txfifosz /= priv->plat->tx_queues_to_use;
--      if (netif_running(dev)) {
--              netdev_err(priv->dev, "must be stopped to change its MTU\n");
--              return -EBUSY;
--      }
--
-       if (stmmac_xdp_is_enabled(priv) && new_mtu > ETH_DATA_LEN) {
-               netdev_dbg(priv->dev, "Jumbo frames not supported for XDP\n");
-               return -EINVAL;
-@@ -5650,8 +5647,29 @@ static int stmmac_change_mtu(struct net_
-       if ((txfifosz < new_mtu) || (new_mtu > BUF_SIZE_16KiB))
-               return -EINVAL;
--      dev->mtu = mtu;
-+      if (netif_running(dev)) {
-+              netdev_dbg(priv->dev, "restarting interface to change its MTU\n");
-+              /* Try to allocate the new DMA conf with the new mtu */
-+              dma_conf = stmmac_setup_dma_desc(priv, mtu);
-+              if (IS_ERR(dma_conf)) {
-+                      netdev_err(priv->dev, "failed allocating new dma conf for new MTU %d\n",
-+                                 mtu);
-+                      return PTR_ERR(dma_conf);
-+              }
-+
-+              stmmac_release(dev);
-+
-+              ret = __stmmac_open(dev, dma_conf);
-+              kfree(dma_conf);
-+              if (ret) {
-+                      netdev_err(priv->dev, "failed reopening the interface after MTU change\n");
-+                      return ret;
-+              }
-+
-+              stmmac_set_rx_mode(dev);
-+      }
-+      dev->mtu = mtu;
-       netdev_update_features(dev);
-       return 0;
diff --git a/target/linux/generic/backport-5.15/776-v6.1-01-net-dsa-qca8k-fix-inband-mgmt-for-big-endian-systems.patch b/target/linux/generic/backport-5.15/776-v6.1-01-net-dsa-qca8k-fix-inband-mgmt-for-big-endian-systems.patch
deleted file mode 100644 (file)
index 4f0d95f..0000000
+++ /dev/null
@@ -1,156 +0,0 @@
-From a2550d3ce53c68f54042bc5e468c4d07491ffe0e Mon Sep 17 00:00:00 2001
-From: Christian Marangi <[email protected]>
-Date: Wed, 12 Oct 2022 19:18:36 +0200
-Subject: [PATCH 1/2] net: dsa: qca8k: fix inband mgmt for big-endian systems
-
-The header and the data of the skb for the inband mgmt requires
-to be in little-endian. This is problematic for big-endian system
-as the mgmt header is written in the cpu byte order.
-
-Fix this by converting each value for the mgmt header and data to
-little-endian, and convert to cpu byte order the mgmt header and
-data sent by the switch.
-
-Fixes: 5950c7c0a68c ("net: dsa: qca8k: add support for mgmt read/write in Ethernet packet")
-Tested-by: Pawel Dembicki <[email protected]>
-Tested-by: Lech Perczak <[email protected]>
-Signed-off-by: Christian Marangi <[email protected]>
-Reviewed-by: Lech Perczak <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/dsa/qca/qca8k-8xxx.c | 63 ++++++++++++++++++++++++--------
- include/linux/dsa/tag_qca.h      |  6 +--
- 2 files changed, 50 insertions(+), 19 deletions(-)
-
---- a/drivers/net/dsa/qca/qca8k-8xxx.c
-+++ b/drivers/net/dsa/qca/qca8k-8xxx.c
-@@ -137,27 +137,42 @@ static void qca8k_rw_reg_ack_handler(str
-       struct qca8k_mgmt_eth_data *mgmt_eth_data;
-       struct qca8k_priv *priv = ds->priv;
-       struct qca_mgmt_ethhdr *mgmt_ethhdr;
-+      u32 command;
-       u8 len, cmd;
-+      int i;
-       mgmt_ethhdr = (struct qca_mgmt_ethhdr *)skb_mac_header(skb);
-       mgmt_eth_data = &priv->mgmt_eth_data;
--      cmd = FIELD_GET(QCA_HDR_MGMT_CMD, mgmt_ethhdr->command);
--      len = FIELD_GET(QCA_HDR_MGMT_LENGTH, mgmt_ethhdr->command);
-+      command = get_unaligned_le32(&mgmt_ethhdr->command);
-+      cmd = FIELD_GET(QCA_HDR_MGMT_CMD, command);
-+      len = FIELD_GET(QCA_HDR_MGMT_LENGTH, command);
-       /* Make sure the seq match the requested packet */
--      if (mgmt_ethhdr->seq == mgmt_eth_data->seq)
-+      if (get_unaligned_le32(&mgmt_ethhdr->seq) == mgmt_eth_data->seq)
-               mgmt_eth_data->ack = true;
-       if (cmd == MDIO_READ) {
--              mgmt_eth_data->data[0] = mgmt_ethhdr->mdio_data;
-+              u32 *val = mgmt_eth_data->data;
-+
-+              *val = get_unaligned_le32(&mgmt_ethhdr->mdio_data);
-               /* Get the rest of the 12 byte of data.
-                * The read/write function will extract the requested data.
-                */
--              if (len > QCA_HDR_MGMT_DATA1_LEN)
--                      memcpy(mgmt_eth_data->data + 1, skb->data,
--                             QCA_HDR_MGMT_DATA2_LEN);
-+              if (len > QCA_HDR_MGMT_DATA1_LEN) {
-+                      __le32 *data2 = (__le32 *)skb->data;
-+                      int data_len = min_t(int, QCA_HDR_MGMT_DATA2_LEN,
-+                                           len - QCA_HDR_MGMT_DATA1_LEN);
-+
-+                      val++;
-+
-+                      for (i = sizeof(u32); i <= data_len; i += sizeof(u32)) {
-+                              *val = get_unaligned_le32(data2);
-+                              val++;
-+                              data2++;
-+                      }
-+              }
-       }
-       complete(&mgmt_eth_data->rw_done);
-@@ -169,8 +184,10 @@ static struct sk_buff *qca8k_alloc_mdio_
-       struct qca_mgmt_ethhdr *mgmt_ethhdr;
-       unsigned int real_len;
-       struct sk_buff *skb;
--      u32 *data2;
-+      __le32 *data2;
-+      u32 command;
-       u16 hdr;
-+      int i;
-       skb = dev_alloc_skb(QCA_HDR_MGMT_PKT_LEN);
-       if (!skb)
-@@ -199,20 +216,32 @@ static struct sk_buff *qca8k_alloc_mdio_
-       hdr |= FIELD_PREP(QCA_HDR_XMIT_DP_BIT, BIT(0));
-       hdr |= FIELD_PREP(QCA_HDR_XMIT_CONTROL, QCA_HDR_XMIT_TYPE_RW_REG);
--      mgmt_ethhdr->command = FIELD_PREP(QCA_HDR_MGMT_ADDR, reg);
--      mgmt_ethhdr->command |= FIELD_PREP(QCA_HDR_MGMT_LENGTH, real_len);
--      mgmt_ethhdr->command |= FIELD_PREP(QCA_HDR_MGMT_CMD, cmd);
--      mgmt_ethhdr->command |= FIELD_PREP(QCA_HDR_MGMT_CHECK_CODE,
-+      command = FIELD_PREP(QCA_HDR_MGMT_ADDR, reg);
-+      command |= FIELD_PREP(QCA_HDR_MGMT_LENGTH, real_len);
-+      command |= FIELD_PREP(QCA_HDR_MGMT_CMD, cmd);
-+      command |= FIELD_PREP(QCA_HDR_MGMT_CHECK_CODE,
-                                          QCA_HDR_MGMT_CHECK_CODE_VAL);
-+      put_unaligned_le32(command, &mgmt_ethhdr->command);
-+
-       if (cmd == MDIO_WRITE)
--              mgmt_ethhdr->mdio_data = *val;
-+              put_unaligned_le32(*val, &mgmt_ethhdr->mdio_data);
-       mgmt_ethhdr->hdr = htons(hdr);
-       data2 = skb_put_zero(skb, QCA_HDR_MGMT_DATA2_LEN + QCA_HDR_MGMT_PADDING_LEN);
--      if (cmd == MDIO_WRITE && len > QCA_HDR_MGMT_DATA1_LEN)
--              memcpy(data2, val + 1, len - QCA_HDR_MGMT_DATA1_LEN);
-+      if (cmd == MDIO_WRITE && len > QCA_HDR_MGMT_DATA1_LEN) {
-+              int data_len = min_t(int, QCA_HDR_MGMT_DATA2_LEN,
-+                                   len - QCA_HDR_MGMT_DATA1_LEN);
-+
-+              val++;
-+
-+              for (i = sizeof(u32); i <= data_len; i += sizeof(u32)) {
-+                      put_unaligned_le32(*val, data2);
-+                      data2++;
-+                      val++;
-+              }
-+      }
-       return skb;
- }
-@@ -220,9 +249,11 @@ static struct sk_buff *qca8k_alloc_mdio_
- static void qca8k_mdio_header_fill_seq_num(struct sk_buff *skb, u32 seq_num)
- {
-       struct qca_mgmt_ethhdr *mgmt_ethhdr;
-+      u32 seq;
-+      seq = FIELD_PREP(QCA_HDR_MGMT_SEQ_NUM, seq_num);
-       mgmt_ethhdr = (struct qca_mgmt_ethhdr *)skb->data;
--      mgmt_ethhdr->seq = FIELD_PREP(QCA_HDR_MGMT_SEQ_NUM, seq_num);
-+      put_unaligned_le32(seq, &mgmt_ethhdr->seq);
- }
- static int qca8k_read_eth(struct qca8k_priv *priv, u32 reg, u32 *val, int len)
---- a/include/linux/dsa/tag_qca.h
-+++ b/include/linux/dsa/tag_qca.h
-@@ -56,9 +56,9 @@
- /* Special struct emulating a Ethernet header */
- struct qca_mgmt_ethhdr {
--      u32 command;            /* command bit 31:0 */
--      u32 seq;                /* seq 63:32 */
--      u32 mdio_data;          /* first 4byte mdio */
-+      __le32 command;         /* command bit 31:0 */
-+      __le32 seq;             /* seq 63:32 */
-+      __le32 mdio_data;               /* first 4byte mdio */
-       __be16 hdr;             /* qca hdr */
- } __packed;
diff --git a/target/linux/generic/backport-5.15/776-v6.1-02-net-dsa-qca8k-fix-ethtool-autocast-mib-for-big-endia.patch b/target/linux/generic/backport-5.15/776-v6.1-02-net-dsa-qca8k-fix-ethtool-autocast-mib-for-big-endia.patch
deleted file mode 100644 (file)
index d13014b..0000000
+++ /dev/null
@@ -1,81 +0,0 @@
-From 0d4636f7d72df3179b20a2d32b647881917a5e2a Mon Sep 17 00:00:00 2001
-From: Christian Marangi <[email protected]>
-Date: Wed, 12 Oct 2022 19:18:37 +0200
-Subject: [PATCH 2/2] net: dsa: qca8k: fix ethtool autocast mib for big-endian
- systems
-
-The switch sends autocast mib in little-endian. This is problematic for
-big-endian system as the values needs to be converted.
-
-Fix this by converting each mib value to cpu byte order.
-
-Fixes: 5c957c7ca78c ("net: dsa: qca8k: add support for mib autocast in Ethernet packet")
-Tested-by: Pawel Dembicki <[email protected]>
-Tested-by: Lech Perczak <[email protected]>
-Signed-off-by: Christian Marangi <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/dsa/qca/qca8k-8xxx.c | 20 ++++++++------------
- include/linux/dsa/tag_qca.h      |  2 +-
- 2 files changed, 9 insertions(+), 13 deletions(-)
-
---- a/drivers/net/dsa/qca/qca8k-8xxx.c
-+++ b/drivers/net/dsa/qca/qca8k-8xxx.c
-@@ -1668,9 +1668,9 @@ static void qca8k_mib_autocast_handler(s
-       struct qca8k_priv *priv = ds->priv;
-       const struct qca8k_mib_desc *mib;
-       struct mib_ethhdr *mib_ethhdr;
--      int i, mib_len, offset = 0;
--      u64 *data;
-+      __le32 *data2;
-       u8 port;
-+      int i;
-       mib_ethhdr = (struct mib_ethhdr *)skb_mac_header(skb);
-       mib_eth_data = &priv->mib_eth_data;
-@@ -1682,28 +1682,24 @@ static void qca8k_mib_autocast_handler(s
-       if (port != mib_eth_data->req_port)
-               goto exit;
--      data = mib_eth_data->data;
-+      data2 = (__le32 *)skb->data;
-       for (i = 0; i < priv->info->mib_count; i++) {
-               mib = &ar8327_mib[i];
-               /* First 3 mib are present in the skb head */
-               if (i < 3) {
--                      data[i] = mib_ethhdr->data[i];
-+                      mib_eth_data->data[i] = get_unaligned_le32(mib_ethhdr->data + i);
-                       continue;
-               }
--              mib_len = sizeof(uint32_t);
--
-               /* Some mib are 64 bit wide */
-               if (mib->size == 2)
--                      mib_len = sizeof(uint64_t);
--
--              /* Copy the mib value from packet to the */
--              memcpy(data + i, skb->data + offset, mib_len);
-+                      mib_eth_data->data[i] = get_unaligned_le64((__le64 *)data2);
-+              else
-+                      mib_eth_data->data[i] = get_unaligned_le32(data2);
--              /* Set the offset for the next mib */
--              offset += mib_len;
-+              data2 += mib->size;
-       }
- exit:
---- a/include/linux/dsa/tag_qca.h
-+++ b/include/linux/dsa/tag_qca.h
-@@ -68,7 +68,7 @@ enum mdio_cmd {
- };
- struct mib_ethhdr {
--      u32 data[3];            /* first 3 mib counter */
-+      __le32 data[3];         /* first 3 mib counter */
-       __be16 hdr;             /* qca hdr */
- } __packed;
diff --git a/target/linux/generic/backport-5.15/777-v6.2-01-net-dsa-qca8k-fix-wrong-length-value-for-mgmt-eth-pa.patch b/target/linux/generic/backport-5.15/777-v6.2-01-net-dsa-qca8k-fix-wrong-length-value-for-mgmt-eth-pa.patch
deleted file mode 100644 (file)
index b61e7ed..0000000
+++ /dev/null
@@ -1,102 +0,0 @@
-From 9807ae69746196ee4bbffe7d22d22ab2b61c6ed0 Mon Sep 17 00:00:00 2001
-From: Christian Marangi <[email protected]>
-Date: Thu, 29 Dec 2022 17:33:32 +0100
-Subject: [PATCH 1/5] net: dsa: qca8k: fix wrong length value for mgmt eth
- packet
-
-The assumption that Documentation was right about how this value work was
-wrong. It was discovered that the length value of the mgmt header is in
-step of word size.
-
-As an example to process 4 byte of data the correct length to set is 2.
-To process 8 byte 4, 12 byte 6, 16 byte 8...
-
-Odd values will always return the next size on the ack packet.
-(length of 3 (6 byte) will always return 8 bytes of data)
-
-This means that a value of 15 (0xf) actually means reading/writing 32 bytes
-of data instead of 16 bytes. This behaviour is totally absent and not
-documented in the switch Documentation.
-
-In fact from Documentation the max value that mgmt eth can process is
-16 byte of data while in reality it can process 32 bytes at once.
-
-To handle this we always round up the length after deviding it for word
-size. We check if the result is odd and we round another time to align
-to what the switch will provide in the ack packet.
-The workaround for the length limit of 15 is still needed as the length
-reg max value is 0xf(15)
-
-Reported-by: Ronald Wahl <[email protected]>
-Tested-by: Ronald Wahl <[email protected]>
-Fixes: 90386223f44e ("net: dsa: qca8k: add support for larger read/write size with mgmt Ethernet")
-Signed-off-by: Christian Marangi <[email protected]>
-Cc: [email protected] # v5.18+
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/dsa/qca/qca8k-8xxx.c | 45 +++++++++++++++++++++++++-------
- 1 file changed, 35 insertions(+), 10 deletions(-)
-
---- a/drivers/net/dsa/qca/qca8k-8xxx.c
-+++ b/drivers/net/dsa/qca/qca8k-8xxx.c
-@@ -146,7 +146,16 @@ static void qca8k_rw_reg_ack_handler(str
-       command = get_unaligned_le32(&mgmt_ethhdr->command);
-       cmd = FIELD_GET(QCA_HDR_MGMT_CMD, command);
-+
-       len = FIELD_GET(QCA_HDR_MGMT_LENGTH, command);
-+      /* Special case for len of 15 as this is the max value for len and needs to
-+       * be increased before converting it from word to dword.
-+       */
-+      if (len == 15)
-+              len++;
-+
-+      /* We can ignore odd value, we always round up them in the alloc function. */
-+      len *= sizeof(u16);
-       /* Make sure the seq match the requested packet */
-       if (get_unaligned_le32(&mgmt_ethhdr->seq) == mgmt_eth_data->seq)
-@@ -193,17 +202,33 @@ static struct sk_buff *qca8k_alloc_mdio_
-       if (!skb)
-               return NULL;
--      /* Max value for len reg is 15 (0xf) but the switch actually return 16 byte
--       * Actually for some reason the steps are:
--       * 0: nothing
--       * 1-4: first 4 byte
--       * 5-6: first 12 byte
--       * 7-15: all 16 byte
-+      /* Hdr mgmt length value is in step of word size.
-+       * As an example to process 4 byte of data the correct length to set is 2.
-+       * To process 8 byte 4, 12 byte 6, 16 byte 8...
-+       *
-+       * Odd values will always return the next size on the ack packet.
-+       * (length of 3 (6 byte) will always return 8 bytes of data)
-+       *
-+       * This means that a value of 15 (0xf) actually means reading/writing 32 bytes
-+       * of data.
-+       *
-+       * To correctly calculate the length we devide the requested len by word and
-+       * round up.
-+       * On the ack function we can skip the odd check as we already handle the
-+       * case here.
-        */
--      if (len == 16)
--              real_len = 15;
--      else
--              real_len = len;
-+      real_len = DIV_ROUND_UP(len, sizeof(u16));
-+
-+      /* We check if the result len is odd and we round up another time to
-+       * the next size. (length of 3 will be increased to 4 as switch will always
-+       * return 8 bytes)
-+       */
-+      if (real_len % sizeof(u16) != 0)
-+              real_len++;
-+
-+      /* Max reg value is 0xf(15) but switch will always return the next size (32 byte) */
-+      if (real_len == 16)
-+              real_len--;
-       skb_reset_mac_header(skb);
-       skb_set_network_header(skb, skb->len);
diff --git a/target/linux/generic/backport-5.15/777-v6.2-02-net-dsa-tag_qca-fix-wrong-MGMT_DATA2-size.patch b/target/linux/generic/backport-5.15/777-v6.2-02-net-dsa-tag_qca-fix-wrong-MGMT_DATA2-size.patch
deleted file mode 100644 (file)
index 55ecb1e..0000000
+++ /dev/null
@@ -1,34 +0,0 @@
-From d9dba91be71f03cc75bcf39fc0d5d99ff33f1ae0 Mon Sep 17 00:00:00 2001
-From: Christian Marangi <[email protected]>
-Date: Thu, 29 Dec 2022 17:33:33 +0100
-Subject: [PATCH 2/5] net: dsa: tag_qca: fix wrong MGMT_DATA2 size
-
-It was discovered that MGMT_DATA2 can contain up to 28 bytes of data
-instead of the 12 bytes written in the Documentation by accounting the
-limit of 16 bytes declared in Documentation subtracting the first 4 byte
-in the packet header.
-
-Update the define with the real world value.
-
-Tested-by: Ronald Wahl <[email protected]>
-Fixes: c2ee8181fddb ("net: dsa: tag_qca: add define for handling mgmt Ethernet packet")
-Signed-off-by: Christian Marangi <[email protected]>
-Cc: [email protected] # v5.18+
-Signed-off-by: David S. Miller <[email protected]>
----
- include/linux/dsa/tag_qca.h | 4 ++--
- 1 file changed, 2 insertions(+), 2 deletions(-)
-
---- a/include/linux/dsa/tag_qca.h
-+++ b/include/linux/dsa/tag_qca.h
-@@ -40,8 +40,8 @@
-                                       QCA_HDR_MGMT_COMMAND_LEN + \
-                                       QCA_HDR_MGMT_DATA1_LEN)
--#define QCA_HDR_MGMT_DATA2_LEN                12 /* Other 12 byte for the mdio data */
--#define QCA_HDR_MGMT_PADDING_LEN      34 /* Padding to reach the min Ethernet packet */
-+#define QCA_HDR_MGMT_DATA2_LEN                28 /* Other 28 byte for the mdio data */
-+#define QCA_HDR_MGMT_PADDING_LEN      18 /* Padding to reach the min Ethernet packet */
- #define QCA_HDR_MGMT_PKT_LEN          (QCA_HDR_MGMT_HEADER_LEN + \
-                                       QCA_HDR_LEN + \
diff --git a/target/linux/generic/backport-5.15/777-v6.2-03-Revert-net-dsa-qca8k-cache-lo-and-hi-for-mdio-write.patch b/target/linux/generic/backport-5.15/777-v6.2-03-Revert-net-dsa-qca8k-cache-lo-and-hi-for-mdio-write.patch
deleted file mode 100644 (file)
index c8e22fd..0000000
+++ /dev/null
@@ -1,172 +0,0 @@
-From 03cb9e6d0b32b768e3d9d473c5c4ca1100877664 Mon Sep 17 00:00:00 2001
-From: Christian Marangi <[email protected]>
-Date: Thu, 29 Dec 2022 17:33:34 +0100
-Subject: [PATCH 3/5] Revert "net: dsa: qca8k: cache lo and hi for mdio write"
-
-This reverts commit 2481d206fae7884cd07014fd1318e63af35e99eb.
-
-The Documentation is very confusing about the topic.
-The cache logic for hi and lo is wrong and actually miss some regs to be
-actually written.
-
-What the Documentation actually intended was that it's possible to skip
-writing hi OR lo if half of the reg is not needed to be written or read.
-
-Revert the change in favor of a better and correct implementation.
-
-Reported-by: Ronald Wahl <[email protected]>
-Signed-off-by: Christian Marangi <[email protected]>
-Cc: [email protected] # v5.18+
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/dsa/qca/qca8k-8xxx.c | 61 +++++++-------------------------
- drivers/net/dsa/qca/qca8k.h      |  5 ---
- 2 files changed, 12 insertions(+), 54 deletions(-)
-
---- a/drivers/net/dsa/qca/qca8k-8xxx.c
-+++ b/drivers/net/dsa/qca/qca8k-8xxx.c
-@@ -37,44 +37,6 @@ qca8k_split_addr(u32 regaddr, u16 *r1, u
- }
- static int
--qca8k_set_lo(struct qca8k_priv *priv, int phy_id, u32 regnum, u16 lo)
--{
--      u16 *cached_lo = &priv->mdio_cache.lo;
--      struct mii_bus *bus = priv->bus;
--      int ret;
--
--      if (lo == *cached_lo)
--              return 0;
--
--      ret = bus->write(bus, phy_id, regnum, lo);
--      if (ret < 0)
--              dev_err_ratelimited(&bus->dev,
--                                  "failed to write qca8k 32bit lo register\n");
--
--      *cached_lo = lo;
--      return 0;
--}
--
--static int
--qca8k_set_hi(struct qca8k_priv *priv, int phy_id, u32 regnum, u16 hi)
--{
--      u16 *cached_hi = &priv->mdio_cache.hi;
--      struct mii_bus *bus = priv->bus;
--      int ret;
--
--      if (hi == *cached_hi)
--              return 0;
--
--      ret = bus->write(bus, phy_id, regnum, hi);
--      if (ret < 0)
--              dev_err_ratelimited(&bus->dev,
--                                  "failed to write qca8k 32bit hi register\n");
--
--      *cached_hi = hi;
--      return 0;
--}
--
--static int
- qca8k_mii_read32(struct mii_bus *bus, int phy_id, u32 regnum, u32 *val)
- {
-       int ret;
-@@ -97,7 +59,7 @@ qca8k_mii_read32(struct mii_bus *bus, in
- }
- static void
--qca8k_mii_write32(struct qca8k_priv *priv, int phy_id, u32 regnum, u32 val)
-+qca8k_mii_write32(struct mii_bus *bus, int phy_id, u32 regnum, u32 val)
- {
-       u16 lo, hi;
-       int ret;
-@@ -105,9 +67,12 @@ qca8k_mii_write32(struct qca8k_priv *pri
-       lo = val & 0xffff;
-       hi = (u16)(val >> 16);
--      ret = qca8k_set_lo(priv, phy_id, regnum, lo);
-+      ret = bus->write(bus, phy_id, regnum, lo);
-       if (ret >= 0)
--              ret = qca8k_set_hi(priv, phy_id, regnum + 1, hi);
-+              ret = bus->write(bus, phy_id, regnum + 1, hi);
-+      if (ret < 0)
-+              dev_err_ratelimited(&bus->dev,
-+                                  "failed to write qca8k 32bit register\n");
- }
- static int
-@@ -442,7 +407,7 @@ qca8k_regmap_write(void *ctx, uint32_t r
-       if (ret < 0)
-               goto exit;
--      qca8k_mii_write32(priv, 0x10 | r2, r1, val);
-+      qca8k_mii_write32(bus, 0x10 | r2, r1, val);
- exit:
-       mutex_unlock(&bus->mdio_lock);
-@@ -475,7 +440,7 @@ qca8k_regmap_update_bits(void *ctx, uint
-       val &= ~mask;
-       val |= write_val;
--      qca8k_mii_write32(priv, 0x10 | r2, r1, val);
-+      qca8k_mii_write32(bus, 0x10 | r2, r1, val);
- exit:
-       mutex_unlock(&bus->mdio_lock);
-@@ -750,14 +715,14 @@ qca8k_mdio_write(struct qca8k_priv *priv
-       if (ret)
-               goto exit;
--      qca8k_mii_write32(priv, 0x10 | r2, r1, val);
-+      qca8k_mii_write32(bus, 0x10 | r2, r1, val);
-       ret = qca8k_mdio_busy_wait(bus, QCA8K_MDIO_MASTER_CTRL,
-                                  QCA8K_MDIO_MASTER_BUSY);
- exit:
-       /* even if the busy_wait timeouts try to clear the MASTER_EN */
--      qca8k_mii_write32(priv, 0x10 | r2, r1, 0);
-+      qca8k_mii_write32(bus, 0x10 | r2, r1, 0);
-       mutex_unlock(&bus->mdio_lock);
-@@ -787,7 +752,7 @@ qca8k_mdio_read(struct qca8k_priv *priv,
-       if (ret)
-               goto exit;
--      qca8k_mii_write32(priv, 0x10 | r2, r1, val);
-+      qca8k_mii_write32(bus, 0x10 | r2, r1, val);
-       ret = qca8k_mdio_busy_wait(bus, QCA8K_MDIO_MASTER_CTRL,
-                                  QCA8K_MDIO_MASTER_BUSY);
-@@ -798,7 +763,7 @@ qca8k_mdio_read(struct qca8k_priv *priv,
- exit:
-       /* even if the busy_wait timeouts try to clear the MASTER_EN */
--      qca8k_mii_write32(priv, 0x10 | r2, r1, 0);
-+      qca8k_mii_write32(bus, 0x10 | r2, r1, 0);
-       mutex_unlock(&bus->mdio_lock);
-@@ -1914,8 +1879,6 @@ qca8k_sw_probe(struct mdio_device *mdiod
-       }
-       priv->mdio_cache.page = 0xffff;
--      priv->mdio_cache.lo = 0xffff;
--      priv->mdio_cache.hi = 0xffff;
-       /* Check the detected switch id */
-       ret = qca8k_read_switch_id(priv);
---- a/drivers/net/dsa/qca/qca8k.h
-+++ b/drivers/net/dsa/qca/qca8k.h
-@@ -375,11 +375,6 @@ struct qca8k_mdio_cache {
-  * mdio writes
-  */
-       u16 page;
--/* lo and hi can also be cached and from Documentation we can skip one
-- * extra mdio write if lo or hi is didn't change.
-- */
--      u16 lo;
--      u16 hi;
- };
- struct qca8k_priv {
diff --git a/target/linux/generic/backport-5.15/777-v6.2-04-net-dsa-qca8k-introduce-single-mii-read-write-lo-hi.patch b/target/linux/generic/backport-5.15/777-v6.2-04-net-dsa-qca8k-introduce-single-mii-read-write-lo-hi.patch
deleted file mode 100644 (file)
index c0320ad..0000000
+++ /dev/null
@@ -1,150 +0,0 @@
-From cfbd6de588ef659c198083205dc954a6d3ed2aec Mon Sep 17 00:00:00 2001
-From: Christian Marangi <[email protected]>
-Date: Thu, 29 Dec 2022 17:33:35 +0100
-Subject: [PATCH 4/5] net: dsa: qca8k: introduce single mii read/write lo/hi
-
-It may be useful to read/write just the lo or hi half of a reg.
-
-This is especially useful for phy poll with the use of mdio master.
-The mdio master reg is composed by the first 16 bit related to setup and
-the other half with the returned data or data to write.
-
-Refactor the mii function to permit single mii read/write of lo or hi
-half of the reg.
-
-Tested-by: Ronald Wahl <[email protected]>
-Signed-off-by: Christian Marangi <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/dsa/qca/qca8k-8xxx.c | 106 ++++++++++++++++++++++++-------
- 1 file changed, 84 insertions(+), 22 deletions(-)
-
---- a/drivers/net/dsa/qca/qca8k-8xxx.c
-+++ b/drivers/net/dsa/qca/qca8k-8xxx.c
-@@ -37,42 +37,104 @@ qca8k_split_addr(u32 regaddr, u16 *r1, u
- }
- static int
--qca8k_mii_read32(struct mii_bus *bus, int phy_id, u32 regnum, u32 *val)
-+qca8k_mii_write_lo(struct mii_bus *bus, int phy_id, u32 regnum, u32 val)
- {
-       int ret;
-+      u16 lo;
--      ret = bus->read(bus, phy_id, regnum);
--      if (ret >= 0) {
--              *val = ret;
--              ret = bus->read(bus, phy_id, regnum + 1);
--              *val |= ret << 16;
--      }
-+      lo = val & 0xffff;
-+      ret = bus->write(bus, phy_id, regnum, lo);
-+      if (ret < 0)
-+              dev_err_ratelimited(&bus->dev,
-+                                  "failed to write qca8k 32bit lo register\n");
-+
-+      return ret;
-+}
--      if (ret < 0) {
-+static int
-+qca8k_mii_write_hi(struct mii_bus *bus, int phy_id, u32 regnum, u32 val)
-+{
-+      int ret;
-+      u16 hi;
-+
-+      hi = (u16)(val >> 16);
-+      ret = bus->write(bus, phy_id, regnum, hi);
-+      if (ret < 0)
-               dev_err_ratelimited(&bus->dev,
--                                  "failed to read qca8k 32bit register\n");
--              *val = 0;
--              return ret;
--      }
-+                                  "failed to write qca8k 32bit hi register\n");
-+      return ret;
-+}
-+
-+static int
-+qca8k_mii_read_lo(struct mii_bus *bus, int phy_id, u32 regnum, u32 *val)
-+{
-+      int ret;
-+
-+      ret = bus->read(bus, phy_id, regnum);
-+      if (ret < 0)
-+              goto err;
-+
-+      *val = ret & 0xffff;
-       return 0;
-+
-+err:
-+      dev_err_ratelimited(&bus->dev,
-+                          "failed to read qca8k 32bit lo register\n");
-+      *val = 0;
-+
-+      return ret;
- }
--static void
--qca8k_mii_write32(struct mii_bus *bus, int phy_id, u32 regnum, u32 val)
-+static int
-+qca8k_mii_read_hi(struct mii_bus *bus, int phy_id, u32 regnum, u32 *val)
- {
--      u16 lo, hi;
-       int ret;
--      lo = val & 0xffff;
--      hi = (u16)(val >> 16);
-+      ret = bus->read(bus, phy_id, regnum);
-+      if (ret < 0)
-+              goto err;
--      ret = bus->write(bus, phy_id, regnum, lo);
--      if (ret >= 0)
--              ret = bus->write(bus, phy_id, regnum + 1, hi);
-+      *val = ret << 16;
-+      return 0;
-+
-+err:
-+      dev_err_ratelimited(&bus->dev,
-+                          "failed to read qca8k 32bit hi register\n");
-+      *val = 0;
-+
-+      return ret;
-+}
-+
-+static int
-+qca8k_mii_read32(struct mii_bus *bus, int phy_id, u32 regnum, u32 *val)
-+{
-+      u32 hi, lo;
-+      int ret;
-+
-+      *val = 0;
-+
-+      ret = qca8k_mii_read_lo(bus, phy_id, regnum, &lo);
-       if (ret < 0)
--              dev_err_ratelimited(&bus->dev,
--                                  "failed to write qca8k 32bit register\n");
-+              goto err;
-+
-+      ret = qca8k_mii_read_hi(bus, phy_id, regnum + 1, &hi);
-+      if (ret < 0)
-+              goto err;
-+
-+      *val = lo | hi;
-+
-+err:
-+      return ret;
-+}
-+
-+static void
-+qca8k_mii_write32(struct mii_bus *bus, int phy_id, u32 regnum, u32 val)
-+{
-+      if (qca8k_mii_write_lo(bus, phy_id, regnum, val) < 0)
-+              return;
-+
-+      qca8k_mii_write_hi(bus, phy_id, regnum + 1, val);
- }
- static int
diff --git a/target/linux/generic/backport-5.15/777-v6.2-05-net-dsa-qca8k-improve-mdio-master-read-write-by-usin.patch b/target/linux/generic/backport-5.15/777-v6.2-05-net-dsa-qca8k-improve-mdio-master-read-write-by-usin.patch
deleted file mode 100644 (file)
index 4cbb66c..0000000
+++ /dev/null
@@ -1,73 +0,0 @@
-From a4165830ca237f2b3318faf62562bce8ce12a389 Mon Sep 17 00:00:00 2001
-From: Christian Marangi <[email protected]>
-Date: Thu, 29 Dec 2022 17:33:36 +0100
-Subject: [PATCH 5/5] net: dsa: qca8k: improve mdio master read/write by using
- single lo/hi
-
-Improve mdio master read/write by using singe mii read/write lo/hi.
-
-In a read and write we need to poll the mdio master regs in a busy loop
-to check for a specific bit present in the upper half of the reg. We can
-ignore the other half since it won't contain useful data. This will save
-an additional useless read for each read and write operation.
-
-In a read operation the returned data is present in the mdio master reg
-lower half. We can ignore the other half since it won't contain useful
-data. This will save an additional useless read for each read operation.
-
-In a read operation it's needed to just set the hi half of the mdio
-master reg as the lo half will be replaced by the result. This will save
-an additional useless write for each read operation.
-
-Tested-by: Ronald Wahl <[email protected]>
-Signed-off-by: Christian Marangi <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/dsa/qca/qca8k-8xxx.c | 12 ++++++------
- 1 file changed, 6 insertions(+), 6 deletions(-)
-
---- a/drivers/net/dsa/qca/qca8k-8xxx.c
-+++ b/drivers/net/dsa/qca/qca8k-8xxx.c
-@@ -740,9 +740,9 @@ qca8k_mdio_busy_wait(struct mii_bus *bus
-       qca8k_split_addr(reg, &r1, &r2, &page);
--      ret = read_poll_timeout(qca8k_mii_read32, ret1, !(val & mask), 0,
-+      ret = read_poll_timeout(qca8k_mii_read_hi, ret1, !(val & mask), 0,
-                               QCA8K_BUSY_WAIT_TIMEOUT * USEC_PER_MSEC, false,
--                              bus, 0x10 | r2, r1, &val);
-+                              bus, 0x10 | r2, r1 + 1, &val);
-       /* Check if qca8k_read has failed for a different reason
-        * before returnting -ETIMEDOUT
-@@ -784,7 +784,7 @@ qca8k_mdio_write(struct qca8k_priv *priv
- exit:
-       /* even if the busy_wait timeouts try to clear the MASTER_EN */
--      qca8k_mii_write32(bus, 0x10 | r2, r1, 0);
-+      qca8k_mii_write_hi(bus, 0x10 | r2, r1 + 1, 0);
-       mutex_unlock(&bus->mdio_lock);
-@@ -814,18 +814,18 @@ qca8k_mdio_read(struct qca8k_priv *priv,
-       if (ret)
-               goto exit;
--      qca8k_mii_write32(bus, 0x10 | r2, r1, val);
-+      qca8k_mii_write_hi(bus, 0x10 | r2, r1 + 1, val);
-       ret = qca8k_mdio_busy_wait(bus, QCA8K_MDIO_MASTER_CTRL,
-                                  QCA8K_MDIO_MASTER_BUSY);
-       if (ret)
-               goto exit;
--      ret = qca8k_mii_read32(bus, 0x10 | r2, r1, &val);
-+      ret = qca8k_mii_read_lo(bus, 0x10 | r2, r1, &val);
- exit:
-       /* even if the busy_wait timeouts try to clear the MASTER_EN */
--      qca8k_mii_write32(bus, 0x10 | r2, r1, 0);
-+      qca8k_mii_write_hi(bus, 0x10 | r2, r1 + 1, 0);
-       mutex_unlock(&bus->mdio_lock);
diff --git a/target/linux/generic/backport-5.15/778-v5.18-01-net-phy-at803x-add-fiber-support.patch b/target/linux/generic/backport-5.15/778-v5.18-01-net-phy-at803x-add-fiber-support.patch
deleted file mode 100644 (file)
index 7cb21ed..0000000
+++ /dev/null
@@ -1,193 +0,0 @@
-From 3265f421887847db9ae2c01a00645e33608556d8 Mon Sep 17 00:00:00 2001
-From: Robert Hancock <[email protected]>
-Date: Tue, 25 Jan 2022 10:54:09 -0600
-Subject: [PATCH] net: phy: at803x: add fiber support
-
-Previously this driver always forced the copper page to be selected,
-however for AR8031 in 100Base-FX or 1000Base-X modes, the fiber page
-needs to be selected. Set the appropriate mode based on the hardware
-mode_cfg strap selection.
-
-Enable the appropriate interrupt bits to detect fiber-side link up
-or down events.
-
-Update config_aneg and read_status methods to use the appropriate
-Clause 37 calls when fiber mode is in use.
-
-Signed-off-by: Robert Hancock <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/phy/at803x.c | 76 +++++++++++++++++++++++++++++++++++-----
- 1 file changed, 67 insertions(+), 9 deletions(-)
-
---- a/drivers/net/phy/at803x.c
-+++ b/drivers/net/phy/at803x.c
-@@ -48,6 +48,8 @@
- #define AT803X_INTR_ENABLE_PAGE_RECEIVED      BIT(12)
- #define AT803X_INTR_ENABLE_LINK_FAIL          BIT(11)
- #define AT803X_INTR_ENABLE_LINK_SUCCESS               BIT(10)
-+#define AT803X_INTR_ENABLE_LINK_FAIL_BX               BIT(8)
-+#define AT803X_INTR_ENABLE_LINK_SUCCESS_BX    BIT(7)
- #define AT803X_INTR_ENABLE_WIRESPEED_DOWNGRADE        BIT(5)
- #define AT803X_INTR_ENABLE_POLARITY_CHANGED   BIT(1)
- #define AT803X_INTR_ENABLE_WOL                        BIT(0)
-@@ -82,6 +84,17 @@
- #define AT803X_MODE_CFG_MASK                  0x0F
- #define AT803X_MODE_CFG_SGMII                 0x01
-+#define AT803X_MODE_CFG_BASET_RGMII           0x00
-+#define AT803X_MODE_CFG_BASET_SGMII           0x01
-+#define AT803X_MODE_CFG_BX1000_RGMII_50OHM    0x02
-+#define AT803X_MODE_CFG_BX1000_RGMII_75OHM    0x03
-+#define AT803X_MODE_CFG_BX1000_CONV_50OHM     0x04
-+#define AT803X_MODE_CFG_BX1000_CONV_75OHM     0x05
-+#define AT803X_MODE_CFG_FX100_RGMII_50OHM     0x06
-+#define AT803X_MODE_CFG_FX100_CONV_50OHM      0x07
-+#define AT803X_MODE_CFG_RGMII_AUTO_MDET               0x0B
-+#define AT803X_MODE_CFG_FX100_RGMII_75OHM     0x0E
-+#define AT803X_MODE_CFG_FX100_CONV_75OHM      0x0F
- #define AT803X_PSSR                           0x11    /*PHY-Specific Status Register*/
- #define AT803X_PSSR_MR_AN_COMPLETE            0x0200
-@@ -199,6 +212,8 @@ struct at803x_priv {
-       u16 clk_25m_mask;
-       u8 smarteee_lpi_tw_1g;
-       u8 smarteee_lpi_tw_100m;
-+      bool is_fiber;
-+      bool is_1000basex;
-       struct regulator_dev *vddio_rdev;
-       struct regulator_dev *vddh_rdev;
-       struct regulator *vddio;
-@@ -674,7 +689,33 @@ static int at803x_probe(struct phy_devic
-                       return ret;
-       }
-+      if (phydev->drv->phy_id == ATH8031_PHY_ID) {
-+              int ccr = phy_read(phydev, AT803X_REG_CHIP_CONFIG);
-+              int mode_cfg;
-+
-+              if (ccr < 0)
-+                      goto err;
-+              mode_cfg = ccr & AT803X_MODE_CFG_MASK;
-+
-+              switch (mode_cfg) {
-+              case AT803X_MODE_CFG_BX1000_RGMII_50OHM:
-+              case AT803X_MODE_CFG_BX1000_RGMII_75OHM:
-+                      priv->is_1000basex = true;
-+                      fallthrough;
-+              case AT803X_MODE_CFG_FX100_RGMII_50OHM:
-+              case AT803X_MODE_CFG_FX100_RGMII_75OHM:
-+                      priv->is_fiber = true;
-+                      break;
-+              }
-+      }
-+
-       return 0;
-+
-+err:
-+      if (priv->vddio)
-+              regulator_disable(priv->vddio);
-+
-+      return ret;
- }
- static void at803x_remove(struct phy_device *phydev)
-@@ -687,6 +728,7 @@ static void at803x_remove(struct phy_dev
- static int at803x_get_features(struct phy_device *phydev)
- {
-+      struct at803x_priv *priv = phydev->priv;
-       int err;
-       err = genphy_read_abilities(phydev);
-@@ -704,12 +746,13 @@ static int at803x_get_features(struct ph
-        * As a result of that, ESTATUS_1000_XFULL is set
-        * to 1 even when operating in copper TP mode.
-        *
--       * Remove this mode from the supported link modes,
--       * as this driver currently only supports copper
--       * operation.
-+       * Remove this mode from the supported link modes
-+       * when not operating in 1000BaseX mode.
-        */
--      linkmode_clear_bit(ETHTOOL_LINK_MODE_1000baseX_Full_BIT,
--                         phydev->supported);
-+      if (!priv->is_1000basex)
-+              linkmode_clear_bit(ETHTOOL_LINK_MODE_1000baseX_Full_BIT,
-+                                 phydev->supported);
-+
-       return 0;
- }
-@@ -773,15 +816,18 @@ static int at8031_pll_config(struct phy_
- static int at803x_config_init(struct phy_device *phydev)
- {
-+      struct at803x_priv *priv = phydev->priv;
-       int ret;
-       if (phydev->drv->phy_id == ATH8031_PHY_ID) {
-               /* Some bootloaders leave the fiber page selected.
--               * Switch to the copper page, as otherwise we read
--               * the PHY capabilities from the fiber side.
-+               * Switch to the appropriate page (fiber or copper), as otherwise we
-+               * read the PHY capabilities from the wrong page.
-                */
-               phy_lock_mdio_bus(phydev);
--              ret = at803x_write_page(phydev, AT803X_PAGE_COPPER);
-+              ret = at803x_write_page(phydev,
-+                                      priv->is_fiber ? AT803X_PAGE_FIBER :
-+                                                       AT803X_PAGE_COPPER);
-               phy_unlock_mdio_bus(phydev);
-               if (ret)
-                       return ret;
-@@ -840,6 +886,7 @@ static int at803x_ack_interrupt(struct p
- static int at803x_config_intr(struct phy_device *phydev)
- {
-+      struct at803x_priv *priv = phydev->priv;
-       int err;
-       int value;
-@@ -856,6 +903,10 @@ static int at803x_config_intr(struct phy
-               value |= AT803X_INTR_ENABLE_DUPLEX_CHANGED;
-               value |= AT803X_INTR_ENABLE_LINK_FAIL;
-               value |= AT803X_INTR_ENABLE_LINK_SUCCESS;
-+              if (priv->is_fiber) {
-+                      value |= AT803X_INTR_ENABLE_LINK_FAIL_BX;
-+                      value |= AT803X_INTR_ENABLE_LINK_SUCCESS_BX;
-+              }
-               err = phy_write(phydev, AT803X_INTR_ENABLE, value);
-       } else {
-@@ -923,8 +974,12 @@ static void at803x_link_change_notify(st
- static int at803x_read_status(struct phy_device *phydev)
- {
-+      struct at803x_priv *priv = phydev->priv;
-       int ss, err, old_link = phydev->link;
-+      if (priv->is_1000basex)
-+              return genphy_c37_read_status(phydev);
-+
-       /* Update the link, but return if there was an error */
-       err = genphy_update_link(phydev);
-       if (err)
-@@ -1023,6 +1078,7 @@ static int at803x_config_mdix(struct phy
- static int at803x_config_aneg(struct phy_device *phydev)
- {
-+      struct at803x_priv *priv = phydev->priv;
-       int ret;
-       ret = at803x_config_mdix(phydev, phydev->mdix_ctrl);
-@@ -1039,6 +1095,9 @@ static int at803x_config_aneg(struct phy
-                       return ret;
-       }
-+      if (priv->is_1000basex)
-+              return genphy_c37_config_aneg(phydev);
-+
-       return genphy_config_aneg(phydev);
- }
diff --git a/target/linux/generic/backport-5.15/778-v5.18-02-net-phy-at803x-support-downstream-SFP-cage.patch b/target/linux/generic/backport-5.15/778-v5.18-02-net-phy-at803x-support-downstream-SFP-cage.patch
deleted file mode 100644 (file)
index 8393cb3..0000000
+++ /dev/null
@@ -1,95 +0,0 @@
-From dc4d5fcc5d365c9f70ea3f5c09bdf70e988fad50 Mon Sep 17 00:00:00 2001
-From: Robert Hancock <[email protected]>
-Date: Tue, 25 Jan 2022 10:54:10 -0600
-Subject: [PATCH] net: phy: at803x: Support downstream SFP cage
-
-Add support for downstream SFP cages for AR8031 and AR8033. This is
-primarily intended for fiber modules or direct-attach cables, however
-copper modules which work in 1000Base-X mode may also function. Such
-modules are allowed with a warning.
-
-Signed-off-by: Robert Hancock <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/phy/at803x.c | 56 ++++++++++++++++++++++++++++++++++++++++
- 1 file changed, 56 insertions(+)
-
---- a/drivers/net/phy/at803x.c
-+++ b/drivers/net/phy/at803x.c
-@@ -19,6 +19,8 @@
- #include <linux/regulator/of_regulator.h>
- #include <linux/regulator/driver.h>
- #include <linux/regulator/consumer.h>
-+#include <linux/phylink.h>
-+#include <linux/sfp.h>
- #include <dt-bindings/net/qca-ar803x.h>
- #define AT803X_SPECIFIC_FUNCTION_CONTROL      0x10
-@@ -555,6 +557,55 @@ static int at8031_register_regulators(st
-       return 0;
- }
-+static int at803x_sfp_insert(void *upstream, const struct sfp_eeprom_id *id)
-+{
-+      struct phy_device *phydev = upstream;
-+      __ETHTOOL_DECLARE_LINK_MODE_MASK(phy_support);
-+      __ETHTOOL_DECLARE_LINK_MODE_MASK(sfp_support);
-+      phy_interface_t iface;
-+
-+      linkmode_zero(phy_support);
-+      phylink_set(phy_support, 1000baseX_Full);
-+      phylink_set(phy_support, 1000baseT_Full);
-+      phylink_set(phy_support, Autoneg);
-+      phylink_set(phy_support, Pause);
-+      phylink_set(phy_support, Asym_Pause);
-+
-+      linkmode_zero(sfp_support);
-+      sfp_parse_support(phydev->sfp_bus, id, sfp_support);
-+      /* Some modules support 10G modes as well as others we support.
-+       * Mask out non-supported modes so the correct interface is picked.
-+       */
-+      linkmode_and(sfp_support, phy_support, sfp_support);
-+
-+      if (linkmode_empty(sfp_support)) {
-+              dev_err(&phydev->mdio.dev, "incompatible SFP module inserted\n");
-+              return -EINVAL;
-+      }
-+
-+      iface = sfp_select_interface(phydev->sfp_bus, sfp_support);
-+
-+      /* Only 1000Base-X is supported by AR8031/8033 as the downstream SerDes
-+       * interface for use with SFP modules.
-+       * However, some copper modules detected as having a preferred SGMII
-+       * interface do default to and function in 1000Base-X mode, so just
-+       * print a warning and allow such modules, as they may have some chance
-+       * of working.
-+       */
-+      if (iface == PHY_INTERFACE_MODE_SGMII)
-+              dev_warn(&phydev->mdio.dev, "module may not function if 1000Base-X not supported\n");
-+      else if (iface != PHY_INTERFACE_MODE_1000BASEX)
-+              return -EINVAL;
-+
-+      return 0;
-+}
-+
-+static const struct sfp_upstream_ops at803x_sfp_ops = {
-+      .attach = phy_sfp_attach,
-+      .detach = phy_sfp_detach,
-+      .module_insert = at803x_sfp_insert,
-+};
-+
- static int at803x_parse_dt(struct phy_device *phydev)
- {
-       struct device_node *node = phydev->mdio.dev.of_node;
-@@ -662,6 +713,11 @@ static int at803x_parse_dt(struct phy_de
-                       phydev_err(phydev, "failed to get VDDIO regulator\n");
-                       return PTR_ERR(priv->vddio);
-               }
-+
-+              /* Only AR8031/8033 support 1000Base-X for SFP modules */
-+              ret = phy_sfp_probe(phydev, &at803x_sfp_ops);
-+              if (ret < 0)
-+                      return ret;
-       }
-       return 0;
diff --git a/target/linux/generic/backport-5.15/778-v5.18-03-net-phy-at803x-fix-NULL-pointer-dereference-on-AR9331-PHY.patch b/target/linux/generic/backport-5.15/778-v5.18-03-net-phy-at803x-fix-NULL-pointer-dereference-on-AR9331-PHY.patch
deleted file mode 100644 (file)
index 53d6325..0000000
+++ /dev/null
@@ -1,56 +0,0 @@
-From 9926de7315be3d606cc011a305ad9adb9e8e14c9 Mon Sep 17 00:00:00 2001
-From: Oleksij Rempel <[email protected]>
-Date: Sat, 18 Jun 2022 14:23:33 +0200
-Subject: [PATCH] net: phy: at803x: fix NULL pointer dereference on AR9331 PHY
-
-Latest kernel will explode on the PHY interrupt config, since it depends
-now on allocated priv. So, run probe to allocate priv to fix it.
-
- ar9331_switch ethernet.1:10 lan0 (uninitialized): PHY [!ahb!ethernet@1a000000!mdio!switch@10:00] driver [Qualcomm Atheros AR9331 built-in PHY] (irq=13)
- CPU 0 Unable to handle kernel paging request at virtual address 0000000a, epc == 8050e8a8, ra == 80504b34
-         ...
- Call Trace:
- [<8050e8a8>] at803x_config_intr+0x5c/0xd0
- [<80504b34>] phy_request_interrupt+0xa8/0xd0
- [<8050289c>] phylink_bringup_phy+0x2d8/0x3ac
- [<80502b68>] phylink_fwnode_phy_connect+0x118/0x130
- [<8074d8ec>] dsa_slave_create+0x270/0x420
- [<80743b04>] dsa_port_setup+0x12c/0x148
- [<8074580c>] dsa_register_switch+0xaf0/0xcc0
- [<80511344>] ar9331_sw_probe+0x370/0x388
- [<8050cb78>] mdio_probe+0x44/0x70
- [<804df300>] really_probe+0x200/0x424
- [<804df7b4>] __driver_probe_device+0x290/0x298
- [<804df810>] driver_probe_device+0x54/0xe4
- [<804dfd50>] __device_attach_driver+0xe4/0x130
- [<804dcb00>] bus_for_each_drv+0xb4/0xd8
- [<804dfac4>] __device_attach+0x104/0x1a4
- [<804ddd24>] bus_probe_device+0x48/0xc4
- [<804deb44>] deferred_probe_work_func+0xf0/0x10c
- [<800a0ffc>] process_one_work+0x314/0x4d4
- [<800a17fc>] worker_thread+0x2a4/0x354
- [<800a9a54>] kthread+0x134/0x13c
- [<8006306c>] ret_from_kernel_thread+0x14/0x1c
-
-Same Issue would affect some other PHYs (QCA8081, QCA9561), so fix it
-too.
-
-Fixes: 3265f4218878 ("net: phy: at803x: add fiber support")
-Signed-off-by: Oleksij Rempel <[email protected]>
-Reviewed-by: Andrew Lunn <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/phy/at803x.c | 6 ++++++
- 1 file changed, 6 insertions(+)
-
---- a/drivers/net/phy/at803x.c
-+++ b/drivers/net/phy/at803x.c
-@@ -1592,6 +1592,8 @@ static struct phy_driver at803x_driver[]
-       /* ATHEROS AR9331 */
-       PHY_ID_MATCH_EXACT(ATH9331_PHY_ID),
-       .name                   = "Qualcomm Atheros AR9331 built-in PHY",
-+      .probe                  = at803x_probe,
-+      .remove                 = at803x_remove,
-       .suspend                = at803x_suspend,
-       .resume                 = at803x_resume,
-       .flags                  = PHY_POLL_CABLE_TEST,
diff --git a/target/linux/generic/backport-5.15/778-v5.18-04-net-phy-at803x-fix-error-return-code-in-at803x_probe.patch b/target/linux/generic/backport-5.15/778-v5.18-04-net-phy-at803x-fix-error-return-code-in-at803x_probe.patch
deleted file mode 100644 (file)
index cdae5b4..0000000
+++ /dev/null
@@ -1,31 +0,0 @@
-From 1f0dd412e34e177621769866bef347f0b22364df Mon Sep 17 00:00:00 2001
-From: Wei Yongjun <[email protected]>
-Date: Fri, 18 Nov 2022 10:36:35 +0000
-Subject: [PATCH] net: phy: at803x: fix error return code in at803x_probe()
-
-Fix to return a negative error code from the ccr read error handling
-case instead of 0, as done elsewhere in this function.
-
-Fixes: 3265f4218878 ("net: phy: at803x: add fiber support")
-Signed-off-by: Wei Yongjun <[email protected]>
-Reviewed-by: Andrew Lunn <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- drivers/net/phy/at803x.c | 4 +++-
- 1 file changed, 3 insertions(+), 1 deletion(-)
-
---- a/drivers/net/phy/at803x.c
-+++ b/drivers/net/phy/at803x.c
-@@ -749,8 +749,10 @@ static int at803x_probe(struct phy_devic
-               int ccr = phy_read(phydev, AT803X_REG_CHIP_CONFIG);
-               int mode_cfg;
--              if (ccr < 0)
-+              if (ccr < 0) {
-+                      ret = ccr;
-                       goto err;
-+              }
-               mode_cfg = ccr & AT803X_MODE_CFG_MASK;
-               switch (mode_cfg) {
diff --git a/target/linux/generic/backport-5.15/780-v5.16-bus-mhi-pci_generic-Introduce-Sierra-EM919X-support.patch b/target/linux/generic/backport-5.15/780-v5.16-bus-mhi-pci_generic-Introduce-Sierra-EM919X-support.patch
deleted file mode 100644 (file)
index 44f0864..0000000
+++ /dev/null
@@ -1,80 +0,0 @@
-From 789d3eeb2367f92193a0882f7cdab03f0f9d6930 Mon Sep 17 00:00:00 2001
-From: Thomas Perrot <[email protected]>
-Date: Thu, 16 Dec 2021 13:42:27 +0530
-Subject: [PATCH] bus: mhi: pci_generic: Introduce Sierra EM919X support
-
-Add support for EM919X modems, this modem series is based on SDX55
-qcom chip.
-
-It is mandatory to use the same ring for control+data and diag events.
-
-Link: https://lore.kernel.org/r/[email protected]
-Tested-by: Aleksander Morgado <[email protected]>
-Reviewed-by: Manivannan Sadhasivam <[email protected]>
-Signed-off-by: Thomas Perrot <[email protected]>
-Signed-off-by: Manivannan Sadhasivam <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/bus/mhi/host/pci_generic.c | 43 +++++++++++++++++++++++++++++++++++
- 1 file changed, 43 insertions(+)
-
---- a/drivers/bus/mhi/host/pci_generic.c
-+++ b/drivers/bus/mhi/host/pci_generic.c
-@@ -406,6 +406,46 @@ static const struct mhi_pci_dev_info mhi
-       .mru_default = 32768,
- };
-+static const struct mhi_channel_config mhi_sierra_em919x_channels[] = {
-+      MHI_CHANNEL_CONFIG_UL_SBL(2, "SAHARA", 32, 0),
-+      MHI_CHANNEL_CONFIG_DL_SBL(3, "SAHARA", 256, 0),
-+      MHI_CHANNEL_CONFIG_UL(4, "DIAG", 32, 0),
-+      MHI_CHANNEL_CONFIG_DL(5, "DIAG", 32, 0),
-+      MHI_CHANNEL_CONFIG_UL(12, "MBIM", 128, 0),
-+      MHI_CHANNEL_CONFIG_DL(13, "MBIM", 128, 0),
-+      MHI_CHANNEL_CONFIG_UL(14, "QMI", 32, 0),
-+      MHI_CHANNEL_CONFIG_DL(15, "QMI", 32, 0),
-+      MHI_CHANNEL_CONFIG_UL(32, "DUN", 32, 0),
-+      MHI_CHANNEL_CONFIG_DL(33, "DUN", 32, 0),
-+      MHI_CHANNEL_CONFIG_HW_UL(100, "IP_HW0", 512, 1),
-+      MHI_CHANNEL_CONFIG_HW_DL(101, "IP_HW0", 512, 2),
-+};
-+
-+static struct mhi_event_config modem_sierra_em919x_mhi_events[] = {
-+      /* first ring is control+data and DIAG ring */
-+      MHI_EVENT_CONFIG_CTRL(0, 2048),
-+      /* Hardware channels request dedicated hardware event rings */
-+      MHI_EVENT_CONFIG_HW_DATA(1, 2048, 100),
-+      MHI_EVENT_CONFIG_HW_DATA(2, 2048, 101)
-+};
-+
-+static const struct mhi_controller_config modem_sierra_em919x_config = {
-+      .max_channels = 128,
-+      .timeout_ms = 24000,
-+      .num_channels = ARRAY_SIZE(mhi_sierra_em919x_channels),
-+      .ch_cfg = mhi_sierra_em919x_channels,
-+      .num_events = ARRAY_SIZE(modem_sierra_em919x_mhi_events),
-+      .event_cfg = modem_sierra_em919x_mhi_events,
-+};
-+
-+static const struct mhi_pci_dev_info mhi_sierra_em919x_info = {
-+      .name = "sierra-em919x",
-+      .config = &modem_sierra_em919x_config,
-+      .bar_num = MHI_PCI_DEFAULT_BAR_NUM,
-+      .dma_data_width = 32,
-+      .sideband_wake = false,
-+};
-+
- static const struct mhi_channel_config mhi_telit_fn980_hw_v1_channels[] = {
-       MHI_CHANNEL_CONFIG_UL(14, "QMI", 32, 0),
-       MHI_CHANNEL_CONFIG_DL(15, "QMI", 32, 0),
-@@ -480,6 +520,9 @@ static const struct mhi_pci_dev_info mhi
- };
- static const struct pci_device_id mhi_pci_id_table[] = {
-+      /* EM919x (sdx55), use the same vid:pid as qcom-sdx55m */
-+      { PCI_DEVICE_SUB(PCI_VENDOR_ID_QCOM, 0x0306, 0x18d7, 0x0200),
-+              .driver_data = (kernel_ulong_t) &mhi_sierra_em919x_info },
-       /* Telit FN980 hardware revision v1 */
-       { PCI_DEVICE_SUB(PCI_VENDOR_ID_QCOM, 0x0306, 0x1C5D, 0x2000),
-               .driver_data = (kernel_ulong_t) &mhi_telit_fn980_hw_v1_info },
diff --git a/target/linux/generic/backport-5.15/781-v6.1-bus-mhi-host-always-print-detected-modem-name.patch b/target/linux/generic/backport-5.15/781-v6.1-bus-mhi-host-always-print-detected-modem-name.patch
deleted file mode 100644 (file)
index 3c71a27..0000000
+++ /dev/null
@@ -1,37 +0,0 @@
-From f369e9ad52ec9361827e21a631b7198c9fca438e Mon Sep 17 00:00:00 2001
-From: Koen Vandeputte <[email protected]>
-Date: Wed, 31 Aug 2022 12:03:49 +0200
-Subject: [PATCH] bus: mhi: host: always print detected modem name
-
-This harmless print provides a very easy way of knowing
-if the modem is detected properly during probing.
-
-Promote it to an informational print so no hassle is required
-enabling kernel debugging info to obtain it.
-
-The rationale here is that:
-On a lot of low-storage embedded devices, extensive kernel
-debugging info is not always present as this would
-increase it's size to much causing partition size issues.
-
-Signed-off-by: Koen Vandeputte <[email protected]>
-Reviewed-by: Manivannan Sadhasivam <[email protected]>
-Reviewed-by: Loic Poulain <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-[mani: added missing review tags]
-Signed-off-by: Manivannan Sadhasivam <[email protected]>
----
- drivers/bus/mhi/host/pci_generic.c | 2 +-
- 1 file changed, 1 insertion(+), 1 deletion(-)
-
---- a/drivers/bus/mhi/host/pci_generic.c
-+++ b/drivers/bus/mhi/host/pci_generic.c
-@@ -806,7 +806,7 @@ static int mhi_pci_probe(struct pci_dev
-       struct mhi_controller *mhi_cntrl;
-       int err;
--      dev_dbg(&pdev->dev, "MHI PCI device found: %s\n", info->name);
-+      dev_info(&pdev->dev, "MHI PCI device found: %s\n", info->name);
-       /* mhi_pdev.mhi_cntrl must be zero-initialized */
-       mhi_pdev = devm_kzalloc(&pdev->dev, sizeof(*mhi_pdev), GFP_KERNEL);
diff --git a/target/linux/generic/backport-5.15/782-v6.1-net-dsa-mt7530-add-support-for-in-band-link-status.patch b/target/linux/generic/backport-5.15/782-v6.1-net-dsa-mt7530-add-support-for-in-band-link-status.patch
deleted file mode 100644 (file)
index 7f16b93..0000000
+++ /dev/null
@@ -1,130 +0,0 @@
-From e19de30d20809af3221ef8a2648b8a8a52e02d90 Mon Sep 17 00:00:00 2001
-From: Daniel Golle <[email protected]>
-Date: Wed, 21 Sep 2022 01:23:14 +0100
-Subject: [PATCH 1/1] net: dsa: mt7530: add support for in-band link status
-
-Read link status from SGMII PCS for in-band managed 2500Base-X and
-1000Base-X connection on a MAC port of the MT7531. This is needed to
-get the SFP cage working which is connected to SGMII interface of
-port 5 of the MT7531 switch IC on the Bananapi BPi-R3 board.
-While at it also handle an_complete for both the autoneg and the
-non-autoneg codepath.
-
-Signed-off-by: Daniel Golle <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/dsa/mt7530.c | 50 +++++++++++++++++++++++++++++-----------
- drivers/net/dsa/mt7530.h |  1 +
- 2 files changed, 38 insertions(+), 13 deletions(-)
-
---- a/drivers/net/dsa/mt7530.c
-+++ b/drivers/net/dsa/mt7530.c
-@@ -2979,9 +2979,6 @@ mt7531_mac_config(struct dsa_switch *ds,
-       case PHY_INTERFACE_MODE_NA:
-       case PHY_INTERFACE_MODE_1000BASEX:
-       case PHY_INTERFACE_MODE_2500BASEX:
--              if (phylink_autoneg_inband(mode))
--                      return -EINVAL;
--
-               return mt7531_sgmii_setup_mode_force(priv, port, interface);
-       default:
-               return -EINVAL;
-@@ -3057,13 +3054,6 @@ unsupported:
-               return;
-       }
--      if (phylink_autoneg_inband(mode) &&
--          state->interface != PHY_INTERFACE_MODE_SGMII) {
--              dev_err(ds->dev, "%s: in-band negotiation unsupported\n",
--                      __func__);
--              return;
--      }
--
-       mcr_cur = mt7530_read(priv, MT7530_PMCR_P(port));
-       mcr_new = mcr_cur;
-       mcr_new &= ~PMCR_LINK_SETTINGS_MASK;
-@@ -3200,6 +3190,9 @@ static void mt753x_phylink_get_caps(stru
-       config->mac_capabilities = MAC_ASYM_PAUSE | MAC_SYM_PAUSE |
-                                  MAC_10 | MAC_100 | MAC_1000FD;
-+      if ((priv->id == ID_MT7531) && mt753x_is_mac_port(port))
-+              config->mac_capabilities |= MAC_2500FD;
-+
-       /* This driver does not make use of the speed, duplex, pause or the
-        * advertisement in its mac_config, so it is safe to mark this driver
-        * as non-legacy.
-@@ -3265,6 +3258,7 @@ mt7531_sgmii_pcs_get_state_an(struct mt7
-       status = mt7530_read(priv, MT7531_PCS_CONTROL_1(port));
-       state->link = !!(status & MT7531_SGMII_LINK_STATUS);
-+      state->an_complete = !!(status & MT7531_SGMII_AN_COMPLETE);
-       if (state->interface == PHY_INTERFACE_MODE_SGMII &&
-           (status & MT7531_SGMII_AN_ENABLE)) {
-               val = mt7530_read(priv, MT7531_PCS_SPEED_ABILITY(port));
-@@ -3295,16 +3289,44 @@ mt7531_sgmii_pcs_get_state_an(struct mt7
-       return 0;
- }
-+static void
-+mt7531_sgmii_pcs_get_state_inband(struct mt7530_priv *priv, int port,
-+                                struct phylink_link_state *state)
-+{
-+      unsigned int val;
-+
-+      val = mt7530_read(priv, MT7531_PCS_CONTROL_1(port));
-+      state->link = !!(val & MT7531_SGMII_LINK_STATUS);
-+      if (!state->link)
-+              return;
-+
-+      state->an_complete = state->link;
-+
-+      if (state->interface == PHY_INTERFACE_MODE_2500BASEX)
-+              state->speed = SPEED_2500;
-+      else
-+              state->speed = SPEED_1000;
-+
-+      state->duplex = DUPLEX_FULL;
-+      state->pause = MLO_PAUSE_NONE;
-+}
-+
- static void mt7531_pcs_get_state(struct phylink_pcs *pcs,
-                                struct phylink_link_state *state)
- {
-       struct mt7530_priv *priv = pcs_to_mt753x_pcs(pcs)->priv;
-       int port = pcs_to_mt753x_pcs(pcs)->port;
--      if (state->interface == PHY_INTERFACE_MODE_SGMII)
-+      if (state->interface == PHY_INTERFACE_MODE_SGMII) {
-               mt7531_sgmii_pcs_get_state_an(priv, port, state);
--      else
--              state->link = false;
-+              return;
-+      } else if ((state->interface == PHY_INTERFACE_MODE_1000BASEX) ||
-+                 (state->interface == PHY_INTERFACE_MODE_2500BASEX)) {
-+              mt7531_sgmii_pcs_get_state_inband(priv, port, state);
-+              return;
-+      }
-+
-+      state->link = false;
- }
- static int mt753x_pcs_config(struct phylink_pcs *pcs, unsigned int mode,
-@@ -3345,6 +3367,8 @@ mt753x_setup(struct dsa_switch *ds)
-               priv->pcs[i].pcs.ops = priv->info->pcs_ops;
-               priv->pcs[i].priv = priv;
-               priv->pcs[i].port = i;
-+              if (mt753x_is_mac_port(i))
-+                      priv->pcs[i].pcs.poll = 1;
-       }
-       ret = priv->info->sw_setup(ds);
---- a/drivers/net/dsa/mt7530.h
-+++ b/drivers/net/dsa/mt7530.h
-@@ -410,6 +410,7 @@ enum mt7530_vlan_port_acc_frm {
- #define  MT7531_SGMII_LINK_STATUS     BIT(18)
- #define  MT7531_SGMII_AN_ENABLE               BIT(12)
- #define  MT7531_SGMII_AN_RESTART      BIT(9)
-+#define  MT7531_SGMII_AN_COMPLETE     BIT(21)
- /* Register for SGMII PCS_SPPED_ABILITY */
- #define MT7531_PCS_SPEED_ABILITY(p)   MT7531_SGMII_REG(p, 0x08)
diff --git a/target/linux/generic/backport-5.15/783-v6.1-net-sfp-re-implement-soft-state-polling-setup.patch b/target/linux/generic/backport-5.15/783-v6.1-net-sfp-re-implement-soft-state-polling-setup.patch
deleted file mode 100644 (file)
index 77cd336..0000000
+++ /dev/null
@@ -1,98 +0,0 @@
-From 8475c4b70b040f9d8cbc308100f2c4d865f810b3 Mon Sep 17 00:00:00 2001
-From: "Russell King (Oracle)" <[email protected]>
-Date: Tue, 13 Sep 2022 20:06:27 +0100
-Subject: [PATCH 1/1] net: sfp: re-implement soft state polling setup
-
-Re-implement the decision making for soft state polling. Instead of
-generating the soft state mask in sfp_soft_start_poll() by looking at
-which GPIOs are available, record their availability in
-sfp_sm_mod_probe() in sfp->state_hw_mask.
-
-This will then allow us to clear bits in sfp->state_hw_mask in module
-specific quirks when the hardware signals should not be used, thereby
-allowing us to switch to using the software state polling.
-
-Signed-off-by: Russell King (Oracle) <[email protected]>
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- drivers/net/phy/sfp.c | 38 ++++++++++++++++++++++++++------------
- 1 file changed, 26 insertions(+), 12 deletions(-)
-
---- a/drivers/net/phy/sfp.c
-+++ b/drivers/net/phy/sfp.c
-@@ -240,6 +240,7 @@ struct sfp {
-       bool need_poll;
-       struct mutex st_mutex;                  /* Protects state */
-+      unsigned int state_hw_mask;
-       unsigned int state_soft_mask;
-       unsigned int state;
-       struct delayed_work poll;
-@@ -505,17 +506,18 @@ static void sfp_soft_set_state(struct sf
- static void sfp_soft_start_poll(struct sfp *sfp)
- {
-       const struct sfp_eeprom_id *id = &sfp->id;
-+      unsigned int mask = 0;
-       sfp->state_soft_mask = 0;
--      if (id->ext.enhopts & SFP_ENHOPTS_SOFT_TX_DISABLE &&
--          !sfp->gpio[GPIO_TX_DISABLE])
--              sfp->state_soft_mask |= SFP_F_TX_DISABLE;
--      if (id->ext.enhopts & SFP_ENHOPTS_SOFT_TX_FAULT &&
--          !sfp->gpio[GPIO_TX_FAULT])
--              sfp->state_soft_mask |= SFP_F_TX_FAULT;
--      if (id->ext.enhopts & SFP_ENHOPTS_SOFT_RX_LOS &&
--          !sfp->gpio[GPIO_LOS])
--              sfp->state_soft_mask |= SFP_F_LOS;
-+      if (id->ext.enhopts & SFP_ENHOPTS_SOFT_TX_DISABLE)
-+              mask |= SFP_F_TX_DISABLE;
-+      if (id->ext.enhopts & SFP_ENHOPTS_SOFT_TX_FAULT)
-+              mask |= SFP_F_TX_FAULT;
-+      if (id->ext.enhopts & SFP_ENHOPTS_SOFT_RX_LOS)
-+              mask |= SFP_F_LOS;
-+
-+      // Poll the soft state for hardware pins we want to ignore
-+      sfp->state_soft_mask = ~sfp->state_hw_mask & mask;
-       if (sfp->state_soft_mask & (SFP_F_LOS | SFP_F_TX_FAULT) &&
-           !sfp->need_poll)
-@@ -529,10 +531,11 @@ static void sfp_soft_stop_poll(struct sf
- static unsigned int sfp_get_state(struct sfp *sfp)
- {
--      unsigned int state = sfp->get_state(sfp);
-+      unsigned int soft = sfp->state_soft_mask & (SFP_F_LOS | SFP_F_TX_FAULT);
-+      unsigned int state;
--      if (state & SFP_F_PRESENT &&
--          sfp->state_soft_mask & (SFP_F_LOS | SFP_F_TX_FAULT))
-+      state = sfp->get_state(sfp) & sfp->state_hw_mask;
-+      if (state & SFP_F_PRESENT && soft)
-               state |= sfp_soft_get_state(sfp);
-       return state;
-@@ -1942,6 +1945,15 @@ static int sfp_sm_mod_probe(struct sfp *
-       if (ret < 0)
-               return ret;
-+      /* Initialise state bits to use from hardware */
-+      sfp->state_hw_mask = SFP_F_PRESENT;
-+      if (sfp->gpio[GPIO_TX_DISABLE])
-+              sfp->state_hw_mask |= SFP_F_TX_DISABLE;
-+      if (sfp->gpio[GPIO_TX_FAULT])
-+              sfp->state_hw_mask |= SFP_F_TX_FAULT;
-+      if (sfp->gpio[GPIO_LOS])
-+              sfp->state_hw_mask |= SFP_F_LOS;
-+
-       if (!memcmp(id.base.vendor_name, "ALCATELLUCENT   ", 16) &&
-           !memcmp(id.base.vendor_pn, "3FE46541AA      ", 16))
-               sfp->module_t_start_up = T_START_UP_BAD_GPON;
-@@ -2568,6 +2580,8 @@ static int sfp_probe(struct platform_dev
-                               return PTR_ERR(sfp->gpio[i]);
-               }
-+      sfp->state_hw_mask = SFP_F_PRESENT;
-+
-       sfp->get_state = sfp_gpio_get_state;
-       sfp->set_state = sfp_gpio_set_state;
diff --git a/target/linux/generic/backport-5.15/784-v6.1-net-sfp-move-quirk-handling-into-sfp.c.patch b/target/linux/generic/backport-5.15/784-v6.1-net-sfp-move-quirk-handling-into-sfp.c.patch
deleted file mode 100644 (file)
index 02fa28c..0000000
+++ /dev/null
@@ -1,291 +0,0 @@
-From 23571c7b96437483d28a990c906cc81f5f66374e Mon Sep 17 00:00:00 2001
-From: "Russell King (Oracle)" <[email protected]>
-Date: Tue, 13 Sep 2022 20:06:32 +0100
-Subject: [PATCH 1/1] net: sfp: move quirk handling into sfp.c
-
-We need to handle more quirks than just those which affect the link
-modes of the module. Move the quirk lookup into sfp.c, and pass the
-quirk to sfp-bus.c
-
-Signed-off-by: Russell King (Oracle) <[email protected]>
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- drivers/net/phy/sfp-bus.c | 98 ++-------------------------------------
- drivers/net/phy/sfp.c     | 94 ++++++++++++++++++++++++++++++++++++-
- drivers/net/phy/sfp.h     |  9 +++-
- 3 files changed, 104 insertions(+), 97 deletions(-)
-
---- a/drivers/net/phy/sfp-bus.c
-+++ b/drivers/net/phy/sfp-bus.c
-@@ -10,12 +10,6 @@
- #include "sfp.h"
--struct sfp_quirk {
--      const char *vendor;
--      const char *part;
--      void (*modes)(const struct sfp_eeprom_id *id, unsigned long *modes);
--};
--
- /**
-  * struct sfp_bus - internal representation of a sfp bus
-  */
-@@ -38,93 +32,6 @@ struct sfp_bus {
-       bool started;
- };
--static void sfp_quirk_2500basex(const struct sfp_eeprom_id *id,
--                              unsigned long *modes)
--{
--      phylink_set(modes, 2500baseX_Full);
--}
--
--static void sfp_quirk_ubnt_uf_instant(const struct sfp_eeprom_id *id,
--                                    unsigned long *modes)
--{
--      /* Ubiquiti U-Fiber Instant module claims that support all transceiver
--       * types including 10G Ethernet which is not truth. So clear all claimed
--       * modes and set only one mode which module supports: 1000baseX_Full.
--       */
--      phylink_zero(modes);
--      phylink_set(modes, 1000baseX_Full);
--}
--
--static const struct sfp_quirk sfp_quirks[] = {
--      {
--              // Alcatel Lucent G-010S-P can operate at 2500base-X, but
--              // incorrectly report 2500MBd NRZ in their EEPROM
--              .vendor = "ALCATELLUCENT",
--              .part = "G010SP",
--              .modes = sfp_quirk_2500basex,
--      }, {
--              // Alcatel Lucent G-010S-A can operate at 2500base-X, but
--              // report 3.2GBd NRZ in their EEPROM
--              .vendor = "ALCATELLUCENT",
--              .part = "3FE46541AA",
--              .modes = sfp_quirk_2500basex,
--      }, {
--              // Huawei MA5671A can operate at 2500base-X, but report 1.2GBd
--              // NRZ in their EEPROM
--              .vendor = "HUAWEI",
--              .part = "MA5671A",
--              .modes = sfp_quirk_2500basex,
--      }, {
--              // Lantech 8330-262D-E can operate at 2500base-X, but
--              // incorrectly report 2500MBd NRZ in their EEPROM
--              .vendor = "Lantech",
--              .part = "8330-262D-E",
--              .modes = sfp_quirk_2500basex,
--      }, {
--              .vendor = "UBNT",
--              .part = "UF-INSTANT",
--              .modes = sfp_quirk_ubnt_uf_instant,
--      },
--};
--
--static size_t sfp_strlen(const char *str, size_t maxlen)
--{
--      size_t size, i;
--
--      /* Trailing characters should be filled with space chars */
--      for (i = 0, size = 0; i < maxlen; i++)
--              if (str[i] != ' ')
--                      size = i + 1;
--
--      return size;
--}
--
--static bool sfp_match(const char *qs, const char *str, size_t len)
--{
--      if (!qs)
--              return true;
--      if (strlen(qs) != len)
--              return false;
--      return !strncmp(qs, str, len);
--}
--
--static const struct sfp_quirk *sfp_lookup_quirk(const struct sfp_eeprom_id *id)
--{
--      const struct sfp_quirk *q;
--      unsigned int i;
--      size_t vs, ps;
--
--      vs = sfp_strlen(id->base.vendor_name, ARRAY_SIZE(id->base.vendor_name));
--      ps = sfp_strlen(id->base.vendor_pn, ARRAY_SIZE(id->base.vendor_pn));
--
--      for (i = 0, q = sfp_quirks; i < ARRAY_SIZE(sfp_quirks); i++, q++)
--              if (sfp_match(q->vendor, id->base.vendor_name, vs) &&
--                  sfp_match(q->part, id->base.vendor_pn, ps))
--                      return q;
--
--      return NULL;
--}
--
- /**
-  * sfp_parse_port() - Parse the EEPROM base ID, setting the port type
-  * @bus: a pointer to the &struct sfp_bus structure for the sfp module
-@@ -786,12 +693,13 @@ void sfp_link_down(struct sfp_bus *bus)
- }
- EXPORT_SYMBOL_GPL(sfp_link_down);
--int sfp_module_insert(struct sfp_bus *bus, const struct sfp_eeprom_id *id)
-+int sfp_module_insert(struct sfp_bus *bus, const struct sfp_eeprom_id *id,
-+                    const struct sfp_quirk *quirk)
- {
-       const struct sfp_upstream_ops *ops = sfp_get_upstream_ops(bus);
-       int ret = 0;
--      bus->sfp_quirk = sfp_lookup_quirk(id);
-+      bus->sfp_quirk = quirk;
-       if (ops && ops->module_insert)
-               ret = ops->module_insert(bus->upstream, id);
---- a/drivers/net/phy/sfp.c
-+++ b/drivers/net/phy/sfp.c
-@@ -259,6 +259,8 @@ struct sfp {
-       unsigned int module_t_start_up;
-       bool tx_fault_ignore;
-+      const struct sfp_quirk *quirk;
-+
- #if IS_ENABLED(CONFIG_HWMON)
-       struct sfp_diag diag;
-       struct delayed_work hwmon_probe;
-@@ -315,6 +317,93 @@ static const struct of_device_id sfp_of_
- };
- MODULE_DEVICE_TABLE(of, sfp_of_match);
-+static void sfp_quirk_2500basex(const struct sfp_eeprom_id *id,
-+                              unsigned long *modes)
-+{
-+      linkmode_set_bit(ETHTOOL_LINK_MODE_2500baseX_Full_BIT, modes);
-+}
-+
-+static void sfp_quirk_ubnt_uf_instant(const struct sfp_eeprom_id *id,
-+                                    unsigned long *modes)
-+{
-+      /* Ubiquiti U-Fiber Instant module claims that support all transceiver
-+       * types including 10G Ethernet which is not truth. So clear all claimed
-+       * modes and set only one mode which module supports: 1000baseX_Full.
-+       */
-+      linkmode_zero(modes);
-+      linkmode_set_bit(ETHTOOL_LINK_MODE_1000baseX_Full_BIT, modes);
-+}
-+
-+static const struct sfp_quirk sfp_quirks[] = {
-+      {
-+              // Alcatel Lucent G-010S-P can operate at 2500base-X, but
-+              // incorrectly report 2500MBd NRZ in their EEPROM
-+              .vendor = "ALCATELLUCENT",
-+              .part = "G010SP",
-+              .modes = sfp_quirk_2500basex,
-+      }, {
-+              // Alcatel Lucent G-010S-A can operate at 2500base-X, but
-+              // report 3.2GBd NRZ in their EEPROM
-+              .vendor = "ALCATELLUCENT",
-+              .part = "3FE46541AA",
-+              .modes = sfp_quirk_2500basex,
-+      }, {
-+              // Huawei MA5671A can operate at 2500base-X, but report 1.2GBd
-+              // NRZ in their EEPROM
-+              .vendor = "HUAWEI",
-+              .part = "MA5671A",
-+              .modes = sfp_quirk_2500basex,
-+      }, {
-+              // Lantech 8330-262D-E can operate at 2500base-X, but
-+              // incorrectly report 2500MBd NRZ in their EEPROM
-+              .vendor = "Lantech",
-+              .part = "8330-262D-E",
-+              .modes = sfp_quirk_2500basex,
-+      }, {
-+              .vendor = "UBNT",
-+              .part = "UF-INSTANT",
-+              .modes = sfp_quirk_ubnt_uf_instant,
-+      },
-+};
-+
-+static size_t sfp_strlen(const char *str, size_t maxlen)
-+{
-+      size_t size, i;
-+
-+      /* Trailing characters should be filled with space chars */
-+      for (i = 0, size = 0; i < maxlen; i++)
-+              if (str[i] != ' ')
-+                      size = i + 1;
-+
-+      return size;
-+}
-+
-+static bool sfp_match(const char *qs, const char *str, size_t len)
-+{
-+      if (!qs)
-+              return true;
-+      if (strlen(qs) != len)
-+              return false;
-+      return !strncmp(qs, str, len);
-+}
-+
-+static const struct sfp_quirk *sfp_lookup_quirk(const struct sfp_eeprom_id *id)
-+{
-+      const struct sfp_quirk *q;
-+      unsigned int i;
-+      size_t vs, ps;
-+
-+      vs = sfp_strlen(id->base.vendor_name, ARRAY_SIZE(id->base.vendor_name));
-+      ps = sfp_strlen(id->base.vendor_pn, ARRAY_SIZE(id->base.vendor_pn));
-+
-+      for (i = 0, q = sfp_quirks; i < ARRAY_SIZE(sfp_quirks); i++, q++)
-+              if (sfp_match(q->vendor, id->base.vendor_name, vs) &&
-+                  sfp_match(q->part, id->base.vendor_pn, ps))
-+                      return q;
-+
-+      return NULL;
-+}
-+
- static unsigned long poll_jiffies;
- static unsigned int sfp_gpio_get_state(struct sfp *sfp)
-@@ -1966,6 +2055,8 @@ static int sfp_sm_mod_probe(struct sfp *
-       else
-               sfp->tx_fault_ignore = false;
-+      sfp->quirk = sfp_lookup_quirk(&id);
-+
-       return 0;
- }
-@@ -2077,7 +2168,8 @@ static void sfp_sm_module(struct sfp *sf
-                       break;
-               /* Report the module insertion to the upstream device */
--              err = sfp_module_insert(sfp->sfp_bus, &sfp->id);
-+              err = sfp_module_insert(sfp->sfp_bus, &sfp->id,
-+                                      sfp->quirk);
-               if (err < 0) {
-                       sfp_sm_mod_next(sfp, SFP_MOD_ERROR, 0);
-                       break;
---- a/drivers/net/phy/sfp.h
-+++ b/drivers/net/phy/sfp.h
-@@ -6,6 +6,12 @@
- struct sfp;
-+struct sfp_quirk {
-+      const char *vendor;
-+      const char *part;
-+      void (*modes)(const struct sfp_eeprom_id *id, unsigned long *modes);
-+};
-+
- struct sfp_socket_ops {
-       void (*attach)(struct sfp *sfp);
-       void (*detach)(struct sfp *sfp);
-@@ -23,7 +29,8 @@ int sfp_add_phy(struct sfp_bus *bus, str
- void sfp_remove_phy(struct sfp_bus *bus);
- void sfp_link_up(struct sfp_bus *bus);
- void sfp_link_down(struct sfp_bus *bus);
--int sfp_module_insert(struct sfp_bus *bus, const struct sfp_eeprom_id *id);
-+int sfp_module_insert(struct sfp_bus *bus, const struct sfp_eeprom_id *id,
-+                    const struct sfp_quirk *quirk);
- void sfp_module_remove(struct sfp_bus *bus);
- int sfp_module_start(struct sfp_bus *bus);
- void sfp_module_stop(struct sfp_bus *bus);
diff --git a/target/linux/generic/backport-5.15/785-v6.1-net-sfp-move-Alcatel-Lucent-3FE46541AA-fixup.patch b/target/linux/generic/backport-5.15/785-v6.1-net-sfp-move-Alcatel-Lucent-3FE46541AA-fixup.patch
deleted file mode 100644 (file)
index b076676..0000000
+++ /dev/null
@@ -1,69 +0,0 @@
-From 275416754e9a262c97a1ad6f806a4bc6e0464aa2 Mon Sep 17 00:00:00 2001
-From: "Russell King (Oracle)" <[email protected]>
-Date: Tue, 13 Sep 2022 20:06:37 +0100
-Subject: [PATCH 1/1] net: sfp: move Alcatel Lucent 3FE46541AA fixup
-
-Add a new fixup mechanism to the SFP quirks, and use it for this
-module.
-
-Signed-off-by: Russell King (Oracle) <[email protected]>
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- drivers/net/phy/sfp.c | 14 +++++++++-----
- drivers/net/phy/sfp.h |  1 +
- 2 files changed, 10 insertions(+), 5 deletions(-)
-
---- a/drivers/net/phy/sfp.c
-+++ b/drivers/net/phy/sfp.c
-@@ -317,6 +317,11 @@ static const struct of_device_id sfp_of_
- };
- MODULE_DEVICE_TABLE(of, sfp_of_match);
-+static void sfp_fixup_long_startup(struct sfp *sfp)
-+{
-+      sfp->module_t_start_up = T_START_UP_BAD_GPON;
-+}
-+
- static void sfp_quirk_2500basex(const struct sfp_eeprom_id *id,
-                               unsigned long *modes)
- {
-@@ -347,6 +352,7 @@ static const struct sfp_quirk sfp_quirks
-               .vendor = "ALCATELLUCENT",
-               .part = "3FE46541AA",
-               .modes = sfp_quirk_2500basex,
-+              .fixup = sfp_fixup_long_startup,
-       }, {
-               // Huawei MA5671A can operate at 2500base-X, but report 1.2GBd
-               // NRZ in their EEPROM
-@@ -2043,11 +2049,7 @@ static int sfp_sm_mod_probe(struct sfp *
-       if (sfp->gpio[GPIO_LOS])
-               sfp->state_hw_mask |= SFP_F_LOS;
--      if (!memcmp(id.base.vendor_name, "ALCATELLUCENT   ", 16) &&
--          !memcmp(id.base.vendor_pn, "3FE46541AA      ", 16))
--              sfp->module_t_start_up = T_START_UP_BAD_GPON;
--      else
--              sfp->module_t_start_up = T_START_UP;
-+      sfp->module_t_start_up = T_START_UP;
-       if (!memcmp(id.base.vendor_name, "HUAWEI          ", 16) &&
-           !memcmp(id.base.vendor_pn, "MA5671A         ", 16))
-@@ -2056,6 +2058,8 @@ static int sfp_sm_mod_probe(struct sfp *
-               sfp->tx_fault_ignore = false;
-       sfp->quirk = sfp_lookup_quirk(&id);
-+      if (sfp->quirk && sfp->quirk->fixup)
-+              sfp->quirk->fixup(sfp);
-       return 0;
- }
---- a/drivers/net/phy/sfp.h
-+++ b/drivers/net/phy/sfp.h
-@@ -10,6 +10,7 @@ struct sfp_quirk {
-       const char *vendor;
-       const char *part;
-       void (*modes)(const struct sfp_eeprom_id *id, unsigned long *modes);
-+      void (*fixup)(struct sfp *sfp);
- };
- struct sfp_socket_ops {
diff --git a/target/linux/generic/backport-5.15/786-v6.1-net-sfp-move-Huawei-MA5671A-fixup.patch b/target/linux/generic/backport-5.15/786-v6.1-net-sfp-move-Huawei-MA5671A-fixup.patch
deleted file mode 100644 (file)
index 7f856e5..0000000
+++ /dev/null
@@ -1,48 +0,0 @@
-From 5029be761161374a3624aa7b4670174c35449bf5 Mon Sep 17 00:00:00 2001
-From: "Russell King (Oracle)" <[email protected]>
-Date: Tue, 13 Sep 2022 20:06:42 +0100
-Subject: [PATCH 1/1] net: sfp: move Huawei MA5671A fixup
-
-Move this module over to the new fixup mechanism.
-
-Signed-off-by: Russell King (Oracle) <[email protected]>
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- drivers/net/phy/sfp.c | 12 +++++++-----
- 1 file changed, 7 insertions(+), 5 deletions(-)
-
---- a/drivers/net/phy/sfp.c
-+++ b/drivers/net/phy/sfp.c
-@@ -322,6 +322,11 @@ static void sfp_fixup_long_startup(struc
-       sfp->module_t_start_up = T_START_UP_BAD_GPON;
- }
-+static void sfp_fixup_ignore_tx_fault(struct sfp *sfp)
-+{
-+      sfp->tx_fault_ignore = true;
-+}
-+
- static void sfp_quirk_2500basex(const struct sfp_eeprom_id *id,
-                               unsigned long *modes)
- {
-@@ -359,6 +364,7 @@ static const struct sfp_quirk sfp_quirks
-               .vendor = "HUAWEI",
-               .part = "MA5671A",
-               .modes = sfp_quirk_2500basex,
-+              .fixup = sfp_fixup_ignore_tx_fault,
-       }, {
-               // Lantech 8330-262D-E can operate at 2500base-X, but
-               // incorrectly report 2500MBd NRZ in their EEPROM
-@@ -2051,11 +2057,7 @@ static int sfp_sm_mod_probe(struct sfp *
-       sfp->module_t_start_up = T_START_UP;
--      if (!memcmp(id.base.vendor_name, "HUAWEI          ", 16) &&
--          !memcmp(id.base.vendor_pn, "MA5671A         ", 16))
--              sfp->tx_fault_ignore = true;
--      else
--              sfp->tx_fault_ignore = false;
-+      sfp->tx_fault_ignore = false;
-       sfp->quirk = sfp_lookup_quirk(&id);
-       if (sfp->quirk && sfp->quirk->fixup)
diff --git a/target/linux/generic/backport-5.15/787-v6.1-net-sfp-add-support-for-HALNy-GPON-SFP.patch b/target/linux/generic/backport-5.15/787-v6.1-net-sfp-add-support-for-HALNy-GPON-SFP.patch
deleted file mode 100644 (file)
index 81108e1..0000000
+++ /dev/null
@@ -1,79 +0,0 @@
-From 73472c830eae5fce2107f7f086f1e6827d215caf Mon Sep 17 00:00:00 2001
-From: "Russell King (Oracle)" <[email protected]>
-Date: Tue, 13 Sep 2022 20:06:48 +0100
-Subject: [PATCH 1/1] net: sfp: add support for HALNy GPON SFP
-
-Add a quirk for the HALNy HL-GSFP module, which appears to have an
-inverted RX_LOS signal, and maybe uses TX_FAULT as a serial port
-transmit pin. Rather than use these hardware signals, switch to
-using software polling for these status signals.
-
-Signed-off-by: Russell King (Oracle) <[email protected]>
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- drivers/net/phy/sfp-bus.c |  2 +-
- drivers/net/phy/sfp.c     | 21 ++++++++++++++++++---
- 2 files changed, 19 insertions(+), 4 deletions(-)
-
---- a/drivers/net/phy/sfp-bus.c
-+++ b/drivers/net/phy/sfp-bus.c
-@@ -283,7 +283,7 @@ void sfp_parse_support(struct sfp_bus *b
-                       phylink_set(modes, 2500baseX_Full);
-       }
--      if (bus->sfp_quirk)
-+      if (bus->sfp_quirk && bus->sfp_quirk->modes)
-               bus->sfp_quirk->modes(id, modes);
-       linkmode_or(support, support, modes);
---- a/drivers/net/phy/sfp.c
-+++ b/drivers/net/phy/sfp.c
-@@ -327,6 +327,15 @@ static void sfp_fixup_ignore_tx_fault(st
-       sfp->tx_fault_ignore = true;
- }
-+static void sfp_fixup_halny_gsfp(struct sfp *sfp)
-+{
-+      /* Ignore the TX_FAULT and LOS signals on this module.
-+       * these are possibly used for other purposes on this
-+       * module, e.g. a serial port.
-+       */
-+      sfp->state_hw_mask &= ~(SFP_F_TX_FAULT | SFP_F_LOS);
-+}
-+
- static void sfp_quirk_2500basex(const struct sfp_eeprom_id *id,
-                               unsigned long *modes)
- {
-@@ -359,6 +368,10 @@ static const struct sfp_quirk sfp_quirks
-               .modes = sfp_quirk_2500basex,
-               .fixup = sfp_fixup_long_startup,
-       }, {
-+              .vendor = "HALNy",
-+              .part = "HL-GSFP",
-+              .fixup = sfp_fixup_halny_gsfp,
-+      }, {
-               // Huawei MA5671A can operate at 2500base-X, but report 1.2GBd
-               // NRZ in their EEPROM
-               .vendor = "HUAWEI",
-@@ -375,16 +388,18 @@ static const struct sfp_quirk sfp_quirks
-               .vendor = "UBNT",
-               .part = "UF-INSTANT",
-               .modes = sfp_quirk_ubnt_uf_instant,
--      },
-+      }
- };
- static size_t sfp_strlen(const char *str, size_t maxlen)
- {
-       size_t size, i;
--      /* Trailing characters should be filled with space chars */
-+      /* Trailing characters should be filled with space chars, but
-+       * some manufacturers can't read SFF-8472 and use NUL.
-+       */
-       for (i = 0, size = 0; i < maxlen; i++)
--              if (str[i] != ' ')
-+              if (str[i] != ' ' && str[i] != '\0')
-                       size = i + 1;
-       return size;
diff --git a/target/linux/generic/backport-5.15/788-v6.3-net-dsa-mt7530-use-external-PCS-driver.patch b/target/linux/generic/backport-5.15/788-v6.3-net-dsa-mt7530-use-external-PCS-driver.patch
deleted file mode 100644 (file)
index 8060ad5..0000000
+++ /dev/null
@@ -1,514 +0,0 @@
-From patchwork Thu Mar  9 10:57:44 2023
-Content-Type: text/plain; charset="utf-8"
-MIME-Version: 1.0
-Content-Transfer-Encoding: 8bit
-X-Patchwork-Submitter: Daniel Golle <[email protected]>
-X-Patchwork-Id: 13167235
-X-Patchwork-Delegate: [email protected]
-Return-Path: <[email protected]>
-Date: Thu, 9 Mar 2023 10:57:44 +0000
-From: Daniel Golle <[email protected]>
-        Russell King <[email protected]>,
-        Heiner Kallweit <[email protected]>,
-        Lorenzo Bianconi <[email protected]>,
-        Mark Lee <[email protected]>,
-        John Crispin <[email protected]>, Felix Fietkau <[email protected]>,
-        AngeloGioacchino Del Regno
-        <[email protected]>,
-        Matthias Brugger <[email protected]>,
-        DENG Qingfang <[email protected]>,
-        Landen Chao <[email protected]>,
-        Sean Wang <[email protected]>,
-        Paolo Abeni <[email protected]>,
-        Jakub Kicinski <[email protected]>,
-        Eric Dumazet <[email protected]>,
-        "David S. Miller" <[email protected]>,
-        Vladimir Oltean <[email protected]>,
-        Florian Fainelli <[email protected]>,
-        Andrew Lunn <[email protected]>,
-        Vladimir Oltean <[email protected]>
-Cc: =?iso-8859-1?q?Bj=F8rn?= Mork <[email protected]>,
- Frank Wunderlich <[email protected]>,
- Alexander Couzens <[email protected]>
-Subject: [PATCH net-next v13 11/16] net: dsa: mt7530: use external PCS driver
-Message-ID: 
- <2ac2ee40d3b0e705461b50613fda6a7edfdbc4b3.1678357225.git.daniel@makrotopia.org>
-References: <[email protected]>
-MIME-Version: 1.0
-Content-Disposition: inline
-In-Reply-To: <[email protected]>
-Precedence: bulk
-List-ID: <netdev.vger.kernel.org>
-X-Mailing-List: [email protected]
-X-Patchwork-Delegate: [email protected]
-
-Implement regmap access wrappers, for now only to be used by the
-pcs-mtk driver.
-Make use of external PCS driver and drop the reduntant implementation
-in mt7530.c.
-As a nice side effect the SGMII registers can now also more easily be
-inspected for debugging via /sys/kernel/debug/regmap.
-
-Reviewed-by: Russell King (Oracle) <[email protected]>
-Tested-by: Bjørn Mork <[email protected]>
-Signed-off-by: Daniel Golle <[email protected]>
-Tested-by: Frank Wunderlich <[email protected]>
----
- drivers/net/dsa/Kconfig  |   1 +
- drivers/net/dsa/mt7530.c | 277 ++++++++++-----------------------------
- drivers/net/dsa/mt7530.h |  47 +------
- 3 files changed, 71 insertions(+), 254 deletions(-)
-
---- a/drivers/net/dsa/Kconfig
-+++ b/drivers/net/dsa/Kconfig
-@@ -37,6 +37,7 @@ config NET_DSA_MT7530
-       tristate "MediaTek MT753x and MT7621 Ethernet switch support"
-       select NET_DSA_TAG_MTK
-       select MEDIATEK_GE_PHY
-+      select PCS_MTK_LYNXI
-       help
-         This enables support for the MediaTek MT7530, MT7531, and MT7621
-         Ethernet switch chips.
---- a/drivers/net/dsa/mt7530.c
-+++ b/drivers/net/dsa/mt7530.c
-@@ -14,6 +14,7 @@
- #include <linux/of_mdio.h>
- #include <linux/of_net.h>
- #include <linux/of_platform.h>
-+#include <linux/pcs/pcs-mtk-lynxi.h>
- #include <linux/phylink.h>
- #include <linux/regmap.h>
- #include <linux/regulator/consumer.h>
-@@ -2831,128 +2832,11 @@ static int mt7531_rgmii_setup(struct mt7
-       return 0;
- }
--static void mt7531_pcs_link_up(struct phylink_pcs *pcs, unsigned int mode,
--                             phy_interface_t interface, int speed, int duplex)
--{
--      struct mt7530_priv *priv = pcs_to_mt753x_pcs(pcs)->priv;
--      int port = pcs_to_mt753x_pcs(pcs)->port;
--      unsigned int val;
--
--      /* For adjusting speed and duplex of SGMII force mode. */
--      if (interface != PHY_INTERFACE_MODE_SGMII ||
--          phylink_autoneg_inband(mode))
--              return;
--
--      /* SGMII force mode setting */
--      val = mt7530_read(priv, MT7531_SGMII_MODE(port));
--      val &= ~MT7531_SGMII_IF_MODE_MASK;
--
--      switch (speed) {
--      case SPEED_10:
--              val |= MT7531_SGMII_FORCE_SPEED_10;
--              break;
--      case SPEED_100:
--              val |= MT7531_SGMII_FORCE_SPEED_100;
--              break;
--      case SPEED_1000:
--              val |= MT7531_SGMII_FORCE_SPEED_1000;
--              break;
--      }
--
--      /* MT7531 SGMII 1G force mode can only work in full duplex mode,
--       * no matter MT7531_SGMII_FORCE_HALF_DUPLEX is set or not.
--       *
--       * The speed check is unnecessary as the MAC capabilities apply
--       * this restriction. --rmk
--       */
--      if ((speed == SPEED_10 || speed == SPEED_100) &&
--          duplex != DUPLEX_FULL)
--              val |= MT7531_SGMII_FORCE_HALF_DUPLEX;
--
--      mt7530_write(priv, MT7531_SGMII_MODE(port), val);
--}
--
- static bool mt753x_is_mac_port(u32 port)
- {
-       return (port == 5 || port == 6);
- }
--static int mt7531_sgmii_setup_mode_force(struct mt7530_priv *priv, u32 port,
--                                       phy_interface_t interface)
--{
--      u32 val;
--
--      if (!mt753x_is_mac_port(port))
--              return -EINVAL;
--
--      mt7530_set(priv, MT7531_QPHY_PWR_STATE_CTRL(port),
--                 MT7531_SGMII_PHYA_PWD);
--
--      val = mt7530_read(priv, MT7531_PHYA_CTRL_SIGNAL3(port));
--      val &= ~MT7531_RG_TPHY_SPEED_MASK;
--      /* Setup 2.5 times faster clock for 2.5Gbps data speeds with 10B/8B
--       * encoding.
--       */
--      val |= (interface == PHY_INTERFACE_MODE_2500BASEX) ?
--              MT7531_RG_TPHY_SPEED_3_125G : MT7531_RG_TPHY_SPEED_1_25G;
--      mt7530_write(priv, MT7531_PHYA_CTRL_SIGNAL3(port), val);
--
--      mt7530_clear(priv, MT7531_PCS_CONTROL_1(port), MT7531_SGMII_AN_ENABLE);
--
--      /* MT7531 SGMII 1G and 2.5G force mode can only work in full duplex
--       * mode, no matter MT7531_SGMII_FORCE_HALF_DUPLEX is set or not.
--       */
--      mt7530_rmw(priv, MT7531_SGMII_MODE(port),
--                 MT7531_SGMII_IF_MODE_MASK | MT7531_SGMII_REMOTE_FAULT_DIS,
--                 MT7531_SGMII_FORCE_SPEED_1000);
--
--      mt7530_write(priv, MT7531_QPHY_PWR_STATE_CTRL(port), 0);
--
--      return 0;
--}
--
--static int mt7531_sgmii_setup_mode_an(struct mt7530_priv *priv, int port,
--                                    phy_interface_t interface)
--{
--      if (!mt753x_is_mac_port(port))
--              return -EINVAL;
--
--      mt7530_set(priv, MT7531_QPHY_PWR_STATE_CTRL(port),
--                 MT7531_SGMII_PHYA_PWD);
--
--      mt7530_rmw(priv, MT7531_PHYA_CTRL_SIGNAL3(port),
--                 MT7531_RG_TPHY_SPEED_MASK, MT7531_RG_TPHY_SPEED_1_25G);
--
--      mt7530_set(priv, MT7531_SGMII_MODE(port),
--                 MT7531_SGMII_REMOTE_FAULT_DIS |
--                 MT7531_SGMII_SPEED_DUPLEX_AN);
--
--      mt7530_rmw(priv, MT7531_PCS_SPEED_ABILITY(port),
--                 MT7531_SGMII_TX_CONFIG_MASK, 1);
--
--      mt7530_set(priv, MT7531_PCS_CONTROL_1(port), MT7531_SGMII_AN_ENABLE);
--
--      mt7530_set(priv, MT7531_PCS_CONTROL_1(port), MT7531_SGMII_AN_RESTART);
--
--      mt7530_write(priv, MT7531_QPHY_PWR_STATE_CTRL(port), 0);
--
--      return 0;
--}
--
--static void mt7531_pcs_an_restart(struct phylink_pcs *pcs)
--{
--      struct mt7530_priv *priv = pcs_to_mt753x_pcs(pcs)->priv;
--      int port = pcs_to_mt753x_pcs(pcs)->port;
--      u32 val;
--
--      /* Only restart AN when AN is enabled */
--      val = mt7530_read(priv, MT7531_PCS_CONTROL_1(port));
--      if (val & MT7531_SGMII_AN_ENABLE) {
--              val |= MT7531_SGMII_AN_RESTART;
--              mt7530_write(priv, MT7531_PCS_CONTROL_1(port), val);
--      }
--}
--
- static int
- mt7531_mac_config(struct dsa_switch *ds, int port, unsigned int mode,
-                 phy_interface_t interface)
-@@ -2975,11 +2859,11 @@ mt7531_mac_config(struct dsa_switch *ds,
-               phydev = dp->slave->phydev;
-               return mt7531_rgmii_setup(priv, port, interface, phydev);
-       case PHY_INTERFACE_MODE_SGMII:
--              return mt7531_sgmii_setup_mode_an(priv, port, interface);
-       case PHY_INTERFACE_MODE_NA:
-       case PHY_INTERFACE_MODE_1000BASEX:
-       case PHY_INTERFACE_MODE_2500BASEX:
--              return mt7531_sgmii_setup_mode_force(priv, port, interface);
-+              /* handled in SGMII PCS driver */
-+              return 0;
-       default:
-               return -EINVAL;
-       }
-@@ -3004,11 +2888,11 @@ mt753x_phylink_mac_select_pcs(struct dsa
-       switch (interface) {
-       case PHY_INTERFACE_MODE_TRGMII:
-+              return &priv->pcs[port].pcs;
-       case PHY_INTERFACE_MODE_SGMII:
-       case PHY_INTERFACE_MODE_1000BASEX:
-       case PHY_INTERFACE_MODE_2500BASEX:
--              return &priv->pcs[port].pcs;
--
-+              return priv->ports[port].sgmii_pcs;
-       default:
-               return NULL;
-       }
-@@ -3249,86 +3133,6 @@ static void mt7530_pcs_get_state(struct
-               state->pause |= MLO_PAUSE_TX;
- }
--static int
--mt7531_sgmii_pcs_get_state_an(struct mt7530_priv *priv, int port,
--                            struct phylink_link_state *state)
--{
--      u32 status, val;
--      u16 config_reg;
--
--      status = mt7530_read(priv, MT7531_PCS_CONTROL_1(port));
--      state->link = !!(status & MT7531_SGMII_LINK_STATUS);
--      state->an_complete = !!(status & MT7531_SGMII_AN_COMPLETE);
--      if (state->interface == PHY_INTERFACE_MODE_SGMII &&
--          (status & MT7531_SGMII_AN_ENABLE)) {
--              val = mt7530_read(priv, MT7531_PCS_SPEED_ABILITY(port));
--              config_reg = val >> 16;
--
--              switch (config_reg & LPA_SGMII_SPD_MASK) {
--              case LPA_SGMII_1000:
--                      state->speed = SPEED_1000;
--                      break;
--              case LPA_SGMII_100:
--                      state->speed = SPEED_100;
--                      break;
--              case LPA_SGMII_10:
--                      state->speed = SPEED_10;
--                      break;
--              default:
--                      dev_err(priv->dev, "invalid sgmii PHY speed\n");
--                      state->link = false;
--                      return -EINVAL;
--              }
--
--              if (config_reg & LPA_SGMII_FULL_DUPLEX)
--                      state->duplex = DUPLEX_FULL;
--              else
--                      state->duplex = DUPLEX_HALF;
--      }
--
--      return 0;
--}
--
--static void
--mt7531_sgmii_pcs_get_state_inband(struct mt7530_priv *priv, int port,
--                                struct phylink_link_state *state)
--{
--      unsigned int val;
--
--      val = mt7530_read(priv, MT7531_PCS_CONTROL_1(port));
--      state->link = !!(val & MT7531_SGMII_LINK_STATUS);
--      if (!state->link)
--              return;
--
--      state->an_complete = state->link;
--
--      if (state->interface == PHY_INTERFACE_MODE_2500BASEX)
--              state->speed = SPEED_2500;
--      else
--              state->speed = SPEED_1000;
--
--      state->duplex = DUPLEX_FULL;
--      state->pause = MLO_PAUSE_NONE;
--}
--
--static void mt7531_pcs_get_state(struct phylink_pcs *pcs,
--                               struct phylink_link_state *state)
--{
--      struct mt7530_priv *priv = pcs_to_mt753x_pcs(pcs)->priv;
--      int port = pcs_to_mt753x_pcs(pcs)->port;
--
--      if (state->interface == PHY_INTERFACE_MODE_SGMII) {
--              mt7531_sgmii_pcs_get_state_an(priv, port, state);
--              return;
--      } else if ((state->interface == PHY_INTERFACE_MODE_1000BASEX) ||
--                 (state->interface == PHY_INTERFACE_MODE_2500BASEX)) {
--              mt7531_sgmii_pcs_get_state_inband(priv, port, state);
--              return;
--      }
--
--      state->link = false;
--}
--
- static int mt753x_pcs_config(struct phylink_pcs *pcs, unsigned int mode,
-                            phy_interface_t interface,
-                            const unsigned long *advertising,
-@@ -3348,18 +3152,57 @@ static const struct phylink_pcs_ops mt75
-       .pcs_an_restart = mt7530_pcs_an_restart,
- };
--static const struct phylink_pcs_ops mt7531_pcs_ops = {
--      .pcs_validate = mt753x_pcs_validate,
--      .pcs_get_state = mt7531_pcs_get_state,
--      .pcs_config = mt753x_pcs_config,
--      .pcs_an_restart = mt7531_pcs_an_restart,
--      .pcs_link_up = mt7531_pcs_link_up,
-+static int mt7530_regmap_read(void *context, unsigned int reg, unsigned int *val)
-+{
-+      struct mt7530_priv *priv = context;
-+
-+      *val = mt7530_read(priv, reg);
-+      return 0;
-+};
-+
-+static int mt7530_regmap_write(void *context, unsigned int reg, unsigned int val)
-+{
-+      struct mt7530_priv *priv = context;
-+
-+      mt7530_write(priv, reg, val);
-+      return 0;
-+};
-+
-+static int mt7530_regmap_update_bits(void *context, unsigned int reg,
-+                                   unsigned int mask, unsigned int val)
-+{
-+      struct mt7530_priv *priv = context;
-+
-+      mt7530_rmw(priv, reg, mask, val);
-+      return 0;
-+};
-+
-+static const struct regmap_bus mt7531_regmap_bus = {
-+      .reg_write = mt7530_regmap_write,
-+      .reg_read = mt7530_regmap_read,
-+      .reg_update_bits = mt7530_regmap_update_bits,
-+};
-+
-+#define MT7531_PCS_REGMAP_CONFIG(_name, _reg_base) \
-+      {                               \
-+              .name = _name,          \
-+              .reg_bits = 16,         \
-+              .val_bits = 32,         \
-+              .reg_stride = 4,        \
-+              .reg_base = _reg_base,  \
-+              .max_register = 0x17c,  \
-+      }
-+
-+static const struct regmap_config mt7531_pcs_config[] = {
-+      MT7531_PCS_REGMAP_CONFIG("port5", MT7531_SGMII_REG_BASE(5)),
-+      MT7531_PCS_REGMAP_CONFIG("port6", MT7531_SGMII_REG_BASE(6)),
- };
- static int
- mt753x_setup(struct dsa_switch *ds)
- {
-       struct mt7530_priv *priv = ds->priv;
-+      struct regmap *regmap;
-       int i, ret;
-       /* Initialise the PCS devices */
-@@ -3367,8 +3210,6 @@ mt753x_setup(struct dsa_switch *ds)
-               priv->pcs[i].pcs.ops = priv->info->pcs_ops;
-               priv->pcs[i].priv = priv;
-               priv->pcs[i].port = i;
--              if (mt753x_is_mac_port(i))
--                      priv->pcs[i].pcs.poll = 1;
-       }
-       ret = priv->info->sw_setup(ds);
-@@ -3383,6 +3224,16 @@ mt753x_setup(struct dsa_switch *ds)
-       if (ret && priv->irq)
-               mt7530_free_irq_common(priv);
-+      if (priv->id == ID_MT7531)
-+              for (i = 0; i < 2; i++) {
-+                      regmap = devm_regmap_init(ds->dev,
-+                                                &mt7531_regmap_bus, priv,
-+                                                &mt7531_pcs_config[i]);
-+                      priv->ports[5 + i].sgmii_pcs =
-+                              mtk_pcs_lynxi_create(ds->dev, regmap,
-+                                                   MT7531_PHYA_CTRL_SIGNAL3, 0);
-+              }
-+
-       return ret;
- }
-@@ -3475,7 +3326,7 @@ static const struct mt753x_info mt753x_t
-       },
-       [ID_MT7531] = {
-               .id = ID_MT7531,
--              .pcs_ops = &mt7531_pcs_ops,
-+              .pcs_ops = &mt7530_pcs_ops,
-               .sw_setup = mt7531_setup,
-               .phy_read = mt7531_ind_phy_read,
-               .phy_write = mt7531_ind_phy_write,
-@@ -3583,7 +3434,7 @@ static void
- mt7530_remove(struct mdio_device *mdiodev)
- {
-       struct mt7530_priv *priv = dev_get_drvdata(&mdiodev->dev);
--      int ret = 0;
-+      int ret = 0, i;
-       if (!priv)
-               return;
-@@ -3602,6 +3453,10 @@ mt7530_remove(struct mdio_device *mdiode
-               mt7530_free_irq(priv);
-       dsa_unregister_switch(priv->ds);
-+
-+      for (i = 0; i < 2; ++i)
-+              mtk_pcs_lynxi_destroy(priv->ports[5 + i].sgmii_pcs);
-+
-       mutex_destroy(&priv->reg_mutex);
-       dev_set_drvdata(&mdiodev->dev, NULL);
---- a/drivers/net/dsa/mt7530.h
-+++ b/drivers/net/dsa/mt7530.h
-@@ -401,47 +401,8 @@ enum mt7530_vlan_port_acc_frm {
-                                        CCR_TX_OCT_CNT_BAD)
- /* MT7531 SGMII register group */
--#define MT7531_SGMII_REG_BASE         0x5000
--#define MT7531_SGMII_REG(p, r)                (MT7531_SGMII_REG_BASE + \
--                                      ((p) - 5) * 0x1000 + (r))
--
--/* Register forSGMII PCS_CONTROL_1 */
--#define MT7531_PCS_CONTROL_1(p)               MT7531_SGMII_REG(p, 0x00)
--#define  MT7531_SGMII_LINK_STATUS     BIT(18)
--#define  MT7531_SGMII_AN_ENABLE               BIT(12)
--#define  MT7531_SGMII_AN_RESTART      BIT(9)
--#define  MT7531_SGMII_AN_COMPLETE     BIT(21)
--
--/* Register for SGMII PCS_SPPED_ABILITY */
--#define MT7531_PCS_SPEED_ABILITY(p)   MT7531_SGMII_REG(p, 0x08)
--#define  MT7531_SGMII_TX_CONFIG_MASK  GENMASK(15, 0)
--#define  MT7531_SGMII_TX_CONFIG               BIT(0)
--
--/* Register for SGMII_MODE */
--#define MT7531_SGMII_MODE(p)          MT7531_SGMII_REG(p, 0x20)
--#define  MT7531_SGMII_REMOTE_FAULT_DIS        BIT(8)
--#define  MT7531_SGMII_IF_MODE_MASK    GENMASK(5, 1)
--#define  MT7531_SGMII_FORCE_DUPLEX    BIT(4)
--#define  MT7531_SGMII_FORCE_SPEED_MASK        GENMASK(3, 2)
--#define  MT7531_SGMII_FORCE_SPEED_1000        BIT(3)
--#define  MT7531_SGMII_FORCE_SPEED_100 BIT(2)
--#define  MT7531_SGMII_FORCE_SPEED_10  0
--#define  MT7531_SGMII_SPEED_DUPLEX_AN BIT(1)
--
--enum mt7531_sgmii_force_duplex {
--      MT7531_SGMII_FORCE_FULL_DUPLEX = 0,
--      MT7531_SGMII_FORCE_HALF_DUPLEX = 0x10,
--};
--
--/* Fields of QPHY_PWR_STATE_CTRL */
--#define MT7531_QPHY_PWR_STATE_CTRL(p) MT7531_SGMII_REG(p, 0xe8)
--#define  MT7531_SGMII_PHYA_PWD                BIT(4)
--
--/* Values of SGMII SPEED */
--#define MT7531_PHYA_CTRL_SIGNAL3(p)   MT7531_SGMII_REG(p, 0x128)
--#define  MT7531_RG_TPHY_SPEED_MASK    (BIT(2) | BIT(3))
--#define  MT7531_RG_TPHY_SPEED_1_25G   0x0
--#define  MT7531_RG_TPHY_SPEED_3_125G  BIT(2)
-+#define MT7531_SGMII_REG_BASE(p)      (0x5000 + ((p) - 5) * 0x1000)
-+#define MT7531_PHYA_CTRL_SIGNAL3      0x128
- /* Register for system reset */
- #define MT7530_SYS_CTRL                       0x7000
-@@ -741,13 +702,13 @@ struct mt7530_fdb {
-  * @pm:               The matrix used to show all connections with the port.
-  * @pvid:     The VLAN specified is to be considered a PVID at ingress.  Any
-  *            untagged frames will be assigned to the related VLAN.
-- * @vlan_filtering: The flags indicating whether the port that can recognize
-- *                VLAN-tagged frames.
-+ * @sgmii_pcs:        Pointer to PCS instance for SerDes ports
-  */
- struct mt7530_port {
-       bool enable;
-       u32 pm;
-       u16 pvid;
-+      struct phylink_pcs *sgmii_pcs;
- };
- /* Port 5 interface select definitions */
diff --git a/target/linux/generic/backport-5.15/789-v6.3-net-sfp-add-quirk-enabling-2500Base-x-for-HG-MXPD-48.patch b/target/linux/generic/backport-5.15/789-v6.3-net-sfp-add-quirk-enabling-2500Base-x-for-HG-MXPD-48.patch
deleted file mode 100644 (file)
index 413c73f..0000000
+++ /dev/null
@@ -1,37 +0,0 @@
-From ad651d68cee75e9ac20002254c4e5d09ee67a84b Mon Sep 17 00:00:00 2001
-From: Daniel Golle <[email protected]>
-Date: Sun, 2 Apr 2023 12:44:37 +0100
-Subject: [PATCH] net: sfp: add quirk enabling 2500Base-x for HG MXPD-483II
-
-The HG MXPD-483II 1310nm SFP module is meant to operate with 2500Base-X,
-however, in their EEPROM they incorrectly specify:
-    Transceiver type                          : Ethernet: 1000BASE-LX
-    ...
-    BR, Nominal                               : 2600MBd
-
-Use sfp_quirk_2500basex for this module to allow 2500Base-X mode anyway.
-
-https://forum.banana-pi.org/t/bpi-r3-sfp-module-compatibility/14573/60
-
-Reported-by: chowtom <[email protected]>
-Tested-by: chowtom <[email protected]>
-Signed-off-by: Daniel Golle <[email protected]>
-Reviewed-by: Russell King (Oracle) <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/phy/sfp.c | 4 ++++
- 1 file changed, 4 insertions(+)
-
---- a/drivers/net/phy/sfp.c
-+++ b/drivers/net/phy/sfp.c
-@@ -372,6 +372,10 @@ static const struct sfp_quirk sfp_quirks
-               .part = "HL-GSFP",
-               .fixup = sfp_fixup_halny_gsfp,
-       }, {
-+              .vendor = "HG GENUINE",
-+              .part = "MXPD-483II",
-+              .modes = sfp_quirk_2500basex,
-+      }, {
-               // Huawei MA5671A can operate at 2500base-X, but report 1.2GBd
-               // NRZ in their EEPROM
-               .vendor = "HUAWEI",
diff --git a/target/linux/generic/backport-5.15/790-v6.0-net-mii-add-mii_bmcr_encode_fixed.patch b/target/linux/generic/backport-5.15/790-v6.0-net-mii-add-mii_bmcr_encode_fixed.patch
deleted file mode 100644 (file)
index 87d7ff6..0000000
+++ /dev/null
@@ -1,55 +0,0 @@
-From bdb6cfe7512f7a214815a3092f0be50963dcacbc Mon Sep 17 00:00:00 2001
-From: "Russell King (Oracle)" <[email protected]>
-Date: Sat, 18 Jun 2022 11:28:32 +0100
-Subject: [PATCH] net: mii: add mii_bmcr_encode_fixed()
-
-Add a function to encode a fixed speed/duplex to a BMCR value.
-
-Signed-off-by: Russell King (Oracle) <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- include/linux/mii.h | 35 +++++++++++++++++++++++++++++++++++
- 1 file changed, 35 insertions(+)
-
---- a/include/linux/mii.h
-+++ b/include/linux/mii.h
-@@ -595,4 +595,39 @@ static inline u8 mii_resolve_flowctrl_fd
-       return cap;
- }
-+/**
-+ * mii_bmcr_encode_fixed - encode fixed speed/duplex settings to a BMCR value
-+ * @speed: a SPEED_* value
-+ * @duplex: a DUPLEX_* value
-+ *
-+ * Encode the speed and duplex to a BMCR value. 2500, 1000, 100 and 10 Mbps are
-+ * supported. 2500Mbps is encoded to 1000Mbps. Other speeds are encoded as 10
-+ * Mbps. Unknown duplex values are encoded to half-duplex.
-+ */
-+static inline u16 mii_bmcr_encode_fixed(int speed, int duplex)
-+{
-+      u16 bmcr;
-+
-+      switch (speed) {
-+      case SPEED_2500:
-+      case SPEED_1000:
-+              bmcr = BMCR_SPEED1000;
-+              break;
-+
-+      case SPEED_100:
-+              bmcr = BMCR_SPEED100;
-+              break;
-+
-+      case SPEED_10:
-+      default:
-+              bmcr = BMCR_SPEED10;
-+              break;
-+      }
-+
-+      if (duplex == DUPLEX_FULL)
-+              bmcr |= BMCR_FULLDPLX;
-+
-+      return bmcr;
-+}
-+
- #endif /* __LINUX_MII_H__ */
diff --git a/target/linux/generic/backport-5.15/790-v6.4-0001-net-dsa-mt7530-make-some-noise-if-register-read-fail.patch b/target/linux/generic/backport-5.15/790-v6.4-0001-net-dsa-mt7530-make-some-noise-if-register-read-fail.patch
deleted file mode 100644 (file)
index cfd0034..0000000
+++ /dev/null
@@ -1,32 +0,0 @@
-From b6f56cddb5f57a0b8da0ce582232a2f1933558c6 Mon Sep 17 00:00:00 2001
-From: Daniel Golle <[email protected]>
-Date: Mon, 3 Apr 2023 02:17:19 +0100
-Subject: [PATCH 04/16] net: dsa: mt7530: make some noise if register read
- fails
-
-Simply returning the negative error value instead of the read value
-doesn't seem like a good idea. Return 0 instead and add WARN_ON_ONCE(1)
-so this kind of error will not go unnoticed.
-
-Suggested-by: Andrew Lunn <[email protected]>
-Signed-off-by: Daniel Golle <[email protected]>
-Reviewed-by: Andrew Lunn <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/dsa/mt7530.c | 3 ++-
- 1 file changed, 2 insertions(+), 1 deletion(-)
-
---- a/drivers/net/dsa/mt7530.c
-+++ b/drivers/net/dsa/mt7530.c
-@@ -225,9 +225,10 @@ mt7530_mii_read(struct mt7530_priv *priv
-       /* MT7530 uses 31 as the pseudo port */
-       ret = bus->write(bus, 0x1f, 0x1f, page);
-       if (ret < 0) {
-+              WARN_ON_ONCE(1);
-               dev_err(&bus->dev,
-                       "failed to read mt7530 register\n");
--              return ret;
-+              return 0;
-       }
-       lo = bus->read(bus, 0x1f, r);
diff --git a/target/linux/generic/backport-5.15/790-v6.4-0002-net-dsa-mt7530-refactor-SGMII-PCS-creation.patch b/target/linux/generic/backport-5.15/790-v6.4-0002-net-dsa-mt7530-refactor-SGMII-PCS-creation.patch
deleted file mode 100644 (file)
index 62d9c78..0000000
+++ /dev/null
@@ -1,111 +0,0 @@
-From 9ecc00164dc2300dfcd40afe549a8ee951dfea9f Mon Sep 17 00:00:00 2001
-From: Daniel Golle <[email protected]>
-Date: Mon, 3 Apr 2023 02:17:30 +0100
-Subject: [PATCH 05/16] net: dsa: mt7530: refactor SGMII PCS creation
-
-Instead of macro templates use a dedidated function and allocated
-regmap_config when creating the regmaps for the pcs-mtk-lynxi
-instances.
-This is in preparation to switching to use unlocked regmap accessors
-and have regmap's locking API handle locking for us.
-
-Signed-off-by: Daniel Golle <[email protected]>
-Reviewed-by: Andrew Lunn <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/dsa/mt7530.c | 74 +++++++++++++++++++++++++++-------------
- 1 file changed, 50 insertions(+), 24 deletions(-)
-
---- a/drivers/net/dsa/mt7530.c
-+++ b/drivers/net/dsa/mt7530.c
-@@ -3184,26 +3184,56 @@ static const struct regmap_bus mt7531_re
-       .reg_update_bits = mt7530_regmap_update_bits,
- };
--#define MT7531_PCS_REGMAP_CONFIG(_name, _reg_base) \
--      {                               \
--              .name = _name,          \
--              .reg_bits = 16,         \
--              .val_bits = 32,         \
--              .reg_stride = 4,        \
--              .reg_base = _reg_base,  \
--              .max_register = 0x17c,  \
-+static int
-+mt7531_create_sgmii(struct mt7530_priv *priv)
-+{
-+      struct regmap_config *mt7531_pcs_config[2];
-+      struct phylink_pcs *pcs;
-+      struct regmap *regmap;
-+      int i, ret = 0;
-+
-+      for (i = 0; i < 2; i++) {
-+              mt7531_pcs_config[i] = devm_kzalloc(priv->dev,
-+                                                  sizeof(struct regmap_config),
-+                                                  GFP_KERNEL);
-+              if (!mt7531_pcs_config[i]) {
-+                      ret = -ENOMEM;
-+                      break;
-+              }
-+
-+              mt7531_pcs_config[i]->name = i ? "port6" : "port5";
-+              mt7531_pcs_config[i]->reg_bits = 16;
-+              mt7531_pcs_config[i]->val_bits = 32;
-+              mt7531_pcs_config[i]->reg_stride = 4;
-+              mt7531_pcs_config[i]->reg_base = MT7531_SGMII_REG_BASE(5 + i);
-+              mt7531_pcs_config[i]->max_register = 0x17c;
-+
-+              regmap = devm_regmap_init(priv->dev,
-+                                        &mt7531_regmap_bus, priv,
-+                                        mt7531_pcs_config[i]);
-+              if (IS_ERR(regmap)) {
-+                      ret = PTR_ERR(regmap);
-+                      break;
-+              }
-+              pcs = mtk_pcs_lynxi_create(priv->dev, regmap,
-+                                         MT7531_PHYA_CTRL_SIGNAL3, 0);
-+              if (!pcs) {
-+                      ret = -ENXIO;
-+                      break;
-+              }
-+              priv->ports[5 + i].sgmii_pcs = pcs;
-       }
--static const struct regmap_config mt7531_pcs_config[] = {
--      MT7531_PCS_REGMAP_CONFIG("port5", MT7531_SGMII_REG_BASE(5)),
--      MT7531_PCS_REGMAP_CONFIG("port6", MT7531_SGMII_REG_BASE(6)),
--};
-+      if (ret && i)
-+              mtk_pcs_lynxi_destroy(priv->ports[5].sgmii_pcs);
-+
-+      return ret;
-+}
- static int
- mt753x_setup(struct dsa_switch *ds)
- {
-       struct mt7530_priv *priv = ds->priv;
--      struct regmap *regmap;
-       int i, ret;
-       /* Initialise the PCS devices */
-@@ -3225,15 +3255,11 @@ mt753x_setup(struct dsa_switch *ds)
-       if (ret && priv->irq)
-               mt7530_free_irq_common(priv);
--      if (priv->id == ID_MT7531)
--              for (i = 0; i < 2; i++) {
--                      regmap = devm_regmap_init(ds->dev,
--                                                &mt7531_regmap_bus, priv,
--                                                &mt7531_pcs_config[i]);
--                      priv->ports[5 + i].sgmii_pcs =
--                              mtk_pcs_lynxi_create(ds->dev, regmap,
--                                                   MT7531_PHYA_CTRL_SIGNAL3, 0);
--              }
-+      if (priv->id == ID_MT7531) {
-+              ret = mt7531_create_sgmii(priv);
-+              if (ret && priv->irq)
-+                      mt7530_free_irq_common(priv);
-+      }
-       return ret;
- }
diff --git a/target/linux/generic/backport-5.15/790-v6.4-0003-net-dsa-mt7530-use-unlocked-regmap-accessors.patch b/target/linux/generic/backport-5.15/790-v6.4-0003-net-dsa-mt7530-use-unlocked-regmap-accessors.patch
deleted file mode 100644 (file)
index e9f69a8..0000000
+++ /dev/null
@@ -1,74 +0,0 @@
-From 1bd099c49f65ed923b9f19b8c4b3cd1ff0024091 Mon Sep 17 00:00:00 2001
-From: Daniel Golle <[email protected]>
-Date: Mon, 3 Apr 2023 02:17:40 +0100
-Subject: [PATCH 06/16] net: dsa: mt7530: use unlocked regmap accessors
-
-Instead of wrapping the locked register accessor functions, use the
-unlocked variants and add locking wrapper functions to let regmap
-handle the locking.
-
-This is a preparation towards being able to always use regmap to
-access switch registers instead of open-coded accessor functions.
-
-Signed-off-by: Daniel Golle <[email protected]>
-Reviewed-by: Andrew Lunn <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/dsa/mt7530.c | 23 ++++++++++++++---------
- 1 file changed, 14 insertions(+), 9 deletions(-)
-
---- a/drivers/net/dsa/mt7530.c
-+++ b/drivers/net/dsa/mt7530.c
-@@ -3157,7 +3157,7 @@ static int mt7530_regmap_read(void *cont
- {
-       struct mt7530_priv *priv = context;
--      *val = mt7530_read(priv, reg);
-+      *val = mt7530_mii_read(priv, reg);
-       return 0;
- };
-@@ -3165,23 +3165,25 @@ static int mt7530_regmap_write(void *con
- {
-       struct mt7530_priv *priv = context;
--      mt7530_write(priv, reg, val);
-+      mt7530_mii_write(priv, reg, val);
-       return 0;
- };
--static int mt7530_regmap_update_bits(void *context, unsigned int reg,
--                                   unsigned int mask, unsigned int val)
-+static void
-+mt7530_mdio_regmap_lock(void *mdio_lock)
- {
--      struct mt7530_priv *priv = context;
-+      mutex_lock_nested(mdio_lock, MDIO_MUTEX_NESTED);
-+}
--      mt7530_rmw(priv, reg, mask, val);
--      return 0;
--};
-+static void
-+mt7530_mdio_regmap_unlock(void *mdio_lock)
-+{
-+      mutex_unlock(mdio_lock);
-+}
- static const struct regmap_bus mt7531_regmap_bus = {
-       .reg_write = mt7530_regmap_write,
-       .reg_read = mt7530_regmap_read,
--      .reg_update_bits = mt7530_regmap_update_bits,
- };
- static int
-@@ -3207,6 +3209,9 @@ mt7531_create_sgmii(struct mt7530_priv *
-               mt7531_pcs_config[i]->reg_stride = 4;
-               mt7531_pcs_config[i]->reg_base = MT7531_SGMII_REG_BASE(5 + i);
-               mt7531_pcs_config[i]->max_register = 0x17c;
-+              mt7531_pcs_config[i]->lock = mt7530_mdio_regmap_lock;
-+              mt7531_pcs_config[i]->unlock = mt7530_mdio_regmap_unlock;
-+              mt7531_pcs_config[i]->lock_arg = &priv->bus->mdio_lock;
-               regmap = devm_regmap_init(priv->dev,
-                                         &mt7531_regmap_bus, priv,
diff --git a/target/linux/generic/backport-5.15/790-v6.4-0004-net-dsa-mt7530-use-regmap-to-access-switch-register-.patch b/target/linux/generic/backport-5.15/790-v6.4-0004-net-dsa-mt7530-use-regmap-to-access-switch-register-.patch
deleted file mode 100644 (file)
index a2dcc08..0000000
+++ /dev/null
@@ -1,224 +0,0 @@
-From a08c045580e060a6886bbb656c50ae20b0c780b5 Mon Sep 17 00:00:00 2001
-From: Daniel Golle <[email protected]>
-Date: Mon, 3 Apr 2023 02:17:52 +0100
-Subject: [PATCH 07/16] net: dsa: mt7530: use regmap to access switch register
- space
-
-Use regmap API to access the switch register space.
-
-Signed-off-by: Daniel Golle <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/dsa/mt7530.c | 99 ++++++++++++++++++++++++----------------
- drivers/net/dsa/mt7530.h |  2 +
- 2 files changed, 62 insertions(+), 39 deletions(-)
-
---- a/drivers/net/dsa/mt7530.c
-+++ b/drivers/net/dsa/mt7530.c
-@@ -184,9 +184,9 @@ core_clear(struct mt7530_priv *priv, u32
- }
- static int
--mt7530_mii_write(struct mt7530_priv *priv, u32 reg, u32 val)
-+mt7530_regmap_write(void *context, unsigned int reg, unsigned int val)
- {
--      struct mii_bus *bus = priv->bus;
-+      struct mii_bus *bus = context;
-       u16 page, r, lo, hi;
-       int ret;
-@@ -198,24 +198,34 @@ mt7530_mii_write(struct mt7530_priv *pri
-       /* MT7530 uses 31 as the pseudo port */
-       ret = bus->write(bus, 0x1f, 0x1f, page);
-       if (ret < 0)
--              goto err;
-+              return ret;
-       ret = bus->write(bus, 0x1f, r,  lo);
-       if (ret < 0)
--              goto err;
-+              return ret;
-       ret = bus->write(bus, 0x1f, 0x10, hi);
--err:
-+      return ret;
-+}
-+
-+static int
-+mt7530_mii_write(struct mt7530_priv *priv, u32 reg, u32 val)
-+{
-+      int ret;
-+
-+      ret = regmap_write(priv->regmap, reg, val);
-+
-       if (ret < 0)
--              dev_err(&bus->dev,
-+              dev_err(priv->dev,
-                       "failed to write mt7530 register\n");
-+
-       return ret;
- }
--static u32
--mt7530_mii_read(struct mt7530_priv *priv, u32 reg)
-+static int
-+mt7530_regmap_read(void *context, unsigned int reg, unsigned int *val)
- {
--      struct mii_bus *bus = priv->bus;
-+      struct mii_bus *bus = context;
-       u16 page, r, lo, hi;
-       int ret;
-@@ -224,17 +234,32 @@ mt7530_mii_read(struct mt7530_priv *priv
-       /* MT7530 uses 31 as the pseudo port */
-       ret = bus->write(bus, 0x1f, 0x1f, page);
--      if (ret < 0) {
-+      if (ret < 0)
-+              return ret;
-+
-+      lo = bus->read(bus, 0x1f, r);
-+      hi = bus->read(bus, 0x1f, 0x10);
-+
-+      *val = (hi << 16) | (lo & 0xffff);
-+
-+      return 0;
-+}
-+
-+static u32
-+mt7530_mii_read(struct mt7530_priv *priv, u32 reg)
-+{
-+      int ret;
-+      u32 val;
-+
-+      ret = regmap_read(priv->regmap, reg, &val);
-+      if (ret) {
-               WARN_ON_ONCE(1);
--              dev_err(&bus->dev,
-+              dev_err(priv->dev,
-                       "failed to read mt7530 register\n");
-               return 0;
-       }
--      lo = bus->read(bus, 0x1f, r);
--      hi = bus->read(bus, 0x1f, 0x10);
--
--      return (hi << 16) | (lo & 0xffff);
-+      return val;
- }
- static void
-@@ -284,14 +309,10 @@ mt7530_rmw(struct mt7530_priv *priv, u32
-          u32 mask, u32 set)
- {
-       struct mii_bus *bus = priv->bus;
--      u32 val;
-       mutex_lock_nested(&bus->mdio_lock, MDIO_MUTEX_NESTED);
--      val = mt7530_mii_read(priv, reg);
--      val &= ~mask;
--      val |= set;
--      mt7530_mii_write(priv, reg, val);
-+      regmap_update_bits(priv->regmap, reg, mask, set);
-       mutex_unlock(&bus->mdio_lock);
- }
-@@ -299,7 +320,7 @@ mt7530_rmw(struct mt7530_priv *priv, u32
- static void
- mt7530_set(struct mt7530_priv *priv, u32 reg, u32 val)
- {
--      mt7530_rmw(priv, reg, 0, val);
-+      mt7530_rmw(priv, reg, val, val);
- }
- static void
-@@ -3153,22 +3174,6 @@ static const struct phylink_pcs_ops mt75
-       .pcs_an_restart = mt7530_pcs_an_restart,
- };
--static int mt7530_regmap_read(void *context, unsigned int reg, unsigned int *val)
--{
--      struct mt7530_priv *priv = context;
--
--      *val = mt7530_mii_read(priv, reg);
--      return 0;
--};
--
--static int mt7530_regmap_write(void *context, unsigned int reg, unsigned int val)
--{
--      struct mt7530_priv *priv = context;
--
--      mt7530_mii_write(priv, reg, val);
--      return 0;
--};
--
- static void
- mt7530_mdio_regmap_lock(void *mdio_lock)
- {
-@@ -3181,7 +3186,7 @@ mt7530_mdio_regmap_unlock(void *mdio_loc
-       mutex_unlock(mdio_lock);
- }
--static const struct regmap_bus mt7531_regmap_bus = {
-+static const struct regmap_bus mt7530_regmap_bus = {
-       .reg_write = mt7530_regmap_write,
-       .reg_read = mt7530_regmap_read,
- };
-@@ -3214,7 +3219,7 @@ mt7531_create_sgmii(struct mt7530_priv *
-               mt7531_pcs_config[i]->lock_arg = &priv->bus->mdio_lock;
-               regmap = devm_regmap_init(priv->dev,
--                                        &mt7531_regmap_bus, priv,
-+                                        &mt7530_regmap_bus, priv->bus,
-                                         mt7531_pcs_config[i]);
-               if (IS_ERR(regmap)) {
-                       ret = PTR_ERR(regmap);
-@@ -3380,6 +3385,7 @@ MODULE_DEVICE_TABLE(of, mt7530_of_match)
- static int
- mt7530_probe(struct mdio_device *mdiodev)
- {
-+      static struct regmap_config *regmap_config;
-       struct mt7530_priv *priv;
-       struct device_node *dn;
-@@ -3459,6 +3465,21 @@ mt7530_probe(struct mdio_device *mdiodev
-       mutex_init(&priv->reg_mutex);
-       dev_set_drvdata(&mdiodev->dev, priv);
-+      regmap_config = devm_kzalloc(&mdiodev->dev, sizeof(*regmap_config),
-+                                   GFP_KERNEL);
-+      if (!regmap_config)
-+              return -ENOMEM;
-+
-+      regmap_config->reg_bits = 16;
-+      regmap_config->val_bits = 32;
-+      regmap_config->reg_stride = 4;
-+      regmap_config->max_register = MT7530_CREV;
-+      regmap_config->disable_locking = true;
-+      priv->regmap = devm_regmap_init(priv->dev, &mt7530_regmap_bus,
-+                                      priv->bus, regmap_config);
-+      if (IS_ERR(priv->regmap))
-+              return PTR_ERR(priv->regmap);
-+
-       return dsa_register_switch(priv->ds);
- }
---- a/drivers/net/dsa/mt7530.h
-+++ b/drivers/net/dsa/mt7530.h
-@@ -785,6 +785,7 @@ struct mt753x_info {
-  * @dev:              The device pointer
-  * @ds:                       The pointer to the dsa core structure
-  * @bus:              The bus used for the device and built-in PHY
-+ * @regmap:           The regmap instance representing all switch registers
-  * @rstc:             The pointer to reset control used by MCM
-  * @core_pwr:         The power supplied into the core
-  * @io_pwr:           The power supplied into the I/O
-@@ -805,6 +806,7 @@ struct mt7530_priv {
-       struct device           *dev;
-       struct dsa_switch       *ds;
-       struct mii_bus          *bus;
-+      struct regmap           *regmap;
-       struct reset_control    *rstc;
-       struct regulator        *core_pwr;
-       struct regulator        *io_pwr;
diff --git a/target/linux/generic/backport-5.15/790-v6.4-0005-net-dsa-mt7530-move-SGMII-PCS-creation-to-mt7530_pro.patch b/target/linux/generic/backport-5.15/790-v6.4-0005-net-dsa-mt7530-move-SGMII-PCS-creation-to-mt7530_pro.patch
deleted file mode 100644 (file)
index abbecd5..0000000
+++ /dev/null
@@ -1,54 +0,0 @@
-From 6de2852297737171ba96b91e89bf302ca1fda869 Mon Sep 17 00:00:00 2001
-From: Daniel Golle <[email protected]>
-Date: Mon, 3 Apr 2023 02:18:04 +0100
-Subject: [PATCH 08/16] net: dsa: mt7530: move SGMII PCS creation to
- mt7530_probe function
-
-Move creating the SGMII PCS from mt753x_setup() to the more appropriate
-mt7530_probe() function.
-This is done also in preparation of moving all functions related to
-MDIO-connected MT753x switches to a separate module.
-
-Signed-off-by: Daniel Golle <[email protected]>
-Reviewed-by: Andrew Lunn <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/dsa/mt7530.c | 13 +++++++------
- 1 file changed, 7 insertions(+), 6 deletions(-)
-
---- a/drivers/net/dsa/mt7530.c
-+++ b/drivers/net/dsa/mt7530.c
-@@ -3265,12 +3265,6 @@ mt753x_setup(struct dsa_switch *ds)
-       if (ret && priv->irq)
-               mt7530_free_irq_common(priv);
--      if (priv->id == ID_MT7531) {
--              ret = mt7531_create_sgmii(priv);
--              if (ret && priv->irq)
--                      mt7530_free_irq_common(priv);
--      }
--
-       return ret;
- }
-@@ -3388,6 +3382,7 @@ mt7530_probe(struct mdio_device *mdiodev
-       static struct regmap_config *regmap_config;
-       struct mt7530_priv *priv;
-       struct device_node *dn;
-+      int ret;
-       dn = mdiodev->dev.of_node;
-@@ -3480,6 +3475,12 @@ mt7530_probe(struct mdio_device *mdiodev
-       if (IS_ERR(priv->regmap))
-               return PTR_ERR(priv->regmap);
-+      if (priv->id == ID_MT7531) {
-+              ret = mt7531_create_sgmii(priv);
-+              if (ret)
-+                      return ret;
-+      }
-+
-       return dsa_register_switch(priv->ds);
- }
diff --git a/target/linux/generic/backport-5.15/790-v6.4-0006-net-dsa-mt7530-introduce-mutex-helpers.patch b/target/linux/generic/backport-5.15/790-v6.4-0006-net-dsa-mt7530-introduce-mutex-helpers.patch
deleted file mode 100644 (file)
index ef02d46..0000000
+++ /dev/null
@@ -1,273 +0,0 @@
-From 1557c679f71c82a994eae0baadbaeb62b71e15bf Mon Sep 17 00:00:00 2001
-From: Daniel Golle <[email protected]>
-Date: Mon, 3 Apr 2023 02:18:16 +0100
-Subject: [PATCH 09/16] net: dsa: mt7530: introduce mutex helpers
-
-As the MDIO bus lock only needs to be involved if actually operating
-on an MDIO-connected switch we will need to skip locking for built-in
-switches which are accessed via MMIO.
-Create helper functions which simplify that upcoming change.
-
-Signed-off-by: Daniel Golle <[email protected]>
-Reviewed-by: Andrew Lunn <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/dsa/mt7530.c | 73 ++++++++++++++++++++--------------------
- 1 file changed, 36 insertions(+), 37 deletions(-)
-
---- a/drivers/net/dsa/mt7530.c
-+++ b/drivers/net/dsa/mt7530.c
-@@ -144,31 +144,40 @@ err:
- }
- static void
--core_write(struct mt7530_priv *priv, u32 reg, u32 val)
-+mt7530_mutex_lock(struct mt7530_priv *priv)
- {
--      struct mii_bus *bus = priv->bus;
-+      mutex_lock_nested(&priv->bus->mdio_lock, MDIO_MUTEX_NESTED);
-+}
--      mutex_lock_nested(&bus->mdio_lock, MDIO_MUTEX_NESTED);
-+static void
-+mt7530_mutex_unlock(struct mt7530_priv *priv)
-+{
-+      mutex_unlock(&priv->bus->mdio_lock);
-+}
-+
-+static void
-+core_write(struct mt7530_priv *priv, u32 reg, u32 val)
-+{
-+      mt7530_mutex_lock(priv);
-       core_write_mmd_indirect(priv, reg, MDIO_MMD_VEND2, val);
--      mutex_unlock(&bus->mdio_lock);
-+      mt7530_mutex_unlock(priv);
- }
- static void
- core_rmw(struct mt7530_priv *priv, u32 reg, u32 mask, u32 set)
- {
--      struct mii_bus *bus = priv->bus;
-       u32 val;
--      mutex_lock_nested(&bus->mdio_lock, MDIO_MUTEX_NESTED);
-+      mt7530_mutex_lock(priv);
-       val = core_read_mmd_indirect(priv, reg, MDIO_MMD_VEND2);
-       val &= ~mask;
-       val |= set;
-       core_write_mmd_indirect(priv, reg, MDIO_MMD_VEND2, val);
--      mutex_unlock(&bus->mdio_lock);
-+      mt7530_mutex_unlock(priv);
- }
- static void
-@@ -265,13 +274,11 @@ mt7530_mii_read(struct mt7530_priv *priv
- static void
- mt7530_write(struct mt7530_priv *priv, u32 reg, u32 val)
- {
--      struct mii_bus *bus = priv->bus;
--
--      mutex_lock_nested(&bus->mdio_lock, MDIO_MUTEX_NESTED);
-+      mt7530_mutex_lock(priv);
-       mt7530_mii_write(priv, reg, val);
--      mutex_unlock(&bus->mdio_lock);
-+      mt7530_mutex_unlock(priv);
- }
- static u32
-@@ -283,14 +290,13 @@ _mt7530_unlocked_read(struct mt7530_dumm
- static u32
- _mt7530_read(struct mt7530_dummy_poll *p)
- {
--      struct mii_bus          *bus = p->priv->bus;
-       u32 val;
--      mutex_lock_nested(&bus->mdio_lock, MDIO_MUTEX_NESTED);
-+      mt7530_mutex_lock(p->priv);
-       val = mt7530_mii_read(p->priv, p->reg);
--      mutex_unlock(&bus->mdio_lock);
-+      mt7530_mutex_unlock(p->priv);
-       return val;
- }
-@@ -308,13 +314,11 @@ static void
- mt7530_rmw(struct mt7530_priv *priv, u32 reg,
-          u32 mask, u32 set)
- {
--      struct mii_bus *bus = priv->bus;
--
--      mutex_lock_nested(&bus->mdio_lock, MDIO_MUTEX_NESTED);
-+      mt7530_mutex_lock(priv);
-       regmap_update_bits(priv->regmap, reg, mask, set);
--      mutex_unlock(&bus->mdio_lock);
-+      mt7530_mutex_unlock(priv);
- }
- static void
-@@ -660,14 +664,13 @@ static int
- mt7531_ind_c45_phy_read(struct mt7530_priv *priv, int port, int devad,
-                       int regnum)
- {
--      struct mii_bus *bus = priv->bus;
-       struct mt7530_dummy_poll p;
-       u32 reg, val;
-       int ret;
-       INIT_MT7530_DUMMY_POLL(&p, priv, MT7531_PHY_IAC);
--      mutex_lock_nested(&bus->mdio_lock, MDIO_MUTEX_NESTED);
-+      mt7530_mutex_lock(priv);
-       ret = readx_poll_timeout(_mt7530_unlocked_read, &p, val,
-                                !(val & MT7531_PHY_ACS_ST), 20, 100000);
-@@ -700,7 +703,7 @@ mt7531_ind_c45_phy_read(struct mt7530_pr
-       ret = val & MT7531_MDIO_RW_DATA_MASK;
- out:
--      mutex_unlock(&bus->mdio_lock);
-+      mt7530_mutex_unlock(priv);
-       return ret;
- }
-@@ -709,14 +712,13 @@ static int
- mt7531_ind_c45_phy_write(struct mt7530_priv *priv, int port, int devad,
-                        int regnum, u32 data)
- {
--      struct mii_bus *bus = priv->bus;
-       struct mt7530_dummy_poll p;
-       u32 val, reg;
-       int ret;
-       INIT_MT7530_DUMMY_POLL(&p, priv, MT7531_PHY_IAC);
--      mutex_lock_nested(&bus->mdio_lock, MDIO_MUTEX_NESTED);
-+      mt7530_mutex_lock(priv);
-       ret = readx_poll_timeout(_mt7530_unlocked_read, &p, val,
-                                !(val & MT7531_PHY_ACS_ST), 20, 100000);
-@@ -748,7 +750,7 @@ mt7531_ind_c45_phy_write(struct mt7530_p
-       }
- out:
--      mutex_unlock(&bus->mdio_lock);
-+      mt7530_mutex_unlock(priv);
-       return ret;
- }
-@@ -756,14 +758,13 @@ out:
- static int
- mt7531_ind_c22_phy_read(struct mt7530_priv *priv, int port, int regnum)
- {
--      struct mii_bus *bus = priv->bus;
-       struct mt7530_dummy_poll p;
-       int ret;
-       u32 val;
-       INIT_MT7530_DUMMY_POLL(&p, priv, MT7531_PHY_IAC);
--      mutex_lock_nested(&bus->mdio_lock, MDIO_MUTEX_NESTED);
-+      mt7530_mutex_lock(priv);
-       ret = readx_poll_timeout(_mt7530_unlocked_read, &p, val,
-                                !(val & MT7531_PHY_ACS_ST), 20, 100000);
-@@ -786,7 +787,7 @@ mt7531_ind_c22_phy_read(struct mt7530_pr
-       ret = val & MT7531_MDIO_RW_DATA_MASK;
- out:
--      mutex_unlock(&bus->mdio_lock);
-+      mt7530_mutex_unlock(priv);
-       return ret;
- }
-@@ -795,14 +796,13 @@ static int
- mt7531_ind_c22_phy_write(struct mt7530_priv *priv, int port, int regnum,
-                        u16 data)
- {
--      struct mii_bus *bus = priv->bus;
-       struct mt7530_dummy_poll p;
-       int ret;
-       u32 reg;
-       INIT_MT7530_DUMMY_POLL(&p, priv, MT7531_PHY_IAC);
--      mutex_lock_nested(&bus->mdio_lock, MDIO_MUTEX_NESTED);
-+      mt7530_mutex_lock(priv);
-       ret = readx_poll_timeout(_mt7530_unlocked_read, &p, reg,
-                                !(reg & MT7531_PHY_ACS_ST), 20, 100000);
-@@ -824,7 +824,7 @@ mt7531_ind_c22_phy_write(struct mt7530_p
-       }
- out:
--      mutex_unlock(&bus->mdio_lock);
-+      mt7530_mutex_unlock(priv);
-       return ret;
- }
-@@ -1344,7 +1344,6 @@ static int
- mt7530_port_change_mtu(struct dsa_switch *ds, int port, int new_mtu)
- {
-       struct mt7530_priv *priv = ds->priv;
--      struct mii_bus *bus = priv->bus;
-       int length;
-       u32 val;
-@@ -1355,7 +1354,7 @@ mt7530_port_change_mtu(struct dsa_switch
-       if (!dsa_is_cpu_port(ds, port))
-               return 0;
--      mutex_lock_nested(&bus->mdio_lock, MDIO_MUTEX_NESTED);
-+      mt7530_mutex_lock(priv);
-       val = mt7530_mii_read(priv, MT7530_GMACCR);
-       val &= ~MAX_RX_PKT_LEN_MASK;
-@@ -1376,7 +1375,7 @@ mt7530_port_change_mtu(struct dsa_switch
-       mt7530_mii_write(priv, MT7530_GMACCR, val);
--      mutex_unlock(&bus->mdio_lock);
-+      mt7530_mutex_unlock(priv);
-       return 0;
- }
-@@ -2172,10 +2171,10 @@ mt7530_irq_thread_fn(int irq, void *dev_
-       u32 val;
-       int p;
--      mutex_lock_nested(&priv->bus->mdio_lock, MDIO_MUTEX_NESTED);
-+      mt7530_mutex_lock(priv);
-       val = mt7530_mii_read(priv, MT7530_SYS_INT_STS);
-       mt7530_mii_write(priv, MT7530_SYS_INT_STS, val);
--      mutex_unlock(&priv->bus->mdio_lock);
-+      mt7530_mutex_unlock(priv);
-       for (p = 0; p < MT7530_NUM_PHYS; p++) {
-               if (BIT(p) & val) {
-@@ -2211,7 +2210,7 @@ mt7530_irq_bus_lock(struct irq_data *d)
- {
-       struct mt7530_priv *priv = irq_data_get_irq_chip_data(d);
--      mutex_lock_nested(&priv->bus->mdio_lock, MDIO_MUTEX_NESTED);
-+      mt7530_mutex_lock(priv);
- }
- static void
-@@ -2220,7 +2219,7 @@ mt7530_irq_bus_sync_unlock(struct irq_da
-       struct mt7530_priv *priv = irq_data_get_irq_chip_data(d);
-       mt7530_mii_write(priv, MT7530_SYS_INT_EN, priv->irq_enable);
--      mutex_unlock(&priv->bus->mdio_lock);
-+      mt7530_mutex_unlock(priv);
- }
- static struct irq_chip mt7530_irq_chip = {
diff --git a/target/linux/generic/backport-5.15/790-v6.4-0007-net-dsa-mt7530-move-p5_intf_modes-function-to-mt7530.patch b/target/linux/generic/backport-5.15/790-v6.4-0007-net-dsa-mt7530-move-p5_intf_modes-function-to-mt7530.patch
deleted file mode 100644 (file)
index 2e1ed2e..0000000
+++ /dev/null
@@ -1,75 +0,0 @@
-From 25d15dee34a1a40d5fd71636a205e3211f09fd1d Mon Sep 17 00:00:00 2001
-From: Daniel Golle <[email protected]>
-Date: Mon, 3 Apr 2023 02:18:28 +0100
-Subject: [PATCH 10/16] net: dsa: mt7530: move p5_intf_modes() function to
- mt7530.c
-
-In preparation of splitting mt7530.c into a driver for MDIO-connected
-as well as MDIO-accessed built-in switches on one hand and MMIO-accessed
-built-in switches move the p5_inft_modes() function from mt7530.h to
-mt7530.c. The function is only needed there and will trigger a compiler
-warning about a defined but unused function otherwise when including
-mt7530.h in the to-be-introduced bus-specific drivers.
-
-Signed-off-by: Daniel Golle <[email protected]>
-Reviewed-by: Andrew Lunn <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/dsa/mt7530.c | 18 ++++++++++++++++++
- drivers/net/dsa/mt7530.h | 18 ------------------
- 2 files changed, 18 insertions(+), 18 deletions(-)
-
---- a/drivers/net/dsa/mt7530.c
-+++ b/drivers/net/dsa/mt7530.c
-@@ -965,6 +965,24 @@ mt7530_set_ageing_time(struct dsa_switch
-       return 0;
- }
-+static const char *p5_intf_modes(unsigned int p5_interface)
-+{
-+      switch (p5_interface) {
-+      case P5_DISABLED:
-+              return "DISABLED";
-+      case P5_INTF_SEL_PHY_P0:
-+              return "PHY P0";
-+      case P5_INTF_SEL_PHY_P4:
-+              return "PHY P4";
-+      case P5_INTF_SEL_GMAC5:
-+              return "GMAC5";
-+      case P5_INTF_SEL_GMAC5_SGMII:
-+              return "GMAC5_SGMII";
-+      default:
-+              return "unknown";
-+      }
-+}
-+
- static void mt7530_setup_port5(struct dsa_switch *ds, phy_interface_t interface)
- {
-       struct mt7530_priv *priv = ds->priv;
---- a/drivers/net/dsa/mt7530.h
-+++ b/drivers/net/dsa/mt7530.h
-@@ -720,24 +720,6 @@ enum p5_interface_select {
-       P5_INTF_SEL_GMAC5_SGMII,
- };
--static const char *p5_intf_modes(unsigned int p5_interface)
--{
--      switch (p5_interface) {
--      case P5_DISABLED:
--              return "DISABLED";
--      case P5_INTF_SEL_PHY_P0:
--              return "PHY P0";
--      case P5_INTF_SEL_PHY_P4:
--              return "PHY P4";
--      case P5_INTF_SEL_GMAC5:
--              return "GMAC5";
--      case P5_INTF_SEL_GMAC5_SGMII:
--              return "GMAC5_SGMII";
--      default:
--              return "unknown";
--      }
--}
--
- struct mt7530_priv;
- struct mt753x_pcs {
diff --git a/target/linux/generic/backport-5.15/790-v6.4-0008-net-dsa-mt7530-introduce-mt7530_probe_common-helper-.patch b/target/linux/generic/backport-5.15/790-v6.4-0008-net-dsa-mt7530-introduce-mt7530_probe_common-helper-.patch
deleted file mode 100644 (file)
index c9ff26f..0000000
+++ /dev/null
@@ -1,155 +0,0 @@
-From 37c9c0d8d0b2e24f8c9af72ecd4edd31537284d3 Mon Sep 17 00:00:00 2001
-From: Daniel Golle <[email protected]>
-Date: Mon, 3 Apr 2023 02:18:39 +0100
-Subject: [PATCH 11/16] net: dsa: mt7530: introduce mt7530_probe_common helper
- function
-
-Move commonly used parts from mt7530_probe into new mt7530_probe_common
-helper function which will be used by both, mt7530_probe and the
-to-be-introduced mt7988_probe.
-
-Signed-off-by: Daniel Golle <[email protected]>
-Reviewed-by: Andrew Lunn <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/dsa/mt7530.c | 98 ++++++++++++++++++++++------------------
- 1 file changed, 54 insertions(+), 44 deletions(-)
-
---- a/drivers/net/dsa/mt7530.c
-+++ b/drivers/net/dsa/mt7530.c
-@@ -3394,44 +3394,21 @@ static const struct of_device_id mt7530_
- MODULE_DEVICE_TABLE(of, mt7530_of_match);
- static int
--mt7530_probe(struct mdio_device *mdiodev)
-+mt7530_probe_common(struct mt7530_priv *priv)
- {
--      static struct regmap_config *regmap_config;
--      struct mt7530_priv *priv;
--      struct device_node *dn;
--      int ret;
-+      struct device *dev = priv->dev;
--      dn = mdiodev->dev.of_node;
--
--      priv = devm_kzalloc(&mdiodev->dev, sizeof(*priv), GFP_KERNEL);
--      if (!priv)
--              return -ENOMEM;
--
--      priv->ds = devm_kzalloc(&mdiodev->dev, sizeof(*priv->ds), GFP_KERNEL);
-+      priv->ds = devm_kzalloc(dev, sizeof(*priv->ds), GFP_KERNEL);
-       if (!priv->ds)
-               return -ENOMEM;
--      priv->ds->dev = &mdiodev->dev;
-+      priv->ds->dev = dev;
-       priv->ds->num_ports = MT7530_NUM_PORTS;
--      /* Use medatek,mcm property to distinguish hardware type that would
--       * casues a little bit differences on power-on sequence.
--       */
--      priv->mcm = of_property_read_bool(dn, "mediatek,mcm");
--      if (priv->mcm) {
--              dev_info(&mdiodev->dev, "MT7530 adapts as multi-chip module\n");
--
--              priv->rstc = devm_reset_control_get(&mdiodev->dev, "mcm");
--              if (IS_ERR(priv->rstc)) {
--                      dev_err(&mdiodev->dev, "Couldn't get our reset line\n");
--                      return PTR_ERR(priv->rstc);
--              }
--      }
--
-       /* Get the hardware identifier from the devicetree node.
-        * We will need it for some of the clock and regulator setup.
-        */
--      priv->info = of_device_get_match_data(&mdiodev->dev);
-+      priv->info = of_device_get_match_data(dev);
-       if (!priv->info)
-               return -EINVAL;
-@@ -3445,23 +3422,53 @@ mt7530_probe(struct mdio_device *mdiodev
-               return -EINVAL;
-       priv->id = priv->info->id;
-+      priv->dev = dev;
-+      priv->ds->priv = priv;
-+      priv->ds->ops = &mt7530_switch_ops;
-+      mutex_init(&priv->reg_mutex);
-+      dev_set_drvdata(dev, priv);
--      if (priv->id == ID_MT7530) {
--              priv->core_pwr = devm_regulator_get(&mdiodev->dev, "core");
--              if (IS_ERR(priv->core_pwr))
--                      return PTR_ERR(priv->core_pwr);
-+      return 0;
-+}
--              priv->io_pwr = devm_regulator_get(&mdiodev->dev, "io");
--              if (IS_ERR(priv->io_pwr))
--                      return PTR_ERR(priv->io_pwr);
--      }
-+static int
-+mt7530_probe(struct mdio_device *mdiodev)
-+{
-+      static struct regmap_config *regmap_config;
-+      struct mt7530_priv *priv;
-+      struct device_node *dn;
-+      int ret;
-+
-+      dn = mdiodev->dev.of_node;
-+
-+      priv = devm_kzalloc(&mdiodev->dev, sizeof(*priv), GFP_KERNEL);
-+      if (!priv)
-+              return -ENOMEM;
--      /* Not MCM that indicates switch works as the remote standalone
-+      priv->bus = mdiodev->bus;
-+      priv->dev = &mdiodev->dev;
-+
-+      ret = mt7530_probe_common(priv);
-+      if (ret)
-+              return ret;
-+
-+      /* Use medatek,mcm property to distinguish hardware type that would
-+       * cause a little bit differences on power-on sequence.
-+       * Not MCM that indicates switch works as the remote standalone
-        * integrated circuit so the GPIO pin would be used to complete
-        * the reset, otherwise memory-mapped register accessing used
-        * through syscon provides in the case of MCM.
-        */
--      if (!priv->mcm) {
-+      priv->mcm = of_property_read_bool(dn, "mediatek,mcm");
-+      if (priv->mcm) {
-+              dev_info(&mdiodev->dev, "MT7530 adapts as multi-chip module\n");
-+
-+              priv->rstc = devm_reset_control_get(&mdiodev->dev, "mcm");
-+              if (IS_ERR(priv->rstc)) {
-+                      dev_err(&mdiodev->dev, "Couldn't get our reset line\n");
-+                      return PTR_ERR(priv->rstc);
-+              }
-+      } else {
-               priv->reset = devm_gpiod_get_optional(&mdiodev->dev, "reset",
-                                                     GPIOD_OUT_LOW);
-               if (IS_ERR(priv->reset)) {
-@@ -3470,12 +3477,15 @@ mt7530_probe(struct mdio_device *mdiodev
-               }
-       }
--      priv->bus = mdiodev->bus;
--      priv->dev = &mdiodev->dev;
--      priv->ds->priv = priv;
--      priv->ds->ops = &mt7530_switch_ops;
--      mutex_init(&priv->reg_mutex);
--      dev_set_drvdata(&mdiodev->dev, priv);
-+      if (priv->id == ID_MT7530) {
-+              priv->core_pwr = devm_regulator_get(&mdiodev->dev, "core");
-+              if (IS_ERR(priv->core_pwr))
-+                      return PTR_ERR(priv->core_pwr);
-+
-+              priv->io_pwr = devm_regulator_get(&mdiodev->dev, "io");
-+              if (IS_ERR(priv->io_pwr))
-+                      return PTR_ERR(priv->io_pwr);
-+      }
-       regmap_config = devm_kzalloc(&mdiodev->dev, sizeof(*regmap_config),
-                                    GFP_KERNEL);
diff --git a/target/linux/generic/backport-5.15/790-v6.4-0009-net-dsa-mt7530-introduce-mt7530_remove_common-helper.patch b/target/linux/generic/backport-5.15/790-v6.4-0009-net-dsa-mt7530-introduce-mt7530_remove_common-helper.patch
deleted file mode 100644 (file)
index 7c1c80e..0000000
+++ /dev/null
@@ -1,55 +0,0 @@
-From 720d736351761574af02ed093658ab60de60576c Mon Sep 17 00:00:00 2001
-From: Daniel Golle <[email protected]>
-Date: Mon, 3 Apr 2023 02:18:50 +0100
-Subject: [PATCH 12/16] net: dsa: mt7530: introduce mt7530_remove_common helper
- function
-
-Move commonly used parts from mt7530_remove into new
-mt7530_remove_common helper function which will be used by both,
-mt7530_remove and the to-be-introduced mt7988_remove.
-
-Signed-off-by: Daniel Golle <[email protected]>
-Reviewed-by: Andrew Lunn <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/dsa/mt7530.c | 18 ++++++++++++------
- 1 file changed, 12 insertions(+), 6 deletions(-)
-
---- a/drivers/net/dsa/mt7530.c
-+++ b/drivers/net/dsa/mt7530.c
-@@ -3512,6 +3512,17 @@ mt7530_probe(struct mdio_device *mdiodev
- }
- static void
-+mt7530_remove_common(struct mt7530_priv *priv)
-+{
-+      if (priv->irq)
-+              mt7530_free_irq(priv);
-+
-+      dsa_unregister_switch(priv->ds);
-+
-+      mutex_destroy(&priv->reg_mutex);
-+}
-+
-+static void
- mt7530_remove(struct mdio_device *mdiodev)
- {
-       struct mt7530_priv *priv = dev_get_drvdata(&mdiodev->dev);
-@@ -3530,16 +3541,11 @@ mt7530_remove(struct mdio_device *mdiode
-               dev_err(priv->dev, "Failed to disable io pwr: %d\n",
-                       ret);
--      if (priv->irq)
--              mt7530_free_irq(priv);
--
--      dsa_unregister_switch(priv->ds);
-+      mt7530_remove_common(priv);
-       for (i = 0; i < 2; ++i)
-               mtk_pcs_lynxi_destroy(priv->ports[5 + i].sgmii_pcs);
--      mutex_destroy(&priv->reg_mutex);
--
-       dev_set_drvdata(&mdiodev->dev, NULL);
- }
diff --git a/target/linux/generic/backport-5.15/790-v6.4-0011-net-dsa-mt7530-introduce-separate-MDIO-driver.patch b/target/linux/generic/backport-5.15/790-v6.4-0011-net-dsa-mt7530-introduce-separate-MDIO-driver.patch
deleted file mode 100644 (file)
index 8488314..0000000
+++ /dev/null
@@ -1,692 +0,0 @@
-From cb675afcddbbeb2bfa6596e3bc236bc026cd425f Mon Sep 17 00:00:00 2001
-From: Daniel Golle <[email protected]>
-Date: Mon, 3 Apr 2023 02:19:13 +0100
-Subject: [PATCH 14/16] net: dsa: mt7530: introduce separate MDIO driver
-
-Split MT7530 switch driver into a common part and a part specific
-for MDIO connected switches and multi-chip modules.
-Move MDIO-specific functions to newly introduced mt7530-mdio.c while
-keeping the common parts in mt7530.c.
-Introduce new Kconfig symbol CONFIG_NET_DSA_MT7530_MDIO which is
-implied by CONFIG_NET_DSA_MT7530.
-
-Signed-off-by: Daniel Golle <[email protected]>
-Reviewed-by: Andrew Lunn <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- MAINTAINERS                   |   1 +
- drivers/net/dsa/Kconfig       |  15 +-
- drivers/net/dsa/Makefile      |   1 +
- drivers/net/dsa/mt7530-mdio.c | 271 ++++++++++++++++++++++++++++++++++
- drivers/net/dsa/mt7530.c      | 264 +--------------------------------
- drivers/net/dsa/mt7530.h      |   6 +
- 6 files changed, 300 insertions(+), 258 deletions(-)
- create mode 100644 drivers/net/dsa/mt7530-mdio.c
-
---- a/MAINTAINERS
-+++ b/MAINTAINERS
-@@ -11902,6 +11902,7 @@ M:     Landen Chao <[email protected]
- M:    DENG Qingfang <[email protected]>
- L:    [email protected]
- S:    Maintained
-+F:    drivers/net/dsa/mt7530-mdio.c
- F:    drivers/net/dsa/mt7530.*
- F:    net/dsa/tag_mtk.c
---- a/drivers/net/dsa/Kconfig
-+++ b/drivers/net/dsa/Kconfig
-@@ -37,10 +37,22 @@ config NET_DSA_MT7530
-       tristate "MediaTek MT753x and MT7621 Ethernet switch support"
-       select NET_DSA_TAG_MTK
-       select MEDIATEK_GE_PHY
-+      imply NET_DSA_MT7530_MDIO
-+      help
-+        This enables support for the MediaTek MT7530 and MT7531 Ethernet
-+        switch chips. Multi-chip module MT7530 in MT7621AT, MT7621DAT,
-+        MT7621ST and MT7623AI SoCs, and built-in switch in MT7988 SoC are
-+        supported as well.
-+
-+config NET_DSA_MT7530_MDIO
-+      tristate "MediaTek MT7530 MDIO interface driver"
-+      depends on NET_DSA_MT7530
-       select PCS_MTK_LYNXI
-       help
--        This enables support for the MediaTek MT7530, MT7531, and MT7621
--        Ethernet switch chips.
-+        This enables support for the MediaTek MT7530 and MT7531 switch
-+        chips which are connected via MDIO, as well as multi-chip
-+        module MT7530 which can be found in the MT7621AT, MT7621DAT,
-+        MT7621ST and MT7623AI SoCs.
- config NET_DSA_MV88E6060
-       tristate "Marvell 88E6060 ethernet switch chip support"
---- a/drivers/net/dsa/Makefile
-+++ b/drivers/net/dsa/Makefile
-@@ -7,6 +7,7 @@ obj-$(CONFIG_FIXED_PHY)                += dsa_loop_bdi
- endif
- obj-$(CONFIG_NET_DSA_LANTIQ_GSWIP) += lantiq_gswip.o
- obj-$(CONFIG_NET_DSA_MT7530)  += mt7530.o
-+obj-$(CONFIG_NET_DSA_MT7530_MDIO) += mt7530-mdio.o
- obj-$(CONFIG_NET_DSA_MV88E6060) += mv88e6060.o
- obj-$(CONFIG_NET_DSA_REALTEK_SMI) += realtek-smi.o
- realtek-smi-objs              := realtek-smi-core.o rtl8366.o rtl8366rb.o
---- /dev/null
-+++ b/drivers/net/dsa/mt7530-mdio.c
-@@ -0,0 +1,271 @@
-+// SPDX-License-Identifier: GPL-2.0-only
-+
-+#include <linux/gpio/consumer.h>
-+#include <linux/mdio.h>
-+#include <linux/module.h>
-+#include <linux/pcs/pcs-mtk-lynxi.h>
-+#include <linux/of_irq.h>
-+#include <linux/of_mdio.h>
-+#include <linux/of_net.h>
-+#include <linux/of_platform.h>
-+#include <linux/regmap.h>
-+#include <linux/reset.h>
-+#include <linux/regulator/consumer.h>
-+#include <net/dsa.h>
-+
-+#include "mt7530.h"
-+
-+static int
-+mt7530_regmap_write(void *context, unsigned int reg, unsigned int val)
-+{
-+      struct mii_bus *bus = context;
-+      u16 page, r, lo, hi;
-+      int ret;
-+
-+      page = (reg >> 6) & 0x3ff;
-+      r  = (reg >> 2) & 0xf;
-+      lo = val & 0xffff;
-+      hi = val >> 16;
-+
-+      /* MT7530 uses 31 as the pseudo port */
-+      ret = bus->write(bus, 0x1f, 0x1f, page);
-+      if (ret < 0)
-+              return ret;
-+
-+      ret = bus->write(bus, 0x1f, r,  lo);
-+      if (ret < 0)
-+              return ret;
-+
-+      ret = bus->write(bus, 0x1f, 0x10, hi);
-+      return ret;
-+}
-+
-+static int
-+mt7530_regmap_read(void *context, unsigned int reg, unsigned int *val)
-+{
-+      struct mii_bus *bus = context;
-+      u16 page, r, lo, hi;
-+      int ret;
-+
-+      page = (reg >> 6) & 0x3ff;
-+      r = (reg >> 2) & 0xf;
-+
-+      /* MT7530 uses 31 as the pseudo port */
-+      ret = bus->write(bus, 0x1f, 0x1f, page);
-+      if (ret < 0)
-+              return ret;
-+
-+      lo = bus->read(bus, 0x1f, r);
-+      hi = bus->read(bus, 0x1f, 0x10);
-+
-+      *val = (hi << 16) | (lo & 0xffff);
-+
-+      return 0;
-+}
-+
-+static void
-+mt7530_mdio_regmap_lock(void *mdio_lock)
-+{
-+      mutex_lock_nested(mdio_lock, MDIO_MUTEX_NESTED);
-+}
-+
-+static void
-+mt7530_mdio_regmap_unlock(void *mdio_lock)
-+{
-+      mutex_unlock(mdio_lock);
-+}
-+
-+static const struct regmap_bus mt7530_regmap_bus = {
-+      .reg_write = mt7530_regmap_write,
-+      .reg_read = mt7530_regmap_read,
-+};
-+
-+static int
-+mt7531_create_sgmii(struct mt7530_priv *priv)
-+{
-+      struct regmap_config *mt7531_pcs_config[2];
-+      struct phylink_pcs *pcs;
-+      struct regmap *regmap;
-+      int i, ret = 0;
-+
-+      for (i = 0; i < 2; i++) {
-+              mt7531_pcs_config[i] = devm_kzalloc(priv->dev,
-+                                                  sizeof(struct regmap_config),
-+                                                  GFP_KERNEL);
-+              if (!mt7531_pcs_config[i]) {
-+                      ret = -ENOMEM;
-+                      break;
-+              }
-+
-+              mt7531_pcs_config[i]->name = i ? "port6" : "port5";
-+              mt7531_pcs_config[i]->reg_bits = 16;
-+              mt7531_pcs_config[i]->val_bits = 32;
-+              mt7531_pcs_config[i]->reg_stride = 4;
-+              mt7531_pcs_config[i]->reg_base = MT7531_SGMII_REG_BASE(5 + i);
-+              mt7531_pcs_config[i]->max_register = 0x17c;
-+              mt7531_pcs_config[i]->lock = mt7530_mdio_regmap_lock;
-+              mt7531_pcs_config[i]->unlock = mt7530_mdio_regmap_unlock;
-+              mt7531_pcs_config[i]->lock_arg = &priv->bus->mdio_lock;
-+
-+              regmap = devm_regmap_init(priv->dev,
-+                                        &mt7530_regmap_bus, priv->bus,
-+                                        mt7531_pcs_config[i]);
-+              if (IS_ERR(regmap)) {
-+                      ret = PTR_ERR(regmap);
-+                      break;
-+              }
-+              pcs = mtk_pcs_lynxi_create(priv->dev, regmap,
-+                                         MT7531_PHYA_CTRL_SIGNAL3, 0);
-+              if (!pcs) {
-+                      ret = -ENXIO;
-+                      break;
-+              }
-+              priv->ports[5 + i].sgmii_pcs = pcs;
-+      }
-+
-+      if (ret && i)
-+              mtk_pcs_lynxi_destroy(priv->ports[5].sgmii_pcs);
-+
-+      return ret;
-+}
-+
-+static const struct of_device_id mt7530_of_match[] = {
-+      { .compatible = "mediatek,mt7621", .data = &mt753x_table[ID_MT7621], },
-+      { .compatible = "mediatek,mt7530", .data = &mt753x_table[ID_MT7530], },
-+      { .compatible = "mediatek,mt7531", .data = &mt753x_table[ID_MT7531], },
-+      { /* sentinel */ },
-+};
-+MODULE_DEVICE_TABLE(of, mt7530_of_match);
-+
-+static int
-+mt7530_probe(struct mdio_device *mdiodev)
-+{
-+      static struct regmap_config *regmap_config;
-+      struct mt7530_priv *priv;
-+      struct device_node *dn;
-+      int ret;
-+
-+      dn = mdiodev->dev.of_node;
-+
-+      priv = devm_kzalloc(&mdiodev->dev, sizeof(*priv), GFP_KERNEL);
-+      if (!priv)
-+              return -ENOMEM;
-+
-+      priv->bus = mdiodev->bus;
-+      priv->dev = &mdiodev->dev;
-+
-+      ret = mt7530_probe_common(priv);
-+      if (ret)
-+              return ret;
-+
-+      /* Use medatek,mcm property to distinguish hardware type that would
-+       * cause a little bit differences on power-on sequence.
-+       * Not MCM that indicates switch works as the remote standalone
-+       * integrated circuit so the GPIO pin would be used to complete
-+       * the reset, otherwise memory-mapped register accessing used
-+       * through syscon provides in the case of MCM.
-+       */
-+      priv->mcm = of_property_read_bool(dn, "mediatek,mcm");
-+      if (priv->mcm) {
-+              dev_info(&mdiodev->dev, "MT7530 adapts as multi-chip module\n");
-+
-+              priv->rstc = devm_reset_control_get(&mdiodev->dev, "mcm");
-+              if (IS_ERR(priv->rstc)) {
-+                      dev_err(&mdiodev->dev, "Couldn't get our reset line\n");
-+                      return PTR_ERR(priv->rstc);
-+              }
-+      } else {
-+              priv->reset = devm_gpiod_get_optional(&mdiodev->dev, "reset",
-+                                                    GPIOD_OUT_LOW);
-+              if (IS_ERR(priv->reset)) {
-+                      dev_err(&mdiodev->dev, "Couldn't get our reset line\n");
-+                      return PTR_ERR(priv->reset);
-+              }
-+      }
-+
-+      if (priv->id == ID_MT7530) {
-+              priv->core_pwr = devm_regulator_get(&mdiodev->dev, "core");
-+              if (IS_ERR(priv->core_pwr))
-+                      return PTR_ERR(priv->core_pwr);
-+
-+              priv->io_pwr = devm_regulator_get(&mdiodev->dev, "io");
-+              if (IS_ERR(priv->io_pwr))
-+                      return PTR_ERR(priv->io_pwr);
-+      }
-+
-+      regmap_config = devm_kzalloc(&mdiodev->dev, sizeof(*regmap_config),
-+                                   GFP_KERNEL);
-+      if (!regmap_config)
-+              return -ENOMEM;
-+
-+      regmap_config->reg_bits = 16;
-+      regmap_config->val_bits = 32;
-+      regmap_config->reg_stride = 4;
-+      regmap_config->max_register = MT7530_CREV;
-+      regmap_config->disable_locking = true;
-+      priv->regmap = devm_regmap_init(priv->dev, &mt7530_regmap_bus,
-+                                      priv->bus, regmap_config);
-+      if (IS_ERR(priv->regmap))
-+              return PTR_ERR(priv->regmap);
-+
-+      if (priv->id == ID_MT7531) {
-+              ret = mt7531_create_sgmii(priv);
-+              if (ret)
-+                      return ret;
-+      }
-+
-+      return dsa_register_switch(priv->ds);
-+}
-+
-+static void
-+mt7530_remove(struct mdio_device *mdiodev)
-+{
-+      struct mt7530_priv *priv = dev_get_drvdata(&mdiodev->dev);
-+      int ret = 0, i;
-+
-+      if (!priv)
-+              return;
-+
-+      ret = regulator_disable(priv->core_pwr);
-+      if (ret < 0)
-+              dev_err(priv->dev,
-+                      "Failed to disable core power: %d\n", ret);
-+
-+      ret = regulator_disable(priv->io_pwr);
-+      if (ret < 0)
-+              dev_err(priv->dev, "Failed to disable io pwr: %d\n",
-+                      ret);
-+
-+      mt7530_remove_common(priv);
-+
-+      for (i = 0; i < 2; ++i)
-+              mtk_pcs_lynxi_destroy(priv->ports[5 + i].sgmii_pcs);
-+}
-+
-+static void mt7530_shutdown(struct mdio_device *mdiodev)
-+{
-+      struct mt7530_priv *priv = dev_get_drvdata(&mdiodev->dev);
-+
-+      if (!priv)
-+              return;
-+
-+      dsa_switch_shutdown(priv->ds);
-+
-+      dev_set_drvdata(&mdiodev->dev, NULL);
-+}
-+
-+static struct mdio_driver mt7530_mdio_driver = {
-+      .probe  = mt7530_probe,
-+      .remove = mt7530_remove,
-+      .shutdown = mt7530_shutdown,
-+      .mdiodrv.driver = {
-+              .name = "mt7530-mdio",
-+              .of_match_table = mt7530_of_match,
-+      },
-+};
-+
-+mdio_module_driver(mt7530_mdio_driver);
-+
-+MODULE_AUTHOR("Sean Wang <[email protected]>");
-+MODULE_DESCRIPTION("Driver for Mediatek MT7530 Switch (MDIO)");
-+MODULE_LICENSE("GPL");
---- a/drivers/net/dsa/mt7530.c
-+++ b/drivers/net/dsa/mt7530.c
-@@ -14,7 +14,6 @@
- #include <linux/of_mdio.h>
- #include <linux/of_net.h>
- #include <linux/of_platform.h>
--#include <linux/pcs/pcs-mtk-lynxi.h>
- #include <linux/phylink.h>
- #include <linux/regmap.h>
- #include <linux/regulator/consumer.h>
-@@ -193,31 +192,6 @@ core_clear(struct mt7530_priv *priv, u32
- }
- static int
--mt7530_regmap_write(void *context, unsigned int reg, unsigned int val)
--{
--      struct mii_bus *bus = context;
--      u16 page, r, lo, hi;
--      int ret;
--
--      page = (reg >> 6) & 0x3ff;
--      r  = (reg >> 2) & 0xf;
--      lo = val & 0xffff;
--      hi = val >> 16;
--
--      /* MT7530 uses 31 as the pseudo port */
--      ret = bus->write(bus, 0x1f, 0x1f, page);
--      if (ret < 0)
--              return ret;
--
--      ret = bus->write(bus, 0x1f, r,  lo);
--      if (ret < 0)
--              return ret;
--
--      ret = bus->write(bus, 0x1f, 0x10, hi);
--      return ret;
--}
--
--static int
- mt7530_mii_write(struct mt7530_priv *priv, u32 reg, u32 val)
- {
-       int ret;
-@@ -231,29 +205,6 @@ mt7530_mii_write(struct mt7530_priv *pri
-       return ret;
- }
--static int
--mt7530_regmap_read(void *context, unsigned int reg, unsigned int *val)
--{
--      struct mii_bus *bus = context;
--      u16 page, r, lo, hi;
--      int ret;
--
--      page = (reg >> 6) & 0x3ff;
--      r = (reg >> 2) & 0xf;
--
--      /* MT7530 uses 31 as the pseudo port */
--      ret = bus->write(bus, 0x1f, 0x1f, page);
--      if (ret < 0)
--              return ret;
--
--      lo = bus->read(bus, 0x1f, r);
--      hi = bus->read(bus, 0x1f, 0x10);
--
--      *val = (hi << 16) | (lo & 0xffff);
--
--      return 0;
--}
--
- static u32
- mt7530_mii_read(struct mt7530_priv *priv, u32 reg)
- {
-@@ -3191,72 +3142,6 @@ static const struct phylink_pcs_ops mt75
-       .pcs_an_restart = mt7530_pcs_an_restart,
- };
--static void
--mt7530_mdio_regmap_lock(void *mdio_lock)
--{
--      mutex_lock_nested(mdio_lock, MDIO_MUTEX_NESTED);
--}
--
--static void
--mt7530_mdio_regmap_unlock(void *mdio_lock)
--{
--      mutex_unlock(mdio_lock);
--}
--
--static const struct regmap_bus mt7530_regmap_bus = {
--      .reg_write = mt7530_regmap_write,
--      .reg_read = mt7530_regmap_read,
--};
--
--static int
--mt7531_create_sgmii(struct mt7530_priv *priv)
--{
--      struct regmap_config *mt7531_pcs_config[2];
--      struct phylink_pcs *pcs;
--      struct regmap *regmap;
--      int i, ret = 0;
--
--      for (i = 0; i < 2; i++) {
--              mt7531_pcs_config[i] = devm_kzalloc(priv->dev,
--                                                  sizeof(struct regmap_config),
--                                                  GFP_KERNEL);
--              if (!mt7531_pcs_config[i]) {
--                      ret = -ENOMEM;
--                      break;
--              }
--
--              mt7531_pcs_config[i]->name = i ? "port6" : "port5";
--              mt7531_pcs_config[i]->reg_bits = 16;
--              mt7531_pcs_config[i]->val_bits = 32;
--              mt7531_pcs_config[i]->reg_stride = 4;
--              mt7531_pcs_config[i]->reg_base = MT7531_SGMII_REG_BASE(5 + i);
--              mt7531_pcs_config[i]->max_register = 0x17c;
--              mt7531_pcs_config[i]->lock = mt7530_mdio_regmap_lock;
--              mt7531_pcs_config[i]->unlock = mt7530_mdio_regmap_unlock;
--              mt7531_pcs_config[i]->lock_arg = &priv->bus->mdio_lock;
--
--              regmap = devm_regmap_init(priv->dev,
--                                        &mt7530_regmap_bus, priv->bus,
--                                        mt7531_pcs_config[i]);
--              if (IS_ERR(regmap)) {
--                      ret = PTR_ERR(regmap);
--                      break;
--              }
--              pcs = mtk_pcs_lynxi_create(priv->dev, regmap,
--                                         MT7531_PHYA_CTRL_SIGNAL3, 0);
--              if (!pcs) {
--                      ret = -ENXIO;
--                      break;
--              }
--              priv->ports[5 + i].sgmii_pcs = pcs;
--      }
--
--      if (ret && i)
--              mtk_pcs_lynxi_destroy(priv->ports[5].sgmii_pcs);
--
--      return ret;
--}
--
- static int
- mt753x_setup(struct dsa_switch *ds)
- {
-@@ -3315,7 +3200,7 @@ static int mt753x_set_mac_eee(struct dsa
-       return 0;
- }
--static const struct dsa_switch_ops mt7530_switch_ops = {
-+const struct dsa_switch_ops mt7530_switch_ops = {
-       .get_tag_protocol       = mtk_get_tag_protocol,
-       .setup                  = mt753x_setup,
-       .preferred_default_local_cpu_port = mt753x_preferred_default_local_cpu_port,
-@@ -3350,8 +3235,9 @@ static const struct dsa_switch_ops mt753
-       .get_mac_eee            = mt753x_get_mac_eee,
-       .set_mac_eee            = mt753x_set_mac_eee,
- };
-+EXPORT_SYMBOL_GPL(mt7530_switch_ops);
--static const struct mt753x_info mt753x_table[] = {
-+const struct mt753x_info mt753x_table[] = {
-       [ID_MT7621] = {
-               .id = ID_MT7621,
-               .pcs_ops = &mt7530_pcs_ops,
-@@ -3384,16 +3270,9 @@ static const struct mt753x_info mt753x_t
-               .mac_port_config = mt7531_mac_config,
-       },
- };
-+EXPORT_SYMBOL_GPL(mt753x_table);
--static const struct of_device_id mt7530_of_match[] = {
--      { .compatible = "mediatek,mt7621", .data = &mt753x_table[ID_MT7621], },
--      { .compatible = "mediatek,mt7530", .data = &mt753x_table[ID_MT7530], },
--      { .compatible = "mediatek,mt7531", .data = &mt753x_table[ID_MT7531], },
--      { /* sentinel */ },
--};
--MODULE_DEVICE_TABLE(of, mt7530_of_match);
--
--static int
-+int
- mt7530_probe_common(struct mt7530_priv *priv)
- {
-       struct device *dev = priv->dev;
-@@ -3430,88 +3309,9 @@ mt7530_probe_common(struct mt7530_priv *
-       return 0;
- }
-+EXPORT_SYMBOL_GPL(mt7530_probe_common);
--static int
--mt7530_probe(struct mdio_device *mdiodev)
--{
--      static struct regmap_config *regmap_config;
--      struct mt7530_priv *priv;
--      struct device_node *dn;
--      int ret;
--
--      dn = mdiodev->dev.of_node;
--
--      priv = devm_kzalloc(&mdiodev->dev, sizeof(*priv), GFP_KERNEL);
--      if (!priv)
--              return -ENOMEM;
--
--      priv->bus = mdiodev->bus;
--      priv->dev = &mdiodev->dev;
--
--      ret = mt7530_probe_common(priv);
--      if (ret)
--              return ret;
--
--      /* Use medatek,mcm property to distinguish hardware type that would
--       * cause a little bit differences on power-on sequence.
--       * Not MCM that indicates switch works as the remote standalone
--       * integrated circuit so the GPIO pin would be used to complete
--       * the reset, otherwise memory-mapped register accessing used
--       * through syscon provides in the case of MCM.
--       */
--      priv->mcm = of_property_read_bool(dn, "mediatek,mcm");
--      if (priv->mcm) {
--              dev_info(&mdiodev->dev, "MT7530 adapts as multi-chip module\n");
--
--              priv->rstc = devm_reset_control_get(&mdiodev->dev, "mcm");
--              if (IS_ERR(priv->rstc)) {
--                      dev_err(&mdiodev->dev, "Couldn't get our reset line\n");
--                      return PTR_ERR(priv->rstc);
--              }
--      } else {
--              priv->reset = devm_gpiod_get_optional(&mdiodev->dev, "reset",
--                                                    GPIOD_OUT_LOW);
--              if (IS_ERR(priv->reset)) {
--                      dev_err(&mdiodev->dev, "Couldn't get our reset line\n");
--                      return PTR_ERR(priv->reset);
--              }
--      }
--
--      if (priv->id == ID_MT7530) {
--              priv->core_pwr = devm_regulator_get(&mdiodev->dev, "core");
--              if (IS_ERR(priv->core_pwr))
--                      return PTR_ERR(priv->core_pwr);
--
--              priv->io_pwr = devm_regulator_get(&mdiodev->dev, "io");
--              if (IS_ERR(priv->io_pwr))
--                      return PTR_ERR(priv->io_pwr);
--      }
--
--      regmap_config = devm_kzalloc(&mdiodev->dev, sizeof(*regmap_config),
--                                   GFP_KERNEL);
--      if (!regmap_config)
--              return -ENOMEM;
--
--      regmap_config->reg_bits = 16;
--      regmap_config->val_bits = 32;
--      regmap_config->reg_stride = 4;
--      regmap_config->max_register = MT7530_CREV;
--      regmap_config->disable_locking = true;
--      priv->regmap = devm_regmap_init(priv->dev, &mt7530_regmap_bus,
--                                      priv->bus, regmap_config);
--      if (IS_ERR(priv->regmap))
--              return PTR_ERR(priv->regmap);
--
--      if (priv->id == ID_MT7531) {
--              ret = mt7531_create_sgmii(priv);
--              if (ret)
--                      return ret;
--      }
--
--      return dsa_register_switch(priv->ds);
--}
--
--static void
-+void
- mt7530_remove_common(struct mt7530_priv *priv)
- {
-       if (priv->irq)
-@@ -3522,57 +3322,6 @@ mt7530_remove_common(struct mt7530_priv
-       mutex_destroy(&priv->reg_mutex);
- }
--static void
--mt7530_remove(struct mdio_device *mdiodev)
--{
--      struct mt7530_priv *priv = dev_get_drvdata(&mdiodev->dev);
--      int ret = 0, i;
--
--      if (!priv)
--              return;
--
--      ret = regulator_disable(priv->core_pwr);
--      if (ret < 0)
--              dev_err(priv->dev,
--                      "Failed to disable core power: %d\n", ret);
--
--      ret = regulator_disable(priv->io_pwr);
--      if (ret < 0)
--              dev_err(priv->dev, "Failed to disable io pwr: %d\n",
--                      ret);
--
--      mt7530_remove_common(priv);
--
--      for (i = 0; i < 2; ++i)
--              mtk_pcs_lynxi_destroy(priv->ports[5 + i].sgmii_pcs);
--
--      dev_set_drvdata(&mdiodev->dev, NULL);
--}
--
--static void mt7530_shutdown(struct mdio_device *mdiodev)
--{
--      struct mt7530_priv *priv = dev_get_drvdata(&mdiodev->dev);
--
--      if (!priv)
--              return;
--
--      dsa_switch_shutdown(priv->ds);
--
--      dev_set_drvdata(&mdiodev->dev, NULL);
--}
--
--static struct mdio_driver mt7530_mdio_driver = {
--      .probe  = mt7530_probe,
--      .remove = mt7530_remove,
--      .shutdown = mt7530_shutdown,
--      .mdiodrv.driver = {
--              .name = "mt7530",
--              .of_match_table = mt7530_of_match,
--      },
--};
--
--mdio_module_driver(mt7530_mdio_driver);
--
- MODULE_AUTHOR("Sean Wang <[email protected]>");
- MODULE_DESCRIPTION("Driver for Mediatek MT7530 Switch");
- MODULE_LICENSE("GPL");
---- a/drivers/net/dsa/mt7530.h
-+++ b/drivers/net/dsa/mt7530.h
-@@ -845,4 +845,10 @@ static inline void INIT_MT7530_DUMMY_POL
-       p->reg = reg;
- }
-+int mt7530_probe_common(struct mt7530_priv *priv);
-+void mt7530_remove_common(struct mt7530_priv *priv);
-+
-+extern const struct dsa_switch_ops mt7530_switch_ops;
-+extern const struct mt753x_info mt753x_table[];
-+
- #endif /* __MT7530_H */
diff --git a/target/linux/generic/backport-5.15/790-v6.4-0012-net-dsa-mt7530-skip-locking-if-MDIO-bus-isn-t-presen.patch b/target/linux/generic/backport-5.15/790-v6.4-0012-net-dsa-mt7530-skip-locking-if-MDIO-bus-isn-t-presen.patch
deleted file mode 100644 (file)
index 59e193f..0000000
+++ /dev/null
@@ -1,47 +0,0 @@
-From 54d4147a121cec5004a673a58572da346e4458f8 Mon Sep 17 00:00:00 2001
-From: Daniel Golle <[email protected]>
-Date: Mon, 3 Apr 2023 02:19:28 +0100
-Subject: [PATCH 15/16] net: dsa: mt7530: skip locking if MDIO bus isn't
- present
-
-As MT7530 and MT7531 internally use 32-bit wide registers, each access
-to any register of the switch requires several operations on the MDIO
-bus. Hence if there is congruent access, e.g. due to PCS or PHY
-polling, this can mess up and interfere with another ongoing register
-access sequence.
-
-However, the MDIO bus mutex is only relevant for MDIO-connected
-switches. Prepare switches which have there registers directly mapped
-into the SoCs register space via MMIO which do not require such
-locking. There we can simply use regmap's default locking mechanism.
-
-Hence guard mutex operations to only be performed in case of MDIO
-connected switches.
-
-Signed-off-by: Daniel Golle <[email protected]>
-Reviewed-by: Andrew Lunn <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/dsa/mt7530.c | 6 ++++--
- 1 file changed, 4 insertions(+), 2 deletions(-)
-
---- a/drivers/net/dsa/mt7530.c
-+++ b/drivers/net/dsa/mt7530.c
-@@ -145,13 +145,15 @@ err:
- static void
- mt7530_mutex_lock(struct mt7530_priv *priv)
- {
--      mutex_lock_nested(&priv->bus->mdio_lock, MDIO_MUTEX_NESTED);
-+      if (priv->bus)
-+              mutex_lock_nested(&priv->bus->mdio_lock, MDIO_MUTEX_NESTED);
- }
- static void
- mt7530_mutex_unlock(struct mt7530_priv *priv)
- {
--      mutex_unlock(&priv->bus->mdio_lock);
-+      if (priv->bus)
-+              mutex_unlock(&priv->bus->mdio_lock);
- }
- static void
diff --git a/target/linux/generic/backport-5.15/790-v6.4-0013-net-dsa-mt7530-introduce-driver-for-MT7988-built-in-.patch b/target/linux/generic/backport-5.15/790-v6.4-0013-net-dsa-mt7530-introduce-driver-for-MT7988-built-in-.patch
deleted file mode 100644 (file)
index c841709..0000000
+++ /dev/null
@@ -1,421 +0,0 @@
-From 110c18bfed41421edd677935dd33be5e6507ba92 Mon Sep 17 00:00:00 2001
-From: Daniel Golle <[email protected]>
-Date: Mon, 3 Apr 2023 02:19:40 +0100
-Subject: [PATCH 16/16] net: dsa: mt7530: introduce driver for MT7988 built-in
- switch
-
-Add driver for the built-in Gigabit Ethernet switch which can be found
-in the MediaTek MT7988 SoC.
-
-The switch shares most of its design with MT7530 and MT7531, but has
-it's registers mapped into the SoCs register space rather than being
-connected externally or internally via MDIO.
-
-Introduce a new platform driver to support that.
-
-Signed-off-by: Daniel Golle <[email protected]>
-Reviewed-by: Andrew Lunn <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- MAINTAINERS                   |   2 +
- drivers/net/dsa/Kconfig       |  12 +++
- drivers/net/dsa/Makefile      |   1 +
- drivers/net/dsa/mt7530-mmio.c | 101 +++++++++++++++++++++++++
- drivers/net/dsa/mt7530.c      | 137 +++++++++++++++++++++++++++++++++-
- drivers/net/dsa/mt7530.h      |  12 +--
- 6 files changed, 255 insertions(+), 10 deletions(-)
- create mode 100644 drivers/net/dsa/mt7530-mmio.c
-
---- a/MAINTAINERS
-+++ b/MAINTAINERS
-@@ -11900,9 +11900,11 @@ MEDIATEK SWITCH DRIVER
- M:    Sean Wang <[email protected]>
- M:    Landen Chao <[email protected]>
- M:    DENG Qingfang <[email protected]>
-+M:    Daniel Golle <[email protected]>
- L:    [email protected]
- S:    Maintained
- F:    drivers/net/dsa/mt7530-mdio.c
-+F:    drivers/net/dsa/mt7530-mmio.c
- F:    drivers/net/dsa/mt7530.*
- F:    net/dsa/tag_mtk.c
---- a/drivers/net/dsa/Kconfig
-+++ b/drivers/net/dsa/Kconfig
-@@ -38,6 +38,7 @@ config NET_DSA_MT7530
-       select NET_DSA_TAG_MTK
-       select MEDIATEK_GE_PHY
-       imply NET_DSA_MT7530_MDIO
-+      imply NET_DSA_MT7530_MMIO
-       help
-         This enables support for the MediaTek MT7530 and MT7531 Ethernet
-         switch chips. Multi-chip module MT7530 in MT7621AT, MT7621DAT,
-@@ -54,6 +55,17 @@ config NET_DSA_MT7530_MDIO
-         module MT7530 which can be found in the MT7621AT, MT7621DAT,
-         MT7621ST and MT7623AI SoCs.
-+config NET_DSA_MT7530_MMIO
-+      tristate "MediaTek MT7530 MMIO interface driver"
-+      depends on NET_DSA_MT7530
-+      depends on HAS_IOMEM
-+      help
-+        This enables support for the built-in Ethernet switch found
-+        in the MediaTek MT7988 SoC.
-+        The switch is a similar design as MT7531, but the switch registers
-+        are directly mapped into the SoCs register space rather than being
-+        accessible via MDIO.
-+
- config NET_DSA_MV88E6060
-       tristate "Marvell 88E6060 ethernet switch chip support"
-       select NET_DSA_TAG_TRAILER
---- a/drivers/net/dsa/Makefile
-+++ b/drivers/net/dsa/Makefile
-@@ -8,6 +8,7 @@ endif
- obj-$(CONFIG_NET_DSA_LANTIQ_GSWIP) += lantiq_gswip.o
- obj-$(CONFIG_NET_DSA_MT7530)  += mt7530.o
- obj-$(CONFIG_NET_DSA_MT7530_MDIO) += mt7530-mdio.o
-+obj-$(CONFIG_NET_DSA_MT7530_MMIO) += mt7530-mmio.o
- obj-$(CONFIG_NET_DSA_MV88E6060) += mv88e6060.o
- obj-$(CONFIG_NET_DSA_REALTEK_SMI) += realtek-smi.o
- realtek-smi-objs              := realtek-smi-core.o rtl8366.o rtl8366rb.o
---- /dev/null
-+++ b/drivers/net/dsa/mt7530-mmio.c
-@@ -0,0 +1,101 @@
-+// SPDX-License-Identifier: GPL-2.0-only
-+
-+#include <linux/module.h>
-+#include <linux/of_platform.h>
-+#include <linux/regmap.h>
-+#include <linux/regulator/consumer.h>
-+#include <linux/reset.h>
-+#include <net/dsa.h>
-+
-+#include "mt7530.h"
-+
-+static const struct of_device_id mt7988_of_match[] = {
-+      { .compatible = "mediatek,mt7988-switch", .data = &mt753x_table[ID_MT7988], },
-+      { /* sentinel */ },
-+};
-+MODULE_DEVICE_TABLE(of, mt7988_of_match);
-+
-+static int
-+mt7988_probe(struct platform_device *pdev)
-+{
-+      static struct regmap_config *sw_regmap_config;
-+      struct mt7530_priv *priv;
-+      void __iomem *base_addr;
-+      int ret;
-+
-+      priv = devm_kzalloc(&pdev->dev, sizeof(*priv), GFP_KERNEL);
-+      if (!priv)
-+              return -ENOMEM;
-+
-+      priv->bus = NULL;
-+      priv->dev = &pdev->dev;
-+
-+      ret = mt7530_probe_common(priv);
-+      if (ret)
-+              return ret;
-+
-+      priv->rstc = devm_reset_control_get(&pdev->dev, NULL);
-+      if (IS_ERR(priv->rstc)) {
-+              dev_err(&pdev->dev, "Couldn't get our reset line\n");
-+              return PTR_ERR(priv->rstc);
-+      }
-+
-+      base_addr = devm_platform_ioremap_resource(pdev, 0);
-+      if (IS_ERR(base_addr)) {
-+              dev_err(&pdev->dev, "cannot request I/O memory space\n");
-+              return -ENXIO;
-+      }
-+
-+      sw_regmap_config = devm_kzalloc(&pdev->dev, sizeof(*sw_regmap_config), GFP_KERNEL);
-+      if (!sw_regmap_config)
-+              return -ENOMEM;
-+
-+      sw_regmap_config->name = "switch";
-+      sw_regmap_config->reg_bits = 16;
-+      sw_regmap_config->val_bits = 32;
-+      sw_regmap_config->reg_stride = 4;
-+      sw_regmap_config->max_register = MT7530_CREV;
-+      priv->regmap = devm_regmap_init_mmio(&pdev->dev, base_addr, sw_regmap_config);
-+      if (IS_ERR(priv->regmap))
-+              return PTR_ERR(priv->regmap);
-+
-+      return dsa_register_switch(priv->ds);
-+}
-+
-+static int
-+mt7988_remove(struct platform_device *pdev)
-+{
-+      struct mt7530_priv *priv = platform_get_drvdata(pdev);
-+
-+      if (priv)
-+              mt7530_remove_common(priv);
-+
-+      return 0;
-+}
-+
-+static void mt7988_shutdown(struct platform_device *pdev)
-+{
-+      struct mt7530_priv *priv = platform_get_drvdata(pdev);
-+
-+      if (!priv)
-+              return;
-+
-+      dsa_switch_shutdown(priv->ds);
-+
-+      dev_set_drvdata(&pdev->dev, NULL);
-+}
-+
-+static struct platform_driver mt7988_platform_driver = {
-+      .probe  = mt7988_probe,
-+      .remove = mt7988_remove,
-+      .shutdown = mt7988_shutdown,
-+      .driver = {
-+              .name = "mt7530-mmio",
-+              .of_match_table = mt7988_of_match,
-+      },
-+};
-+module_platform_driver(mt7988_platform_driver);
-+
-+MODULE_AUTHOR("Daniel Golle <[email protected]>");
-+MODULE_DESCRIPTION("Driver for Mediatek MT7530 Switch (MMIO)");
-+MODULE_LICENSE("GPL");
---- a/drivers/net/dsa/mt7530.c
-+++ b/drivers/net/dsa/mt7530.c
-@@ -2219,6 +2219,47 @@ static const struct irq_domain_ops mt753
- };
- static void
-+mt7988_irq_mask(struct irq_data *d)
-+{
-+      struct mt7530_priv *priv = irq_data_get_irq_chip_data(d);
-+
-+      priv->irq_enable &= ~BIT(d->hwirq);
-+      mt7530_mii_write(priv, MT7530_SYS_INT_EN, priv->irq_enable);
-+}
-+
-+static void
-+mt7988_irq_unmask(struct irq_data *d)
-+{
-+      struct mt7530_priv *priv = irq_data_get_irq_chip_data(d);
-+
-+      priv->irq_enable |= BIT(d->hwirq);
-+      mt7530_mii_write(priv, MT7530_SYS_INT_EN, priv->irq_enable);
-+}
-+
-+static struct irq_chip mt7988_irq_chip = {
-+      .name = KBUILD_MODNAME,
-+      .irq_mask = mt7988_irq_mask,
-+      .irq_unmask = mt7988_irq_unmask,
-+};
-+
-+static int
-+mt7988_irq_map(struct irq_domain *domain, unsigned int irq,
-+             irq_hw_number_t hwirq)
-+{
-+      irq_set_chip_data(irq, domain->host_data);
-+      irq_set_chip_and_handler(irq, &mt7988_irq_chip, handle_simple_irq);
-+      irq_set_nested_thread(irq, true);
-+      irq_set_noprobe(irq);
-+
-+      return 0;
-+}
-+
-+static const struct irq_domain_ops mt7988_irq_domain_ops = {
-+      .map = mt7988_irq_map,
-+      .xlate = irq_domain_xlate_onecell,
-+};
-+
-+static void
- mt7530_setup_mdio_irq(struct mt7530_priv *priv)
- {
-       struct dsa_switch *ds = priv->ds;
-@@ -2252,8 +2293,15 @@ mt7530_setup_irq(struct mt7530_priv *pri
-               return priv->irq ? : -EINVAL;
-       }
--      priv->irq_domain = irq_domain_add_linear(np, MT7530_NUM_PHYS,
--                                               &mt7530_irq_domain_ops, priv);
-+      if (priv->id == ID_MT7988)
-+              priv->irq_domain = irq_domain_add_linear(np, MT7530_NUM_PHYS,
-+                                                       &mt7988_irq_domain_ops,
-+                                                       priv);
-+      else
-+              priv->irq_domain = irq_domain_add_linear(np, MT7530_NUM_PHYS,
-+                                                       &mt7530_irq_domain_ops,
-+                                                       priv);
-+
-       if (!priv->irq_domain) {
-               dev_err(dev, "failed to create IRQ domain\n");
-               return -ENOMEM;
-@@ -2754,6 +2802,25 @@ static void mt7531_mac_port_get_caps(str
-       }
- }
-+static void mt7988_mac_port_get_caps(struct dsa_switch *ds, int port,
-+                                   struct phylink_config *config)
-+{
-+      phy_interface_zero(config->supported_interfaces);
-+
-+      switch (port) {
-+      case 0 ... 4: /* Internal phy */
-+              __set_bit(PHY_INTERFACE_MODE_INTERNAL,
-+                        config->supported_interfaces);
-+              break;
-+
-+      case 6:
-+              __set_bit(PHY_INTERFACE_MODE_INTERNAL,
-+                        config->supported_interfaces);
-+              config->mac_capabilities = MAC_ASYM_PAUSE | MAC_SYM_PAUSE |
-+                                         MAC_10000FD;
-+      }
-+}
-+
- static int
- mt753x_pad_setup(struct dsa_switch *ds, const struct phylink_link_state *state)
- {
-@@ -2830,6 +2897,17 @@ static bool mt753x_is_mac_port(u32 port)
- }
- static int
-+mt7988_mac_config(struct dsa_switch *ds, int port, unsigned int mode,
-+                phy_interface_t interface)
-+{
-+      if (dsa_is_cpu_port(ds, port) &&
-+          interface == PHY_INTERFACE_MODE_INTERNAL)
-+              return 0;
-+
-+      return -EINVAL;
-+}
-+
-+static int
- mt7531_mac_config(struct dsa_switch *ds, int port, unsigned int mode,
-                 phy_interface_t interface)
- {
-@@ -2899,7 +2977,8 @@ mt753x_phylink_mac_config(struct dsa_swi
-       switch (port) {
-       case 0 ... 4: /* Internal phy */
--              if (state->interface != PHY_INTERFACE_MODE_GMII)
-+              if (state->interface != PHY_INTERFACE_MODE_GMII &&
-+                  state->interface != PHY_INTERFACE_MODE_INTERNAL)
-                       goto unsupported;
-               break;
-       case 5: /* 2nd cpu port with phy of port 0 or 4 / external phy */
-@@ -2977,7 +3056,8 @@ static void mt753x_phylink_mac_link_up(s
-       /* MT753x MAC works in 1G full duplex mode for all up-clocked
-        * variants.
-        */
--      if (interface == PHY_INTERFACE_MODE_TRGMII ||
-+      if (interface == PHY_INTERFACE_MODE_INTERNAL ||
-+          interface == PHY_INTERFACE_MODE_TRGMII ||
-           (phy_interface_mode_is_8023z(interface))) {
-               speed = SPEED_1000;
-               duplex = DUPLEX_FULL;
-@@ -3057,6 +3137,21 @@ mt7531_cpu_port_config(struct dsa_switch
-       return 0;
- }
-+static int
-+mt7988_cpu_port_config(struct dsa_switch *ds, int port)
-+{
-+      struct mt7530_priv *priv = ds->priv;
-+
-+      mt7530_write(priv, MT7530_PMCR_P(port),
-+                   PMCR_CPU_PORT_SETTING(priv->id));
-+
-+      mt753x_phylink_mac_link_up(ds, port, MLO_AN_FIXED,
-+                                 PHY_INTERFACE_MODE_INTERNAL, NULL,
-+                                 SPEED_10000, DUPLEX_FULL, true, true);
-+
-+      return 0;
-+}
-+
- static void mt753x_phylink_get_caps(struct dsa_switch *ds, int port,
-                                   struct phylink_config *config)
- {
-@@ -3202,6 +3297,27 @@ static int mt753x_set_mac_eee(struct dsa
-       return 0;
- }
-+static int mt7988_pad_setup(struct dsa_switch *ds, phy_interface_t interface)
-+{
-+      return 0;
-+}
-+
-+static int mt7988_setup(struct dsa_switch *ds)
-+{
-+      struct mt7530_priv *priv = ds->priv;
-+
-+      /* Reset the switch */
-+      reset_control_assert(priv->rstc);
-+      usleep_range(20, 50);
-+      reset_control_deassert(priv->rstc);
-+      usleep_range(20, 50);
-+
-+      /* Reset the switch PHYs */
-+      mt7530_write(priv, MT7530_SYS_CTRL, SYS_CTRL_PHY_RST);
-+
-+      return mt7531_setup_common(ds);
-+}
-+
- const struct dsa_switch_ops mt7530_switch_ops = {
-       .get_tag_protocol       = mtk_get_tag_protocol,
-       .setup                  = mt753x_setup,
-@@ -3271,6 +3387,17 @@ const struct mt753x_info mt753x_table[]
-               .mac_port_get_caps = mt7531_mac_port_get_caps,
-               .mac_port_config = mt7531_mac_config,
-       },
-+      [ID_MT7988] = {
-+              .id = ID_MT7988,
-+              .pcs_ops = &mt7530_pcs_ops,
-+              .sw_setup = mt7988_setup,
-+              .phy_read = mt7531_ind_phy_read,
-+              .phy_write = mt7531_ind_phy_write,
-+              .pad_setup = mt7988_pad_setup,
-+              .cpu_port_config = mt7988_cpu_port_config,
-+              .mac_port_get_caps = mt7988_mac_port_get_caps,
-+              .mac_port_config = mt7988_mac_config,
-+      },
- };
- EXPORT_SYMBOL_GPL(mt753x_table);
---- a/drivers/net/dsa/mt7530.h
-+++ b/drivers/net/dsa/mt7530.h
-@@ -18,6 +18,7 @@ enum mt753x_id {
-       ID_MT7530 = 0,
-       ID_MT7621 = 1,
-       ID_MT7531 = 2,
-+      ID_MT7988 = 3,
- };
- #define       NUM_TRGMII_CTRL                 5
-@@ -59,11 +60,11 @@ enum mt753x_id {
- #define  MT7531_CPU_PMAP_MASK         GENMASK(7, 0)
- #define  MT7531_CPU_PMAP(x)           FIELD_PREP(MT7531_CPU_PMAP_MASK, x)
--#define MT753X_MIRROR_REG(id)         (((id) == ID_MT7531) ? \
-+#define MT753X_MIRROR_REG(id)         ((((id) == ID_MT7531) || ((id) == ID_MT7988)) ? \
-                                        MT7531_CFC : MT7530_MFC)
--#define MT753X_MIRROR_EN(id)          (((id) == ID_MT7531) ? \
-+#define MT753X_MIRROR_EN(id)          ((((id) == ID_MT7531) || ((id) == ID_MT7988)) ? \
-                                        MT7531_MIRROR_EN : MIRROR_EN)
--#define MT753X_MIRROR_MASK(id)                (((id) == ID_MT7531) ? \
-+#define MT753X_MIRROR_MASK(id)                ((((id) == ID_MT7531) || ((id) == ID_MT7988)) ? \
-                                        MT7531_MIRROR_MASK : MIRROR_MASK)
- /* Registers for BPDU and PAE frame control*/
-@@ -332,9 +333,8 @@ enum mt7530_vlan_port_acc_frm {
-                                        MT7531_FORCE_DPX | \
-                                        MT7531_FORCE_RX_FC | \
-                                        MT7531_FORCE_TX_FC)
--#define  PMCR_FORCE_MODE_ID(id)               (((id) == ID_MT7531) ? \
--                                       MT7531_FORCE_MODE : \
--                                       PMCR_FORCE_MODE)
-+#define  PMCR_FORCE_MODE_ID(id)               ((((id) == ID_MT7531) || ((id) == ID_MT7988)) ? \
-+                                       MT7531_FORCE_MODE : PMCR_FORCE_MODE)
- #define  PMCR_LINK_SETTINGS_MASK      (PMCR_TX_EN | PMCR_FORCE_SPEED_1000 | \
-                                        PMCR_RX_EN | PMCR_FORCE_SPEED_100 | \
-                                        PMCR_TX_FC_EN | PMCR_RX_FC_EN | \
diff --git a/target/linux/generic/backport-5.15/790-v6.4-0014-net-dsa-mt7530-fix-support-for-MT7531BE.patch b/target/linux/generic/backport-5.15/790-v6.4-0014-net-dsa-mt7530-fix-support-for-MT7531BE.patch
deleted file mode 100644 (file)
index 2689647..0000000
+++ /dev/null
@@ -1,118 +0,0 @@
-From 91daa4f62ce878b6e1ac5908aceb83550332447f Mon Sep 17 00:00:00 2001
-From: Daniel Golle <[email protected]>
-Date: Sun, 16 Apr 2023 13:08:14 +0100
-Subject: [PATCH] net: dsa: mt7530: fix support for MT7531BE
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-There are two variants of the MT7531 switch IC which got different
-features (and pins) regarding port 5:
- * MT7531AE: SGMII/1000Base-X/2500Base-X SerDes PCS
- * MT7531BE: RGMII
-
-Moving the creation of the SerDes PCS from mt753x_setup to mt7530_probe
-with commit 6de285229773 ("net: dsa: mt7530: move SGMII PCS creation
-to mt7530_probe function") works fine for MT7531AE which got two
-instances of mtk-pcs-lynxi, however, MT7531BE requires mt7531_pll_setup
-to setup clocks before the single PCS on port 6 (usually used as CPU
-port) starts to work and hence the PCS creation failed on MT7531BE.
-
-Fix this by introducing a pointer to mt7531_create_sgmii function in
-struct mt7530_priv and call it again at the end of mt753x_setup like it
-was before commit 6de285229773 ("net: dsa: mt7530: move SGMII PCS
-creation to mt7530_probe function").
-
-Fixes: 6de285229773 ("net: dsa: mt7530: move SGMII PCS creation to mt7530_probe function")
-Signed-off-by: Daniel Golle <[email protected]>
-Acked-by: Arınç ÜNAL <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- drivers/net/dsa/mt7530-mdio.c | 16 ++++++++--------
- drivers/net/dsa/mt7530.c      |  6 ++++++
- drivers/net/dsa/mt7530.h      |  4 ++--
- 3 files changed, 16 insertions(+), 10 deletions(-)
-
---- a/drivers/net/dsa/mt7530-mdio.c
-+++ b/drivers/net/dsa/mt7530-mdio.c
-@@ -81,14 +81,17 @@ static const struct regmap_bus mt7530_re
- };
- static int
--mt7531_create_sgmii(struct mt7530_priv *priv)
-+mt7531_create_sgmii(struct mt7530_priv *priv, bool dual_sgmii)
- {
--      struct regmap_config *mt7531_pcs_config[2];
-+      struct regmap_config *mt7531_pcs_config[2] = {};
-       struct phylink_pcs *pcs;
-       struct regmap *regmap;
-       int i, ret = 0;
--      for (i = 0; i < 2; i++) {
-+      /* MT7531AE has two SGMII units for port 5 and port 6
-+       * MT7531BE has only one SGMII unit for port 6
-+       */
-+      for (i = dual_sgmii ? 0 : 1; i < 2; i++) {
-               mt7531_pcs_config[i] = devm_kzalloc(priv->dev,
-                                                   sizeof(struct regmap_config),
-                                                   GFP_KERNEL);
-@@ -208,11 +211,8 @@ mt7530_probe(struct mdio_device *mdiodev
-       if (IS_ERR(priv->regmap))
-               return PTR_ERR(priv->regmap);
--      if (priv->id == ID_MT7531) {
--              ret = mt7531_create_sgmii(priv);
--              if (ret)
--                      return ret;
--      }
-+      if (priv->id == ID_MT7531)
-+              priv->create_sgmii = mt7531_create_sgmii;
-       return dsa_register_switch(priv->ds);
- }
---- a/drivers/net/dsa/mt7530.c
-+++ b/drivers/net/dsa/mt7530.c
-@@ -3264,6 +3264,12 @@ mt753x_setup(struct dsa_switch *ds)
-       if (ret && priv->irq)
-               mt7530_free_irq_common(priv);
-+      if (priv->create_sgmii) {
-+              ret = priv->create_sgmii(priv, mt7531_dual_sgmii_supported(priv));
-+              if (ret && priv->irq)
-+                      mt7530_free_irq(priv);
-+      }
-+
-       return ret;
- }
---- a/drivers/net/dsa/mt7530.h
-+++ b/drivers/net/dsa/mt7530.h
-@@ -779,10 +779,10 @@ struct mt753x_info {
-  *                    registers
-  * @p6_interface      Holding the current port 6 interface
-  * @p5_intf_sel:      Holding the current port 5 interface select
-- *
-  * @irq:              IRQ number of the switch
-  * @irq_domain:               IRQ domain of the switch irq_chip
-  * @irq_enable:               IRQ enable bits, synced to SYS_INT_EN
-+ * @create_sgmii:     Pointer to function creating SGMII PCS instance(s)
-  */
- struct mt7530_priv {
-       struct device           *dev;
-@@ -801,7 +801,6 @@ struct mt7530_priv {
-       unsigned int            p5_intf_sel;
-       u8                      mirror_rx;
-       u8                      mirror_tx;
--
-       struct mt7530_port      ports[MT7530_NUM_PORTS];
-       struct mt753x_pcs       pcs[MT7530_NUM_PORTS];
-       /* protect among processes for registers access*/
-@@ -809,6 +808,7 @@ struct mt7530_priv {
-       int irq;
-       struct irq_domain *irq_domain;
-       u32 irq_enable;
-+      int (*create_sgmii)(struct mt7530_priv *priv, bool dual_sgmii);
- };
- struct mt7530_hw_vlan_entry {
diff --git a/target/linux/generic/backport-5.15/791-v6.2-01-net-phy-Add-driver-for-Motorcomm-yt8521-gigabit-ethernet.patch b/target/linux/generic/backport-5.15/791-v6.2-01-net-phy-Add-driver-for-Motorcomm-yt8521-gigabit-ethernet.patch
deleted file mode 100644 (file)
index c7f5856..0000000
+++ /dev/null
@@ -1,1724 +0,0 @@
-From 70479a40954cf353e87a486997a3477108c75aa9 Mon Sep 17 00:00:00 2001
-From: Frank <[email protected]>
-Date: Fri, 28 Oct 2022 17:26:21 +0800
-Subject: [PATCH] net: phy: Add driver for Motorcomm yt8521 gigabit ethernet
- phy
-
-Add a driver for the motorcomm yt8521 gigabit ethernet phy. We have verified
- the driver on StarFive VisionFive development board, which is developed by
- Shanghai StarFive Technology Co., Ltd.. On the board, yt8521 gigabit ethernet
- phy works in utp mode, RGMII interface, supports 1000M/100M/10M speeds, and
- wol(magic package).
-
-Signed-off-by: Frank <[email protected]>
-Reviewed-by: Andrew Lunn <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- MAINTAINERS                 |    1 +
- drivers/net/phy/Kconfig     |    2 +-
- drivers/net/phy/motorcomm.c | 1635 ++++++++++++++++++++++++++++++++++-
- 3 files changed, 1635 insertions(+), 3 deletions(-)
-
---- a/MAINTAINERS
-+++ b/MAINTAINERS
-@@ -12701,6 +12701,7 @@ F:     include/uapi/linux/meye.h
- MOTORCOMM PHY DRIVER
- M:    Peter Geis <[email protected]>
-+M:    Frank <[email protected]>
- L:    [email protected]
- S:    Maintained
- F:    drivers/net/phy/motorcomm.c
---- a/drivers/net/phy/Kconfig
-+++ b/drivers/net/phy/Kconfig
-@@ -242,7 +242,7 @@ config MOTORCOMM_PHY
-       tristate "Motorcomm PHYs"
-       help
-         Enables support for Motorcomm network PHYs.
--        Currently supports the YT8511 gigabit PHY.
-+        Currently supports the YT8511, YT8521 Gigabit Ethernet PHYs.
- config NATIONAL_PHY
-       tristate "National Semiconductor PHYs"
---- a/drivers/net/phy/motorcomm.c
-+++ b/drivers/net/phy/motorcomm.c
-@@ -1,15 +1,106 @@
- // SPDX-License-Identifier: GPL-2.0+
- /*
-- * Driver for Motorcomm PHYs
-+ * Motorcomm 8511/8521 PHY driver.
-  *
-  * Author: Peter Geis <[email protected]>
-+ * Author: Frank <[email protected]>
-  */
-+#include <linux/etherdevice.h>
- #include <linux/kernel.h>
- #include <linux/module.h>
- #include <linux/phy.h>
- #define PHY_ID_YT8511         0x0000010a
-+#define PHY_ID_YT8521                         0x0000011A
-+
-+/* YT8521 Register Overview
-+ *    UTP Register space      |       FIBER Register space
-+ *  ------------------------------------------------------------
-+ * |  UTP MII                 |       FIBER MII               |
-+ * |  UTP MMD                 |                               |
-+ * |  UTP Extended            |       FIBER Extended          |
-+ *  ------------------------------------------------------------
-+ * |                  Common Extended                         |
-+ *  ------------------------------------------------------------
-+ */
-+
-+/* 0x10 ~ 0x15 , 0x1E and 0x1F are common MII registers of yt phy */
-+
-+/* Specific Function Control Register */
-+#define YTPHY_SPECIFIC_FUNCTION_CONTROL_REG   0x10
-+
-+/* 2b00 Manual MDI configuration
-+ * 2b01 Manual MDIX configuration
-+ * 2b10 Reserved
-+ * 2b11 Enable automatic crossover for all modes  *default*
-+ */
-+#define YTPHY_SFCR_MDI_CROSSOVER_MODE_MASK    (BIT(6) | BIT(5))
-+#define YTPHY_SFCR_CROSSOVER_EN                       BIT(3)
-+#define YTPHY_SFCR_SQE_TEST_EN                        BIT(2)
-+#define YTPHY_SFCR_POLARITY_REVERSAL_EN               BIT(1)
-+#define YTPHY_SFCR_JABBER_DIS                 BIT(0)
-+
-+/* Specific Status Register */
-+#define YTPHY_SPECIFIC_STATUS_REG             0x11
-+#define YTPHY_SSR_SPEED_MODE_OFFSET           14
-+
-+#define YTPHY_SSR_SPEED_MODE_MASK             (BIT(15) | BIT(14))
-+#define YTPHY_SSR_SPEED_10M                   0x0
-+#define YTPHY_SSR_SPEED_100M                  0x1
-+#define YTPHY_SSR_SPEED_1000M                 0x2
-+#define YTPHY_SSR_DUPLEX_OFFSET                       13
-+#define YTPHY_SSR_DUPLEX                      BIT(13)
-+#define YTPHY_SSR_PAGE_RECEIVED                       BIT(12)
-+#define YTPHY_SSR_SPEED_DUPLEX_RESOLVED               BIT(11)
-+#define YTPHY_SSR_LINK                                BIT(10)
-+#define YTPHY_SSR_MDIX_CROSSOVER              BIT(6)
-+#define YTPHY_SSR_DOWNGRADE                   BIT(5)
-+#define YTPHY_SSR_TRANSMIT_PAUSE              BIT(3)
-+#define YTPHY_SSR_RECEIVE_PAUSE                       BIT(2)
-+#define YTPHY_SSR_POLARITY                    BIT(1)
-+#define YTPHY_SSR_JABBER                      BIT(0)
-+
-+/* Interrupt enable Register */
-+#define YTPHY_INTERRUPT_ENABLE_REG            0x12
-+#define YTPHY_IER_WOL                         BIT(6)
-+
-+/* Interrupt Status Register */
-+#define YTPHY_INTERRUPT_STATUS_REG            0x13
-+#define YTPHY_ISR_AUTONEG_ERR                 BIT(15)
-+#define YTPHY_ISR_SPEED_CHANGED                       BIT(14)
-+#define YTPHY_ISR_DUPLEX_CHANGED              BIT(13)
-+#define YTPHY_ISR_PAGE_RECEIVED                       BIT(12)
-+#define YTPHY_ISR_LINK_FAILED                 BIT(11)
-+#define YTPHY_ISR_LINK_SUCCESSED              BIT(10)
-+#define YTPHY_ISR_WOL                         BIT(6)
-+#define YTPHY_ISR_WIRESPEED_DOWNGRADE         BIT(5)
-+#define YTPHY_ISR_SERDES_LINK_FAILED          BIT(3)
-+#define YTPHY_ISR_SERDES_LINK_SUCCESSED               BIT(2)
-+#define YTPHY_ISR_POLARITY_CHANGED            BIT(1)
-+#define YTPHY_ISR_JABBER_HAPPENED             BIT(0)
-+
-+/* Speed Auto Downgrade Control Register */
-+#define YTPHY_SPEED_AUTO_DOWNGRADE_CONTROL_REG        0x14
-+#define YTPHY_SADCR_SPEED_DOWNGRADE_EN                BIT(5)
-+
-+/* If these bits are set to 3, the PHY attempts five times ( 3(set value) +
-+ * additional 2) before downgrading, default 0x3
-+ */
-+#define YTPHY_SADCR_SPEED_RETRY_LIMIT         (0x3 << 2)
-+
-+/* Rx Error Counter Register */
-+#define YTPHY_RX_ERROR_COUNTER_REG            0x15
-+
-+/* Extended Register's Address Offset Register */
-+#define YTPHY_PAGE_SELECT                     0x1E
-+
-+/* Extended Register's Data Register */
-+#define YTPHY_PAGE_DATA                               0x1F
-+
-+/* FIBER Auto-Negotiation link partner ability */
-+#define YTPHY_FLPA_PAUSE                      (0x3 << 7)
-+#define YTPHY_FLPA_ASYM_PAUSE                 (0x2 << 7)
- #define YT8511_PAGE_SELECT    0x1e
- #define YT8511_PAGE           0x1f
-@@ -38,6 +129,352 @@
- #define YT8511_DELAY_FE_TX_EN (0xf << 12)
- #define YT8511_DELAY_FE_TX_DIS        (0x2 << 12)
-+/* Extended register is different from MMD Register and MII Register.
-+ * We can use ytphy_read_ext/ytphy_write_ext/ytphy_modify_ext function to
-+ * operate extended register.
-+ * Extended Register  start
-+ */
-+
-+/* Phy gmii clock gating Register */
-+#define YT8521_CLOCK_GATING_REG                       0xC
-+#define YT8521_CGR_RX_CLK_EN                  BIT(12)
-+
-+#define YT8521_EXTREG_SLEEP_CONTROL1_REG      0x27
-+#define YT8521_ESC1R_SLEEP_SW                 BIT(15)
-+#define YT8521_ESC1R_PLLON_SLP                        BIT(14)
-+
-+/* Phy fiber Link timer cfg2 Register */
-+#define YT8521_LINK_TIMER_CFG2_REG            0xA5
-+#define YT8521_LTCR_EN_AUTOSEN                        BIT(15)
-+
-+/* 0xA000, 0xA001, 0xA003 ,and 0xA006 ~ 0xA00A  are common ext registers
-+ * of yt8521 phy. There is no need to switch reg space when operating these
-+ * registers.
-+ */
-+
-+#define YT8521_REG_SPACE_SELECT_REG           0xA000
-+#define YT8521_RSSR_SPACE_MASK                        BIT(1)
-+#define YT8521_RSSR_FIBER_SPACE                       (0x1 << 1)
-+#define YT8521_RSSR_UTP_SPACE                 (0x0 << 1)
-+#define YT8521_RSSR_TO_BE_ARBITRATED          (0xFF)
-+
-+#define YT8521_CHIP_CONFIG_REG                        0xA001
-+#define YT8521_CCR_SW_RST                     BIT(15)
-+
-+#define YT8521_CCR_MODE_SEL_MASK              (BIT(2) | BIT(1) | BIT(0))
-+#define YT8521_CCR_MODE_UTP_TO_RGMII          0
-+#define YT8521_CCR_MODE_FIBER_TO_RGMII                1
-+#define YT8521_CCR_MODE_UTP_FIBER_TO_RGMII    2
-+#define YT8521_CCR_MODE_UTP_TO_SGMII          3
-+#define YT8521_CCR_MODE_SGPHY_TO_RGMAC                4
-+#define YT8521_CCR_MODE_SGMAC_TO_RGPHY                5
-+#define YT8521_CCR_MODE_UTP_TO_FIBER_AUTO     6
-+#define YT8521_CCR_MODE_UTP_TO_FIBER_FORCE    7
-+
-+/* 3 phy polling modes,poll mode combines utp and fiber mode*/
-+#define YT8521_MODE_FIBER                     0x1
-+#define YT8521_MODE_UTP                               0x2
-+#define YT8521_MODE_POLL                      0x3
-+
-+#define YT8521_RGMII_CONFIG1_REG              0xA003
-+
-+/* TX Gig-E Delay is bits 3:0, default 0x1
-+ * TX Fast-E Delay is bits 7:4, default 0xf
-+ * RX Delay is bits 13:10, default 0x0
-+ * Delay = 150ps * N
-+ * On = 2250ps, off = 0ps
-+ */
-+#define YT8521_RC1R_RX_DELAY_MASK             (0xF << 10)
-+#define YT8521_RC1R_RX_DELAY_EN                       (0xF << 10)
-+#define YT8521_RC1R_RX_DELAY_DIS              (0x0 << 10)
-+#define YT8521_RC1R_FE_TX_DELAY_MASK          (0xF << 4)
-+#define YT8521_RC1R_FE_TX_DELAY_EN            (0xF << 4)
-+#define YT8521_RC1R_FE_TX_DELAY_DIS           (0x0 << 4)
-+#define YT8521_RC1R_GE_TX_DELAY_MASK          (0xF << 0)
-+#define YT8521_RC1R_GE_TX_DELAY_EN            (0xF << 0)
-+#define YT8521_RC1R_GE_TX_DELAY_DIS           (0x0 << 0)
-+
-+#define YTPHY_MISC_CONFIG_REG                 0xA006
-+#define YTPHY_MCR_FIBER_SPEED_MASK            BIT(0)
-+#define YTPHY_MCR_FIBER_1000BX                        (0x1 << 0)
-+#define YTPHY_MCR_FIBER_100FX                 (0x0 << 0)
-+
-+/* WOL MAC ADDR: MACADDR2(highest), MACADDR1(middle), MACADDR0(lowest) */
-+#define YTPHY_WOL_MACADDR2_REG                        0xA007
-+#define YTPHY_WOL_MACADDR1_REG                        0xA008
-+#define YTPHY_WOL_MACADDR0_REG                        0xA009
-+
-+#define YTPHY_WOL_CONFIG_REG                  0xA00A
-+#define YTPHY_WCR_INTR_SEL                    BIT(6)
-+#define YTPHY_WCR_ENABLE                      BIT(3)
-+
-+/* 2b00 84ms
-+ * 2b01 168ms  *default*
-+ * 2b10 336ms
-+ * 2b11 672ms
-+ */
-+#define YTPHY_WCR_PULSE_WIDTH_MASK            (BIT(2) | BIT(1))
-+#define YTPHY_WCR_PULSE_WIDTH_672MS           (BIT(2) | BIT(1))
-+
-+/* 1b0 Interrupt and WOL events is level triggered and active LOW  *default*
-+ * 1b1 Interrupt and WOL events is pulse triggered and active LOW
-+ */
-+#define YTPHY_WCR_TYPE_PULSE                  BIT(0)
-+
-+/* Extended Register  end */
-+
-+struct yt8521_priv {
-+      /* combo_advertising is used for case of YT8521 in combo mode,
-+       * this means that yt8521 may work in utp or fiber mode which depends
-+       * on which media is connected (YT8521_RSSR_TO_BE_ARBITRATED).
-+       */
-+      __ETHTOOL_DECLARE_LINK_MODE_MASK(combo_advertising);
-+
-+      /* YT8521_MODE_FIBER / YT8521_MODE_UTP / YT8521_MODE_POLL*/
-+      u8 polling_mode;
-+      u8 strap_mode; /* 8 working modes  */
-+      /* current reg page of yt8521 phy:
-+       * YT8521_RSSR_UTP_SPACE
-+       * YT8521_RSSR_FIBER_SPACE
-+       * YT8521_RSSR_TO_BE_ARBITRATED
-+       */
-+      u8 reg_page;
-+};
-+
-+/**
-+ * ytphy_read_ext() - read a PHY's extended register
-+ * @phydev: a pointer to a &struct phy_device
-+ * @regnum: register number to read
-+ *
-+ * NOTE:The caller must have taken the MDIO bus lock.
-+ *
-+ * returns the value of regnum reg or negative error code
-+ */
-+static int ytphy_read_ext(struct phy_device *phydev, u16 regnum)
-+{
-+      int ret;
-+
-+      ret = __phy_write(phydev, YTPHY_PAGE_SELECT, regnum);
-+      if (ret < 0)
-+              return ret;
-+
-+      return __phy_read(phydev, YTPHY_PAGE_DATA);
-+}
-+
-+/**
-+ * ytphy_read_ext_with_lock() - read a PHY's extended register
-+ * @phydev: a pointer to a &struct phy_device
-+ * @regnum: register number to read
-+ *
-+ * returns the value of regnum reg or negative error code
-+ */
-+static int ytphy_read_ext_with_lock(struct phy_device *phydev, u16 regnum)
-+{
-+      int ret;
-+
-+      phy_lock_mdio_bus(phydev);
-+      ret = ytphy_read_ext(phydev, regnum);
-+      phy_unlock_mdio_bus(phydev);
-+
-+      return ret;
-+}
-+
-+/**
-+ * ytphy_write_ext() - write a PHY's extended register
-+ * @phydev: a pointer to a &struct phy_device
-+ * @regnum: register number to write
-+ * @val: value to write to @regnum
-+ *
-+ * NOTE:The caller must have taken the MDIO bus lock.
-+ *
-+ * returns 0 or negative error code
-+ */
-+static int ytphy_write_ext(struct phy_device *phydev, u16 regnum, u16 val)
-+{
-+      int ret;
-+
-+      ret = __phy_write(phydev, YTPHY_PAGE_SELECT, regnum);
-+      if (ret < 0)
-+              return ret;
-+
-+      return __phy_write(phydev, YTPHY_PAGE_DATA, val);
-+}
-+
-+/**
-+ * ytphy_write_ext_with_lock() - write a PHY's extended register
-+ * @phydev: a pointer to a &struct phy_device
-+ * @regnum: register number to write
-+ * @val: value to write to @regnum
-+ *
-+ * returns 0 or negative error code
-+ */
-+static int ytphy_write_ext_with_lock(struct phy_device *phydev, u16 regnum,
-+                                   u16 val)
-+{
-+      int ret;
-+
-+      phy_lock_mdio_bus(phydev);
-+      ret = ytphy_write_ext(phydev, regnum, val);
-+      phy_unlock_mdio_bus(phydev);
-+
-+      return ret;
-+}
-+
-+/**
-+ * ytphy_modify_ext() - bits modify a PHY's extended register
-+ * @phydev: a pointer to a &struct phy_device
-+ * @regnum: register number to write
-+ * @mask: bit mask of bits to clear
-+ * @set: bit mask of bits to set
-+ *
-+ * NOTE: Convenience function which allows a PHY's extended register to be
-+ * modified as new register value = (old register value & ~mask) | set.
-+ * The caller must have taken the MDIO bus lock.
-+ *
-+ * returns 0 or negative error code
-+ */
-+static int ytphy_modify_ext(struct phy_device *phydev, u16 regnum, u16 mask,
-+                          u16 set)
-+{
-+      int ret;
-+
-+      ret = __phy_write(phydev, YTPHY_PAGE_SELECT, regnum);
-+      if (ret < 0)
-+              return ret;
-+
-+      return __phy_modify(phydev, YTPHY_PAGE_DATA, mask, set);
-+}
-+
-+/**
-+ * ytphy_modify_ext_with_lock() - bits modify a PHY's extended register
-+ * @phydev: a pointer to a &struct phy_device
-+ * @regnum: register number to write
-+ * @mask: bit mask of bits to clear
-+ * @set: bit mask of bits to set
-+ *
-+ * NOTE: Convenience function which allows a PHY's extended register to be
-+ * modified as new register value = (old register value & ~mask) | set.
-+ *
-+ * returns 0 or negative error code
-+ */
-+static int ytphy_modify_ext_with_lock(struct phy_device *phydev, u16 regnum,
-+                                    u16 mask, u16 set)
-+{
-+      int ret;
-+
-+      phy_lock_mdio_bus(phydev);
-+      ret = ytphy_modify_ext(phydev, regnum, mask, set);
-+      phy_unlock_mdio_bus(phydev);
-+
-+      return ret;
-+}
-+
-+/**
-+ * ytphy_get_wol() - report whether wake-on-lan is enabled
-+ * @phydev: a pointer to a &struct phy_device
-+ * @wol: a pointer to a &struct ethtool_wolinfo
-+ *
-+ * NOTE: YTPHY_WOL_CONFIG_REG is common ext reg.
-+ */
-+static void ytphy_get_wol(struct phy_device *phydev,
-+                        struct ethtool_wolinfo *wol)
-+{
-+      int wol_config;
-+
-+      wol->supported = WAKE_MAGIC;
-+      wol->wolopts = 0;
-+
-+      wol_config = ytphy_read_ext_with_lock(phydev, YTPHY_WOL_CONFIG_REG);
-+      if (wol_config < 0)
-+              return;
-+
-+      if (wol_config & YTPHY_WCR_ENABLE)
-+              wol->wolopts |= WAKE_MAGIC;
-+}
-+
-+/**
-+ * ytphy_set_wol() - turn wake-on-lan on or off
-+ * @phydev: a pointer to a &struct phy_device
-+ * @wol: a pointer to a &struct ethtool_wolinfo
-+ *
-+ * NOTE: YTPHY_WOL_CONFIG_REG, YTPHY_WOL_MACADDR2_REG, YTPHY_WOL_MACADDR1_REG
-+ * and YTPHY_WOL_MACADDR0_REG are common ext reg. The
-+ * YTPHY_INTERRUPT_ENABLE_REG of UTP is special, fiber also use this register.
-+ *
-+ * returns 0 or negative errno code
-+ */
-+static int ytphy_set_wol(struct phy_device *phydev, struct ethtool_wolinfo *wol)
-+{
-+      struct net_device *p_attached_dev;
-+      const u16 mac_addr_reg[] = {
-+              YTPHY_WOL_MACADDR2_REG,
-+              YTPHY_WOL_MACADDR1_REG,
-+              YTPHY_WOL_MACADDR0_REG,
-+      };
-+      const u8 *mac_addr;
-+      int old_page;
-+      int ret = 0;
-+      u16 mask;
-+      u16 val;
-+      u8 i;
-+
-+      if (wol->wolopts & WAKE_MAGIC) {
-+              p_attached_dev = phydev->attached_dev;
-+              if (!p_attached_dev)
-+                      return -ENODEV;
-+
-+              mac_addr = (const u8 *)p_attached_dev->dev_addr;
-+              if (!is_valid_ether_addr(mac_addr))
-+                      return -EINVAL;
-+
-+              /* lock mdio bus then switch to utp reg space */
-+              old_page = phy_select_page(phydev, YT8521_RSSR_UTP_SPACE);
-+              if (old_page < 0)
-+                      goto err_restore_page;
-+
-+              /* Store the device address for the magic packet */
-+              for (i = 0; i < 3; i++) {
-+                      ret = ytphy_write_ext(phydev, mac_addr_reg[i],
-+                                            ((mac_addr[i * 2] << 8)) |
-+                                                    (mac_addr[i * 2 + 1]));
-+                      if (ret < 0)
-+                              goto err_restore_page;
-+              }
-+
-+              /* Enable WOL feature */
-+              mask = YTPHY_WCR_PULSE_WIDTH_MASK | YTPHY_WCR_INTR_SEL;
-+              val = YTPHY_WCR_ENABLE | YTPHY_WCR_INTR_SEL;
-+              val |= YTPHY_WCR_TYPE_PULSE | YTPHY_WCR_PULSE_WIDTH_672MS;
-+              ret = ytphy_modify_ext(phydev, YTPHY_WOL_CONFIG_REG, mask, val);
-+              if (ret < 0)
-+                      goto err_restore_page;
-+
-+              /* Enable WOL interrupt */
-+              ret = __phy_modify(phydev, YTPHY_INTERRUPT_ENABLE_REG, 0,
-+                                 YTPHY_IER_WOL);
-+              if (ret < 0)
-+                      goto err_restore_page;
-+
-+      } else {
-+              old_page = phy_select_page(phydev, YT8521_RSSR_UTP_SPACE);
-+              if (old_page < 0)
-+                      goto err_restore_page;
-+
-+              /* Disable WOL feature */
-+              mask = YTPHY_WCR_ENABLE | YTPHY_WCR_INTR_SEL;
-+              ret = ytphy_modify_ext(phydev, YTPHY_WOL_CONFIG_REG, mask, 0);
-+
-+              /* Disable WOL interrupt */
-+              ret = __phy_modify(phydev, YTPHY_INTERRUPT_ENABLE_REG,
-+                                 YTPHY_IER_WOL, 0);
-+              if (ret < 0)
-+                      goto err_restore_page;
-+      }
-+
-+err_restore_page:
-+      return phy_restore_page(phydev, old_page, ret);
-+}
-+
- static int yt8511_read_page(struct phy_device *phydev)
- {
-       return __phy_read(phydev, YT8511_PAGE_SELECT);
-@@ -111,6 +548,1181 @@ err_restore_page:
-       return phy_restore_page(phydev, oldpage, ret);
- }
-+/**
-+ * yt8521_read_page() - read reg page
-+ * @phydev: a pointer to a &struct phy_device
-+ *
-+ * returns current reg space of yt8521 (YT8521_RSSR_FIBER_SPACE/
-+ * YT8521_RSSR_UTP_SPACE) or negative errno code
-+ */
-+static int yt8521_read_page(struct phy_device *phydev)
-+{
-+      int old_page;
-+
-+      old_page = ytphy_read_ext(phydev, YT8521_REG_SPACE_SELECT_REG);
-+      if (old_page < 0)
-+              return old_page;
-+
-+      if ((old_page & YT8521_RSSR_SPACE_MASK) == YT8521_RSSR_FIBER_SPACE)
-+              return YT8521_RSSR_FIBER_SPACE;
-+
-+      return YT8521_RSSR_UTP_SPACE;
-+};
-+
-+/**
-+ * yt8521_write_page() - write reg page
-+ * @phydev: a pointer to a &struct phy_device
-+ * @page: The reg page(YT8521_RSSR_FIBER_SPACE/YT8521_RSSR_UTP_SPACE) to write.
-+ *
-+ * returns 0 or negative errno code
-+ */
-+static int yt8521_write_page(struct phy_device *phydev, int page)
-+{
-+      int mask = YT8521_RSSR_SPACE_MASK;
-+      int set;
-+
-+      if ((page & YT8521_RSSR_SPACE_MASK) == YT8521_RSSR_FIBER_SPACE)
-+              set = YT8521_RSSR_FIBER_SPACE;
-+      else
-+              set = YT8521_RSSR_UTP_SPACE;
-+
-+      return ytphy_modify_ext(phydev, YT8521_REG_SPACE_SELECT_REG, mask, set);
-+};
-+
-+/**
-+ * yt8521_probe() - read chip config then set suitable polling_mode
-+ * @phydev: a pointer to a &struct phy_device
-+ *
-+ * returns 0 or negative errno code
-+ */
-+static int yt8521_probe(struct phy_device *phydev)
-+{
-+      struct device *dev = &phydev->mdio.dev;
-+      struct yt8521_priv *priv;
-+      int chip_config;
-+      int ret;
-+
-+      priv = devm_kzalloc(dev, sizeof(*priv), GFP_KERNEL);
-+      if (!priv)
-+              return -ENOMEM;
-+
-+      phydev->priv = priv;
-+
-+      chip_config = ytphy_read_ext_with_lock(phydev, YT8521_CHIP_CONFIG_REG);
-+      if (chip_config < 0)
-+              return chip_config;
-+
-+      priv->strap_mode = chip_config & YT8521_CCR_MODE_SEL_MASK;
-+      switch (priv->strap_mode) {
-+      case YT8521_CCR_MODE_FIBER_TO_RGMII:
-+      case YT8521_CCR_MODE_SGPHY_TO_RGMAC:
-+      case YT8521_CCR_MODE_SGMAC_TO_RGPHY:
-+              priv->polling_mode = YT8521_MODE_FIBER;
-+              priv->reg_page = YT8521_RSSR_FIBER_SPACE;
-+              phydev->port = PORT_FIBRE;
-+              break;
-+      case YT8521_CCR_MODE_UTP_FIBER_TO_RGMII:
-+      case YT8521_CCR_MODE_UTP_TO_FIBER_AUTO:
-+      case YT8521_CCR_MODE_UTP_TO_FIBER_FORCE:
-+              priv->polling_mode = YT8521_MODE_POLL;
-+              priv->reg_page = YT8521_RSSR_TO_BE_ARBITRATED;
-+              phydev->port = PORT_NONE;
-+              break;
-+      case YT8521_CCR_MODE_UTP_TO_SGMII:
-+      case YT8521_CCR_MODE_UTP_TO_RGMII:
-+              priv->polling_mode = YT8521_MODE_UTP;
-+              priv->reg_page = YT8521_RSSR_UTP_SPACE;
-+              phydev->port = PORT_TP;
-+              break;
-+      }
-+      /* set default reg space */
-+      if (priv->reg_page != YT8521_RSSR_TO_BE_ARBITRATED) {
-+              ret = ytphy_write_ext_with_lock(phydev,
-+                                              YT8521_REG_SPACE_SELECT_REG,
-+                                              priv->reg_page);
-+              if (ret < 0)
-+                      return ret;
-+      }
-+
-+      return 0;
-+}
-+
-+/**
-+ * ytphy_utp_read_lpa() - read LPA then setup lp_advertising for utp
-+ * @phydev: a pointer to a &struct phy_device
-+ *
-+ * NOTE:The caller must have taken the MDIO bus lock.
-+ *
-+ * returns 0 or negative errno code
-+ */
-+static int ytphy_utp_read_lpa(struct phy_device *phydev)
-+{
-+      int lpa, lpagb;
-+
-+      if (phydev->autoneg == AUTONEG_ENABLE) {
-+              if (!phydev->autoneg_complete) {
-+                      mii_stat1000_mod_linkmode_lpa_t(phydev->lp_advertising,
-+                                                      0);
-+                      mii_lpa_mod_linkmode_lpa_t(phydev->lp_advertising, 0);
-+                      return 0;
-+              }
-+
-+              if (phydev->is_gigabit_capable) {
-+                      lpagb = __phy_read(phydev, MII_STAT1000);
-+                      if (lpagb < 0)
-+                              return lpagb;
-+
-+                      if (lpagb & LPA_1000MSFAIL) {
-+                              int adv = __phy_read(phydev, MII_CTRL1000);
-+
-+                              if (adv < 0)
-+                                      return adv;
-+
-+                              if (adv & CTL1000_ENABLE_MASTER)
-+                                      phydev_err(phydev, "Master/Slave resolution failed, maybe conflicting manual settings?\n");
-+                              else
-+                                      phydev_err(phydev, "Master/Slave resolution failed\n");
-+                              return -ENOLINK;
-+                      }
-+
-+                      mii_stat1000_mod_linkmode_lpa_t(phydev->lp_advertising,
-+                                                      lpagb);
-+              }
-+
-+              lpa = __phy_read(phydev, MII_LPA);
-+              if (lpa < 0)
-+                      return lpa;
-+
-+              mii_lpa_mod_linkmode_lpa_t(phydev->lp_advertising, lpa);
-+      } else {
-+              linkmode_zero(phydev->lp_advertising);
-+      }
-+
-+      return 0;
-+}
-+
-+/**
-+ * yt8521_adjust_status() - update speed and duplex to phydev. when in fiber
-+ * mode, adjust speed and duplex.
-+ * @phydev: a pointer to a &struct phy_device
-+ * @status: yt8521 status read from YTPHY_SPECIFIC_STATUS_REG
-+ * @is_utp: false(yt8521 work in fiber mode) or true(yt8521 work in utp mode)
-+ *
-+ * NOTE:The caller must have taken the MDIO bus lock.
-+ *
-+ * returns 0
-+ */
-+static int yt8521_adjust_status(struct phy_device *phydev, int status,
-+                              bool is_utp)
-+{
-+      int speed_mode, duplex;
-+      int speed;
-+      int err;
-+      int lpa;
-+
-+      if (is_utp)
-+              duplex = (status & YTPHY_SSR_DUPLEX) >> YTPHY_SSR_DUPLEX_OFFSET;
-+      else
-+              duplex = DUPLEX_FULL;   /* for fiber, it always DUPLEX_FULL */
-+
-+      speed_mode = (status & YTPHY_SSR_SPEED_MODE_MASK) >>
-+                   YTPHY_SSR_SPEED_MODE_OFFSET;
-+
-+      switch (speed_mode) {
-+      case YTPHY_SSR_SPEED_10M:
-+              if (is_utp)
-+                      speed = SPEED_10;
-+              else
-+                      /* for fiber, it will never run here, default to
-+                       * SPEED_UNKNOWN
-+                       */
-+                      speed = SPEED_UNKNOWN;
-+              break;
-+      case YTPHY_SSR_SPEED_100M:
-+              speed = SPEED_100;
-+              break;
-+      case YTPHY_SSR_SPEED_1000M:
-+              speed = SPEED_1000;
-+              break;
-+      default:
-+              speed = SPEED_UNKNOWN;
-+              break;
-+      }
-+
-+      phydev->speed = speed;
-+      phydev->duplex = duplex;
-+
-+      if (is_utp) {
-+              err = ytphy_utp_read_lpa(phydev);
-+              if (err < 0)
-+                      return err;
-+
-+              phy_resolve_aneg_pause(phydev);
-+      } else {
-+              lpa = __phy_read(phydev, MII_LPA);
-+              if (lpa < 0)
-+                      return lpa;
-+
-+              /* only support 1000baseX Full */
-+              linkmode_mod_bit(ETHTOOL_LINK_MODE_1000baseX_Full_BIT,
-+                               phydev->lp_advertising, lpa & LPA_1000XFULL);
-+
-+              if (!(lpa & YTPHY_FLPA_PAUSE)) {
-+                      phydev->pause = 0;
-+                      phydev->asym_pause = 0;
-+              } else if ((lpa & YTPHY_FLPA_ASYM_PAUSE)) {
-+                      phydev->pause = 1;
-+                      phydev->asym_pause = 1;
-+              } else {
-+                      phydev->pause = 1;
-+                      phydev->asym_pause = 0;
-+              }
-+      }
-+
-+      return 0;
-+}
-+
-+/**
-+ * yt8521_read_status_paged() -  determines the speed and duplex of one page
-+ * @phydev: a pointer to a &struct phy_device
-+ * @page: The reg page(YT8521_RSSR_FIBER_SPACE/YT8521_RSSR_UTP_SPACE) to
-+ * operate.
-+ *
-+ * returns 1 (utp or fiber link),0 (no link) or negative errno code
-+ */
-+static int yt8521_read_status_paged(struct phy_device *phydev, int page)
-+{
-+      int fiber_latch_val;
-+      int fiber_curr_val;
-+      int old_page;
-+      int ret = 0;
-+      int status;
-+      int link;
-+
-+      linkmode_zero(phydev->lp_advertising);
-+      phydev->duplex = DUPLEX_UNKNOWN;
-+      phydev->speed = SPEED_UNKNOWN;
-+      phydev->asym_pause = 0;
-+      phydev->pause = 0;
-+
-+      /* YT8521 has two reg space (utp/fiber) for linkup with utp/fiber
-+       * respectively. but for utp/fiber combo mode, reg space should be
-+       * arbitrated based on media priority. by default, utp takes
-+       * priority. reg space should be properly set before read
-+       * YTPHY_SPECIFIC_STATUS_REG.
-+       */
-+
-+      page &= YT8521_RSSR_SPACE_MASK;
-+      old_page = phy_select_page(phydev, page);
-+      if (old_page < 0)
-+              goto err_restore_page;
-+
-+      /* Read YTPHY_SPECIFIC_STATUS_REG, which indicates the speed and duplex
-+       * of the PHY is actually using.
-+       */
-+      ret = __phy_read(phydev, YTPHY_SPECIFIC_STATUS_REG);
-+      if (ret < 0)
-+              goto err_restore_page;
-+
-+      status = ret;
-+      link = !!(status & YTPHY_SSR_LINK);
-+
-+      /* When PHY is in fiber mode, speed transferred from 1000Mbps to
-+       * 100Mbps,there is not link down from YTPHY_SPECIFIC_STATUS_REG, so
-+       * we need check MII_BMSR to identify such case.
-+       */
-+      if (page == YT8521_RSSR_FIBER_SPACE) {
-+              ret = __phy_read(phydev, MII_BMSR);
-+              if (ret < 0)
-+                      goto err_restore_page;
-+
-+              fiber_latch_val = ret;
-+              ret = __phy_read(phydev, MII_BMSR);
-+              if (ret < 0)
-+                      goto err_restore_page;
-+
-+              fiber_curr_val = ret;
-+              if (link && fiber_latch_val != fiber_curr_val) {
-+                      link = 0;
-+                      phydev_info(phydev,
-+                                  "%s, fiber link down detect, latch = %04x, curr = %04x\n",
-+                                  __func__, fiber_latch_val, fiber_curr_val);
-+              }
-+      } else {
-+              /* Read autonegotiation status */
-+              ret = __phy_read(phydev, MII_BMSR);
-+              if (ret < 0)
-+                      goto err_restore_page;
-+
-+              phydev->autoneg_complete = ret & BMSR_ANEGCOMPLETE ? 1 : 0;
-+      }
-+
-+      if (link) {
-+              if (page == YT8521_RSSR_UTP_SPACE)
-+                      yt8521_adjust_status(phydev, status, true);
-+              else
-+                      yt8521_adjust_status(phydev, status, false);
-+      }
-+      return phy_restore_page(phydev, old_page, link);
-+
-+err_restore_page:
-+      return phy_restore_page(phydev, old_page, ret);
-+}
-+
-+/**
-+ * yt8521_read_status() -  determines the negotiated speed and duplex
-+ * @phydev: a pointer to a &struct phy_device
-+ *
-+ * returns 0 or negative errno code
-+ */
-+static int yt8521_read_status(struct phy_device *phydev)
-+{
-+      struct yt8521_priv *priv = phydev->priv;
-+      int link_fiber = 0;
-+      int link_utp;
-+      int link;
-+      int ret;
-+
-+      if (priv->reg_page != YT8521_RSSR_TO_BE_ARBITRATED) {
-+              link = yt8521_read_status_paged(phydev, priv->reg_page);
-+              if (link < 0)
-+                      return link;
-+      } else {
-+              /* when page is YT8521_RSSR_TO_BE_ARBITRATED, arbitration is
-+               * needed. by default, utp is higher priority.
-+               */
-+
-+              link_utp = yt8521_read_status_paged(phydev,
-+                                                  YT8521_RSSR_UTP_SPACE);
-+              if (link_utp < 0)
-+                      return link_utp;
-+
-+              if (!link_utp) {
-+                      link_fiber = yt8521_read_status_paged(phydev,
-+                                                            YT8521_RSSR_FIBER_SPACE);
-+                      if (link_fiber < 0)
-+                              return link_fiber;
-+              }
-+
-+              link = link_utp || link_fiber;
-+      }
-+
-+      if (link) {
-+              if (phydev->link == 0) {
-+                      /* arbitrate reg space based on linkup media type. */
-+                      if (priv->polling_mode == YT8521_MODE_POLL &&
-+                          priv->reg_page == YT8521_RSSR_TO_BE_ARBITRATED) {
-+                              if (link_fiber)
-+                                      priv->reg_page =
-+                                              YT8521_RSSR_FIBER_SPACE;
-+                              else
-+                                      priv->reg_page = YT8521_RSSR_UTP_SPACE;
-+
-+                              ret = ytphy_write_ext_with_lock(phydev,
-+                                                              YT8521_REG_SPACE_SELECT_REG,
-+                                                              priv->reg_page);
-+                              if (ret < 0)
-+                                      return ret;
-+
-+                              phydev->port = link_fiber ? PORT_FIBRE : PORT_TP;
-+
-+                              phydev_info(phydev, "%s, link up, media: %s\n",
-+                                          __func__,
-+                                          (phydev->port == PORT_TP) ?
-+                                          "UTP" : "Fiber");
-+                      }
-+              }
-+              phydev->link = 1;
-+      } else {
-+              if (phydev->link == 1) {
-+                      phydev_info(phydev, "%s, link down, media: %s\n",
-+                                  __func__, (phydev->port == PORT_TP) ?
-+                                  "UTP" : "Fiber");
-+
-+                      /* When in YT8521_MODE_POLL mode, need prepare for next
-+                       * arbitration.
-+                       */
-+                      if (priv->polling_mode == YT8521_MODE_POLL) {
-+                              priv->reg_page = YT8521_RSSR_TO_BE_ARBITRATED;
-+                              phydev->port = PORT_NONE;
-+                      }
-+              }
-+
-+              phydev->link = 0;
-+      }
-+
-+      return 0;
-+}
-+
-+/**
-+ * yt8521_modify_bmcr_paged - bits modify a PHY's BMCR register of one page
-+ * @phydev: the phy_device struct
-+ * @page: The reg page(YT8521_RSSR_FIBER_SPACE/YT8521_RSSR_UTP_SPACE) to operate
-+ * @mask: bit mask of bits to clear
-+ * @set: bit mask of bits to set
-+ *
-+ * NOTE: Convenience function which allows a PHY's BMCR register to be
-+ * modified as new register value = (old register value & ~mask) | set.
-+ * YT8521 has two space (utp/fiber) and three mode (utp/fiber/poll), each space
-+ * has MII_BMCR. poll mode combines utp and faber,so need do both.
-+ * If it is reset, it will wait for completion.
-+ *
-+ * returns 0 or negative errno code
-+ */
-+static int yt8521_modify_bmcr_paged(struct phy_device *phydev, int page,
-+                                  u16 mask, u16 set)
-+{
-+      int max_cnt = 500; /* the max wait time of reset ~ 500 ms */
-+      int old_page;
-+      int ret = 0;
-+
-+      old_page = phy_select_page(phydev, page & YT8521_RSSR_SPACE_MASK);
-+      if (old_page < 0)
-+              goto err_restore_page;
-+
-+      ret = __phy_modify(phydev, MII_BMCR, mask, set);
-+      if (ret < 0)
-+              goto err_restore_page;
-+
-+      /* If it is reset, need to wait for the reset to complete */
-+      if (set == BMCR_RESET) {
-+              while (max_cnt--) {
-+                      usleep_range(1000, 1100);
-+                      ret = __phy_read(phydev, MII_BMCR);
-+                      if (ret < 0)
-+                              goto err_restore_page;
-+
-+                      if (!(ret & BMCR_RESET))
-+                              return phy_restore_page(phydev, old_page, 0);
-+              }
-+      }
-+
-+err_restore_page:
-+      return phy_restore_page(phydev, old_page, ret);
-+}
-+
-+/**
-+ * yt8521_modify_utp_fiber_bmcr - bits modify a PHY's BMCR register
-+ * @phydev: the phy_device struct
-+ * @mask: bit mask of bits to clear
-+ * @set: bit mask of bits to set
-+ *
-+ * NOTE: Convenience function which allows a PHY's BMCR register to be
-+ * modified as new register value = (old register value & ~mask) | set.
-+ * YT8521 has two space (utp/fiber) and three mode (utp/fiber/poll), each space
-+ * has MII_BMCR. poll mode combines utp and faber,so need do both.
-+ *
-+ * returns 0 or negative errno code
-+ */
-+static int yt8521_modify_utp_fiber_bmcr(struct phy_device *phydev, u16 mask,
-+                                      u16 set)
-+{
-+      struct yt8521_priv *priv = phydev->priv;
-+      int ret;
-+
-+      if (priv->reg_page != YT8521_RSSR_TO_BE_ARBITRATED) {
-+              ret = yt8521_modify_bmcr_paged(phydev, priv->reg_page, mask,
-+                                             set);
-+              if (ret < 0)
-+                      return ret;
-+      } else {
-+              ret = yt8521_modify_bmcr_paged(phydev, YT8521_RSSR_UTP_SPACE,
-+                                             mask, set);
-+              if (ret < 0)
-+                      return ret;
-+
-+              ret = yt8521_modify_bmcr_paged(phydev, YT8521_RSSR_FIBER_SPACE,
-+                                             mask, set);
-+              if (ret < 0)
-+                      return ret;
-+      }
-+      return 0;
-+}
-+
-+/**
-+ * yt8521_soft_reset() - called to issue a PHY software reset
-+ * @phydev: a pointer to a &struct phy_device
-+ *
-+ * returns 0 or negative errno code
-+ */
-+static int yt8521_soft_reset(struct phy_device *phydev)
-+{
-+      return yt8521_modify_utp_fiber_bmcr(phydev, 0, BMCR_RESET);
-+}
-+
-+/**
-+ * yt8521_suspend() - suspend the hardware
-+ * @phydev: a pointer to a &struct phy_device
-+ *
-+ * returns 0 or negative errno code
-+ */
-+static int yt8521_suspend(struct phy_device *phydev)
-+{
-+      int wol_config;
-+
-+      /* YTPHY_WOL_CONFIG_REG is common ext reg */
-+      wol_config = ytphy_read_ext_with_lock(phydev, YTPHY_WOL_CONFIG_REG);
-+      if (wol_config < 0)
-+              return wol_config;
-+
-+      /* if wol enable, do nothing */
-+      if (wol_config & YTPHY_WCR_ENABLE)
-+              return 0;
-+
-+      return yt8521_modify_utp_fiber_bmcr(phydev, 0, BMCR_PDOWN);
-+}
-+
-+/**
-+ * yt8521_resume() - resume the hardware
-+ * @phydev: a pointer to a &struct phy_device
-+ *
-+ * returns 0 or negative errno code
-+ */
-+static int yt8521_resume(struct phy_device *phydev)
-+{
-+      int ret;
-+      int wol_config;
-+
-+      /* disable auto sleep */
-+      ret = ytphy_modify_ext_with_lock(phydev,
-+                                       YT8521_EXTREG_SLEEP_CONTROL1_REG,
-+                                       YT8521_ESC1R_SLEEP_SW, 0);
-+      if (ret < 0)
-+              return ret;
-+
-+      wol_config = ytphy_read_ext_with_lock(phydev, YTPHY_WOL_CONFIG_REG);
-+      if (wol_config < 0)
-+              return wol_config;
-+
-+      /* if wol enable, do nothing */
-+      if (wol_config & YTPHY_WCR_ENABLE)
-+              return 0;
-+
-+      return yt8521_modify_utp_fiber_bmcr(phydev, BMCR_PDOWN, 0);
-+}
-+
-+/**
-+ * yt8521_config_init() - called to initialize the PHY
-+ * @phydev: a pointer to a &struct phy_device
-+ *
-+ * returns 0 or negative errno code
-+ */
-+static int yt8521_config_init(struct phy_device *phydev)
-+{
-+      int old_page;
-+      int ret = 0;
-+      u16 val;
-+
-+      old_page = phy_select_page(phydev, YT8521_RSSR_UTP_SPACE);
-+      if (old_page < 0)
-+              goto err_restore_page;
-+
-+      switch (phydev->interface) {
-+      case PHY_INTERFACE_MODE_RGMII:
-+              val = YT8521_RC1R_GE_TX_DELAY_DIS | YT8521_RC1R_GE_TX_DELAY_DIS;
-+              val |= YT8521_RC1R_RX_DELAY_DIS;
-+              break;
-+      case PHY_INTERFACE_MODE_RGMII_RXID:
-+              val = YT8521_RC1R_GE_TX_DELAY_DIS | YT8521_RC1R_GE_TX_DELAY_DIS;
-+              val |= YT8521_RC1R_RX_DELAY_EN;
-+              break;
-+      case PHY_INTERFACE_MODE_RGMII_TXID:
-+              val = YT8521_RC1R_GE_TX_DELAY_EN | YT8521_RC1R_GE_TX_DELAY_EN;
-+              val |= YT8521_RC1R_RX_DELAY_DIS;
-+              break;
-+      case PHY_INTERFACE_MODE_RGMII_ID:
-+              val = YT8521_RC1R_GE_TX_DELAY_EN | YT8521_RC1R_GE_TX_DELAY_EN;
-+              val |= YT8521_RC1R_RX_DELAY_EN;
-+              break;
-+      case PHY_INTERFACE_MODE_SGMII:
-+              break;
-+      default: /* do not support other modes */
-+              ret = -EOPNOTSUPP;
-+              goto err_restore_page;
-+      }
-+
-+      /* set rgmii delay mode */
-+      if (phydev->interface != PHY_INTERFACE_MODE_SGMII) {
-+              ret = ytphy_modify_ext(phydev, YT8521_RGMII_CONFIG1_REG,
-+                                     (YT8521_RC1R_RX_DELAY_MASK |
-+                                     YT8521_RC1R_FE_TX_DELAY_MASK |
-+                                     YT8521_RC1R_GE_TX_DELAY_MASK),
-+                                     val);
-+              if (ret < 0)
-+                      goto err_restore_page;
-+      }
-+
-+      /* disable auto sleep */
-+      ret = ytphy_modify_ext(phydev, YT8521_EXTREG_SLEEP_CONTROL1_REG,
-+                             YT8521_ESC1R_SLEEP_SW, 0);
-+      if (ret < 0)
-+              goto err_restore_page;
-+
-+      /* enable RXC clock when no wire plug */
-+      ret = ytphy_modify_ext(phydev, YT8521_CLOCK_GATING_REG,
-+                             YT8521_CGR_RX_CLK_EN, 0);
-+      if (ret < 0)
-+              goto err_restore_page;
-+
-+err_restore_page:
-+      return phy_restore_page(phydev, old_page, ret);
-+}
-+
-+/**
-+ * yt8521_prepare_fiber_features() -  A small helper function that setup
-+ * fiber's features.
-+ * @phydev: a pointer to a &struct phy_device
-+ * @dst: a pointer to store fiber's features
-+ */
-+static void yt8521_prepare_fiber_features(struct phy_device *phydev,
-+                                        unsigned long *dst)
-+{
-+      linkmode_set_bit(ETHTOOL_LINK_MODE_100baseFX_Full_BIT, dst);
-+      linkmode_set_bit(ETHTOOL_LINK_MODE_1000baseX_Full_BIT, dst);
-+      linkmode_set_bit(ETHTOOL_LINK_MODE_Autoneg_BIT, dst);
-+      linkmode_set_bit(ETHTOOL_LINK_MODE_FIBRE_BIT, dst);
-+}
-+
-+/**
-+ * yt8521_fiber_setup_forced - configures/forces speed from @phydev
-+ * @phydev: target phy_device struct
-+ *
-+ * NOTE:The caller must have taken the MDIO bus lock.
-+ *
-+ * returns 0 or negative errno code
-+ */
-+static int yt8521_fiber_setup_forced(struct phy_device *phydev)
-+{
-+      u16 val;
-+      int ret;
-+
-+      if (phydev->speed == SPEED_1000)
-+              val = YTPHY_MCR_FIBER_1000BX;
-+      else if (phydev->speed == SPEED_100)
-+              val = YTPHY_MCR_FIBER_100FX;
-+      else
-+              return -EINVAL;
-+
-+      ret =  __phy_modify(phydev, MII_BMCR, BMCR_ANENABLE, 0);
-+      if (ret < 0)
-+              return ret;
-+
-+      /* disable Fiber auto sensing */
-+      ret =  ytphy_modify_ext(phydev, YT8521_LINK_TIMER_CFG2_REG,
-+                              YT8521_LTCR_EN_AUTOSEN, 0);
-+      if (ret < 0)
-+              return ret;
-+
-+      ret =  ytphy_modify_ext(phydev, YTPHY_MISC_CONFIG_REG,
-+                              YTPHY_MCR_FIBER_SPEED_MASK, val);
-+      if (ret < 0)
-+              return ret;
-+
-+      return ytphy_modify_ext(phydev, YT8521_CHIP_CONFIG_REG,
-+                              YT8521_CCR_SW_RST, 0);
-+}
-+
-+/**
-+ * ytphy_check_and_restart_aneg - Enable and restart auto-negotiation
-+ * @phydev: target phy_device struct
-+ * @restart: whether aneg restart is requested
-+ *
-+ * NOTE:The caller must have taken the MDIO bus lock.
-+ *
-+ * returns 0 or negative errno code
-+ */
-+static int ytphy_check_and_restart_aneg(struct phy_device *phydev, bool restart)
-+{
-+      int ret;
-+
-+      if (!restart) {
-+              /* Advertisement hasn't changed, but maybe aneg was never on to
-+               * begin with?  Or maybe phy was isolated?
-+               */
-+              ret = __phy_read(phydev, MII_BMCR);
-+              if (ret < 0)
-+                      return ret;
-+
-+              if (!(ret & BMCR_ANENABLE) || (ret & BMCR_ISOLATE))
-+                      restart = true;
-+      }
-+      /* Enable and Restart Autonegotiation
-+       * Don't isolate the PHY if we're negotiating
-+       */
-+      if (restart)
-+              return __phy_modify(phydev, MII_BMCR, BMCR_ISOLATE,
-+                                  BMCR_ANENABLE | BMCR_ANRESTART);
-+
-+      return 0;
-+}
-+
-+/**
-+ * yt8521_fiber_config_aneg - restart auto-negotiation or write
-+ * YTPHY_MISC_CONFIG_REG.
-+ * @phydev: target phy_device struct
-+ *
-+ * NOTE:The caller must have taken the MDIO bus lock.
-+ *
-+ * returns 0 or negative errno code
-+ */
-+static int yt8521_fiber_config_aneg(struct phy_device *phydev)
-+{
-+      int err, changed = 0;
-+      int bmcr;
-+      u16 adv;
-+
-+      if (phydev->autoneg != AUTONEG_ENABLE)
-+              return yt8521_fiber_setup_forced(phydev);
-+
-+      /* enable Fiber auto sensing */
-+      err =  ytphy_modify_ext(phydev, YT8521_LINK_TIMER_CFG2_REG,
-+                              0, YT8521_LTCR_EN_AUTOSEN);
-+      if (err < 0)
-+              return err;
-+
-+      err =  ytphy_modify_ext(phydev, YT8521_CHIP_CONFIG_REG,
-+                              YT8521_CCR_SW_RST, 0);
-+      if (err < 0)
-+              return err;
-+
-+      bmcr = __phy_read(phydev, MII_BMCR);
-+      if (bmcr < 0)
-+              return bmcr;
-+
-+      /* When it is coming from fiber forced mode, add bmcr power down
-+       * and power up to let aneg work fine.
-+       */
-+      if (!(bmcr & BMCR_ANENABLE)) {
-+              __phy_modify(phydev, MII_BMCR, 0, BMCR_PDOWN);
-+              usleep_range(1000, 1100);
-+              __phy_modify(phydev, MII_BMCR, BMCR_PDOWN, 0);
-+      }
-+
-+      adv = linkmode_adv_to_mii_adv_x(phydev->advertising,
-+                                      ETHTOOL_LINK_MODE_1000baseX_Full_BIT);
-+
-+      /* Setup fiber advertisement */
-+      err = __phy_modify_changed(phydev, MII_ADVERTISE,
-+                                 ADVERTISE_1000XHALF | ADVERTISE_1000XFULL |
-+                                 ADVERTISE_1000XPAUSE |
-+                                 ADVERTISE_1000XPSE_ASYM,
-+                                 adv);
-+      if (err < 0)
-+              return err;
-+
-+      if (err > 0)
-+              changed = 1;
-+
-+      return ytphy_check_and_restart_aneg(phydev, changed);
-+}
-+
-+/**
-+ * ytphy_setup_master_slave
-+ * @phydev: target phy_device struct
-+ *
-+ * NOTE: The caller must have taken the MDIO bus lock.
-+ *
-+ * returns 0 or negative errno code
-+ */
-+static int ytphy_setup_master_slave(struct phy_device *phydev)
-+{
-+      u16 ctl = 0;
-+
-+      if (!phydev->is_gigabit_capable)
-+              return 0;
-+
-+      switch (phydev->master_slave_set) {
-+      case MASTER_SLAVE_CFG_MASTER_PREFERRED:
-+              ctl |= CTL1000_PREFER_MASTER;
-+              break;
-+      case MASTER_SLAVE_CFG_SLAVE_PREFERRED:
-+              break;
-+      case MASTER_SLAVE_CFG_MASTER_FORCE:
-+              ctl |= CTL1000_AS_MASTER;
-+              fallthrough;
-+      case MASTER_SLAVE_CFG_SLAVE_FORCE:
-+              ctl |= CTL1000_ENABLE_MASTER;
-+              break;
-+      case MASTER_SLAVE_CFG_UNKNOWN:
-+      case MASTER_SLAVE_CFG_UNSUPPORTED:
-+              return 0;
-+      default:
-+              phydev_warn(phydev, "Unsupported Master/Slave mode\n");
-+              return -EOPNOTSUPP;
-+      }
-+
-+      return __phy_modify_changed(phydev, MII_CTRL1000,
-+                                  (CTL1000_ENABLE_MASTER | CTL1000_AS_MASTER |
-+                                  CTL1000_PREFER_MASTER), ctl);
-+}
-+
-+/**
-+ * ytphy_utp_config_advert - sanitize and advertise auto-negotiation parameters
-+ * @phydev: target phy_device struct
-+ *
-+ * NOTE: Writes MII_ADVERTISE with the appropriate values,
-+ * after sanitizing the values to make sure we only advertise
-+ * what is supported.  Returns < 0 on error, 0 if the PHY's advertisement
-+ * hasn't changed, and > 0 if it has changed.
-+ * The caller must have taken the MDIO bus lock.
-+ *
-+ * returns 0 or negative errno code
-+ */
-+static int ytphy_utp_config_advert(struct phy_device *phydev)
-+{
-+      int err, bmsr, changed = 0;
-+      u32 adv;
-+
-+      /* Only allow advertising what this PHY supports */
-+      linkmode_and(phydev->advertising, phydev->advertising,
-+                   phydev->supported);
-+
-+      adv = linkmode_adv_to_mii_adv_t(phydev->advertising);
-+
-+      /* Setup standard advertisement */
-+      err = __phy_modify_changed(phydev, MII_ADVERTISE,
-+                                 ADVERTISE_ALL | ADVERTISE_100BASE4 |
-+                                 ADVERTISE_PAUSE_CAP | ADVERTISE_PAUSE_ASYM,
-+                                 adv);
-+      if (err < 0)
-+              return err;
-+      if (err > 0)
-+              changed = 1;
-+
-+      bmsr = __phy_read(phydev, MII_BMSR);
-+      if (bmsr < 0)
-+              return bmsr;
-+
-+      /* Per 802.3-2008, Section 22.2.4.2.16 Extended status all
-+       * 1000Mbits/sec capable PHYs shall have the BMSR_ESTATEN bit set to a
-+       * logical 1.
-+       */
-+      if (!(bmsr & BMSR_ESTATEN))
-+              return changed;
-+
-+      adv = linkmode_adv_to_mii_ctrl1000_t(phydev->advertising);
-+
-+      err = __phy_modify_changed(phydev, MII_CTRL1000,
-+                                 ADVERTISE_1000FULL | ADVERTISE_1000HALF,
-+                                 adv);
-+      if (err < 0)
-+              return err;
-+      if (err > 0)
-+              changed = 1;
-+
-+      return changed;
-+}
-+
-+/**
-+ * ytphy_utp_config_aneg - restart auto-negotiation or write BMCR
-+ * @phydev: target phy_device struct
-+ * @changed: whether autoneg is requested
-+ *
-+ * NOTE: If auto-negotiation is enabled, we configure the
-+ * advertising, and then restart auto-negotiation.  If it is not
-+ * enabled, then we write the BMCR.
-+ * The caller must have taken the MDIO bus lock.
-+ *
-+ * returns 0 or negative errno code
-+ */
-+static int ytphy_utp_config_aneg(struct phy_device *phydev, bool changed)
-+{
-+      int err;
-+      u16 ctl;
-+
-+      err = ytphy_setup_master_slave(phydev);
-+      if (err < 0)
-+              return err;
-+      else if (err)
-+              changed = true;
-+
-+      if (phydev->autoneg != AUTONEG_ENABLE) {
-+              /* configures/forces speed/duplex from @phydev */
-+
-+              ctl = mii_bmcr_encode_fixed(phydev->speed, phydev->duplex);
-+
-+              return __phy_modify(phydev, MII_BMCR, ~(BMCR_LOOPBACK |
-+                                  BMCR_ISOLATE | BMCR_PDOWN), ctl);
-+      }
-+
-+      err = ytphy_utp_config_advert(phydev);
-+      if (err < 0) /* error */
-+              return err;
-+      else if (err)
-+              changed = true;
-+
-+      return ytphy_check_and_restart_aneg(phydev, changed);
-+}
-+
-+/**
-+ * yt8521_config_aneg_paged() - switch reg space then call genphy_config_aneg
-+ * of one page
-+ * @phydev: a pointer to a &struct phy_device
-+ * @page: The reg page(YT8521_RSSR_FIBER_SPACE/YT8521_RSSR_UTP_SPACE) to
-+ * operate.
-+ *
-+ * returns 0 or negative errno code
-+ */
-+static int yt8521_config_aneg_paged(struct phy_device *phydev, int page)
-+{
-+      __ETHTOOL_DECLARE_LINK_MODE_MASK(fiber_supported);
-+      struct yt8521_priv *priv = phydev->priv;
-+      int old_page;
-+      int ret = 0;
-+
-+      page &= YT8521_RSSR_SPACE_MASK;
-+
-+      old_page = phy_select_page(phydev, page);
-+      if (old_page < 0)
-+              goto err_restore_page;
-+
-+      /* If reg_page is YT8521_RSSR_TO_BE_ARBITRATED,
-+       * phydev->advertising should be updated.
-+       */
-+      if (priv->reg_page == YT8521_RSSR_TO_BE_ARBITRATED) {
-+              linkmode_zero(fiber_supported);
-+              yt8521_prepare_fiber_features(phydev, fiber_supported);
-+
-+              /* prepare fiber_supported, then setup advertising. */
-+              if (page == YT8521_RSSR_FIBER_SPACE) {
-+                      linkmode_set_bit(ETHTOOL_LINK_MODE_Pause_BIT,
-+                                       fiber_supported);
-+                      linkmode_set_bit(ETHTOOL_LINK_MODE_Asym_Pause_BIT,
-+                                       fiber_supported);
-+                      linkmode_and(phydev->advertising,
-+                                   priv->combo_advertising, fiber_supported);
-+              } else {
-+                      /* ETHTOOL_LINK_MODE_Autoneg_BIT is also used in utp */
-+                      linkmode_clear_bit(ETHTOOL_LINK_MODE_Autoneg_BIT,
-+                                         fiber_supported);
-+                      linkmode_andnot(phydev->advertising,
-+                                      priv->combo_advertising,
-+                                      fiber_supported);
-+              }
-+      }
-+
-+      if (page == YT8521_RSSR_FIBER_SPACE)
-+              ret = yt8521_fiber_config_aneg(phydev);
-+      else
-+              ret = ytphy_utp_config_aneg(phydev, false);
-+
-+err_restore_page:
-+      return phy_restore_page(phydev, old_page, ret);
-+}
-+
-+/**
-+ * yt8521_config_aneg() - change reg space then call yt8521_config_aneg_paged
-+ * @phydev: a pointer to a &struct phy_device
-+ *
-+ * returns 0 or negative errno code
-+ */
-+static int yt8521_config_aneg(struct phy_device *phydev)
-+{
-+      struct yt8521_priv *priv = phydev->priv;
-+      int ret;
-+
-+      if (priv->reg_page != YT8521_RSSR_TO_BE_ARBITRATED) {
-+              ret = yt8521_config_aneg_paged(phydev, priv->reg_page);
-+              if (ret < 0)
-+                      return ret;
-+      } else {
-+              /* If reg_page is YT8521_RSSR_TO_BE_ARBITRATED,
-+               * phydev->advertising need to be saved at first run.
-+               * Because it contains the advertising which supported by both
-+               * mac and yt8521(utp and fiber).
-+               */
-+              if (linkmode_empty(priv->combo_advertising)) {
-+                      linkmode_copy(priv->combo_advertising,
-+                                    phydev->advertising);
-+              }
-+
-+              ret = yt8521_config_aneg_paged(phydev, YT8521_RSSR_UTP_SPACE);
-+              if (ret < 0)
-+                      return ret;
-+
-+              ret = yt8521_config_aneg_paged(phydev, YT8521_RSSR_FIBER_SPACE);
-+              if (ret < 0)
-+                      return ret;
-+
-+              /* we don't known which will be link, so restore
-+               * phydev->advertising as default value.
-+               */
-+              linkmode_copy(phydev->advertising, priv->combo_advertising);
-+      }
-+      return 0;
-+}
-+
-+/**
-+ * yt8521_aneg_done_paged() - determines the auto negotiation result of one
-+ * page.
-+ * @phydev: a pointer to a &struct phy_device
-+ * @page: The reg page(YT8521_RSSR_FIBER_SPACE/YT8521_RSSR_UTP_SPACE) to
-+ * operate.
-+ *
-+ * returns 0(no link)or 1(fiber or utp link) or negative errno code
-+ */
-+static int yt8521_aneg_done_paged(struct phy_device *phydev, int page)
-+{
-+      int old_page;
-+      int ret = 0;
-+      int link;
-+
-+      old_page = phy_select_page(phydev, page & YT8521_RSSR_SPACE_MASK);
-+      if (old_page < 0)
-+              goto err_restore_page;
-+
-+      ret = __phy_read(phydev, YTPHY_SPECIFIC_STATUS_REG);
-+      if (ret < 0)
-+              goto err_restore_page;
-+
-+      link = !!(ret & YTPHY_SSR_LINK);
-+      ret = link;
-+
-+err_restore_page:
-+      return phy_restore_page(phydev, old_page, ret);
-+}
-+
-+/**
-+ * yt8521_aneg_done() - determines the auto negotiation result
-+ * @phydev: a pointer to a &struct phy_device
-+ *
-+ * returns 0(no link)or 1(fiber or utp link) or negative errno code
-+ */
-+static int yt8521_aneg_done(struct phy_device *phydev)
-+{
-+      struct yt8521_priv *priv = phydev->priv;
-+      int link_fiber = 0;
-+      int link_utp;
-+      int link;
-+
-+      if (priv->reg_page != YT8521_RSSR_TO_BE_ARBITRATED) {
-+              link = yt8521_aneg_done_paged(phydev, priv->reg_page);
-+      } else {
-+              link_utp = yt8521_aneg_done_paged(phydev,
-+                                                YT8521_RSSR_UTP_SPACE);
-+              if (link_utp < 0)
-+                      return link_utp;
-+
-+              if (!link_utp) {
-+                      link_fiber = yt8521_aneg_done_paged(phydev,
-+                                                          YT8521_RSSR_FIBER_SPACE);
-+                      if (link_fiber < 0)
-+                              return link_fiber;
-+              }
-+              link = link_fiber || link_utp;
-+              phydev_info(phydev, "%s, link_fiber: %d, link_utp: %d\n",
-+                          __func__, link_fiber, link_utp);
-+      }
-+
-+      return link;
-+}
-+
-+/**
-+ * ytphy_utp_read_abilities - read PHY abilities from Clause 22 registers
-+ * @phydev: target phy_device struct
-+ *
-+ * NOTE: Reads the PHY's abilities and populates
-+ * phydev->supported accordingly.
-+ * The caller must have taken the MDIO bus lock.
-+ *
-+ * returns 0 or negative errno code
-+ */
-+static int ytphy_utp_read_abilities(struct phy_device *phydev)
-+{
-+      int val;
-+
-+      linkmode_set_bit_array(phy_basic_ports_array,
-+                             ARRAY_SIZE(phy_basic_ports_array),
-+                             phydev->supported);
-+
-+      val = __phy_read(phydev, MII_BMSR);
-+      if (val < 0)
-+              return val;
-+
-+      linkmode_mod_bit(ETHTOOL_LINK_MODE_Autoneg_BIT, phydev->supported,
-+                       val & BMSR_ANEGCAPABLE);
-+
-+      linkmode_mod_bit(ETHTOOL_LINK_MODE_100baseT_Full_BIT, phydev->supported,
-+                       val & BMSR_100FULL);
-+      linkmode_mod_bit(ETHTOOL_LINK_MODE_100baseT_Half_BIT, phydev->supported,
-+                       val & BMSR_100HALF);
-+      linkmode_mod_bit(ETHTOOL_LINK_MODE_10baseT_Full_BIT, phydev->supported,
-+                       val & BMSR_10FULL);
-+      linkmode_mod_bit(ETHTOOL_LINK_MODE_10baseT_Half_BIT, phydev->supported,
-+                       val & BMSR_10HALF);
-+
-+      if (val & BMSR_ESTATEN) {
-+              val = __phy_read(phydev, MII_ESTATUS);
-+              if (val < 0)
-+                      return val;
-+
-+              linkmode_mod_bit(ETHTOOL_LINK_MODE_1000baseT_Full_BIT,
-+                               phydev->supported, val & ESTATUS_1000_TFULL);
-+              linkmode_mod_bit(ETHTOOL_LINK_MODE_1000baseT_Half_BIT,
-+                               phydev->supported, val & ESTATUS_1000_THALF);
-+              linkmode_mod_bit(ETHTOOL_LINK_MODE_1000baseX_Full_BIT,
-+                               phydev->supported, val & ESTATUS_1000_XFULL);
-+      }
-+
-+      return 0;
-+}
-+
-+/**
-+ * yt8521_get_features_paged() -  read supported link modes for one page
-+ * @phydev: a pointer to a &struct phy_device
-+ * @page: The reg page(YT8521_RSSR_FIBER_SPACE/YT8521_RSSR_UTP_SPACE) to
-+ * operate.
-+ *
-+ * returns 0 or negative errno code
-+ */
-+static int yt8521_get_features_paged(struct phy_device *phydev, int page)
-+{
-+      int old_page;
-+      int ret = 0;
-+
-+      page &= YT8521_RSSR_SPACE_MASK;
-+      old_page = phy_select_page(phydev, page);
-+      if (old_page < 0)
-+              goto err_restore_page;
-+
-+      if (page == YT8521_RSSR_FIBER_SPACE) {
-+              linkmode_zero(phydev->supported);
-+              yt8521_prepare_fiber_features(phydev, phydev->supported);
-+      } else {
-+              ret = ytphy_utp_read_abilities(phydev);
-+              if (ret < 0)
-+                      goto err_restore_page;
-+      }
-+
-+err_restore_page:
-+      return phy_restore_page(phydev, old_page, ret);
-+}
-+
-+/**
-+ * yt8521_get_features - switch reg space then call yt8521_get_features_paged
-+ * @phydev: target phy_device struct
-+ *
-+ * returns 0 or negative errno code
-+ */
-+static int yt8521_get_features(struct phy_device *phydev)
-+{
-+      struct yt8521_priv *priv = phydev->priv;
-+      int ret;
-+
-+      if (priv->reg_page != YT8521_RSSR_TO_BE_ARBITRATED) {
-+              ret = yt8521_get_features_paged(phydev, priv->reg_page);
-+      } else {
-+              ret = yt8521_get_features_paged(phydev,
-+                                              YT8521_RSSR_UTP_SPACE);
-+              if (ret < 0)
-+                      return ret;
-+
-+              /* add fiber's features to phydev->supported */
-+              yt8521_prepare_fiber_features(phydev, phydev->supported);
-+      }
-+      return ret;
-+}
-+
- static struct phy_driver motorcomm_phy_drvs[] = {
-       {
-               PHY_ID_MATCH_EXACT(PHY_ID_YT8511),
-@@ -121,16 +1733,35 @@ static struct phy_driver motorcomm_phy_d
-               .read_page      = yt8511_read_page,
-               .write_page     = yt8511_write_page,
-       },
-+      {
-+              PHY_ID_MATCH_EXACT(PHY_ID_YT8521),
-+              .name           = "YT8521 Gigabit Ethernet",
-+              .get_features   = yt8521_get_features,
-+              .probe          = yt8521_probe,
-+              .read_page      = yt8521_read_page,
-+              .write_page     = yt8521_write_page,
-+              .get_wol        = ytphy_get_wol,
-+              .set_wol        = ytphy_set_wol,
-+              .config_aneg    = yt8521_config_aneg,
-+              .aneg_done      = yt8521_aneg_done,
-+              .config_init    = yt8521_config_init,
-+              .read_status    = yt8521_read_status,
-+              .soft_reset     = yt8521_soft_reset,
-+              .suspend        = yt8521_suspend,
-+              .resume         = yt8521_resume,
-+      },
- };
- module_phy_driver(motorcomm_phy_drvs);
--MODULE_DESCRIPTION("Motorcomm PHY driver");
-+MODULE_DESCRIPTION("Motorcomm 8511/8521 PHY driver");
- MODULE_AUTHOR("Peter Geis");
-+MODULE_AUTHOR("Frank");
- MODULE_LICENSE("GPL");
- static const struct mdio_device_id __maybe_unused motorcomm_tbl[] = {
-       { PHY_ID_MATCH_EXACT(PHY_ID_YT8511) },
-+      { PHY_ID_MATCH_EXACT(PHY_ID_YT8521) },
-       { /* sentinal */ }
- };
diff --git a/target/linux/generic/backport-5.15/791-v6.2-02-net-phy-fix-yt8521-duplicated-argument-to-or.patch b/target/linux/generic/backport-5.15/791-v6.2-02-net-phy-fix-yt8521-duplicated-argument-to-or.patch
deleted file mode 100644 (file)
index cce71c8..0000000
+++ /dev/null
@@ -1,49 +0,0 @@
-From 4e0243e7128c9b25ea2739136076a95d6adaba5e Mon Sep 17 00:00:00 2001
-From: Frank <[email protected]>
-Date: Fri, 4 Nov 2022 16:44:41 +0800
-Subject: [PATCH] net: phy: fix yt8521 duplicated argument to & or |
-
-cocci warnings: (new ones prefixed by >>)
->> drivers/net/phy/motorcomm.c:1122:8-35: duplicated argument to & or |
-  drivers/net/phy/motorcomm.c:1126:8-35: duplicated argument to & or |
-  drivers/net/phy/motorcomm.c:1130:8-34: duplicated argument to & or |
-  drivers/net/phy/motorcomm.c:1134:8-34: duplicated argument to & or |
-
- The second YT8521_RC1R_GE_TX_DELAY_xx should be YT8521_RC1R_FE_TX_DELAY_xx.
-
-Fixes: 70479a40954c ("net: phy: Add driver for Motorcomm yt8521 gigabit ethernet phy")
-Reported-by: kernel test robot <[email protected]>
-Reported-by: Julia Lawall <[email protected]>
-Signed-off-by: Frank <[email protected]>
-Reviewed-by: Andrew Lunn <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/phy/motorcomm.c | 8 ++++----
- 1 file changed, 4 insertions(+), 4 deletions(-)
-
---- a/drivers/net/phy/motorcomm.c
-+++ b/drivers/net/phy/motorcomm.c
-@@ -1119,19 +1119,19 @@ static int yt8521_config_init(struct phy
-       switch (phydev->interface) {
-       case PHY_INTERFACE_MODE_RGMII:
--              val = YT8521_RC1R_GE_TX_DELAY_DIS | YT8521_RC1R_GE_TX_DELAY_DIS;
-+              val = YT8521_RC1R_GE_TX_DELAY_DIS | YT8521_RC1R_FE_TX_DELAY_DIS;
-               val |= YT8521_RC1R_RX_DELAY_DIS;
-               break;
-       case PHY_INTERFACE_MODE_RGMII_RXID:
--              val = YT8521_RC1R_GE_TX_DELAY_DIS | YT8521_RC1R_GE_TX_DELAY_DIS;
-+              val = YT8521_RC1R_GE_TX_DELAY_DIS | YT8521_RC1R_FE_TX_DELAY_DIS;
-               val |= YT8521_RC1R_RX_DELAY_EN;
-               break;
-       case PHY_INTERFACE_MODE_RGMII_TXID:
--              val = YT8521_RC1R_GE_TX_DELAY_EN | YT8521_RC1R_GE_TX_DELAY_EN;
-+              val = YT8521_RC1R_GE_TX_DELAY_EN | YT8521_RC1R_FE_TX_DELAY_EN;
-               val |= YT8521_RC1R_RX_DELAY_DIS;
-               break;
-       case PHY_INTERFACE_MODE_RGMII_ID:
--              val = YT8521_RC1R_GE_TX_DELAY_EN | YT8521_RC1R_GE_TX_DELAY_EN;
-+              val = YT8521_RC1R_GE_TX_DELAY_EN | YT8521_RC1R_FE_TX_DELAY_EN;
-               val |= YT8521_RC1R_RX_DELAY_EN;
-               break;
-       case PHY_INTERFACE_MODE_SGMII:
diff --git a/target/linux/generic/backport-5.15/791-v6.2-03-net-phy-add-Motorcomm-YT8531S-phy-id.patch b/target/linux/generic/backport-5.15/791-v6.2-03-net-phy-add-Motorcomm-YT8531S-phy-id.patch
deleted file mode 100644 (file)
index 94d0909..0000000
+++ /dev/null
@@ -1,140 +0,0 @@
-From 813abcd98fb1b2cccf850cdfa092a4bfc50b2363 Mon Sep 17 00:00:00 2001
-From: Frank <[email protected]>
-Date: Tue, 22 Nov 2022 16:42:32 +0800
-Subject: [PATCH] net: phy: add Motorcomm YT8531S phy id.
-
-We added patch for motorcomm.c to support YT8531S. This patch has
-been tested on AM335x platform which has one YT8531S interface
-card and passed all test cases.
-The tested cases indluding: YT8531S UTP function with support of
-10M/100M/1000M; YT8531S Fiber function with support of 100M/1000M;
-and YT8531S Combo function that supports auto detection of media type.
-
-Since most functions of YT8531S are similar to YT8521 and we reuse some
-codes for YT8521 in the patch file.
-
-Signed-off-by: Frank <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/phy/Kconfig     |  2 +-
- drivers/net/phy/motorcomm.c | 52 +++++++++++++++++++++++++++++++++----
- 2 files changed, 48 insertions(+), 6 deletions(-)
-
---- a/drivers/net/phy/Kconfig
-+++ b/drivers/net/phy/Kconfig
-@@ -242,7 +242,7 @@ config MOTORCOMM_PHY
-       tristate "Motorcomm PHYs"
-       help
-         Enables support for Motorcomm network PHYs.
--        Currently supports the YT8511, YT8521 Gigabit Ethernet PHYs.
-+        Currently supports the YT8511, YT8521, YT8531S Gigabit Ethernet PHYs.
- config NATIONAL_PHY
-       tristate "National Semiconductor PHYs"
---- a/drivers/net/phy/motorcomm.c
-+++ b/drivers/net/phy/motorcomm.c
-@@ -1,6 +1,6 @@
- // SPDX-License-Identifier: GPL-2.0+
- /*
-- * Motorcomm 8511/8521 PHY driver.
-+ * Motorcomm 8511/8521/8531S PHY driver.
-  *
-  * Author: Peter Geis <[email protected]>
-  * Author: Frank <[email protected]>
-@@ -12,9 +12,10 @@
- #include <linux/phy.h>
- #define PHY_ID_YT8511         0x0000010a
--#define PHY_ID_YT8521                         0x0000011A
-+#define PHY_ID_YT8521         0x0000011A
-+#define PHY_ID_YT8531S                0x4F51E91A
--/* YT8521 Register Overview
-+/* YT8521/YT8531S Register Overview
-  *    UTP Register space      |       FIBER Register space
-  *  ------------------------------------------------------------
-  * |  UTP MII                 |       FIBER MII               |
-@@ -147,7 +148,7 @@
- #define YT8521_LINK_TIMER_CFG2_REG            0xA5
- #define YT8521_LTCR_EN_AUTOSEN                        BIT(15)
--/* 0xA000, 0xA001, 0xA003 ,and 0xA006 ~ 0xA00A  are common ext registers
-+/* 0xA000, 0xA001, 0xA003, 0xA006 ~ 0xA00A and 0xA012 are common ext registers
-  * of yt8521 phy. There is no need to switch reg space when operating these
-  * registers.
-  */
-@@ -221,6 +222,9 @@
-  */
- #define YTPHY_WCR_TYPE_PULSE                  BIT(0)
-+#define YT8531S_SYNCE_CFG_REG                 0xA012
-+#define YT8531S_SCR_SYNCE_ENABLE              BIT(6)
-+
- /* Extended Register  end */
- struct yt8521_priv {
-@@ -648,6 +652,26 @@ static int yt8521_probe(struct phy_devic
- }
- /**
-+ * yt8531s_probe() - read chip config then set suitable polling_mode
-+ * @phydev: a pointer to a &struct phy_device
-+ *
-+ * returns 0 or negative errno code
-+ */
-+static int yt8531s_probe(struct phy_device *phydev)
-+{
-+      int ret;
-+
-+      /* Disable SyncE clock output by default */
-+      ret = ytphy_modify_ext_with_lock(phydev, YT8531S_SYNCE_CFG_REG,
-+                                       YT8531S_SCR_SYNCE_ENABLE, 0);
-+      if (ret < 0)
-+              return ret;
-+
-+      /* same as yt8521_probe */
-+      return yt8521_probe(phydev);
-+}
-+
-+/**
-  * ytphy_utp_read_lpa() - read LPA then setup lp_advertising for utp
-  * @phydev: a pointer to a &struct phy_device
-  *
-@@ -1750,11 +1774,28 @@ static struct phy_driver motorcomm_phy_d
-               .suspend        = yt8521_suspend,
-               .resume         = yt8521_resume,
-       },
-+      {
-+              PHY_ID_MATCH_EXACT(PHY_ID_YT8531S),
-+              .name           = "YT8531S Gigabit Ethernet",
-+              .get_features   = yt8521_get_features,
-+              .probe          = yt8531s_probe,
-+              .read_page      = yt8521_read_page,
-+              .write_page     = yt8521_write_page,
-+              .get_wol        = ytphy_get_wol,
-+              .set_wol        = ytphy_set_wol,
-+              .config_aneg    = yt8521_config_aneg,
-+              .aneg_done      = yt8521_aneg_done,
-+              .config_init    = yt8521_config_init,
-+              .read_status    = yt8521_read_status,
-+              .soft_reset     = yt8521_soft_reset,
-+              .suspend        = yt8521_suspend,
-+              .resume         = yt8521_resume,
-+      },
- };
- module_phy_driver(motorcomm_phy_drvs);
--MODULE_DESCRIPTION("Motorcomm 8511/8521 PHY driver");
-+MODULE_DESCRIPTION("Motorcomm 8511/8521/8531S PHY driver");
- MODULE_AUTHOR("Peter Geis");
- MODULE_AUTHOR("Frank");
- MODULE_LICENSE("GPL");
-@@ -1762,6 +1803,7 @@ MODULE_LICENSE("GPL");
- static const struct mdio_device_id __maybe_unused motorcomm_tbl[] = {
-       { PHY_ID_MATCH_EXACT(PHY_ID_YT8511) },
-       { PHY_ID_MATCH_EXACT(PHY_ID_YT8521) },
-+      { PHY_ID_MATCH_EXACT(PHY_ID_YT8531S) },
-       { /* sentinal */ }
- };
diff --git a/target/linux/generic/backport-5.15/791-v6.3-04-net-phy-fix-the-spelling-problem-of-Sentinel.patch b/target/linux/generic/backport-5.15/791-v6.3-04-net-phy-fix-the-spelling-problem-of-Sentinel.patch
deleted file mode 100644 (file)
index 94fc32a..0000000
+++ /dev/null
@@ -1,26 +0,0 @@
-From 4104a713204d62aca482eebb0c6226d82a0721eb Mon Sep 17 00:00:00 2001
-From: Frank Sae <[email protected]>
-Date: Sat, 28 Jan 2023 14:35:57 +0800
-Subject: [PATCH] net: phy: fix the spelling problem of Sentinel
-
-CHECK: 'sentinal' may be misspelled - perhaps 'sentinel'?
-
-Signed-off-by: Frank Sae <[email protected]>
-Reviewed-by: Andrew Lunn <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- drivers/net/phy/motorcomm.c | 2 +-
- 1 file changed, 1 insertion(+), 1 deletion(-)
-
---- a/drivers/net/phy/motorcomm.c
-+++ b/drivers/net/phy/motorcomm.c
-@@ -1804,7 +1804,7 @@ static const struct mdio_device_id __may
-       { PHY_ID_MATCH_EXACT(PHY_ID_YT8511) },
-       { PHY_ID_MATCH_EXACT(PHY_ID_YT8521) },
-       { PHY_ID_MATCH_EXACT(PHY_ID_YT8531S) },
--      { /* sentinal */ }
-+      { /* sentinel */ }
- };
- MODULE_DEVICE_TABLE(mdio, motorcomm_tbl);
diff --git a/target/linux/generic/backport-5.15/791-v6.3-05-net-phy-motorcomm-change-the-phy-id-of-yt8521-and-yt8531s.patch b/target/linux/generic/backport-5.15/791-v6.3-05-net-phy-motorcomm-change-the-phy-id-of-yt8521-and-yt8531s.patch
deleted file mode 100644 (file)
index 076fa82..0000000
+++ /dev/null
@@ -1,29 +0,0 @@
-From 3c1dc22162d673d595855d24f95200ed2643f88f Mon Sep 17 00:00:00 2001
-From: Frank Sae <[email protected]>
-Date: Sat, 28 Jan 2023 14:35:58 +0800
-Subject: [PATCH] net: phy: motorcomm: change the phy id of yt8521 and yt8531s
- to lowercase
-
-The phy id is usually defined in lower case.
-
-Signed-off-by: Frank Sae <[email protected]>
-Reviewed-by: Andrew Lunn <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- drivers/net/phy/motorcomm.c | 4 ++--
- 1 file changed, 2 insertions(+), 2 deletions(-)
-
---- a/drivers/net/phy/motorcomm.c
-+++ b/drivers/net/phy/motorcomm.c
-@@ -12,8 +12,8 @@
- #include <linux/phy.h>
- #define PHY_ID_YT8511         0x0000010a
--#define PHY_ID_YT8521         0x0000011A
--#define PHY_ID_YT8531S                0x4F51E91A
-+#define PHY_ID_YT8521         0x0000011a
-+#define PHY_ID_YT8531S                0x4f51e91a
- /* YT8521/YT8531S Register Overview
-  *    UTP Register space      |       FIBER Register space
diff --git a/target/linux/generic/backport-5.15/791-v6.3-06-net-phy-Add-BIT-macro-for-Motorcomm-yt8521-yt8531-gigabit.patch b/target/linux/generic/backport-5.15/791-v6.3-06-net-phy-Add-BIT-macro-for-Motorcomm-yt8521-yt8531-gigabit.patch
deleted file mode 100644 (file)
index ba9a6ab..0000000
+++ /dev/null
@@ -1,107 +0,0 @@
-From 4869a146cd60fc8115230f0a45e15e534c531922 Mon Sep 17 00:00:00 2001
-From: Frank Sae <[email protected]>
-Date: Thu, 2 Feb 2023 11:00:34 +0800
-Subject: [PATCH] net: phy: Add BIT macro for Motorcomm yt8521/yt8531 gigabit
- ethernet phy
-
-Add BIT macro for Motorcomm yt8521/yt8531 gigabit ethernet phy.
- This is a preparatory patch. Add BIT macro for 0xA012 reg, and
- supplement for 0xA001 and 0xA003 reg. These will be used to support dts.
-
-Signed-off-by: Frank Sae <[email protected]>
-Reviewed-by: Andrew Lunn <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/phy/motorcomm.c | 55 ++++++++++++++++++++++++++++++++++---
- 1 file changed, 51 insertions(+), 4 deletions(-)
-
---- a/drivers/net/phy/motorcomm.c
-+++ b/drivers/net/phy/motorcomm.c
-@@ -161,6 +161,11 @@
- #define YT8521_CHIP_CONFIG_REG                        0xA001
- #define YT8521_CCR_SW_RST                     BIT(15)
-+/* 1b0 disable 1.9ns rxc clock delay  *default*
-+ * 1b1 enable 1.9ns rxc clock delay
-+ */
-+#define YT8521_CCR_RXC_DLY_EN                 BIT(8)
-+#define YT8521_CCR_RXC_DLY_1_900_NS           1900
- #define YT8521_CCR_MODE_SEL_MASK              (BIT(2) | BIT(1) | BIT(0))
- #define YT8521_CCR_MODE_UTP_TO_RGMII          0
-@@ -178,22 +183,41 @@
- #define YT8521_MODE_POLL                      0x3
- #define YT8521_RGMII_CONFIG1_REG              0xA003
--
-+/* 1b0 use original tx_clk_rgmii  *default*
-+ * 1b1 use inverted tx_clk_rgmii.
-+ */
-+#define YT8521_RC1R_TX_CLK_SEL_INVERTED               BIT(14)
- /* TX Gig-E Delay is bits 3:0, default 0x1
-  * TX Fast-E Delay is bits 7:4, default 0xf
-  * RX Delay is bits 13:10, default 0x0
-  * Delay = 150ps * N
-  * On = 2250ps, off = 0ps
-  */
--#define YT8521_RC1R_RX_DELAY_MASK             (0xF << 10)
-+#define YT8521_RC1R_RX_DELAY_MASK             GENMASK(13, 10)
- #define YT8521_RC1R_RX_DELAY_EN                       (0xF << 10)
- #define YT8521_RC1R_RX_DELAY_DIS              (0x0 << 10)
--#define YT8521_RC1R_FE_TX_DELAY_MASK          (0xF << 4)
-+#define YT8521_RC1R_FE_TX_DELAY_MASK          GENMASK(7, 4)
- #define YT8521_RC1R_FE_TX_DELAY_EN            (0xF << 4)
- #define YT8521_RC1R_FE_TX_DELAY_DIS           (0x0 << 4)
--#define YT8521_RC1R_GE_TX_DELAY_MASK          (0xF << 0)
-+#define YT8521_RC1R_GE_TX_DELAY_MASK          GENMASK(3, 0)
- #define YT8521_RC1R_GE_TX_DELAY_EN            (0xF << 0)
- #define YT8521_RC1R_GE_TX_DELAY_DIS           (0x0 << 0)
-+#define YT8521_RC1R_RGMII_0_000_NS            0
-+#define YT8521_RC1R_RGMII_0_150_NS            1
-+#define YT8521_RC1R_RGMII_0_300_NS            2
-+#define YT8521_RC1R_RGMII_0_450_NS            3
-+#define YT8521_RC1R_RGMII_0_600_NS            4
-+#define YT8521_RC1R_RGMII_0_750_NS            5
-+#define YT8521_RC1R_RGMII_0_900_NS            6
-+#define YT8521_RC1R_RGMII_1_050_NS            7
-+#define YT8521_RC1R_RGMII_1_200_NS            8
-+#define YT8521_RC1R_RGMII_1_350_NS            9
-+#define YT8521_RC1R_RGMII_1_500_NS            10
-+#define YT8521_RC1R_RGMII_1_650_NS            11
-+#define YT8521_RC1R_RGMII_1_800_NS            12
-+#define YT8521_RC1R_RGMII_1_950_NS            13
-+#define YT8521_RC1R_RGMII_2_100_NS            14
-+#define YT8521_RC1R_RGMII_2_250_NS            15
- #define YTPHY_MISC_CONFIG_REG                 0xA006
- #define YTPHY_MCR_FIBER_SPEED_MASK            BIT(0)
-@@ -222,6 +246,29 @@
-  */
- #define YTPHY_WCR_TYPE_PULSE                  BIT(0)
-+#define YTPHY_SYNCE_CFG_REG                   0xA012
-+#define YT8521_SCR_SYNCE_ENABLE                       BIT(5)
-+/* 1b0 output 25m clock
-+ * 1b1 output 125m clock  *default*
-+ */
-+#define YT8521_SCR_CLK_FRE_SEL_125M           BIT(3)
-+#define YT8521_SCR_CLK_SRC_MASK                       GENMASK(2, 1)
-+#define YT8521_SCR_CLK_SRC_PLL_125M           0
-+#define YT8521_SCR_CLK_SRC_UTP_RX             1
-+#define YT8521_SCR_CLK_SRC_SDS_RX             2
-+#define YT8521_SCR_CLK_SRC_REF_25M            3
-+#define YT8531_SCR_SYNCE_ENABLE                       BIT(6)
-+/* 1b0 output 25m clock   *default*
-+ * 1b1 output 125m clock
-+ */
-+#define YT8531_SCR_CLK_FRE_SEL_125M           BIT(4)
-+#define YT8531_SCR_CLK_SRC_MASK                       GENMASK(3, 1)
-+#define YT8531_SCR_CLK_SRC_PLL_125M           0
-+#define YT8531_SCR_CLK_SRC_UTP_RX             1
-+#define YT8531_SCR_CLK_SRC_SDS_RX             2
-+#define YT8531_SCR_CLK_SRC_CLOCK_FROM_DIGITAL 3
-+#define YT8531_SCR_CLK_SRC_REF_25M            4
-+#define YT8531_SCR_CLK_SRC_SSC_25M            5
- #define YT8531S_SYNCE_CFG_REG                 0xA012
- #define YT8531S_SCR_SYNCE_ENABLE              BIT(6)
diff --git a/target/linux/generic/backport-5.15/791-v6.3-07-net-phy-Add-dts-support-for-Motorcomm-yt8521-gigabit.patch b/target/linux/generic/backport-5.15/791-v6.3-07-net-phy-Add-dts-support-for-Motorcomm-yt8521-gigabit.patch
deleted file mode 100644 (file)
index 6d89fae..0000000
+++ /dev/null
@@ -1,343 +0,0 @@
-From a6e68f0f8769f79c67cdcfb6302feecd36197dec Mon Sep 17 00:00:00 2001
-From: Frank Sae <[email protected]>
-Date: Thu, 2 Feb 2023 11:00:35 +0800
-Subject: [PATCH] net: phy: Add dts support for Motorcomm yt8521 gigabit
- ethernet phy
-
-Add dts support for Motorcomm yt8521 gigabit ethernet phy.
- Add ytphy_rgmii_clk_delay_config function to support dst config for
- the delay of rgmii clk. This funciont is common for yt8521, yt8531s
- and yt8531.
- This patch has been verified on AM335x platform.
-
-Signed-off-by: Frank Sae <[email protected]>
-Reviewed-by: Andrew Lunn <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/phy/motorcomm.c | 253 ++++++++++++++++++++++++++++--------
- 1 file changed, 199 insertions(+), 54 deletions(-)
-
---- a/drivers/net/phy/motorcomm.c
-+++ b/drivers/net/phy/motorcomm.c
-@@ -10,6 +10,7 @@
- #include <linux/kernel.h>
- #include <linux/module.h>
- #include <linux/phy.h>
-+#include <linux/of.h>
- #define PHY_ID_YT8511         0x0000010a
- #define PHY_ID_YT8521         0x0000011a
-@@ -187,21 +188,9 @@
-  * 1b1 use inverted tx_clk_rgmii.
-  */
- #define YT8521_RC1R_TX_CLK_SEL_INVERTED               BIT(14)
--/* TX Gig-E Delay is bits 3:0, default 0x1
-- * TX Fast-E Delay is bits 7:4, default 0xf
-- * RX Delay is bits 13:10, default 0x0
-- * Delay = 150ps * N
-- * On = 2250ps, off = 0ps
-- */
- #define YT8521_RC1R_RX_DELAY_MASK             GENMASK(13, 10)
--#define YT8521_RC1R_RX_DELAY_EN                       (0xF << 10)
--#define YT8521_RC1R_RX_DELAY_DIS              (0x0 << 10)
- #define YT8521_RC1R_FE_TX_DELAY_MASK          GENMASK(7, 4)
--#define YT8521_RC1R_FE_TX_DELAY_EN            (0xF << 4)
--#define YT8521_RC1R_FE_TX_DELAY_DIS           (0x0 << 4)
- #define YT8521_RC1R_GE_TX_DELAY_MASK          GENMASK(3, 0)
--#define YT8521_RC1R_GE_TX_DELAY_EN            (0xF << 0)
--#define YT8521_RC1R_GE_TX_DELAY_DIS           (0x0 << 0)
- #define YT8521_RC1R_RGMII_0_000_NS            0
- #define YT8521_RC1R_RGMII_0_150_NS            1
- #define YT8521_RC1R_RGMII_0_300_NS            2
-@@ -274,6 +263,10 @@
- /* Extended Register  end */
-+#define YTPHY_DTS_OUTPUT_CLK_DIS              0
-+#define YTPHY_DTS_OUTPUT_CLK_25M              25000000
-+#define YTPHY_DTS_OUTPUT_CLK_125M             125000000
-+
- struct yt8521_priv {
-       /* combo_advertising is used for case of YT8521 in combo mode,
-        * this means that yt8521 may work in utp or fiber mode which depends
-@@ -641,6 +634,142 @@ static int yt8521_write_page(struct phy_
- };
- /**
-+ * struct ytphy_cfg_reg_map - map a config value to a register value
-+ * @cfg: value in device configuration
-+ * @reg: value in the register
-+ */
-+struct ytphy_cfg_reg_map {
-+      u32 cfg;
-+      u32 reg;
-+};
-+
-+static const struct ytphy_cfg_reg_map ytphy_rgmii_delays[] = {
-+      /* for tx delay / rx delay with YT8521_CCR_RXC_DLY_EN is not set. */
-+      { 0,    YT8521_RC1R_RGMII_0_000_NS },
-+      { 150,  YT8521_RC1R_RGMII_0_150_NS },
-+      { 300,  YT8521_RC1R_RGMII_0_300_NS },
-+      { 450,  YT8521_RC1R_RGMII_0_450_NS },
-+      { 600,  YT8521_RC1R_RGMII_0_600_NS },
-+      { 750,  YT8521_RC1R_RGMII_0_750_NS },
-+      { 900,  YT8521_RC1R_RGMII_0_900_NS },
-+      { 1050, YT8521_RC1R_RGMII_1_050_NS },
-+      { 1200, YT8521_RC1R_RGMII_1_200_NS },
-+      { 1350, YT8521_RC1R_RGMII_1_350_NS },
-+      { 1500, YT8521_RC1R_RGMII_1_500_NS },
-+      { 1650, YT8521_RC1R_RGMII_1_650_NS },
-+      { 1800, YT8521_RC1R_RGMII_1_800_NS },
-+      { 1950, YT8521_RC1R_RGMII_1_950_NS },   /* default tx/rx delay */
-+      { 2100, YT8521_RC1R_RGMII_2_100_NS },
-+      { 2250, YT8521_RC1R_RGMII_2_250_NS },
-+
-+      /* only for rx delay with YT8521_CCR_RXC_DLY_EN is set. */
-+      { 0    + YT8521_CCR_RXC_DLY_1_900_NS,   YT8521_RC1R_RGMII_0_000_NS },
-+      { 150  + YT8521_CCR_RXC_DLY_1_900_NS,   YT8521_RC1R_RGMII_0_150_NS },
-+      { 300  + YT8521_CCR_RXC_DLY_1_900_NS,   YT8521_RC1R_RGMII_0_300_NS },
-+      { 450  + YT8521_CCR_RXC_DLY_1_900_NS,   YT8521_RC1R_RGMII_0_450_NS },
-+      { 600  + YT8521_CCR_RXC_DLY_1_900_NS,   YT8521_RC1R_RGMII_0_600_NS },
-+      { 750  + YT8521_CCR_RXC_DLY_1_900_NS,   YT8521_RC1R_RGMII_0_750_NS },
-+      { 900  + YT8521_CCR_RXC_DLY_1_900_NS,   YT8521_RC1R_RGMII_0_900_NS },
-+      { 1050 + YT8521_CCR_RXC_DLY_1_900_NS,   YT8521_RC1R_RGMII_1_050_NS },
-+      { 1200 + YT8521_CCR_RXC_DLY_1_900_NS,   YT8521_RC1R_RGMII_1_200_NS },
-+      { 1350 + YT8521_CCR_RXC_DLY_1_900_NS,   YT8521_RC1R_RGMII_1_350_NS },
-+      { 1500 + YT8521_CCR_RXC_DLY_1_900_NS,   YT8521_RC1R_RGMII_1_500_NS },
-+      { 1650 + YT8521_CCR_RXC_DLY_1_900_NS,   YT8521_RC1R_RGMII_1_650_NS },
-+      { 1800 + YT8521_CCR_RXC_DLY_1_900_NS,   YT8521_RC1R_RGMII_1_800_NS },
-+      { 1950 + YT8521_CCR_RXC_DLY_1_900_NS,   YT8521_RC1R_RGMII_1_950_NS },
-+      { 2100 + YT8521_CCR_RXC_DLY_1_900_NS,   YT8521_RC1R_RGMII_2_100_NS },
-+      { 2250 + YT8521_CCR_RXC_DLY_1_900_NS,   YT8521_RC1R_RGMII_2_250_NS }
-+};
-+
-+static u32 ytphy_get_delay_reg_value(struct phy_device *phydev,
-+                                   const char *prop_name,
-+                                   const struct ytphy_cfg_reg_map *tbl,
-+                                   int tb_size,
-+                                   u16 *rxc_dly_en,
-+                                   u32 dflt)
-+{
-+      struct device_node *node = phydev->mdio.dev.of_node;
-+      int tb_size_half = tb_size / 2;
-+      u32 val;
-+      int i;
-+
-+      if (of_property_read_u32(node, prop_name, &val))
-+              goto err_dts_val;
-+
-+      /* when rxc_dly_en is NULL, it is get the delay for tx, only half of
-+       * tb_size is valid.
-+       */
-+      if (!rxc_dly_en)
-+              tb_size = tb_size_half;
-+
-+      for (i = 0; i < tb_size; i++) {
-+              if (tbl[i].cfg == val) {
-+                      if (rxc_dly_en && i < tb_size_half)
-+                              *rxc_dly_en = 0;
-+                      return tbl[i].reg;
-+              }
-+      }
-+
-+      phydev_warn(phydev, "Unsupported value %d for %s using default (%u)\n",
-+                  val, prop_name, dflt);
-+
-+err_dts_val:
-+      /* when rxc_dly_en is not NULL, it is get the delay for rx.
-+       * The rx default in dts and ytphy_rgmii_clk_delay_config is 1950 ps,
-+       * so YT8521_CCR_RXC_DLY_EN should not be set.
-+       */
-+      if (rxc_dly_en)
-+              *rxc_dly_en = 0;
-+
-+      return dflt;
-+}
-+
-+static int ytphy_rgmii_clk_delay_config(struct phy_device *phydev)
-+{
-+      int tb_size = ARRAY_SIZE(ytphy_rgmii_delays);
-+      u16 rxc_dly_en = YT8521_CCR_RXC_DLY_EN;
-+      u32 rx_reg, tx_reg;
-+      u16 mask, val = 0;
-+      int ret;
-+
-+      rx_reg = ytphy_get_delay_reg_value(phydev, "rx-internal-delay-ps",
-+                                         ytphy_rgmii_delays, tb_size,
-+                                         &rxc_dly_en,
-+                                         YT8521_RC1R_RGMII_1_950_NS);
-+      tx_reg = ytphy_get_delay_reg_value(phydev, "tx-internal-delay-ps",
-+                                         ytphy_rgmii_delays, tb_size, NULL,
-+                                         YT8521_RC1R_RGMII_1_950_NS);
-+
-+      switch (phydev->interface) {
-+      case PHY_INTERFACE_MODE_RGMII:
-+              rxc_dly_en = 0;
-+              break;
-+      case PHY_INTERFACE_MODE_RGMII_RXID:
-+              val |= FIELD_PREP(YT8521_RC1R_RX_DELAY_MASK, rx_reg);
-+              break;
-+      case PHY_INTERFACE_MODE_RGMII_TXID:
-+              rxc_dly_en = 0;
-+              val |= FIELD_PREP(YT8521_RC1R_GE_TX_DELAY_MASK, tx_reg);
-+              break;
-+      case PHY_INTERFACE_MODE_RGMII_ID:
-+              val |= FIELD_PREP(YT8521_RC1R_RX_DELAY_MASK, rx_reg) |
-+                     FIELD_PREP(YT8521_RC1R_GE_TX_DELAY_MASK, tx_reg);
-+              break;
-+      default: /* do not support other modes */
-+              return -EOPNOTSUPP;
-+      }
-+
-+      ret = ytphy_modify_ext(phydev, YT8521_CHIP_CONFIG_REG,
-+                             YT8521_CCR_RXC_DLY_EN, rxc_dly_en);
-+      if (ret < 0)
-+              return ret;
-+
-+      /* Generally, it is not necessary to adjust YT8521_RC1R_FE_TX_DELAY */
-+      mask = YT8521_RC1R_RX_DELAY_MASK | YT8521_RC1R_GE_TX_DELAY_MASK;
-+      return ytphy_modify_ext(phydev, YT8521_RGMII_CONFIG1_REG, mask, val);
-+}
-+
-+/**
-  * yt8521_probe() - read chip config then set suitable polling_mode
-  * @phydev: a pointer to a &struct phy_device
-  *
-@@ -648,9 +777,12 @@ static int yt8521_write_page(struct phy_
-  */
- static int yt8521_probe(struct phy_device *phydev)
- {
-+      struct device_node *node = phydev->mdio.dev.of_node;
-       struct device *dev = &phydev->mdio.dev;
-       struct yt8521_priv *priv;
-       int chip_config;
-+      u16 mask, val;
-+      u32 freq;
-       int ret;
-       priv = devm_kzalloc(dev, sizeof(*priv), GFP_KERNEL);
-@@ -695,7 +827,45 @@ static int yt8521_probe(struct phy_devic
-                       return ret;
-       }
--      return 0;
-+      if (of_property_read_u32(node, "motorcomm,clk-out-frequency-hz", &freq))
-+              freq = YTPHY_DTS_OUTPUT_CLK_DIS;
-+
-+      if (phydev->drv->phy_id == PHY_ID_YT8521) {
-+              switch (freq) {
-+              case YTPHY_DTS_OUTPUT_CLK_DIS:
-+                      mask = YT8521_SCR_SYNCE_ENABLE;
-+                      val = 0;
-+                      break;
-+              case YTPHY_DTS_OUTPUT_CLK_25M:
-+                      mask = YT8521_SCR_SYNCE_ENABLE |
-+                             YT8521_SCR_CLK_SRC_MASK |
-+                             YT8521_SCR_CLK_FRE_SEL_125M;
-+                      val = YT8521_SCR_SYNCE_ENABLE |
-+                            FIELD_PREP(YT8521_SCR_CLK_SRC_MASK,
-+                                       YT8521_SCR_CLK_SRC_REF_25M);
-+                      break;
-+              case YTPHY_DTS_OUTPUT_CLK_125M:
-+                      mask = YT8521_SCR_SYNCE_ENABLE |
-+                             YT8521_SCR_CLK_SRC_MASK |
-+                             YT8521_SCR_CLK_FRE_SEL_125M;
-+                      val = YT8521_SCR_SYNCE_ENABLE |
-+                            YT8521_SCR_CLK_FRE_SEL_125M |
-+                            FIELD_PREP(YT8521_SCR_CLK_SRC_MASK,
-+                                       YT8521_SCR_CLK_SRC_PLL_125M);
-+                      break;
-+              default:
-+                      phydev_warn(phydev, "Freq err:%u\n", freq);
-+                      return -EINVAL;
-+              }
-+      } else if (phydev->drv->phy_id == PHY_ID_YT8531S) {
-+              return 0;
-+      } else {
-+              phydev_warn(phydev, "PHY id err\n");
-+              return -EINVAL;
-+      }
-+
-+      return ytphy_modify_ext_with_lock(phydev, YTPHY_SYNCE_CFG_REG, mask,
-+                                        val);
- }
- /**
-@@ -1180,61 +1350,36 @@ static int yt8521_resume(struct phy_devi
-  */
- static int yt8521_config_init(struct phy_device *phydev)
- {
-+      struct device_node *node = phydev->mdio.dev.of_node;
-       int old_page;
-       int ret = 0;
--      u16 val;
-       old_page = phy_select_page(phydev, YT8521_RSSR_UTP_SPACE);
-       if (old_page < 0)
-               goto err_restore_page;
--      switch (phydev->interface) {
--      case PHY_INTERFACE_MODE_RGMII:
--              val = YT8521_RC1R_GE_TX_DELAY_DIS | YT8521_RC1R_FE_TX_DELAY_DIS;
--              val |= YT8521_RC1R_RX_DELAY_DIS;
--              break;
--      case PHY_INTERFACE_MODE_RGMII_RXID:
--              val = YT8521_RC1R_GE_TX_DELAY_DIS | YT8521_RC1R_FE_TX_DELAY_DIS;
--              val |= YT8521_RC1R_RX_DELAY_EN;
--              break;
--      case PHY_INTERFACE_MODE_RGMII_TXID:
--              val = YT8521_RC1R_GE_TX_DELAY_EN | YT8521_RC1R_FE_TX_DELAY_EN;
--              val |= YT8521_RC1R_RX_DELAY_DIS;
--              break;
--      case PHY_INTERFACE_MODE_RGMII_ID:
--              val = YT8521_RC1R_GE_TX_DELAY_EN | YT8521_RC1R_FE_TX_DELAY_EN;
--              val |= YT8521_RC1R_RX_DELAY_EN;
--              break;
--      case PHY_INTERFACE_MODE_SGMII:
--              break;
--      default: /* do not support other modes */
--              ret = -EOPNOTSUPP;
--              goto err_restore_page;
--      }
--
-       /* set rgmii delay mode */
-       if (phydev->interface != PHY_INTERFACE_MODE_SGMII) {
--              ret = ytphy_modify_ext(phydev, YT8521_RGMII_CONFIG1_REG,
--                                     (YT8521_RC1R_RX_DELAY_MASK |
--                                     YT8521_RC1R_FE_TX_DELAY_MASK |
--                                     YT8521_RC1R_GE_TX_DELAY_MASK),
--                                     val);
-+              ret = ytphy_rgmii_clk_delay_config(phydev);
-               if (ret < 0)
-                       goto err_restore_page;
-       }
--      /* disable auto sleep */
--      ret = ytphy_modify_ext(phydev, YT8521_EXTREG_SLEEP_CONTROL1_REG,
--                             YT8521_ESC1R_SLEEP_SW, 0);
--      if (ret < 0)
--              goto err_restore_page;
--
--      /* enable RXC clock when no wire plug */
--      ret = ytphy_modify_ext(phydev, YT8521_CLOCK_GATING_REG,
--                             YT8521_CGR_RX_CLK_EN, 0);
--      if (ret < 0)
--              goto err_restore_page;
-+      if (of_property_read_bool(node, "motorcomm,auto-sleep-disabled")) {
-+              /* disable auto sleep */
-+              ret = ytphy_modify_ext(phydev, YT8521_EXTREG_SLEEP_CONTROL1_REG,
-+                                     YT8521_ESC1R_SLEEP_SW, 0);
-+              if (ret < 0)
-+                      goto err_restore_page;
-+      }
-+      if (of_property_read_bool(node, "motorcomm,keep-pll-enabled")) {
-+              /* enable RXC clock when no wire plug */
-+              ret = ytphy_modify_ext(phydev, YT8521_CLOCK_GATING_REG,
-+                                     YT8521_CGR_RX_CLK_EN, 0);
-+              if (ret < 0)
-+                      goto err_restore_page;
-+      }
- err_restore_page:
-       return phy_restore_page(phydev, old_page, ret);
- }
diff --git a/target/linux/generic/backport-5.15/791-v6.3-08-net-phy-Add-dts-support-for-Motorcomm-yt8531s-gigabit.patch b/target/linux/generic/backport-5.15/791-v6.3-08-net-phy-Add-dts-support-for-Motorcomm-yt8531s-gigabit.patch
deleted file mode 100644 (file)
index 86fc046..0000000
+++ /dev/null
@@ -1,100 +0,0 @@
-From 36152f87dda4af221b16258751451d9cd3d0fb0b Mon Sep 17 00:00:00 2001
-From: Frank Sae <[email protected]>
-Date: Thu, 2 Feb 2023 11:00:36 +0800
-Subject: [PATCH] net: phy: Add dts support for Motorcomm yt8531s gigabit
- ethernet phy
-
-Add dts support for Motorcomm yt8531s gigabit ethernet phy.
- Change yt8521_probe to support clk config of yt8531s. Becase
- yt8521_probe does the things which yt8531s is needed, so
- removed yt8531s function.
- This patch has been verified on AM335x platform with yt8531s board.
-
-Signed-off-by: Frank Sae <[email protected]>
-Reviewed-by: Andrew Lunn <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/phy/motorcomm.c | 51 ++++++++++++++++++++-----------------
- 1 file changed, 27 insertions(+), 24 deletions(-)
-
---- a/drivers/net/phy/motorcomm.c
-+++ b/drivers/net/phy/motorcomm.c
-@@ -258,8 +258,6 @@
- #define YT8531_SCR_CLK_SRC_CLOCK_FROM_DIGITAL 3
- #define YT8531_SCR_CLK_SRC_REF_25M            4
- #define YT8531_SCR_CLK_SRC_SSC_25M            5
--#define YT8531S_SYNCE_CFG_REG                 0xA012
--#define YT8531S_SCR_SYNCE_ENABLE              BIT(6)
- /* Extended Register  end */
-@@ -858,7 +856,32 @@ static int yt8521_probe(struct phy_devic
-                       return -EINVAL;
-               }
-       } else if (phydev->drv->phy_id == PHY_ID_YT8531S) {
--              return 0;
-+              switch (freq) {
-+              case YTPHY_DTS_OUTPUT_CLK_DIS:
-+                      mask = YT8531_SCR_SYNCE_ENABLE;
-+                      val = 0;
-+                      break;
-+              case YTPHY_DTS_OUTPUT_CLK_25M:
-+                      mask = YT8531_SCR_SYNCE_ENABLE |
-+                             YT8531_SCR_CLK_SRC_MASK |
-+                             YT8531_SCR_CLK_FRE_SEL_125M;
-+                      val = YT8531_SCR_SYNCE_ENABLE |
-+                            FIELD_PREP(YT8531_SCR_CLK_SRC_MASK,
-+                                       YT8531_SCR_CLK_SRC_REF_25M);
-+                      break;
-+              case YTPHY_DTS_OUTPUT_CLK_125M:
-+                      mask = YT8531_SCR_SYNCE_ENABLE |
-+                             YT8531_SCR_CLK_SRC_MASK |
-+                             YT8531_SCR_CLK_FRE_SEL_125M;
-+                      val = YT8531_SCR_SYNCE_ENABLE |
-+                            YT8531_SCR_CLK_FRE_SEL_125M |
-+                            FIELD_PREP(YT8531_SCR_CLK_SRC_MASK,
-+                                       YT8531_SCR_CLK_SRC_PLL_125M);
-+                      break;
-+              default:
-+                      phydev_warn(phydev, "Freq err:%u\n", freq);
-+                      return -EINVAL;
-+              }
-       } else {
-               phydev_warn(phydev, "PHY id err\n");
-               return -EINVAL;
-@@ -869,26 +892,6 @@ static int yt8521_probe(struct phy_devic
- }
- /**
-- * yt8531s_probe() - read chip config then set suitable polling_mode
-- * @phydev: a pointer to a &struct phy_device
-- *
-- * returns 0 or negative errno code
-- */
--static int yt8531s_probe(struct phy_device *phydev)
--{
--      int ret;
--
--      /* Disable SyncE clock output by default */
--      ret = ytphy_modify_ext_with_lock(phydev, YT8531S_SYNCE_CFG_REG,
--                                       YT8531S_SCR_SYNCE_ENABLE, 0);
--      if (ret < 0)
--              return ret;
--
--      /* same as yt8521_probe */
--      return yt8521_probe(phydev);
--}
--
--/**
-  * ytphy_utp_read_lpa() - read LPA then setup lp_advertising for utp
-  * @phydev: a pointer to a &struct phy_device
-  *
-@@ -1970,7 +1973,7 @@ static struct phy_driver motorcomm_phy_d
-               PHY_ID_MATCH_EXACT(PHY_ID_YT8531S),
-               .name           = "YT8531S Gigabit Ethernet",
-               .get_features   = yt8521_get_features,
--              .probe          = yt8531s_probe,
-+              .probe          = yt8521_probe,
-               .read_page      = yt8521_read_page,
-               .write_page     = yt8521_write_page,
-               .get_wol        = ytphy_get_wol,
diff --git a/target/linux/generic/backport-5.15/791-v6.3-09-net-phy-Add-driver-for-Motorcomm-yt8531-gigabit-ethernet.patch b/target/linux/generic/backport-5.15/791-v6.3-09-net-phy-Add-driver-for-Motorcomm-yt8531-gigabit-ethernet.patch
deleted file mode 100644 (file)
index a8b9e3d..0000000
+++ /dev/null
@@ -1,302 +0,0 @@
-From 4ac94f728a588e7096dd5010cd7141a309ea7805 Mon Sep 17 00:00:00 2001
-From: Frank Sae <[email protected]>
-Date: Thu, 2 Feb 2023 11:00:37 +0800
-Subject: [PATCH] net: phy: Add driver for Motorcomm yt8531 gigabit ethernet
- phy
-
-Add a driver for the motorcomm yt8531 gigabit ethernet phy. We have
- verified the driver on AM335x platform with yt8531 board. On the
- board, yt8531 gigabit ethernet phy works in utp mode, RGMII
- interface, supports 1000M/100M/10M speeds, and wol(magic package).
-
-Signed-off-by: Frank Sae <[email protected]>
-Reviewed-by: Andrew Lunn <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/phy/Kconfig     |   2 +-
- drivers/net/phy/motorcomm.c | 208 +++++++++++++++++++++++++++++++++++-
- 2 files changed, 207 insertions(+), 3 deletions(-)
-
---- a/drivers/net/phy/Kconfig
-+++ b/drivers/net/phy/Kconfig
-@@ -242,7 +242,7 @@ config MOTORCOMM_PHY
-       tristate "Motorcomm PHYs"
-       help
-         Enables support for Motorcomm network PHYs.
--        Currently supports the YT8511, YT8521, YT8531S Gigabit Ethernet PHYs.
-+        Currently supports YT85xx Gigabit Ethernet PHYs.
- config NATIONAL_PHY
-       tristate "National Semiconductor PHYs"
---- a/drivers/net/phy/motorcomm.c
-+++ b/drivers/net/phy/motorcomm.c
-@@ -1,6 +1,6 @@
- // SPDX-License-Identifier: GPL-2.0+
- /*
-- * Motorcomm 8511/8521/8531S PHY driver.
-+ * Motorcomm 8511/8521/8531/8531S PHY driver.
-  *
-  * Author: Peter Geis <[email protected]>
-  * Author: Frank <[email protected]>
-@@ -14,6 +14,7 @@
- #define PHY_ID_YT8511         0x0000010a
- #define PHY_ID_YT8521         0x0000011a
-+#define PHY_ID_YT8531         0x4f51e91b
- #define PHY_ID_YT8531S                0x4f51e91a
- /* YT8521/YT8531S Register Overview
-@@ -517,6 +518,61 @@ err_restore_page:
-       return phy_restore_page(phydev, old_page, ret);
- }
-+static int yt8531_set_wol(struct phy_device *phydev,
-+                        struct ethtool_wolinfo *wol)
-+{
-+      const u16 mac_addr_reg[] = {
-+              YTPHY_WOL_MACADDR2_REG,
-+              YTPHY_WOL_MACADDR1_REG,
-+              YTPHY_WOL_MACADDR0_REG,
-+      };
-+      const u8 *mac_addr;
-+      u16 mask, val;
-+      int ret;
-+      u8 i;
-+
-+      if (wol->wolopts & WAKE_MAGIC) {
-+              mac_addr = phydev->attached_dev->dev_addr;
-+
-+              /* Store the device address for the magic packet */
-+              for (i = 0; i < 3; i++) {
-+                      ret = ytphy_write_ext_with_lock(phydev, mac_addr_reg[i],
-+                                                      ((mac_addr[i * 2] << 8)) |
-+                                                      (mac_addr[i * 2 + 1]));
-+                      if (ret < 0)
-+                              return ret;
-+              }
-+
-+              /* Enable WOL feature */
-+              mask = YTPHY_WCR_PULSE_WIDTH_MASK | YTPHY_WCR_INTR_SEL;
-+              val = YTPHY_WCR_ENABLE | YTPHY_WCR_INTR_SEL;
-+              val |= YTPHY_WCR_TYPE_PULSE | YTPHY_WCR_PULSE_WIDTH_672MS;
-+              ret = ytphy_modify_ext_with_lock(phydev, YTPHY_WOL_CONFIG_REG,
-+                                               mask, val);
-+              if (ret < 0)
-+                      return ret;
-+
-+              /* Enable WOL interrupt */
-+              ret = phy_modify(phydev, YTPHY_INTERRUPT_ENABLE_REG, 0,
-+                               YTPHY_IER_WOL);
-+              if (ret < 0)
-+                      return ret;
-+      } else {
-+              /* Disable WOL feature */
-+              mask = YTPHY_WCR_ENABLE | YTPHY_WCR_INTR_SEL;
-+              ret = ytphy_modify_ext_with_lock(phydev, YTPHY_WOL_CONFIG_REG,
-+                                               mask, 0);
-+
-+              /* Disable WOL interrupt */
-+              ret = phy_modify(phydev, YTPHY_INTERRUPT_ENABLE_REG,
-+                               YTPHY_IER_WOL, 0);
-+              if (ret < 0)
-+                      return ret;
-+      }
-+
-+      return 0;
-+}
-+
- static int yt8511_read_page(struct phy_device *phydev)
- {
-       return __phy_read(phydev, YT8511_PAGE_SELECT);
-@@ -767,6 +823,17 @@ static int ytphy_rgmii_clk_delay_config(
-       return ytphy_modify_ext(phydev, YT8521_RGMII_CONFIG1_REG, mask, val);
- }
-+static int ytphy_rgmii_clk_delay_config_with_lock(struct phy_device *phydev)
-+{
-+      int ret;
-+
-+      phy_lock_mdio_bus(phydev);
-+      ret = ytphy_rgmii_clk_delay_config(phydev);
-+      phy_unlock_mdio_bus(phydev);
-+
-+      return ret;
-+}
-+
- /**
-  * yt8521_probe() - read chip config then set suitable polling_mode
-  * @phydev: a pointer to a &struct phy_device
-@@ -891,6 +958,43 @@ static int yt8521_probe(struct phy_devic
-                                         val);
- }
-+static int yt8531_probe(struct phy_device *phydev)
-+{
-+      struct device_node *node = phydev->mdio.dev.of_node;
-+      u16 mask, val;
-+      u32 freq;
-+
-+      if (of_property_read_u32(node, "motorcomm,clk-out-frequency-hz", &freq))
-+              freq = YTPHY_DTS_OUTPUT_CLK_DIS;
-+
-+      switch (freq) {
-+      case YTPHY_DTS_OUTPUT_CLK_DIS:
-+              mask = YT8531_SCR_SYNCE_ENABLE;
-+              val = 0;
-+              break;
-+      case YTPHY_DTS_OUTPUT_CLK_25M:
-+              mask = YT8531_SCR_SYNCE_ENABLE | YT8531_SCR_CLK_SRC_MASK |
-+                     YT8531_SCR_CLK_FRE_SEL_125M;
-+              val = YT8531_SCR_SYNCE_ENABLE |
-+                    FIELD_PREP(YT8531_SCR_CLK_SRC_MASK,
-+                               YT8531_SCR_CLK_SRC_REF_25M);
-+              break;
-+      case YTPHY_DTS_OUTPUT_CLK_125M:
-+              mask = YT8531_SCR_SYNCE_ENABLE | YT8531_SCR_CLK_SRC_MASK |
-+                     YT8531_SCR_CLK_FRE_SEL_125M;
-+              val = YT8531_SCR_SYNCE_ENABLE | YT8531_SCR_CLK_FRE_SEL_125M |
-+                    FIELD_PREP(YT8531_SCR_CLK_SRC_MASK,
-+                               YT8531_SCR_CLK_SRC_PLL_125M);
-+              break;
-+      default:
-+              phydev_warn(phydev, "Freq err:%u\n", freq);
-+              return -EINVAL;
-+      }
-+
-+      return ytphy_modify_ext_with_lock(phydev, YTPHY_SYNCE_CFG_REG, mask,
-+                                        val);
-+}
-+
- /**
-  * ytphy_utp_read_lpa() - read LPA then setup lp_advertising for utp
-  * @phydev: a pointer to a &struct phy_device
-@@ -1387,6 +1491,94 @@ err_restore_page:
-       return phy_restore_page(phydev, old_page, ret);
- }
-+static int yt8531_config_init(struct phy_device *phydev)
-+{
-+      struct device_node *node = phydev->mdio.dev.of_node;
-+      int ret;
-+
-+      ret = ytphy_rgmii_clk_delay_config_with_lock(phydev);
-+      if (ret < 0)
-+              return ret;
-+
-+      if (of_property_read_bool(node, "motorcomm,auto-sleep-disabled")) {
-+              /* disable auto sleep */
-+              ret = ytphy_modify_ext_with_lock(phydev,
-+                                               YT8521_EXTREG_SLEEP_CONTROL1_REG,
-+                                               YT8521_ESC1R_SLEEP_SW, 0);
-+              if (ret < 0)
-+                      return ret;
-+      }
-+
-+      if (of_property_read_bool(node, "motorcomm,keep-pll-enabled")) {
-+              /* enable RXC clock when no wire plug */
-+              ret = ytphy_modify_ext_with_lock(phydev,
-+                                               YT8521_CLOCK_GATING_REG,
-+                                               YT8521_CGR_RX_CLK_EN, 0);
-+              if (ret < 0)
-+                      return ret;
-+      }
-+
-+      return 0;
-+}
-+
-+/**
-+ * yt8531_link_change_notify() - Adjust the tx clock direction according to
-+ * the current speed and dts config.
-+ * @phydev: a pointer to a &struct phy_device
-+ *
-+ * NOTE: This function is only used to adapt to VF2 with JH7110 SoC. Please
-+ * keep "motorcomm,tx-clk-adj-enabled" not exist in dts when the soc is not
-+ * JH7110.
-+ */
-+static void yt8531_link_change_notify(struct phy_device *phydev)
-+{
-+      struct device_node *node = phydev->mdio.dev.of_node;
-+      bool tx_clk_adj_enabled = false;
-+      bool tx_clk_1000_inverted;
-+      bool tx_clk_100_inverted;
-+      bool tx_clk_10_inverted;
-+      u16 val = 0;
-+      int ret;
-+
-+      if (of_property_read_bool(node, "motorcomm,tx-clk-adj-enabled"))
-+              tx_clk_adj_enabled = true;
-+
-+      if (!tx_clk_adj_enabled)
-+              return;
-+
-+      if (of_property_read_bool(node, "motorcomm,tx-clk-10-inverted"))
-+              tx_clk_10_inverted = true;
-+      if (of_property_read_bool(node, "motorcomm,tx-clk-100-inverted"))
-+              tx_clk_100_inverted = true;
-+      if (of_property_read_bool(node, "motorcomm,tx-clk-1000-inverted"))
-+              tx_clk_1000_inverted = true;
-+
-+      if (phydev->speed < 0)
-+              return;
-+
-+      switch (phydev->speed) {
-+      case SPEED_1000:
-+              if (tx_clk_1000_inverted)
-+                      val = YT8521_RC1R_TX_CLK_SEL_INVERTED;
-+              break;
-+      case SPEED_100:
-+              if (tx_clk_100_inverted)
-+                      val = YT8521_RC1R_TX_CLK_SEL_INVERTED;
-+              break;
-+      case SPEED_10:
-+              if (tx_clk_10_inverted)
-+                      val = YT8521_RC1R_TX_CLK_SEL_INVERTED;
-+              break;
-+      default:
-+              return;
-+      }
-+
-+      ret = ytphy_modify_ext_with_lock(phydev, YT8521_RGMII_CONFIG1_REG,
-+                                       YT8521_RC1R_TX_CLK_SEL_INVERTED, val);
-+      if (ret < 0)
-+              phydev_warn(phydev, "Modify TX_CLK_SEL err:%d\n", ret);
-+}
-+
- /**
-  * yt8521_prepare_fiber_features() -  A small helper function that setup
-  * fiber's features.
-@@ -1970,6 +2162,17 @@ static struct phy_driver motorcomm_phy_d
-               .resume         = yt8521_resume,
-       },
-       {
-+              PHY_ID_MATCH_EXACT(PHY_ID_YT8531),
-+              .name           = "YT8531 Gigabit Ethernet",
-+              .probe          = yt8531_probe,
-+              .config_init    = yt8531_config_init,
-+              .suspend        = genphy_suspend,
-+              .resume         = genphy_resume,
-+              .get_wol        = ytphy_get_wol,
-+              .set_wol        = yt8531_set_wol,
-+              .link_change_notify = yt8531_link_change_notify,
-+      },
-+      {
-               PHY_ID_MATCH_EXACT(PHY_ID_YT8531S),
-               .name           = "YT8531S Gigabit Ethernet",
-               .get_features   = yt8521_get_features,
-@@ -1990,7 +2193,7 @@ static struct phy_driver motorcomm_phy_d
- module_phy_driver(motorcomm_phy_drvs);
--MODULE_DESCRIPTION("Motorcomm 8511/8521/8531S PHY driver");
-+MODULE_DESCRIPTION("Motorcomm 8511/8521/8531/8531S PHY driver");
- MODULE_AUTHOR("Peter Geis");
- MODULE_AUTHOR("Frank");
- MODULE_LICENSE("GPL");
-@@ -1998,6 +2201,7 @@ MODULE_LICENSE("GPL");
- static const struct mdio_device_id __maybe_unused motorcomm_tbl[] = {
-       { PHY_ID_MATCH_EXACT(PHY_ID_YT8511) },
-       { PHY_ID_MATCH_EXACT(PHY_ID_YT8521) },
-+      { PHY_ID_MATCH_EXACT(PHY_ID_YT8531) },
-       { PHY_ID_MATCH_EXACT(PHY_ID_YT8531S) },
-       { /* sentinel */ }
- };
diff --git a/target/linux/generic/backport-5.15/791-v6.3-10-net-phy-motorcomm-uninitialized-variables-in.patch b/target/linux/generic/backport-5.15/791-v6.3-10-net-phy-motorcomm-uninitialized-variables-in.patch
deleted file mode 100644 (file)
index 29ae86d..0000000
+++ /dev/null
@@ -1,34 +0,0 @@
-From 9753613f7399601f9bae6ee81e9d4274246c98ab Mon Sep 17 00:00:00 2001
-From: Dan Carpenter <[email protected]>
-Date: Wed, 15 Feb 2023 07:21:47 +0300
-Subject: [PATCH] net: phy: motorcomm: uninitialized variables in
- yt8531_link_change_notify()
-
-These booleans are never set to false, but are just used without being
-initialized.
-
-Fixes: 4ac94f728a58 ("net: phy: Add driver for Motorcomm yt8531 gigabit ethernet phy")
-Signed-off-by: Dan Carpenter <[email protected]>
-Reviewed-by: Frank Sae <[email protected]>
-Link: https://lore.kernel.org/r/Y+xd2yJet2ImHLoQ@kili
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- drivers/net/phy/motorcomm.c | 6 +++---
- 1 file changed, 3 insertions(+), 3 deletions(-)
-
---- a/drivers/net/phy/motorcomm.c
-+++ b/drivers/net/phy/motorcomm.c
-@@ -1533,10 +1533,10 @@ static int yt8531_config_init(struct phy
- static void yt8531_link_change_notify(struct phy_device *phydev)
- {
-       struct device_node *node = phydev->mdio.dev.of_node;
-+      bool tx_clk_1000_inverted = false;
-+      bool tx_clk_100_inverted = false;
-+      bool tx_clk_10_inverted = false;
-       bool tx_clk_adj_enabled = false;
--      bool tx_clk_1000_inverted;
--      bool tx_clk_100_inverted;
--      bool tx_clk_10_inverted;
-       u16 val = 0;
-       int ret;
diff --git a/target/linux/generic/backport-5.15/791-v6.6-11-net-phy-motorcomm-Add-pad-drive-strength-cfg-support.patch b/target/linux/generic/backport-5.15/791-v6.6-11-net-phy-motorcomm-Add-pad-drive-strength-cfg-support.patch
deleted file mode 100644 (file)
index 010ca9b..0000000
+++ /dev/null
@@ -1,170 +0,0 @@
-From 7a561e9351ae7e3fb1f08584d40b49c1e55dde60 Mon Sep 17 00:00:00 2001
-From: Samin Guo <[email protected]>
-Date: Thu, 20 Jul 2023 19:15:09 +0800
-Subject: [PATCH] net: phy: motorcomm: Add pad drive strength cfg support
-
-The motorcomm phy (YT8531) supports the ability to adjust the drive
-strength of the rx_clk/rx_data, and the default strength may not be
-suitable for all boards. So add configurable options to better match
-the boards.(e.g. StarFive VisionFive 2)
-
-When we configure the drive strength, we need to read the current
-LDO voltage value to ensure that it is a legal value at that LDO
-voltage.
-
-Reviewed-by: Hal Feng <[email protected]>
-Signed-off-by: Samin Guo <[email protected]>
-Reviewed-by: Andrew Lunn <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/phy/motorcomm.c | 118 ++++++++++++++++++++++++++++++++++++
- 1 file changed, 118 insertions(+)
-
---- a/drivers/net/phy/motorcomm.c
-+++ b/drivers/net/phy/motorcomm.c
-@@ -163,6 +163,10 @@
- #define YT8521_CHIP_CONFIG_REG                        0xA001
- #define YT8521_CCR_SW_RST                     BIT(15)
-+#define YT8531_RGMII_LDO_VOL_MASK             GENMASK(5, 4)
-+#define YT8531_LDO_VOL_3V3                    0x0
-+#define YT8531_LDO_VOL_1V8                    0x2
-+
- /* 1b0 disable 1.9ns rxc clock delay  *default*
-  * 1b1 enable 1.9ns rxc clock delay
-  */
-@@ -236,6 +240,12 @@
-  */
- #define YTPHY_WCR_TYPE_PULSE                  BIT(0)
-+#define YTPHY_PAD_DRIVE_STRENGTH_REG          0xA010
-+#define YT8531_RGMII_RXC_DS_MASK              GENMASK(15, 13)
-+#define YT8531_RGMII_RXD_DS_HI_MASK           BIT(12)         /* Bit 2 of rxd_ds */
-+#define YT8531_RGMII_RXD_DS_LOW_MASK          GENMASK(5, 4)   /* Bit 1/0 of rxd_ds */
-+#define YT8531_RGMII_RX_DS_DEFAULT            0x3
-+
- #define YTPHY_SYNCE_CFG_REG                   0xA012
- #define YT8521_SCR_SYNCE_ENABLE                       BIT(5)
- /* 1b0 output 25m clock
-@@ -835,6 +845,110 @@ static int ytphy_rgmii_clk_delay_config_
- }
- /**
-+ * struct ytphy_ldo_vol_map - map a current value to a register value
-+ * @vol: ldo voltage
-+ * @ds:  value in the register
-+ * @cur: value in device configuration
-+ */
-+struct ytphy_ldo_vol_map {
-+      u32 vol;
-+      u32 ds;
-+      u32 cur;
-+};
-+
-+static const struct ytphy_ldo_vol_map yt8531_ldo_vol[] = {
-+      {.vol = YT8531_LDO_VOL_1V8, .ds = 0, .cur = 1200},
-+      {.vol = YT8531_LDO_VOL_1V8, .ds = 1, .cur = 2100},
-+      {.vol = YT8531_LDO_VOL_1V8, .ds = 2, .cur = 2700},
-+      {.vol = YT8531_LDO_VOL_1V8, .ds = 3, .cur = 2910},
-+      {.vol = YT8531_LDO_VOL_1V8, .ds = 4, .cur = 3110},
-+      {.vol = YT8531_LDO_VOL_1V8, .ds = 5, .cur = 3600},
-+      {.vol = YT8531_LDO_VOL_1V8, .ds = 6, .cur = 3970},
-+      {.vol = YT8531_LDO_VOL_1V8, .ds = 7, .cur = 4350},
-+      {.vol = YT8531_LDO_VOL_3V3, .ds = 0, .cur = 3070},
-+      {.vol = YT8531_LDO_VOL_3V3, .ds = 1, .cur = 4080},
-+      {.vol = YT8531_LDO_VOL_3V3, .ds = 2, .cur = 4370},
-+      {.vol = YT8531_LDO_VOL_3V3, .ds = 3, .cur = 4680},
-+      {.vol = YT8531_LDO_VOL_3V3, .ds = 4, .cur = 5020},
-+      {.vol = YT8531_LDO_VOL_3V3, .ds = 5, .cur = 5450},
-+      {.vol = YT8531_LDO_VOL_3V3, .ds = 6, .cur = 5740},
-+      {.vol = YT8531_LDO_VOL_3V3, .ds = 7, .cur = 6140},
-+};
-+
-+static u32 yt8531_get_ldo_vol(struct phy_device *phydev)
-+{
-+      u32 val;
-+
-+      val = ytphy_read_ext_with_lock(phydev, YT8521_CHIP_CONFIG_REG);
-+      val = FIELD_GET(YT8531_RGMII_LDO_VOL_MASK, val);
-+
-+      return val <= YT8531_LDO_VOL_1V8 ? val : YT8531_LDO_VOL_1V8;
-+}
-+
-+static int yt8531_get_ds_map(struct phy_device *phydev, u32 cur)
-+{
-+      u32 vol;
-+      int i;
-+
-+      vol = yt8531_get_ldo_vol(phydev);
-+      for (i = 0; i < ARRAY_SIZE(yt8531_ldo_vol); i++) {
-+              if (yt8531_ldo_vol[i].vol == vol && yt8531_ldo_vol[i].cur == cur)
-+                      return yt8531_ldo_vol[i].ds;
-+      }
-+
-+      return -EINVAL;
-+}
-+
-+static int yt8531_set_ds(struct phy_device *phydev)
-+{
-+      struct device_node *node = phydev->mdio.dev.of_node;
-+      u32 ds_field_low, ds_field_hi, val;
-+      int ret, ds;
-+
-+      /* set rgmii rx clk driver strength */
-+      if (!of_property_read_u32(node, "motorcomm,rx-clk-drv-microamp", &val)) {
-+              ds = yt8531_get_ds_map(phydev, val);
-+              if (ds < 0)
-+                      return dev_err_probe(&phydev->mdio.dev, ds,
-+                                           "No matching current value was found.\n");
-+      } else {
-+              ds = YT8531_RGMII_RX_DS_DEFAULT;
-+      }
-+
-+      ret = ytphy_modify_ext_with_lock(phydev,
-+                                       YTPHY_PAD_DRIVE_STRENGTH_REG,
-+                                       YT8531_RGMII_RXC_DS_MASK,
-+                                       FIELD_PREP(YT8531_RGMII_RXC_DS_MASK, ds));
-+      if (ret < 0)
-+              return ret;
-+
-+      /* set rgmii rx data driver strength */
-+      if (!of_property_read_u32(node, "motorcomm,rx-data-drv-microamp", &val)) {
-+              ds = yt8531_get_ds_map(phydev, val);
-+              if (ds < 0)
-+                      return dev_err_probe(&phydev->mdio.dev, ds,
-+                                           "No matching current value was found.\n");
-+      } else {
-+              ds = YT8531_RGMII_RX_DS_DEFAULT;
-+      }
-+
-+      ds_field_hi = FIELD_GET(BIT(2), ds);
-+      ds_field_hi = FIELD_PREP(YT8531_RGMII_RXD_DS_HI_MASK, ds_field_hi);
-+
-+      ds_field_low = FIELD_GET(GENMASK(1, 0), ds);
-+      ds_field_low = FIELD_PREP(YT8531_RGMII_RXD_DS_LOW_MASK, ds_field_low);
-+
-+      ret = ytphy_modify_ext_with_lock(phydev,
-+                                       YTPHY_PAD_DRIVE_STRENGTH_REG,
-+                                       YT8531_RGMII_RXD_DS_LOW_MASK | YT8531_RGMII_RXD_DS_HI_MASK,
-+                                       ds_field_low | ds_field_hi);
-+      if (ret < 0)
-+              return ret;
-+
-+      return 0;
-+}
-+
-+/**
-  * yt8521_probe() - read chip config then set suitable polling_mode
-  * @phydev: a pointer to a &struct phy_device
-  *
-@@ -1518,6 +1632,10 @@ static int yt8531_config_init(struct phy
-                       return ret;
-       }
-+      ret = yt8531_set_ds(phydev);
-+      if (ret < 0)
-+              return ret;
-+
-       return 0;
- }
diff --git a/target/linux/generic/backport-5.15/792-01-v6.0-net-phylink-disable-PCS-polling-over-major-configura.patch b/target/linux/generic/backport-5.15/792-01-v6.0-net-phylink-disable-PCS-polling-over-major-configura.patch
deleted file mode 100644 (file)
index a0cb367..0000000
+++ /dev/null
@@ -1,81 +0,0 @@
-From bfac8c490d605bea03b1f1927582b6f396462164 Mon Sep 17 00:00:00 2001
-From: "Russell King (Oracle)" <[email protected]>
-Date: Mon, 27 Jun 2022 12:44:43 +0100
-Subject: [PATCH] net: phylink: disable PCS polling over major configuration
-
-While we are performing a major configuration, there is no point having
-the PCS polling timer running. Stop it before we begin preparing for
-the configuration change, and restart it only once we've successfully
-completed the change.
-
-Reviewed-by: Andrew Lunn <[email protected]>
-Signed-off-by: Russell King (Oracle) <[email protected]>
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- drivers/net/phy/phylink.c | 30 ++++++++++++++++++++----------
- 1 file changed, 20 insertions(+), 10 deletions(-)
-
---- a/drivers/net/phy/phylink.c
-+++ b/drivers/net/phy/phylink.c
-@@ -759,6 +759,18 @@ static void phylink_resolve_flow(struct
-       }
- }
-+static void phylink_pcs_poll_stop(struct phylink *pl)
-+{
-+      if (pl->cfg_link_an_mode == MLO_AN_INBAND)
-+              del_timer(&pl->link_poll);
-+}
-+
-+static void phylink_pcs_poll_start(struct phylink *pl)
-+{
-+      if (pl->pcs->poll && pl->cfg_link_an_mode == MLO_AN_INBAND)
-+              mod_timer(&pl->link_poll, jiffies + HZ);
-+}
-+
- static void phylink_mac_config(struct phylink *pl,
-                              const struct phylink_link_state *state)
- {
-@@ -790,6 +802,7 @@ static void phylink_major_config(struct
-                                 const struct phylink_link_state *state)
- {
-       struct phylink_pcs *pcs = NULL;
-+      bool pcs_changed = false;
-       int err;
-       phylink_dbg(pl, "major config %s\n", phy_modes(state->interface));
-@@ -802,8 +815,12 @@ static void phylink_major_config(struct
-                                   pcs);
-                       return;
-               }
-+
-+              pcs_changed = pcs && pl->pcs != pcs;
-       }
-+      phylink_pcs_poll_stop(pl);
-+
-       if (pl->mac_ops->mac_prepare) {
-               err = pl->mac_ops->mac_prepare(pl->config, pl->cur_link_an_mode,
-                                              state->interface);
-@@ -817,8 +834,10 @@ static void phylink_major_config(struct
-       /* If we have a new PCS, switch to the new PCS after preparing the MAC
-        * for the change.
-        */
--      if (pcs)
--              phylink_set_pcs(pl, pcs);
-+      if (pcs_changed) {
-+              pl->pcs = pcs;
-+              pl->pcs_ops = pcs->ops;
-+      }
-       phylink_mac_config(pl, state);
-@@ -844,6 +863,8 @@ static void phylink_major_config(struct
-                       phylink_err(pl, "mac_finish failed: %pe\n",
-                                   ERR_PTR(err));
-       }
-+
-+      phylink_pcs_poll_start(pl);
- }
- /*
diff --git a/target/linux/generic/backport-5.15/792-02-v6.0-net-phylink-fix-NULL-pl-pcs-dereference-during-phyli.patch b/target/linux/generic/backport-5.15/792-02-v6.0-net-phylink-fix-NULL-pl-pcs-dereference-during-phyli.patch
deleted file mode 100644 (file)
index fec2fdd..0000000
+++ /dev/null
@@ -1,38 +0,0 @@
-From b7d78b46d5e8dc77c656c13885d31e931923b915 Mon Sep 17 00:00:00 2001
-From: Vladimir Oltean <[email protected]>
-Date: Wed, 29 Jun 2022 22:33:58 +0300
-Subject: [PATCH] net: phylink: fix NULL pl->pcs dereference during
- phylink_pcs_poll_start
-
-The current link mode of the phylink instance may not require an
-attached PCS. However, phylink_major_config() unconditionally
-dereferences this potentially NULL pointer when restarting the link poll
-timer, which will panic the kernel.
-
-Fix the problem by checking whether a PCS exists in phylink_pcs_poll_start(),
-otherwise do nothing. The code prior to the blamed patch also only
-looked at pcs->poll within an "if (pcs)" block.
-
-Fixes: bfac8c490d60 ("net: phylink: disable PCS polling over major configuration")
-Signed-off-by: Vladimir Oltean <[email protected]>
-Reviewed-by: Russell King (Oracle) <[email protected]>
-Tested-by: Gerhard Engleder <[email protected]>
-Tested-by: Michael Walle <[email protected]> # on kontron-kbox-a-230-ls
-Tested-by: Nicolas Ferre <[email protected]> # on sam9x60ek
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- drivers/net/phy/phylink.c | 2 +-
- 1 file changed, 1 insertion(+), 1 deletion(-)
-
---- a/drivers/net/phy/phylink.c
-+++ b/drivers/net/phy/phylink.c
-@@ -767,7 +767,7 @@ static void phylink_pcs_poll_stop(struct
- static void phylink_pcs_poll_start(struct phylink *pl)
- {
--      if (pl->pcs->poll && pl->cfg_link_an_mode == MLO_AN_INBAND)
-+      if (pl->pcs && pl->pcs->poll && pl->cfg_link_an_mode == MLO_AN_INBAND)
-               mod_timer(&pl->link_poll, jiffies + HZ);
- }
diff --git a/target/linux/generic/backport-5.15/792-03-v6.6-net-phylink-add-pcs_enable-pcs_disable-methods.patch b/target/linux/generic/backport-5.15/792-03-v6.6-net-phylink-add-pcs_enable-pcs_disable-methods.patch
deleted file mode 100644 (file)
index 71b09cb..0000000
+++ /dev/null
@@ -1,172 +0,0 @@
-From 90ef0a7b0622c62758b2638604927867775479ea Mon Sep 17 00:00:00 2001
-From: "Russell King (Oracle)" <[email protected]>
-Date: Thu, 13 Jul 2023 09:42:07 +0100
-Subject: [PATCH] net: phylink: add pcs_enable()/pcs_disable() methods
-
-Add phylink PCS enable/disable callbacks that will allow us to place
-IEEE 802.3 register compliant PCS in power-down mode while not being
-used.
-
-Signed-off-by: Russell King (Oracle) <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/phy/phylink.c | 48 +++++++++++++++++++++++++++++++--------
- include/linux/phylink.h   | 16 +++++++++++++
- 2 files changed, 55 insertions(+), 9 deletions(-)
-
---- a/drivers/net/phy/phylink.c
-+++ b/drivers/net/phy/phylink.c
-@@ -34,6 +34,10 @@ enum {
-       PHYLINK_DISABLE_STOPPED,
-       PHYLINK_DISABLE_LINK,
-       PHYLINK_DISABLE_MAC_WOL,
-+
-+      PCS_STATE_DOWN = 0,
-+      PCS_STATE_STARTING,
-+      PCS_STATE_STARTED,
- };
- /**
-@@ -72,6 +76,7 @@ struct phylink {
-       struct mutex state_mutex;
-       struct phylink_link_state phy_state;
-       struct work_struct resolve;
-+      unsigned int pcs_state;
-       bool mac_link_dropped;
-       bool using_mac_select_pcs;
-@@ -798,6 +803,22 @@ static void phylink_mac_pcs_an_restart(s
-       }
- }
-+static void phylink_pcs_disable(struct phylink_pcs *pcs)
-+{
-+      if (pcs && pcs->ops->pcs_disable)
-+              pcs->ops->pcs_disable(pcs);
-+}
-+
-+static int phylink_pcs_enable(struct phylink_pcs *pcs)
-+{
-+      int err = 0;
-+
-+      if (pcs && pcs->ops->pcs_enable)
-+              err = pcs->ops->pcs_enable(pcs);
-+
-+      return err;
-+}
-+
- static void phylink_major_config(struct phylink *pl, bool restart,
-                                 const struct phylink_link_state *state)
- {
-@@ -835,12 +856,16 @@ static void phylink_major_config(struct
-        * for the change.
-        */
-       if (pcs_changed) {
-+              phylink_pcs_disable(pl->pcs);
-               pl->pcs = pcs;
-               pl->pcs_ops = pcs->ops;
-       }
-       phylink_mac_config(pl, state);
-+      if (pl->pcs_state == PCS_STATE_STARTING || pcs_changed)
-+              phylink_pcs_enable(pl->pcs);
-+
-       if (pl->pcs_ops) {
-               err = pl->pcs_ops->pcs_config(pl->pcs, pl->cur_link_an_mode,
-                                             state->interface,
-@@ -1264,6 +1289,7 @@ struct phylink *phylink_create(struct ph
-       pl->link_config.speed = SPEED_UNKNOWN;
-       pl->link_config.duplex = DUPLEX_UNKNOWN;
-       pl->link_config.an_enabled = true;
-+      pl->pcs_state = PCS_STATE_DOWN;
-       pl->mac_ops = mac_ops;
-       __set_bit(PHYLINK_DISABLE_STOPPED, &pl->phylink_disable_state);
-       timer_setup(&pl->link_poll, phylink_fixed_poll, 0);
-@@ -1655,6 +1681,8 @@ void phylink_start(struct phylink *pl)
-       if (pl->netdev)
-               netif_carrier_off(pl->netdev);
-+      pl->pcs_state = PCS_STATE_STARTING;
-+
-       /* Apply the link configuration to the MAC when starting. This allows
-        * a fixed-link to start with the correct parameters, and also
-        * ensures that we set the appropriate advertisement for Serdes links.
-@@ -1665,6 +1693,8 @@ void phylink_start(struct phylink *pl)
-        */
-       phylink_mac_initial_config(pl, true);
-+      pl->pcs_state = PCS_STATE_STARTED;
-+
-       clear_bit(PHYLINK_DISABLE_STOPPED, &pl->phylink_disable_state);
-       phylink_run_resolve(pl);
-@@ -1684,16 +1714,9 @@ void phylink_start(struct phylink *pl)
-                       poll = true;
-       }
--      switch (pl->cfg_link_an_mode) {
--      case MLO_AN_FIXED:
-+      if (pl->cfg_link_an_mode == MLO_AN_FIXED)
-               poll |= pl->config->poll_fixed_state;
--              break;
--      case MLO_AN_INBAND:
--              poll |= pl->config->pcs_poll;
--              if (pl->pcs)
--                      poll |= pl->pcs->poll;
--              break;
--      }
-+
-       if (poll)
-               mod_timer(&pl->link_poll, jiffies + HZ);
-       if (pl->phydev)
-@@ -1730,6 +1753,10 @@ void phylink_stop(struct phylink *pl)
-       }
-       phylink_run_resolve_and_disable(pl, PHYLINK_DISABLE_STOPPED);
-+
-+      pl->pcs_state = PCS_STATE_DOWN;
-+
-+      phylink_pcs_disable(pl->pcs);
- }
- EXPORT_SYMBOL_GPL(phylink_stop);
---- a/include/linux/phylink.h
-+++ b/include/linux/phylink.h
-@@ -419,6 +419,8 @@ struct phylink_pcs {
- /**
-  * struct phylink_pcs_ops - MAC PCS operations structure.
-  * @pcs_validate: validate the link configuration.
-+ * @pcs_enable: enable the PCS.
-+ * @pcs_disable: disable the PCS.
-  * @pcs_get_state: read the current MAC PCS link state from the hardware.
-  * @pcs_config: configure the MAC PCS for the selected mode and state.
-  * @pcs_an_restart: restart 802.3z BaseX autonegotiation.
-@@ -428,6 +430,8 @@ struct phylink_pcs {
- struct phylink_pcs_ops {
-       int (*pcs_validate)(struct phylink_pcs *pcs, unsigned long *supported,
-                           const struct phylink_link_state *state);
-+      int (*pcs_enable)(struct phylink_pcs *pcs);
-+      void (*pcs_disable)(struct phylink_pcs *pcs);
-       void (*pcs_get_state)(struct phylink_pcs *pcs,
-                             struct phylink_link_state *state);
-       int (*pcs_config)(struct phylink_pcs *pcs, unsigned int mode,
-@@ -458,6 +462,18 @@ int pcs_validate(struct phylink_pcs *pcs
-                const struct phylink_link_state *state);
- /**
-+ * pcs_enable() - enable the PCS.
-+ * @pcs: a pointer to a &struct phylink_pcs.
-+ */
-+int pcs_enable(struct phylink_pcs *pcs);
-+
-+/**
-+ * pcs_disable() - disable the PCS.
-+ * @pcs: a pointer to a &struct phylink_pcs.
-+ */
-+void pcs_disable(struct phylink_pcs *pcs);
-+
-+/**
-  * pcs_get_state() - Read the current inband link state from the hardware
-  * @pcs: a pointer to a &struct phylink_pcs.
-  * @state: a pointer to a &struct phylink_link_state.
diff --git a/target/linux/generic/backport-5.15/793-v6.6-net-pcs-lynxi-implement-pcs_disable-op.patch b/target/linux/generic/backport-5.15/793-v6.6-net-pcs-lynxi-implement-pcs_disable-op.patch
deleted file mode 100644 (file)
index eb9b4b7..0000000
+++ /dev/null
@@ -1,44 +0,0 @@
-From e4ccdfb78a47132f2d215658aab8902fc457c4b4 Mon Sep 17 00:00:00 2001
-From: Daniel Golle <[email protected]>
-Date: Fri, 18 Aug 2023 04:07:46 +0100
-Subject: [PATCH 082/125] net: pcs: lynxi: implement pcs_disable op
-
-When switching from 10GBase-R/5GBase-R/USXGMII to one of the interface
-modes provided by mtk-pcs-lynxi we need to make sure to always perform
-a full configuration of the PHYA.
-
-Implement pcs_disable op which resets the stored interface mode to
-PHY_INTERFACE_MODE_NA to trigger a full reconfiguration once the LynxI
-PCS driver had previously been deselected in favor of another PCS
-driver such as the to-be-added driver for the USXGMII PCS found in
-MT7988.
-
-Signed-off-by: Daniel Golle <[email protected]>
-Link: https://lore.kernel.org/r/f23d1a60d2c9d2fb72e32dcb0eaa5f7e867a3d68.1692327891.git.daniel@makrotopia.org
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- drivers/net/pcs/pcs-mtk-lynxi.c | 8 ++++++++
- 1 file changed, 8 insertions(+)
-
---- a/drivers/net/pcs/pcs-mtk-lynxi.c
-+++ b/drivers/net/pcs/pcs-mtk-lynxi.c
-@@ -241,11 +241,19 @@ static void mtk_pcs_lynxi_link_up(struct
-       }
- }
-+static void mtk_pcs_lynxi_disable(struct phylink_pcs *pcs)
-+{
-+      struct mtk_pcs_lynxi *mpcs = pcs_to_mtk_pcs_lynxi(pcs);
-+
-+      mpcs->interface = PHY_INTERFACE_MODE_NA;
-+}
-+
- static const struct phylink_pcs_ops mtk_pcs_lynxi_ops = {
-       .pcs_get_state = mtk_pcs_lynxi_get_state,
-       .pcs_config = mtk_pcs_lynxi_config,
-       .pcs_an_restart = mtk_pcs_lynxi_restart_an,
-       .pcs_link_up = mtk_pcs_lynxi_link_up,
-+      .pcs_disable = mtk_pcs_lynxi_disable,
- };
- struct phylink_pcs *mtk_pcs_lynxi_create(struct device *dev,
diff --git a/target/linux/generic/backport-5.15/794-v6.2-net-core-Allow-live-renaming-when-an-interface-is-up.patch b/target/linux/generic/backport-5.15/794-v6.2-net-core-Allow-live-renaming-when-an-interface-is-up.patch
deleted file mode 100644 (file)
index b0860db..0000000
+++ /dev/null
@@ -1,136 +0,0 @@
-From: Andy Ren <[email protected]>
-Date: Mon, 7 Nov 2022 09:42:42 -0800
-Subject: [PATCH] net/core: Allow live renaming when an interface is up
-
-Allow a network interface to be renamed when the interface
-is up.
-
-As described in the netconsole documentation [1], when netconsole is
-used as a built-in, it will bring up the specified interface as soon as
-possible. As a result, user space will not be able to rename the
-interface since the kernel disallows renaming of interfaces that are
-administratively up unless the 'IFF_LIVE_RENAME_OK' private flag was set
-by the kernel.
-
-The original solution [2] to this problem was to add a new parameter to
-the netconsole configuration parameters that allows renaming of
-the interface used by netconsole while it is administratively up.
-However, during the discussion that followed, it became apparent that we
-have no reason to keep the current restriction and instead we should
-allow user space to rename interfaces regardless of their administrative
-state:
-
-1. The restriction was put in place over 20 years ago when renaming was
-only possible via IOCTL and before rtnetlink started notifying user
-space about such changes like it does today.
-
-2. The 'IFF_LIVE_RENAME_OK' flag was added over 3 years ago in version
-5.2 and no regressions were reported.
-
-3. In-kernel listeners to 'NETDEV_CHANGENAME' do not seem to care about
-the administrative state of interface.
-
-Therefore, allow user space to rename running interfaces by removing the
-restriction and the associated 'IFF_LIVE_RENAME_OK' flag. Help in
-possible triage by emitting a message to the kernel log that an
-interface was renamed while UP.
-
-[1] https://www.kernel.org/doc/Documentation/networking/netconsole.rst
-[2] https://lore.kernel.org/netdev/[email protected]/
-
-Signed-off-by: Andy Ren <[email protected]>
-Reviewed-by: Ido Schimmel <[email protected]>
-Reviewed-by: David Ahern <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
-
---- a/include/linux/netdevice.h
-+++ b/include/linux/netdevice.h
-@@ -1643,7 +1643,6 @@ struct net_device_ops {
-  * @IFF_FAILOVER: device is a failover master device
-  * @IFF_FAILOVER_SLAVE: device is lower dev of a failover master device
-  * @IFF_L3MDEV_RX_HANDLER: only invoke the rx handler of L3 master device
-- * @IFF_LIVE_RENAME_OK: rename is allowed while device is up and running
-  * @IFF_TX_SKB_NO_LINEAR: device/driver is capable of xmitting frames with
-  *    skb_headlen(skb) == 0 (data starts from frag0)
-  */
-@@ -1678,7 +1677,7 @@ enum netdev_priv_flags {
-       IFF_FAILOVER                    = 1<<27,
-       IFF_FAILOVER_SLAVE              = 1<<28,
-       IFF_L3MDEV_RX_HANDLER           = 1<<29,
--      IFF_LIVE_RENAME_OK              = 1<<30,
-+      /* was IFF_LIVE_RENAME_OK */
-       IFF_TX_SKB_NO_LINEAR            = BIT_ULL(31),
- };
-@@ -1712,7 +1711,6 @@ enum netdev_priv_flags {
- #define IFF_FAILOVER                  IFF_FAILOVER
- #define IFF_FAILOVER_SLAVE            IFF_FAILOVER_SLAVE
- #define IFF_L3MDEV_RX_HANDLER         IFF_L3MDEV_RX_HANDLER
--#define IFF_LIVE_RENAME_OK            IFF_LIVE_RENAME_OK
- #define IFF_TX_SKB_NO_LINEAR          IFF_TX_SKB_NO_LINEAR
- /* Specifies the type of the struct net_device::ml_priv pointer */
---- a/net/core/dev.c
-+++ b/net/core/dev.c
-@@ -1242,22 +1242,6 @@ int dev_change_name(struct net_device *d
-       net = dev_net(dev);
--      /* Some auto-enslaved devices e.g. failover slaves are
--       * special, as userspace might rename the device after
--       * the interface had been brought up and running since
--       * the point kernel initiated auto-enslavement. Allow
--       * live name change even when these slave devices are
--       * up and running.
--       *
--       * Typically, users of these auto-enslaving devices
--       * don't actually care about slave name change, as
--       * they are supposed to operate on master interface
--       * directly.
--       */
--      if (dev->flags & IFF_UP &&
--          likely(!(dev->priv_flags & IFF_LIVE_RENAME_OK)))
--              return -EBUSY;
--
-       down_write(&devnet_rename_sem);
-       if (strncmp(newname, dev->name, IFNAMSIZ) == 0) {
-@@ -1274,7 +1258,8 @@ int dev_change_name(struct net_device *d
-       }
-       if (oldname[0] && !strchr(oldname, '%'))
--              netdev_info(dev, "renamed from %s\n", oldname);
-+              netdev_info(dev, "renamed from %s%s\n", oldname,
-+                          dev->flags & IFF_UP ? " (while UP)" : "");
-       old_assign_type = dev->name_assign_type;
-       dev->name_assign_type = NET_NAME_RENAMED;
---- a/net/core/failover.c
-+++ b/net/core/failover.c
-@@ -80,14 +80,14 @@ static int failover_slave_register(struc
-               goto err_upper_link;
-       }
--      slave_dev->priv_flags |= (IFF_FAILOVER_SLAVE | IFF_LIVE_RENAME_OK);
-+      slave_dev->priv_flags |= IFF_FAILOVER_SLAVE;
-       if (fops && fops->slave_register &&
-           !fops->slave_register(slave_dev, failover_dev))
-               return NOTIFY_OK;
-       netdev_upper_dev_unlink(slave_dev, failover_dev);
--      slave_dev->priv_flags &= ~(IFF_FAILOVER_SLAVE | IFF_LIVE_RENAME_OK);
-+      slave_dev->priv_flags &= ~IFF_FAILOVER_SLAVE;
- err_upper_link:
-       netdev_rx_handler_unregister(slave_dev);
- done:
-@@ -121,7 +121,7 @@ int failover_slave_unregister(struct net
-       netdev_rx_handler_unregister(slave_dev);
-       netdev_upper_dev_unlink(slave_dev, failover_dev);
--      slave_dev->priv_flags &= ~(IFF_FAILOVER_SLAVE | IFF_LIVE_RENAME_OK);
-+      slave_dev->priv_flags &= ~IFF_FAILOVER_SLAVE;
-       if (fops && fops->slave_unregister &&
-           !fops->slave_unregister(slave_dev, failover_dev))
diff --git a/target/linux/generic/backport-5.15/795-v6.3-02-cdc_ether-no-need-to-blacklist-any-r8152-devices.patch b/target/linux/generic/backport-5.15/795-v6.3-02-cdc_ether-no-need-to-blacklist-any-r8152-devices.patch
deleted file mode 100644 (file)
index 2b3272c..0000000
+++ /dev/null
@@ -1,158 +0,0 @@
-From 69649ef8405320f81497f4757faac8234f61b167 Mon Sep 17 00:00:00 2001
-From: Bjørn Mork <[email protected]>
-Date: Fri, 6 Jan 2023 17:07:39 +0100
-Subject: [PATCH] cdc_ether: no need to blacklist any r8152 devices
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-The r8152 driver does not need this anymore.
-
-Dropping blacklist entries adds optional support for these
-devices in ECM mode.
-
-The 8153 devices are handled by the r8153_ecm driver when
-in ECM mode, and must still be blacklisted here.
-
-Signed-off-by: Bjørn Mork <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/usb/cdc_ether.c | 114 ------------------------------------
- 1 file changed, 114 deletions(-)
-
---- a/drivers/net/usb/cdc_ether.c
-+++ b/drivers/net/usb/cdc_ether.c
-@@ -767,13 +767,6 @@ static const struct usb_device_id produc
-       .driver_info = 0,
- },
--/* Realtek RTL8152 Based USB 2.0 Ethernet Adapters */
--{
--      USB_DEVICE_AND_INTERFACE_INFO(REALTEK_VENDOR_ID, 0x8152, USB_CLASS_COMM,
--                      USB_CDC_SUBCLASS_ETHERNET, USB_CDC_PROTO_NONE),
--      .driver_info = 0,
--},
--
- /* Realtek RTL8153 Based USB 3.0 Ethernet Adapters */
- {
-       USB_DEVICE_AND_INTERFACE_INFO(REALTEK_VENDOR_ID, 0x8153, USB_CLASS_COMM,
-@@ -781,119 +774,12 @@ static const struct usb_device_id       produc
-       .driver_info = 0,
- },
--/* Samsung USB Ethernet Adapters */
--{
--      USB_DEVICE_AND_INTERFACE_INFO(SAMSUNG_VENDOR_ID, 0xa101, USB_CLASS_COMM,
--                      USB_CDC_SUBCLASS_ETHERNET, USB_CDC_PROTO_NONE),
--      .driver_info = 0,
--},
--
--#if IS_ENABLED(CONFIG_USB_RTL8152)
--/* Linksys USB3GIGV1 Ethernet Adapter */
--{
--      USB_DEVICE_AND_INTERFACE_INFO(LINKSYS_VENDOR_ID, 0x0041, USB_CLASS_COMM,
--                      USB_CDC_SUBCLASS_ETHERNET, USB_CDC_PROTO_NONE),
--      .driver_info = 0,
--},
--#endif
--
--/* Lenovo ThinkPad OneLink+ Dock (based on Realtek RTL8153) */
--{
--      USB_DEVICE_AND_INTERFACE_INFO(LENOVO_VENDOR_ID, 0x3054, USB_CLASS_COMM,
--                      USB_CDC_SUBCLASS_ETHERNET, USB_CDC_PROTO_NONE),
--      .driver_info = 0,
--},
--
--/* ThinkPad USB-C Dock (based on Realtek RTL8153) */
--{
--      USB_DEVICE_AND_INTERFACE_INFO(LENOVO_VENDOR_ID, 0x3062, USB_CLASS_COMM,
--                      USB_CDC_SUBCLASS_ETHERNET, USB_CDC_PROTO_NONE),
--      .driver_info = 0,
--},
--
--/* ThinkPad Thunderbolt 3 Dock (based on Realtek RTL8153) */
--{
--      USB_DEVICE_AND_INTERFACE_INFO(LENOVO_VENDOR_ID, 0x3069, USB_CLASS_COMM,
--                      USB_CDC_SUBCLASS_ETHERNET, USB_CDC_PROTO_NONE),
--      .driver_info = 0,
--},
--
--/* ThinkPad Thunderbolt 3 Dock Gen 2 (based on Realtek RTL8153) */
--{
--      USB_DEVICE_AND_INTERFACE_INFO(LENOVO_VENDOR_ID, 0x3082, USB_CLASS_COMM,
--                      USB_CDC_SUBCLASS_ETHERNET, USB_CDC_PROTO_NONE),
--      .driver_info = 0,
--},
--
--/* Lenovo Thinkpad USB 3.0 Ethernet Adapters (based on Realtek RTL8153) */
--{
--      USB_DEVICE_AND_INTERFACE_INFO(LENOVO_VENDOR_ID, 0x7205, USB_CLASS_COMM,
--                      USB_CDC_SUBCLASS_ETHERNET, USB_CDC_PROTO_NONE),
--      .driver_info = 0,
--},
--
--/* Lenovo USB C to Ethernet Adapter (based on Realtek RTL8153) */
--{
--      USB_DEVICE_AND_INTERFACE_INFO(LENOVO_VENDOR_ID, 0x720c, USB_CLASS_COMM,
--                      USB_CDC_SUBCLASS_ETHERNET, USB_CDC_PROTO_NONE),
--      .driver_info = 0,
--},
--
--/* Lenovo USB-C Travel Hub (based on Realtek RTL8153) */
--{
--      USB_DEVICE_AND_INTERFACE_INFO(LENOVO_VENDOR_ID, 0x7214, USB_CLASS_COMM,
--                      USB_CDC_SUBCLASS_ETHERNET, USB_CDC_PROTO_NONE),
--      .driver_info = 0,
--},
--
- /* Lenovo Powered USB-C Travel Hub (4X90S92381, based on Realtek RTL8153) */
- {
-       USB_DEVICE_AND_INTERFACE_INFO(LENOVO_VENDOR_ID, 0x721e, USB_CLASS_COMM,
-                       USB_CDC_SUBCLASS_ETHERNET, USB_CDC_PROTO_NONE),
-       .driver_info = 0,
- },
--
--/* ThinkPad USB-C Dock Gen 2 (based on Realtek RTL8153) */
--{
--      USB_DEVICE_AND_INTERFACE_INFO(LENOVO_VENDOR_ID, 0xa387, USB_CLASS_COMM,
--                      USB_CDC_SUBCLASS_ETHERNET, USB_CDC_PROTO_NONE),
--      .driver_info = 0,
--},
--
--/* NVIDIA Tegra USB 3.0 Ethernet Adapters (based on Realtek RTL8153) */
--{
--      USB_DEVICE_AND_INTERFACE_INFO(NVIDIA_VENDOR_ID, 0x09ff, USB_CLASS_COMM,
--                      USB_CDC_SUBCLASS_ETHERNET, USB_CDC_PROTO_NONE),
--      .driver_info = 0,
--},
--
--/* Microsoft Surface 2 dock (based on Realtek RTL8152) */
--{
--      USB_DEVICE_AND_INTERFACE_INFO(MICROSOFT_VENDOR_ID, 0x07ab, USB_CLASS_COMM,
--                      USB_CDC_SUBCLASS_ETHERNET, USB_CDC_PROTO_NONE),
--      .driver_info = 0,
--},
--
--/* Microsoft Surface Ethernet Adapter (based on Realtek RTL8153) */
--{
--      USB_DEVICE_AND_INTERFACE_INFO(MICROSOFT_VENDOR_ID, 0x07c6, USB_CLASS_COMM,
--                      USB_CDC_SUBCLASS_ETHERNET, USB_CDC_PROTO_NONE),
--      .driver_info = 0,
--},
--
--/* Microsoft Surface Ethernet Adapter (based on Realtek RTL8153B) */
--{
--      USB_DEVICE_AND_INTERFACE_INFO(MICROSOFT_VENDOR_ID, 0x0927, USB_CLASS_COMM,
--                      USB_CDC_SUBCLASS_ETHERNET, USB_CDC_PROTO_NONE),
--      .driver_info = 0,
--},
--
--/* TP-LINK UE300 USB 3.0 Ethernet Adapters (based on Realtek RTL8153) */
--{
--      USB_DEVICE_AND_INTERFACE_INFO(TPLINK_VENDOR_ID, 0x0601, USB_CLASS_COMM,
--                      USB_CDC_SUBCLASS_ETHERNET, USB_CDC_PROTO_NONE),
--      .driver_info = 0,
--},
- /* Aquantia AQtion USB to 5GbE Controller (based on AQC111U) */
- {
diff --git a/target/linux/generic/backport-5.15/795-v6.3-05-r8152-reduce-the-control-transfer-of-rtl8152_get_ver.patch b/target/linux/generic/backport-5.15/795-v6.3-05-r8152-reduce-the-control-transfer-of-rtl8152_get_ver.patch
deleted file mode 100644 (file)
index 482c6c6..0000000
+++ /dev/null
@@ -1,46 +0,0 @@
-From 02767440e1dda9861a11ca1dbe0f19a760b1d5c2 Mon Sep 17 00:00:00 2001
-From: Hayes Wang <[email protected]>
-Date: Thu, 19 Jan 2023 15:40:43 +0800
-Subject: [PATCH] r8152: reduce the control transfer of rtl8152_get_version()
-
-Reduce the control transfer by moving calling rtl8152_get_version() in
-rtl8152_probe(). This could prevent from calling rtl8152_get_version()
-for unnecessary situations. For example, after setting config #2 for the
-device, there are two interfaces and rtl8152_probe() may be called
-twice. However, we don't need to call rtl8152_get_version() for this
-situation.
-
-Signed-off-by: Hayes Wang <[email protected]>
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- drivers/net/usb/r8152.c | 9 +++++----
- 1 file changed, 5 insertions(+), 4 deletions(-)
-
---- a/drivers/net/usb/r8152.c
-+++ b/drivers/net/usb/r8152.c
-@@ -9602,20 +9602,21 @@ static int rtl8152_probe(struct usb_inte
-                        const struct usb_device_id *id)
- {
-       struct usb_device *udev = interface_to_usbdev(intf);
--      u8 version = rtl8152_get_version(intf);
-       struct r8152 *tp;
-       struct net_device *netdev;
-+      u8 version;
-       int ret;
--      if (version == RTL_VER_UNKNOWN)
--              return -ENODEV;
--
-       if (intf->cur_altsetting->desc.bInterfaceClass != USB_CLASS_VENDOR_SPEC)
-               return -ENODEV;
-       if (!rtl_check_vendor_ok(intf))
-               return -ENODEV;
-+      version = rtl8152_get_version(intf);
-+      if (version == RTL_VER_UNKNOWN)
-+              return -ENODEV;
-+
-       usb_reset_device(udev);
-       netdev = alloc_etherdev(sizeof(struct r8152));
-       if (!netdev) {
diff --git a/target/linux/generic/backport-5.15/795-v6.3-06-r8152-Add-__GFP_NOWARN-to-big-allocations.patch b/target/linux/generic/backport-5.15/795-v6.3-06-r8152-Add-__GFP_NOWARN-to-big-allocations.patch
deleted file mode 100644 (file)
index 5d1dfe3..0000000
+++ /dev/null
@@ -1,55 +0,0 @@
-From 5cc33f139e11b893ff6dc60d8a0ae865a65521ac Mon Sep 17 00:00:00 2001
-From: Douglas Anderson <[email protected]>
-Date: Thu, 6 Apr 2023 17:14:26 -0700
-Subject: [PATCH] r8152: Add __GFP_NOWARN to big allocations
-
-When memory is a little tight on my system, it's pretty easy to see
-warnings that look like this.
-
-  ksoftirqd/0: page allocation failure: order:3, mode:0x40a20(GFP_ATOMIC|__GFP_COMP), nodemask=(null),cpuset=/,mems_allowed=0
-  ...
-  Call trace:
-   dump_backtrace+0x0/0x1e8
-   show_stack+0x20/0x2c
-   dump_stack_lvl+0x60/0x78
-   dump_stack+0x18/0x38
-   warn_alloc+0x104/0x174
-   __alloc_pages+0x588/0x67c
-   alloc_rx_agg+0xa0/0x190 [r8152 ...]
-   r8152_poll+0x270/0x760 [r8152 ...]
-   __napi_poll+0x44/0x1ec
-   net_rx_action+0x100/0x300
-   __do_softirq+0xec/0x38c
-   run_ksoftirqd+0x38/0xec
-   smpboot_thread_fn+0xb8/0x248
-   kthread+0x134/0x154
-   ret_from_fork+0x10/0x20
-
-On a fragmented system it's normal that order 3 allocations will
-sometimes fail, especially atomic ones. The driver handles these
-failures fine and the WARN just creates spam in the logs for this
-case. The __GFP_NOWARN flag is exactly for this situation, so add it
-to the allocation.
-
-NOTE: my testing is on a 5.15 system, but there should be no reason
-that this would be fundamentally different on a mainline kernel.
-
-Signed-off-by: Douglas Anderson <[email protected]>
-Acked-by: Hayes Wang <[email protected]>
-Link: https://lore.kernel.org/r/20230406171411.1.I84dbef45786af440fd269b71e9436a96a8e7a152@changeid
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- drivers/net/usb/r8152.c | 2 +-
- 1 file changed, 1 insertion(+), 1 deletion(-)
-
---- a/drivers/net/usb/r8152.c
-+++ b/drivers/net/usb/r8152.c
-@@ -1944,7 +1944,7 @@ static struct rx_agg *alloc_rx_agg(struc
-       if (!rx_agg)
-               return NULL;
--      rx_agg->page = alloc_pages(mflags | __GFP_COMP, order);
-+      rx_agg->page = alloc_pages(mflags | __GFP_COMP | __GFP_NOWARN, order);
-       if (!rx_agg->page)
-               goto free_rx;
diff --git a/target/linux/generic/backport-5.15/795-v6.6-08-r8152-adjust-generic_ocp_write-function.patch b/target/linux/generic/backport-5.15/795-v6.6-08-r8152-adjust-generic_ocp_write-function.patch
deleted file mode 100644 (file)
index 0da1a5b..0000000
+++ /dev/null
@@ -1,70 +0,0 @@
-From 57df0fb9d511f91202114813e90128d65c0589f0 Mon Sep 17 00:00:00 2001
-From: Hayes Wang <[email protected]>
-Date: Wed, 26 Jul 2023 11:08:07 +0800
-Subject: [PATCH] r8152: adjust generic_ocp_write function
-
-Reduce the control transfer if all bytes of first or the last DWORD are
-written.
-
-The original method is to split the control transfer into three parts
-(the first DWORD, middle continuous data, and the last DWORD). However,
-they could be combined if whole bytes of the first DWORD or last DWORD
-are written. That is, the first DWORD or the last DWORD could be combined
-with the middle continuous data, if the byte_en is 0xff.
-
-Signed-off-by: Hayes Wang <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- drivers/net/usb/r8152.c | 29 ++++++++++++++++++-----------
- 1 file changed, 18 insertions(+), 11 deletions(-)
-
---- a/drivers/net/usb/r8152.c
-+++ b/drivers/net/usb/r8152.c
-@@ -1310,16 +1310,24 @@ static int generic_ocp_write(struct r815
-       byteen_end = byteen & BYTE_EN_END_MASK;
-       byen = byteen_start | (byteen_start << 4);
--      ret = set_registers(tp, index, type | byen, 4, data);
--      if (ret < 0)
--              goto error1;
--
--      index += 4;
--      data += 4;
--      size -= 4;
--      if (size) {
-+      /* Split the first DWORD if the byte_en is not 0xff */
-+      if (byen != BYTE_EN_DWORD) {
-+              ret = set_registers(tp, index, type | byen, 4, data);
-+              if (ret < 0)
-+                      goto error1;
-+
-+              index += 4;
-+              data += 4;
-               size -= 4;
-+      }
-+
-+      if (size) {
-+              byen = byteen_end | (byteen_end >> 4);
-+
-+              /* Split the last DWORD if the byte_en is not 0xff */
-+              if (byen != BYTE_EN_DWORD)
-+                      size -= 4;
-               while (size) {
-                       if (size > limit) {
-@@ -1346,10 +1354,9 @@ static int generic_ocp_write(struct r815
-                       }
-               }
--              byen = byteen_end | (byteen_end >> 4);
--              ret = set_registers(tp, index, type | byen, 4, data);
--              if (ret < 0)
--                      goto error1;
-+              /* Set the last DWORD */
-+              if (byen != BYTE_EN_DWORD)
-+                      ret = set_registers(tp, index, type | byen, 4, data);
-       }
- error1:
diff --git a/target/linux/generic/backport-5.15/795-v6.6-09-r8152-set-bp-in-bulk.patch b/target/linux/generic/backport-5.15/795-v6.6-09-r8152-set-bp-in-bulk.patch
deleted file mode 100644 (file)
index 6c7efd7..0000000
+++ /dev/null
@@ -1,129 +0,0 @@
-From e5c266a61186b462c388c53a3564c375e72f2244 Mon Sep 17 00:00:00 2001
-From: Hayes Wang <[email protected]>
-Date: Wed, 26 Jul 2023 11:08:08 +0800
-Subject: [PATCH] r8152: set bp in bulk
-
-PLA_BP_0 ~ PLA_BP_15 (0xfc28 ~ 0xfc46) are continuous registers, so we
-could combine the control transfers into one control transfer.
-
-Signed-off-by: Hayes Wang <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- drivers/net/usb/r8152.c | 75 ++++++++++++++---------------------------
- 1 file changed, 25 insertions(+), 50 deletions(-)
-
---- a/drivers/net/usb/r8152.c
-+++ b/drivers/net/usb/r8152.c
-@@ -3983,29 +3983,10 @@ static void rtl_reset_bmu(struct r8152 *
- /* Clear the bp to stop the firmware before loading a new one */
- static void rtl_clear_bp(struct r8152 *tp, u16 type)
- {
--      switch (tp->version) {
--      case RTL_VER_01:
--      case RTL_VER_02:
--      case RTL_VER_07:
--              break;
--      case RTL_VER_03:
--      case RTL_VER_04:
--      case RTL_VER_05:
--      case RTL_VER_06:
--              ocp_write_byte(tp, type, PLA_BP_EN, 0);
--              break;
--      case RTL_VER_14:
--              ocp_write_word(tp, type, USB_BP2_EN, 0);
-+      u16 bp[16] = {0};
-+      u16 bp_num;
--              ocp_write_word(tp, type, USB_BP_8, 0);
--              ocp_write_word(tp, type, USB_BP_9, 0);
--              ocp_write_word(tp, type, USB_BP_10, 0);
--              ocp_write_word(tp, type, USB_BP_11, 0);
--              ocp_write_word(tp, type, USB_BP_12, 0);
--              ocp_write_word(tp, type, USB_BP_13, 0);
--              ocp_write_word(tp, type, USB_BP_14, 0);
--              ocp_write_word(tp, type, USB_BP_15, 0);
--              break;
-+      switch (tp->version) {
-       case RTL_VER_08:
-       case RTL_VER_09:
-       case RTL_VER_10:
-@@ -4013,32 +3994,31 @@ static void rtl_clear_bp(struct r8152 *t
-       case RTL_VER_12:
-       case RTL_VER_13:
-       case RTL_VER_15:
--      default:
-               if (type == MCU_TYPE_USB) {
-                       ocp_write_word(tp, MCU_TYPE_USB, USB_BP2_EN, 0);
--
--                      ocp_write_word(tp, MCU_TYPE_USB, USB_BP_8, 0);
--                      ocp_write_word(tp, MCU_TYPE_USB, USB_BP_9, 0);
--                      ocp_write_word(tp, MCU_TYPE_USB, USB_BP_10, 0);
--                      ocp_write_word(tp, MCU_TYPE_USB, USB_BP_11, 0);
--                      ocp_write_word(tp, MCU_TYPE_USB, USB_BP_12, 0);
--                      ocp_write_word(tp, MCU_TYPE_USB, USB_BP_13, 0);
--                      ocp_write_word(tp, MCU_TYPE_USB, USB_BP_14, 0);
--                      ocp_write_word(tp, MCU_TYPE_USB, USB_BP_15, 0);
--              } else {
--                      ocp_write_byte(tp, MCU_TYPE_PLA, PLA_BP_EN, 0);
-+                      bp_num = 16;
-+                      break;
-               }
-+              fallthrough;
-+      case RTL_VER_03:
-+      case RTL_VER_04:
-+      case RTL_VER_05:
-+      case RTL_VER_06:
-+              ocp_write_byte(tp, type, PLA_BP_EN, 0);
-+              fallthrough;
-+      case RTL_VER_01:
-+      case RTL_VER_02:
-+      case RTL_VER_07:
-+              bp_num = 8;
-+              break;
-+      case RTL_VER_14:
-+      default:
-+              ocp_write_word(tp, type, USB_BP2_EN, 0);
-+              bp_num = 16;
-               break;
-       }
--      ocp_write_word(tp, type, PLA_BP_0, 0);
--      ocp_write_word(tp, type, PLA_BP_1, 0);
--      ocp_write_word(tp, type, PLA_BP_2, 0);
--      ocp_write_word(tp, type, PLA_BP_3, 0);
--      ocp_write_word(tp, type, PLA_BP_4, 0);
--      ocp_write_word(tp, type, PLA_BP_5, 0);
--      ocp_write_word(tp, type, PLA_BP_6, 0);
--      ocp_write_word(tp, type, PLA_BP_7, 0);
-+      generic_ocp_write(tp, PLA_BP_0, BYTE_EN_DWORD, bp_num << 1, bp, type);
-       /* wait 3 ms to make sure the firmware is stopped */
-       usleep_range(3000, 6000);
-@@ -5015,10 +4995,9 @@ static void rtl8152_fw_phy_nc_apply(stru
- static void rtl8152_fw_mac_apply(struct r8152 *tp, struct fw_mac *mac)
- {
--      u16 bp_en_addr, bp_index, type, bp_num, fw_ver_reg;
-+      u16 bp_en_addr, type, fw_ver_reg;
-       u32 length;
-       u8 *data;
--      int i;
-       switch (__le32_to_cpu(mac->blk_hdr.type)) {
-       case RTL_FW_PLA:
-@@ -5060,12 +5039,8 @@ static void rtl8152_fw_mac_apply(struct
-       ocp_write_word(tp, type, __le16_to_cpu(mac->bp_ba_addr),
-                      __le16_to_cpu(mac->bp_ba_value));
--      bp_index = __le16_to_cpu(mac->bp_start);
--      bp_num = __le16_to_cpu(mac->bp_num);
--      for (i = 0; i < bp_num; i++) {
--              ocp_write_word(tp, type, bp_index, __le16_to_cpu(mac->bp[i]));
--              bp_index += 2;
--      }
-+      generic_ocp_write(tp, __le16_to_cpu(mac->bp_start), BYTE_EN_DWORD,
-+                        __le16_to_cpu(mac->bp_num) << 1, mac->bp, type);
-       bp_en_addr = __le16_to_cpu(mac->bp_en_addr);
-       if (bp_en_addr)
diff --git a/target/linux/generic/backport-5.15/795-v6.6-13-r8152-Block-future-register-access-if-register-acces.patch b/target/linux/generic/backport-5.15/795-v6.6-13-r8152-Block-future-register-access-if-register-acces.patch
deleted file mode 100644 (file)
index 3ef8f37..0000000
+++ /dev/null
@@ -1,398 +0,0 @@
-From d9962b0d42029bcb40fe3c38bce06d1870fa4df4 Mon Sep 17 00:00:00 2001
-From: Douglas Anderson <[email protected]>
-Date: Fri, 20 Oct 2023 14:06:59 -0700
-Subject: [PATCH] r8152: Block future register access if register access fails
-
-Even though the functions to read/write registers can fail, most of
-the places in the r8152 driver that read/write register values don't
-check error codes. The lack of error code checking is problematic in
-at least two ways.
-
-The first problem is that the r8152 driver often uses code patterns
-similar to this:
-  x = read_register()
-  x = x | SOME_BIT;
-  write_register(x);
-
-...with the above pattern, if the read_register() fails and returns
-garbage then we'll end up trying to write modified garbage back to the
-Realtek adapter. If the write_register() succeeds that's bad. Note
-that as of commit f53a7ad18959 ("r8152: Set memory to all 0xFFs on
-failed reg reads") the "garbage" returned by read_register() will at
-least be consistent garbage, but it is still garbage.
-
-It turns out that this problem is very serious. Writing garbage to
-some of the hardware registers on the Ethernet adapter can put the
-adapter in such a bad state that it needs to be power cycled (fully
-unplugged and plugged in again) before it can enumerate again.
-
-The second problem is that the r8152 driver generally has functions
-that are long sequences of register writes. Assuming everything will
-be OK if a random register write fails in the middle isn't a great
-assumption.
-
-One might wonder if the above two problems are real. You could ask if
-we would really have a successful write after a failed read. It turns
-out that the answer appears to be "yes, this can happen". In fact,
-we've seen at least two distinct failure modes where this happens.
-
-On a sc7180-trogdor Chromebook if you drop into kdb for a while and
-then resume, you can see:
-1. We get a "Tx timeout"
-2. The "Tx timeout" queues up a USB reset.
-3. In rtl8152_pre_reset() we try to reinit the hardware.
-4. The first several (2-9) register accesses fail with a timeout, then
-   things recover.
-
-The above test case was actually fixed by the patch ("r8152: Increase
-USB control msg timeout to 5000ms as per spec") but at least shows
-that we really can see successful calls after failed ones.
-
-On a different (AMD) based Chromebook with a particular adapter, we
-found that during reboot tests we'd also sometimes get a transitory
-failure. In this case we saw -EPIPE being returned sometimes. Retrying
-worked, but retrying is not always safe for all register accesses
-since reading/writing some registers might have side effects (like
-registers that clear on read).
-
-Let's fully lock out all register access if a register access fails.
-When we do this, we'll try to queue up a USB reset and try to unlock
-register access after the reset. This is slightly tricker than it
-sounds since the r8152 driver has an optimized reset sequence that
-only works reliably after probe happens. In order to handle this, we
-avoid the optimized reset if probe didn't finish. Instead, we simply
-retry the probe routine in this case.
-
-When locking out access, we'll use the existing infrastructure that
-the driver was using when it detected we were unplugged. This keeps us
-from getting stuck in delay loops in some parts of the driver.
-
-Signed-off-by: Douglas Anderson <[email protected]>
-Reviewed-by: Grant Grundler <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/usb/r8152.c | 207 ++++++++++++++++++++++++++++++++++------
- 1 file changed, 176 insertions(+), 31 deletions(-)
-
---- a/drivers/net/usb/r8152.c
-+++ b/drivers/net/usb/r8152.c
-@@ -772,6 +772,9 @@ enum rtl8152_flags {
-       SCHEDULE_TASKLET,
-       GREEN_ETHERNET,
-       RX_EPROTO,
-+      IN_PRE_RESET,
-+      PROBED_WITH_NO_ERRORS,
-+      PROBE_SHOULD_RETRY,
- };
- #define DEVICE_ID_THINKPAD_ONELINK_PLUS_DOCK          0x3054
-@@ -949,6 +952,8 @@ struct r8152 {
-       u8 version;
-       u8 duplex;
-       u8 autoneg;
-+
-+      unsigned int reg_access_reset_count;
- };
- /**
-@@ -1196,6 +1201,96 @@ static unsigned int agg_buf_sz = 16384;
- #define RTL_LIMITED_TSO_SIZE  (size_to_mtu(agg_buf_sz) - sizeof(struct tx_desc))
-+/* If register access fails then we block access and issue a reset. If this
-+ * happens too many times in a row without a successful access then we stop
-+ * trying to reset and just leave access blocked.
-+ */
-+#define REGISTER_ACCESS_MAX_RESETS    3
-+
-+static void rtl_set_inaccessible(struct r8152 *tp)
-+{
-+      set_bit(RTL8152_INACCESSIBLE, &tp->flags);
-+      smp_mb__after_atomic();
-+}
-+
-+static void rtl_set_accessible(struct r8152 *tp)
-+{
-+      clear_bit(RTL8152_INACCESSIBLE, &tp->flags);
-+      smp_mb__after_atomic();
-+}
-+
-+static
-+int r8152_control_msg(struct r8152 *tp, unsigned int pipe, __u8 request,
-+                    __u8 requesttype, __u16 value, __u16 index, void *data,
-+                    __u16 size, const char *msg_tag)
-+{
-+      struct usb_device *udev = tp->udev;
-+      int ret;
-+
-+      if (test_bit(RTL8152_INACCESSIBLE, &tp->flags))
-+              return -ENODEV;
-+
-+      ret = usb_control_msg(udev, pipe, request, requesttype,
-+                            value, index, data, size,
-+                            USB_CTRL_GET_TIMEOUT);
-+
-+      /* No need to issue a reset to report an error if the USB device got
-+       * unplugged; just return immediately.
-+       */
-+      if (ret == -ENODEV)
-+              return ret;
-+
-+      /* If the write was successful then we're done */
-+      if (ret >= 0) {
-+              tp->reg_access_reset_count = 0;
-+              return ret;
-+      }
-+
-+      dev_err(&udev->dev,
-+              "Failed to %s %d bytes at %#06x/%#06x (%d)\n",
-+              msg_tag, size, value, index, ret);
-+
-+      /* Block all future register access until we reset. Much of the code
-+       * in the driver doesn't check for errors. Notably, many parts of the
-+       * driver do a read/modify/write of a register value without
-+       * confirming that the read succeeded. Writing back modified garbage
-+       * like this can fully wedge the adapter, requiring a power cycle.
-+       */
-+      rtl_set_inaccessible(tp);
-+
-+      /* If probe hasn't yet finished, then we'll request a retry of the
-+       * whole probe routine if we get any control transfer errors. We
-+       * never have to clear this bit since we free/reallocate the whole "tp"
-+       * structure if we retry probe.
-+       */
-+      if (!test_bit(PROBED_WITH_NO_ERRORS, &tp->flags)) {
-+              set_bit(PROBE_SHOULD_RETRY, &tp->flags);
-+              return ret;
-+      }
-+
-+      /* Failing to access registers in pre-reset is not surprising since we
-+       * wouldn't be resetting if things were behaving normally. The register
-+       * access we do in pre-reset isn't truly mandatory--we're just reusing
-+       * the disable() function and trying to be nice by powering the
-+       * adapter down before resetting it. Thus, if we're in pre-reset,
-+       * we'll return right away and not try to queue up yet another reset.
-+       * We know the post-reset is already coming.
-+       */
-+      if (test_bit(IN_PRE_RESET, &tp->flags))
-+              return ret;
-+
-+      if (tp->reg_access_reset_count < REGISTER_ACCESS_MAX_RESETS) {
-+              usb_queue_reset_device(tp->intf);
-+              tp->reg_access_reset_count++;
-+      } else if (tp->reg_access_reset_count == REGISTER_ACCESS_MAX_RESETS) {
-+              dev_err(&udev->dev,
-+                      "Tried to reset %d times; giving up.\n",
-+                      REGISTER_ACCESS_MAX_RESETS);
-+      }
-+
-+      return ret;
-+}
-+
- static
- int get_registers(struct r8152 *tp, u16 value, u16 index, u16 size, void *data)
- {
-@@ -1206,9 +1301,10 @@ int get_registers(struct r8152 *tp, u16
-       if (!tmp)
-               return -ENOMEM;
--      ret = usb_control_msg(tp->udev, tp->pipe_ctrl_in,
--                            RTL8152_REQ_GET_REGS, RTL8152_REQT_READ,
--                            value, index, tmp, size, USB_CTRL_GET_TIMEOUT);
-+      ret = r8152_control_msg(tp, tp->pipe_ctrl_in,
-+                              RTL8152_REQ_GET_REGS, RTL8152_REQT_READ,
-+                              value, index, tmp, size, "read");
-+
-       if (ret < 0)
-               memset(data, 0xff, size);
-       else
-@@ -1229,9 +1325,9 @@ int set_registers(struct r8152 *tp, u16
-       if (!tmp)
-               return -ENOMEM;
--      ret = usb_control_msg(tp->udev, tp->pipe_ctrl_out,
--                            RTL8152_REQ_SET_REGS, RTL8152_REQT_WRITE,
--                            value, index, tmp, size, USB_CTRL_SET_TIMEOUT);
-+      ret = r8152_control_msg(tp, tp->pipe_ctrl_out,
-+                              RTL8152_REQ_SET_REGS, RTL8152_REQT_WRITE,
-+                              value, index, tmp, size, "write");
-       kfree(tmp);
-@@ -1240,10 +1336,8 @@ int set_registers(struct r8152 *tp, u16
- static void rtl_set_unplug(struct r8152 *tp)
- {
--      if (tp->udev->state == USB_STATE_NOTATTACHED) {
--              set_bit(RTL8152_INACCESSIBLE, &tp->flags);
--              smp_mb__after_atomic();
--      }
-+      if (tp->udev->state == USB_STATE_NOTATTACHED)
-+              rtl_set_inaccessible(tp);
- }
- static int generic_ocp_read(struct r8152 *tp, u16 index, u16 size,
-@@ -8268,7 +8362,7 @@ static int rtl8152_pre_reset(struct usb_
-       struct r8152 *tp = usb_get_intfdata(intf);
-       struct net_device *netdev;
--      if (!tp)
-+      if (!tp || !test_bit(PROBED_WITH_NO_ERRORS, &tp->flags))
-               return 0;
-       netdev = tp->netdev;
-@@ -8283,7 +8377,9 @@ static int rtl8152_pre_reset(struct usb_
-       napi_disable(&tp->napi);
-       if (netif_carrier_ok(netdev)) {
-               mutex_lock(&tp->control);
-+              set_bit(IN_PRE_RESET, &tp->flags);
-               tp->rtl_ops.disable(tp);
-+              clear_bit(IN_PRE_RESET, &tp->flags);
-               mutex_unlock(&tp->control);
-       }
-@@ -8296,9 +8392,11 @@ static int rtl8152_post_reset(struct usb
-       struct net_device *netdev;
-       struct sockaddr sa;
--      if (!tp)
-+      if (!tp || !test_bit(PROBED_WITH_NO_ERRORS, &tp->flags))
-               return 0;
-+      rtl_set_accessible(tp);
-+
-       /* reset the MAC address in case of policy change */
-       if (determine_ethernet_addr(tp, &sa) >= 0) {
-               rtnl_lock();
-@@ -9496,17 +9594,29 @@ static u8 __rtl_get_hw_ver(struct usb_de
-       __le32 *tmp;
-       u8 version;
-       int ret;
-+      int i;
-       tmp = kmalloc(sizeof(*tmp), GFP_KERNEL);
-       if (!tmp)
-               return 0;
--      ret = usb_control_msg(udev, usb_rcvctrlpipe(udev, 0),
--                            RTL8152_REQ_GET_REGS, RTL8152_REQT_READ,
--                            PLA_TCR0, MCU_TYPE_PLA, tmp, sizeof(*tmp),
--                            USB_CTRL_GET_TIMEOUT);
--      if (ret > 0)
--              ocp_data = (__le32_to_cpu(*tmp) >> 16) & VERSION_MASK;
-+      /* Retry up to 3 times in case there is a transitory error. We do this
-+       * since retrying a read of the version is always safe and this
-+       * function doesn't take advantage of r8152_control_msg().
-+       */
-+      for (i = 0; i < 3; i++) {
-+              ret = usb_control_msg(udev, usb_rcvctrlpipe(udev, 0),
-+                                    RTL8152_REQ_GET_REGS, RTL8152_REQT_READ,
-+                                    PLA_TCR0, MCU_TYPE_PLA, tmp, sizeof(*tmp),
-+                                    USB_CTRL_GET_TIMEOUT);
-+              if (ret > 0) {
-+                      ocp_data = (__le32_to_cpu(*tmp) >> 16) & VERSION_MASK;
-+                      break;
-+              }
-+      }
-+
-+      if (i != 0 && ret > 0)
-+              dev_warn(&udev->dev, "Needed %d retries to read version\n", i);
-       kfree(tmp);
-@@ -9580,25 +9690,14 @@ u8 rtl8152_get_version(struct usb_interf
- }
- EXPORT_SYMBOL_GPL(rtl8152_get_version);
--static int rtl8152_probe(struct usb_interface *intf,
--                       const struct usb_device_id *id)
-+static int rtl8152_probe_once(struct usb_interface *intf,
-+                            const struct usb_device_id *id, u8 version)
- {
-       struct usb_device *udev = interface_to_usbdev(intf);
-       struct r8152 *tp;
-       struct net_device *netdev;
--      u8 version;
-       int ret;
--      if (intf->cur_altsetting->desc.bInterfaceClass != USB_CLASS_VENDOR_SPEC)
--              return -ENODEV;
--
--      if (!rtl_check_vendor_ok(intf))
--              return -ENODEV;
--
--      version = rtl8152_get_version(intf);
--      if (version == RTL_VER_UNKNOWN)
--              return -ENODEV;
--
-       usb_reset_device(udev);
-       netdev = alloc_etherdev(sizeof(struct r8152));
-       if (!netdev) {
-@@ -9771,10 +9870,20 @@ static int rtl8152_probe(struct usb_inte
-       else
-               device_set_wakeup_enable(&udev->dev, false);
-+      /* If we saw a control transfer error while probing then we may
-+       * want to try probe() again. Consider this an error.
-+       */
-+      if (test_bit(PROBE_SHOULD_RETRY, &tp->flags))
-+              goto out2;
-+
-+      set_bit(PROBED_WITH_NO_ERRORS, &tp->flags);
-       netif_info(tp, probe, netdev, "%s\n", DRIVER_VERSION);
-       return 0;
-+out2:
-+      unregister_netdev(netdev);
-+
- out1:
-       tasklet_kill(&tp->tx_tl);
-       cancel_delayed_work_sync(&tp->hw_phy_work);
-@@ -9783,10 +9892,46 @@ out1:
-       rtl8152_release_firmware(tp);
-       usb_set_intfdata(intf, NULL);
- out:
-+      if (test_bit(PROBE_SHOULD_RETRY, &tp->flags))
-+              ret = -EAGAIN;
-+
-       free_netdev(netdev);
-       return ret;
- }
-+#define RTL8152_PROBE_TRIES   3
-+
-+static int rtl8152_probe(struct usb_interface *intf,
-+                       const struct usb_device_id *id)
-+{
-+      u8 version;
-+      int ret;
-+      int i;
-+
-+      if (intf->cur_altsetting->desc.bInterfaceClass != USB_CLASS_VENDOR_SPEC)
-+              return -ENODEV;
-+
-+      if (!rtl_check_vendor_ok(intf))
-+              return -ENODEV;
-+
-+      version = rtl8152_get_version(intf);
-+      if (version == RTL_VER_UNKNOWN)
-+              return -ENODEV;
-+
-+      for (i = 0; i < RTL8152_PROBE_TRIES; i++) {
-+              ret = rtl8152_probe_once(intf, id, version);
-+              if (ret != -EAGAIN)
-+                      break;
-+      }
-+      if (ret == -EAGAIN) {
-+              dev_err(&intf->dev,
-+                      "r8152 failed probe after %d tries; giving up\n", i);
-+              return -ENODEV;
-+      }
-+
-+      return ret;
-+}
-+
- static void rtl8152_disconnect(struct usb_interface *intf)
- {
-       struct r8152 *tp = usb_get_intfdata(intf);
diff --git a/target/linux/generic/backport-5.15/795-v6.6-14-r8152-break-the-loop-when-the-budget-is-exhausted.patch b/target/linux/generic/backport-5.15/795-v6.6-14-r8152-break-the-loop-when-the-budget-is-exhausted.patch
deleted file mode 100644 (file)
index 42ca9e2..0000000
+++ /dev/null
@@ -1,83 +0,0 @@
-From 66eee612a1ba39f9a76a9ace4a34d012044767fb Mon Sep 17 00:00:00 2001
-From: Hayes Wang <[email protected]>
-Date: Tue, 26 Sep 2023 19:17:13 +0800
-Subject: [PATCH] r8152: break the loop when the budget is exhausted
-
-[ Upstream commit 2cf51f931797d9a47e75d999d0993a68cbd2a560 ]
-
-A bulk transfer of the USB may contain many packets. And, the total
-number of the packets in the bulk transfer may be more than budget.
-
-Originally, only budget packets would be handled by napi_gro_receive(),
-and the other packets would be queued in the driver for next schedule.
-
-This patch would break the loop about getting next bulk transfer, when
-the budget is exhausted. That is, only the current bulk transfer would
-be handled, and the other bulk transfers would be queued for next
-schedule. Besides, the packets which are more than the budget in the
-current bulk trasnfer would be still queued in the driver, as the
-original method.
-
-In addition, a bulk transfer wouldn't contain more than 400 packets, so
-the check of queue length is unnecessary. Therefore, I replace it with
-WARN_ON_ONCE().
-
-Fixes: cf74eb5a5bc8 ("eth: r8152: try to use a normal budget")
-Signed-off-by: Hayes Wang <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Jakub Kicinski <[email protected]>
-Signed-off-by: Sasha Levin <[email protected]>
----
- drivers/net/usb/r8152.c | 18 +++++++++++++-----
- 1 file changed, 13 insertions(+), 5 deletions(-)
-
---- a/drivers/net/usb/r8152.c
-+++ b/drivers/net/usb/r8152.c
-@@ -2539,7 +2539,7 @@ static int rx_bottom(struct r8152 *tp, i
-               }
-       }
--      if (list_empty(&tp->rx_done))
-+      if (list_empty(&tp->rx_done) || work_done >= budget)
-               goto out1;
-       clear_bit(RX_EPROTO, &tp->flags);
-@@ -2555,6 +2555,15 @@ static int rx_bottom(struct r8152 *tp, i
-               struct urb *urb;
-               u8 *rx_data;
-+              /* A bulk transfer of USB may contain may packets, so the
-+               * total packets may more than the budget. Deal with all
-+               * packets in current bulk transfer, and stop to handle the
-+               * next bulk transfer until next schedule, if budget is
-+               * exhausted.
-+               */
-+              if (work_done >= budget)
-+                      break;
-+
-               list_del_init(cursor);
-               agg = list_entry(cursor, struct rx_agg, list);
-@@ -2574,9 +2583,7 @@ static int rx_bottom(struct r8152 *tp, i
-                       unsigned int pkt_len, rx_frag_head_sz;
-                       struct sk_buff *skb;
--                      /* limit the skb numbers for rx_queue */
--                      if (unlikely(skb_queue_len(&tp->rx_queue) >= 1000))
--                              break;
-+                      WARN_ON_ONCE(skb_queue_len(&tp->rx_queue) >= 1000);
-                       pkt_len = le32_to_cpu(rx_desc->opts1) & RX_LEN_MASK;
-                       if (pkt_len < ETH_ZLEN)
-@@ -2654,9 +2661,10 @@ submit:
-               }
-       }
-+      /* Splice the remained list back to rx_done for next schedule */
-       if (!list_empty(&rx_queue)) {
-               spin_lock_irqsave(&tp->rx_lock, flags);
--              list_splice_tail(&rx_queue, &tp->rx_done);
-+              list_splice(&rx_queue, &tp->rx_done);
-               spin_unlock_irqrestore(&tp->rx_lock, flags);
-       }
diff --git a/target/linux/generic/backport-5.15/795-v6.6-15-net-usb-cdc_ether-add-u-blox-0x1313-composition.patch b/target/linux/generic/backport-5.15/795-v6.6-15-net-usb-cdc_ether-add-u-blox-0x1313-composition.patch
deleted file mode 100644 (file)
index d578d01..0000000
+++ /dev/null
@@ -1,47 +0,0 @@
-From 1b0fce8c8e69485e49a7d34aac3d4c2a2aa15d62 Mon Sep 17 00:00:00 2001
-From: Davide Tronchin <[email protected]>
-Date: Thu, 29 Jun 2023 12:37:36 +0200
-Subject: [PATCH] net: usb: cdc_ether: add u-blox 0x1313 composition.
-
-Add CDC-ECM support for LARA-R6 01B.
-
-The new LARA-R6 product variant identified by the "01B" string can be
-configured (by AT interface) in three different USB modes:
-* Default mode (Vendor ID: 0x1546 Product ID: 0x1311) with 4 serial
-interfaces
-* RmNet mode (Vendor ID: 0x1546 Product ID: 0x1312) with 4 serial
-interfaces and 1 RmNet virtual network interface
-* CDC-ECM mode (Vendor ID: 0x1546 Product ID: 0x1313) with 4 serial
-interface and 1 CDC-ECM virtual network interface
-The first 4 interfaces of all the 3 configurations (default, RmNet, ECM)
-are the same.
-
-In CDC-ECM mode LARA-R6 01B exposes the following interfaces:
-If 0: Diagnostic
-If 1: AT parser
-If 2: AT parser
-If 3: AT parset/alternative functions
-If 4: CDC-ECM interface
-
-Signed-off-by: Davide Tronchin <[email protected]>
-Reviewed-by: Simon Horman <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/usb/cdc_ether.c | 6 ++++++
- 1 file changed, 6 insertions(+)
-
---- a/drivers/net/usb/cdc_ether.c
-+++ b/drivers/net/usb/cdc_ether.c
-@@ -878,6 +878,12 @@ static const struct usb_device_id produc
-                                     USB_CDC_PROTO_NONE),
-       .driver_info = (unsigned long)&wwan_info,
- }, {
-+      /* U-blox LARA-R6 01B */
-+      USB_DEVICE_AND_INTERFACE_INFO(UBLOX_VENDOR_ID, 0x1313, USB_CLASS_COMM,
-+                                    USB_CDC_SUBCLASS_ETHERNET,
-+                                    USB_CDC_PROTO_NONE),
-+      .driver_info = (unsigned long)&wwan_info,
-+}, {
-       /* ZTE modules */
-       USB_VENDOR_AND_INTERFACE_INFO(ZTE_VENDOR_ID, USB_CLASS_COMM,
-                                     USB_CDC_SUBCLASS_ETHERNET,
diff --git a/target/linux/generic/backport-5.15/796-v6.5-01-usbnet-ipheth-fix-risk-of-NULL-pointer-deallocation.patch b/target/linux/generic/backport-5.15/796-v6.5-01-usbnet-ipheth-fix-risk-of-NULL-pointer-deallocation.patch
deleted file mode 100644 (file)
index d9d6f36..0000000
+++ /dev/null
@@ -1,30 +0,0 @@
-From 2203718c2f59ffdd6c78d54e5add594aebb4461e Mon Sep 17 00:00:00 2001
-From: Georgi Valkov <[email protected]>
-Date: Wed, 7 Jun 2023 15:56:59 +0200
-Subject: [PATCH 1/4] usbnet: ipheth: fix risk of NULL pointer deallocation
-
-The cleanup precedure in ipheth_probe will attempt to free a
-NULL pointer in dev->ctrl_buf if the memory allocation for
-this buffer is not successful. While kfree ignores NULL pointers,
-and the existing code is safe, it is a better design to rearrange
-the goto labels and avoid this.
-
-Signed-off-by: Georgi Valkov <[email protected]>
-Signed-off-by: Foster Snowhill <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/usb/ipheth.c | 2 +-
- 1 file changed, 1 insertion(+), 1 deletion(-)
-
---- a/drivers/net/usb/ipheth.c
-+++ b/drivers/net/usb/ipheth.c
-@@ -510,8 +510,8 @@ err_register_netdev:
-       ipheth_free_urbs(dev);
- err_alloc_urbs:
- err_get_macaddr:
--err_alloc_ctrl_buf:
-       kfree(dev->ctrl_buf);
-+err_alloc_ctrl_buf:
- err_endpoints:
-       free_netdev(netdev);
-       return retval;
diff --git a/target/linux/generic/backport-5.15/796-v6.5-02-usbnet-ipheth-transmit-URBs-without-trailing-padding.patch b/target/linux/generic/backport-5.15/796-v6.5-02-usbnet-ipheth-transmit-URBs-without-trailing-padding.patch
deleted file mode 100644 (file)
index adfec35..0000000
+++ /dev/null
@@ -1,35 +0,0 @@
-From 3e65efcca87a9bb5f3b864e0a43d167bc0a8688c Mon Sep 17 00:00:00 2001
-From: Foster Snowhill <[email protected]>
-Date: Wed, 7 Jun 2023 15:57:00 +0200
-Subject: [PATCH 2/4] usbnet: ipheth: transmit URBs without trailing padding
-
-The behaviour of the official iOS tethering driver on macOS is to not
-transmit any trailing padding at the end of URBs. This is applicable
-to both NCM and legacy modes, including older devices.
-
-Adapt the driver to not include trailing padding in TX URBs, matching
-the behaviour of the official macOS driver.
-
-Signed-off-by: Foster Snowhill <[email protected]>
-Tested-by: Georgi Valkov <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/usb/ipheth.c | 4 +---
- 1 file changed, 1 insertion(+), 3 deletions(-)
-
---- a/drivers/net/usb/ipheth.c
-+++ b/drivers/net/usb/ipheth.c
-@@ -373,12 +373,10 @@ static netdev_tx_t ipheth_tx(struct sk_b
-       }
-       memcpy(dev->tx_buf, skb->data, skb->len);
--      if (skb->len < IPHETH_BUF_SIZE)
--              memset(dev->tx_buf + skb->len, 0, IPHETH_BUF_SIZE - skb->len);
-       usb_fill_bulk_urb(dev->tx_urb, udev,
-                         usb_sndbulkpipe(udev, dev->bulk_out),
--                        dev->tx_buf, IPHETH_BUF_SIZE,
-+                        dev->tx_buf, skb->len,
-                         ipheth_sndbulk_callback,
-                         dev);
-       dev->tx_urb->transfer_flags |= URB_NO_TRANSFER_DMA_MAP;
diff --git a/target/linux/generic/backport-5.15/796-v6.5-03-usbnet-ipheth-add-CDC-NCM-support.patch b/target/linux/generic/backport-5.15/796-v6.5-03-usbnet-ipheth-add-CDC-NCM-support.patch
deleted file mode 100644 (file)
index e3f2b9c..0000000
+++ /dev/null
@@ -1,326 +0,0 @@
-From a2d274c62e44b1995c170595db3865c6fe701226 Mon Sep 17 00:00:00 2001
-From: Foster Snowhill <[email protected]>
-Date: Wed, 7 Jun 2023 15:57:01 +0200
-Subject: [PATCH 3/4] usbnet: ipheth: add CDC NCM support
-
-Recent iOS releases support CDC NCM encapsulation on RX. This mode is
-the default on macOS and Windows. In this mode, an iOS device may include
-one or more Ethernet frames inside a single URB.
-
-Freshly booted iOS devices start in legacy mode, but are put into
-NCM mode by the official Apple driver. When reconnecting such a device
-from a macOS/Windows machine to a Linux host, the device stays in
-NCM mode, making it unusable with the legacy ipheth driver code.
-
-To correctly support such a device, the driver has to either support
-the NCM mode too, or put the device back into legacy mode.
-
-To match the behaviour of the macOS/Windows driver, and since there
-is no documented control command to revert to legacy mode, implement
-NCM support. The device is attempted to be put into NCM mode by default,
-and falls back to legacy mode if the attempt fails.
-
-Signed-off-by: Foster Snowhill <[email protected]>
-Tested-by: Georgi Valkov <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/usb/ipheth.c | 180 +++++++++++++++++++++++++++++++++------
- 1 file changed, 155 insertions(+), 25 deletions(-)
-
---- a/drivers/net/usb/ipheth.c
-+++ b/drivers/net/usb/ipheth.c
-@@ -52,6 +52,7 @@
- #include <linux/ethtool.h>
- #include <linux/usb.h>
- #include <linux/workqueue.h>
-+#include <linux/usb/cdc.h>
- #define USB_VENDOR_APPLE        0x05ac
-@@ -59,8 +60,12 @@
- #define IPHETH_USBINTF_SUBCLASS 253
- #define IPHETH_USBINTF_PROTO    1
--#define IPHETH_BUF_SIZE         1514
- #define IPHETH_IP_ALIGN               2       /* padding at front of URB */
-+#define IPHETH_NCM_HEADER_SIZE  (12 + 96) /* NCMH + NCM0 */
-+#define IPHETH_TX_BUF_SIZE      ETH_FRAME_LEN
-+#define IPHETH_RX_BUF_SIZE_LEGACY (IPHETH_IP_ALIGN + ETH_FRAME_LEN)
-+#define IPHETH_RX_BUF_SIZE_NCM        65536
-+
- #define IPHETH_TX_TIMEOUT       (5 * HZ)
- #define IPHETH_INTFNUM          2
-@@ -71,6 +76,7 @@
- #define IPHETH_CTRL_TIMEOUT     (5 * HZ)
- #define IPHETH_CMD_GET_MACADDR   0x00
-+#define IPHETH_CMD_ENABLE_NCM    0x04
- #define IPHETH_CMD_CARRIER_CHECK 0x45
- #define IPHETH_CARRIER_CHECK_TIMEOUT round_jiffies_relative(1 * HZ)
-@@ -97,6 +103,8 @@ struct ipheth_device {
-       u8 bulk_out;
-       struct delayed_work carrier_work;
-       bool confirmed_pairing;
-+      int (*rcvbulk_callback)(struct urb *urb);
-+      size_t rx_buf_len;
- };
- static int ipheth_rx_submit(struct ipheth_device *dev, gfp_t mem_flags);
-@@ -116,12 +124,12 @@ static int ipheth_alloc_urbs(struct iphe
-       if (rx_urb == NULL)
-               goto free_tx_urb;
--      tx_buf = usb_alloc_coherent(iphone->udev, IPHETH_BUF_SIZE,
-+      tx_buf = usb_alloc_coherent(iphone->udev, IPHETH_TX_BUF_SIZE,
-                                   GFP_KERNEL, &tx_urb->transfer_dma);
-       if (tx_buf == NULL)
-               goto free_rx_urb;
--      rx_buf = usb_alloc_coherent(iphone->udev, IPHETH_BUF_SIZE + IPHETH_IP_ALIGN,
-+      rx_buf = usb_alloc_coherent(iphone->udev, iphone->rx_buf_len,
-                                   GFP_KERNEL, &rx_urb->transfer_dma);
-       if (rx_buf == NULL)
-               goto free_tx_buf;
-@@ -134,7 +142,7 @@ static int ipheth_alloc_urbs(struct iphe
-       return 0;
- free_tx_buf:
--      usb_free_coherent(iphone->udev, IPHETH_BUF_SIZE, tx_buf,
-+      usb_free_coherent(iphone->udev, IPHETH_TX_BUF_SIZE, tx_buf,
-                         tx_urb->transfer_dma);
- free_rx_urb:
-       usb_free_urb(rx_urb);
-@@ -146,9 +154,9 @@ error_nomem:
- static void ipheth_free_urbs(struct ipheth_device *iphone)
- {
--      usb_free_coherent(iphone->udev, IPHETH_BUF_SIZE + IPHETH_IP_ALIGN, iphone->rx_buf,
-+      usb_free_coherent(iphone->udev, iphone->rx_buf_len, iphone->rx_buf,
-                         iphone->rx_urb->transfer_dma);
--      usb_free_coherent(iphone->udev, IPHETH_BUF_SIZE, iphone->tx_buf,
-+      usb_free_coherent(iphone->udev, IPHETH_TX_BUF_SIZE, iphone->tx_buf,
-                         iphone->tx_urb->transfer_dma);
-       usb_free_urb(iphone->rx_urb);
-       usb_free_urb(iphone->tx_urb);
-@@ -160,15 +168,106 @@ static void ipheth_kill_urbs(struct iphe
-       usb_kill_urb(dev->rx_urb);
- }
--static void ipheth_rcvbulk_callback(struct urb *urb)
-+static int ipheth_consume_skb(char *buf, int len, struct ipheth_device *dev)
- {
--      struct ipheth_device *dev;
-       struct sk_buff *skb;
--      int status;
-+
-+      skb = dev_alloc_skb(len);
-+      if (!skb) {
-+              dev->net->stats.rx_dropped++;
-+              return -ENOMEM;
-+      }
-+
-+      skb_put_data(skb, buf, len);
-+      skb->dev = dev->net;
-+      skb->protocol = eth_type_trans(skb, dev->net);
-+
-+      dev->net->stats.rx_packets++;
-+      dev->net->stats.rx_bytes += len;
-+      netif_rx(skb);
-+
-+      return 0;
-+}
-+
-+static int ipheth_rcvbulk_callback_legacy(struct urb *urb)
-+{
-+      struct ipheth_device *dev;
-+      char *buf;
-+      int len;
-+
-+      dev = urb->context;
-+
-+      if (urb->actual_length <= IPHETH_IP_ALIGN) {
-+              dev->net->stats.rx_length_errors++;
-+              return -EINVAL;
-+      }
-+      len = urb->actual_length - IPHETH_IP_ALIGN;
-+      buf = urb->transfer_buffer + IPHETH_IP_ALIGN;
-+
-+      return ipheth_consume_skb(buf, len, dev);
-+}
-+
-+static int ipheth_rcvbulk_callback_ncm(struct urb *urb)
-+{
-+      struct usb_cdc_ncm_nth16 *ncmh;
-+      struct usb_cdc_ncm_ndp16 *ncm0;
-+      struct usb_cdc_ncm_dpe16 *dpe;
-+      struct ipheth_device *dev;
-+      int retval = -EINVAL;
-       char *buf;
-       int len;
-       dev = urb->context;
-+
-+      if (urb->actual_length < IPHETH_NCM_HEADER_SIZE) {
-+              dev->net->stats.rx_length_errors++;
-+              return retval;
-+      }
-+
-+      ncmh = urb->transfer_buffer;
-+      if (ncmh->dwSignature != cpu_to_le32(USB_CDC_NCM_NTH16_SIGN) ||
-+          le16_to_cpu(ncmh->wNdpIndex) >= urb->actual_length) {
-+              dev->net->stats.rx_errors++;
-+              return retval;
-+      }
-+
-+      ncm0 = urb->transfer_buffer + le16_to_cpu(ncmh->wNdpIndex);
-+      if (ncm0->dwSignature != cpu_to_le32(USB_CDC_NCM_NDP16_NOCRC_SIGN) ||
-+          le16_to_cpu(ncmh->wHeaderLength) + le16_to_cpu(ncm0->wLength) >=
-+          urb->actual_length) {
-+              dev->net->stats.rx_errors++;
-+              return retval;
-+      }
-+
-+      dpe = ncm0->dpe16;
-+      while (le16_to_cpu(dpe->wDatagramIndex) != 0 &&
-+             le16_to_cpu(dpe->wDatagramLength) != 0) {
-+              if (le16_to_cpu(dpe->wDatagramIndex) >= urb->actual_length ||
-+                  le16_to_cpu(dpe->wDatagramIndex) +
-+                  le16_to_cpu(dpe->wDatagramLength) > urb->actual_length) {
-+                      dev->net->stats.rx_length_errors++;
-+                      return retval;
-+              }
-+
-+              buf = urb->transfer_buffer + le16_to_cpu(dpe->wDatagramIndex);
-+              len = le16_to_cpu(dpe->wDatagramLength);
-+
-+              retval = ipheth_consume_skb(buf, len, dev);
-+              if (retval != 0)
-+                      return retval;
-+
-+              dpe++;
-+      }
-+
-+      return 0;
-+}
-+
-+static void ipheth_rcvbulk_callback(struct urb *urb)
-+{
-+      struct ipheth_device *dev;
-+      int retval, status;
-+
-+      dev = urb->context;
-       if (dev == NULL)
-               return;
-@@ -191,25 +290,27 @@ static void ipheth_rcvbulk_callback(stru
-               dev->net->stats.rx_length_errors++;
-               return;
-       }
--      len = urb->actual_length - IPHETH_IP_ALIGN;
--      buf = urb->transfer_buffer + IPHETH_IP_ALIGN;
--      skb = dev_alloc_skb(len);
--      if (!skb) {
--              dev_err(&dev->intf->dev, "%s: dev_alloc_skb: -ENOMEM\n",
--                      __func__);
--              dev->net->stats.rx_dropped++;
-+      /* RX URBs starting with 0x00 0x01 do not encapsulate Ethernet frames,
-+       * but rather are control frames. Their purpose is not documented, and
-+       * they don't affect driver functionality, okay to drop them.
-+       * There is usually just one 4-byte control frame as the very first
-+       * URB received from the bulk IN endpoint.
-+       */
-+      if (unlikely
-+              (((char *)urb->transfer_buffer)[0] == 0 &&
-+               ((char *)urb->transfer_buffer)[1] == 1))
-+              goto rx_submit;
-+
-+      retval = dev->rcvbulk_callback(urb);
-+      if (retval != 0) {
-+              dev_err(&dev->intf->dev, "%s: callback retval: %d\n",
-+                      __func__, retval);
-               return;
-       }
--      skb_put_data(skb, buf, len);
--      skb->dev = dev->net;
--      skb->protocol = eth_type_trans(skb, dev->net);
--
--      dev->net->stats.rx_packets++;
--      dev->net->stats.rx_bytes += len;
-+rx_submit:
-       dev->confirmed_pairing = true;
--      netif_rx(skb);
-       ipheth_rx_submit(dev, GFP_ATOMIC);
- }
-@@ -310,6 +411,27 @@ static int ipheth_get_macaddr(struct iph
-       return retval;
- }
-+static int ipheth_enable_ncm(struct ipheth_device *dev)
-+{
-+      struct usb_device *udev = dev->udev;
-+      int retval;
-+
-+      retval = usb_control_msg(udev,
-+                               usb_sndctrlpipe(udev, IPHETH_CTRL_ENDP),
-+                               IPHETH_CMD_ENABLE_NCM, /* request */
-+                               0x41, /* request type */
-+                               0x00, /* value */
-+                               0x02, /* index */
-+                               NULL,
-+                               0,
-+                               IPHETH_CTRL_TIMEOUT);
-+
-+      dev_info(&dev->intf->dev, "%s: usb_control_msg: %d\n",
-+               __func__, retval);
-+
-+      return retval;
-+}
-+
- static int ipheth_rx_submit(struct ipheth_device *dev, gfp_t mem_flags)
- {
-       struct usb_device *udev = dev->udev;
-@@ -317,7 +439,7 @@ static int ipheth_rx_submit(struct iphet
-       usb_fill_bulk_urb(dev->rx_urb, udev,
-                         usb_rcvbulkpipe(udev, dev->bulk_in),
--                        dev->rx_buf, IPHETH_BUF_SIZE + IPHETH_IP_ALIGN,
-+                        dev->rx_buf, dev->rx_buf_len,
-                         ipheth_rcvbulk_callback,
-                         dev);
-       dev->rx_urb->transfer_flags |= URB_NO_TRANSFER_DMA_MAP;
-@@ -365,7 +487,7 @@ static netdev_tx_t ipheth_tx(struct sk_b
-       int retval;
-       /* Paranoid */
--      if (skb->len > IPHETH_BUF_SIZE) {
-+      if (skb->len > IPHETH_TX_BUF_SIZE) {
-               WARN(1, "%s: skb too large: %d bytes\n", __func__, skb->len);
-               dev->net->stats.tx_dropped++;
-               dev_kfree_skb_any(skb);
-@@ -448,6 +570,8 @@ static int ipheth_probe(struct usb_inter
-       dev->net = netdev;
-       dev->intf = intf;
-       dev->confirmed_pairing = false;
-+      dev->rx_buf_len = IPHETH_RX_BUF_SIZE_LEGACY;
-+      dev->rcvbulk_callback = ipheth_rcvbulk_callback_legacy;
-       /* Set up endpoints */
-       hintf = usb_altnum_to_altsetting(intf, IPHETH_ALT_INTFNUM);
-       if (hintf == NULL) {
-@@ -479,6 +603,12 @@ static int ipheth_probe(struct usb_inter
-       if (retval)
-               goto err_get_macaddr;
-+      retval = ipheth_enable_ncm(dev);
-+      if (!retval) {
-+              dev->rx_buf_len = IPHETH_RX_BUF_SIZE_NCM;
-+              dev->rcvbulk_callback = ipheth_rcvbulk_callback_ncm;
-+      }
-+
-       INIT_DELAYED_WORK(&dev->carrier_work, ipheth_carrier_check_work);
-       retval = ipheth_alloc_urbs(dev);
diff --git a/target/linux/generic/backport-5.15/796-v6.5-04-usbnet-ipheth-update-Kconfig-description.patch b/target/linux/generic/backport-5.15/796-v6.5-04-usbnet-ipheth-update-Kconfig-description.patch
deleted file mode 100644 (file)
index 2ab7e8f..0000000
+++ /dev/null
@@ -1,36 +0,0 @@
-From 0c6e9d32ef0ccfcf2d875cbcff23bf345a54d585 Mon Sep 17 00:00:00 2001
-From: Foster Snowhill <[email protected]>
-Date: Wed, 7 Jun 2023 15:57:02 +0200
-Subject: [PATCH 4/4] usbnet: ipheth: update Kconfig description
-
-This module has for a long time not been limited to iPhone <= 3GS.
-Update description to match the actual state of the driver.
-
-Remove dead link from 2010, instead reference an existing userspace
-iOS device pairing implementation as part of libimobiledevice.
-
-Signed-off-by: Foster Snowhill <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/usb/Kconfig | 10 ++++------
- 1 file changed, 4 insertions(+), 6 deletions(-)
-
---- a/drivers/net/usb/Kconfig
-+++ b/drivers/net/usb/Kconfig
-@@ -582,12 +582,10 @@ config USB_IPHETH
-       default n
-       help
-         Module used to share Internet connection (tethering) from your
--        iPhone (Original, 3G and 3GS) to your system.
--        Note that you need userspace libraries and programs that are needed
--        to pair your device with your system and that understand the iPhone
--        protocol.
--
--        For more information: http://giagio.com/wiki/moin.cgi/iPhoneEthernetDriver
-+        iPhone to your system.
-+        Note that you need a corresponding userspace library/program
-+        to pair your device with your system, for example usbmuxd
-+        <https://github.com/libimobiledevice/usbmuxd>.
- config USB_SIERRA_NET
-       tristate "USB-to-WWAN Driver for Sierra Wireless modems"
diff --git a/target/linux/generic/backport-5.15/797-v5.17-net-usb-ax88179_178a-add-TSO-feature.patch b/target/linux/generic/backport-5.15/797-v5.17-net-usb-ax88179_178a-add-TSO-feature.patch
deleted file mode 100644 (file)
index b2af169..0000000
+++ /dev/null
@@ -1,68 +0,0 @@
-From 16b1c4e01c89ba07367461e0bc4cb84993c2d027 Mon Sep 17 00:00:00 2001
-From: Jacky Chou <[email protected]>
-Date: Mon, 15 Nov 2021 11:49:41 +0800
-Subject: [PATCH] net: usb: ax88179_178a: add TSO feature
-
-On low-effciency embedded platforms, transmission performance is poor
-due to on Bulk-out with single packet.
-Adding TSO feature improves the transmission performance and reduces
-the number of interrupt caused by Bulk-out complete.
-
-Reference to module, net: usb: aqc111.
-
-Signed-off-by: Jacky Chou <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/usb/ax88179_178a.c | 17 +++++++++++------
- 1 file changed, 11 insertions(+), 6 deletions(-)
-
---- a/drivers/net/usb/ax88179_178a.c
-+++ b/drivers/net/usb/ax88179_178a.c
-@@ -1333,11 +1333,12 @@ static int ax88179_bind(struct usbnet *d
-       dev->mii.phy_id = 0x03;
-       dev->mii.supports_gmii = 1;
--      dev->net->features |= NETIF_F_IP_CSUM | NETIF_F_IPV6_CSUM |
--                            NETIF_F_RXCSUM;
-+      dev->net->features |= NETIF_F_SG | NETIF_F_IP_CSUM |
-+                            NETIF_F_IPV6_CSUM | NETIF_F_RXCSUM | NETIF_F_TSO;
--      dev->net->hw_features |= NETIF_F_IP_CSUM | NETIF_F_IPV6_CSUM |
--                               NETIF_F_RXCSUM;
-+      dev->net->hw_features |= dev->net->features;
-+
-+      netif_set_gso_max_size(dev->net, 16384);
-       ax88179_reset(dev);
-@@ -1502,17 +1503,19 @@ ax88179_tx_fixup(struct usbnet *dev, str
- {
-       u32 tx_hdr1, tx_hdr2;
-       int frame_size = dev->maxpacket;
--      int mss = skb_shinfo(skb)->gso_size;
-       int headroom;
-       void *ptr;
-       tx_hdr1 = skb->len;
--      tx_hdr2 = mss;
-+      tx_hdr2 = skb_shinfo(skb)->gso_size; /* Set TSO mss */
-       if (((skb->len + 8) % frame_size) == 0)
-               tx_hdr2 |= 0x80008000;  /* Enable padding */
-       headroom = skb_headroom(skb) - 8;
-+      if ((dev->net->features & NETIF_F_SG) && skb_linearize(skb))
-+              return NULL;
-+
-       if ((skb_header_cloned(skb) || headroom < 0) &&
-           pskb_expand_head(skb, headroom < 0 ? 8 : 0, 0, GFP_ATOMIC)) {
-               dev_kfree_skb_any(skb);
-@@ -1523,6 +1526,8 @@ ax88179_tx_fixup(struct usbnet *dev, str
-       put_unaligned_le32(tx_hdr1, ptr);
-       put_unaligned_le32(tx_hdr2, ptr + 4);
-+      usbnet_set_skb_tx_stats(skb, (skb_shinfo(skb)->gso_segs ?: 1), 0);
-+
-       return skb;
- }
diff --git a/target/linux/generic/backport-5.15/798-net-next-net-sfp-add-quirk-for-Fiberstone-GPON-ONU-34-20BI.patch b/target/linux/generic/backport-5.15/798-net-next-net-sfp-add-quirk-for-Fiberstone-GPON-ONU-34-20BI.patch
deleted file mode 100644 (file)
index d6015a5..0000000
+++ /dev/null
@@ -1,34 +0,0 @@
-From d387e34fec407f881fdf165b5d7ec128ebff362f Mon Sep 17 00:00:00 2001
-From: Christian Marangi <[email protected]>
-Date: Tue, 19 Sep 2023 14:47:20 +0200
-Subject: [PATCH] net: sfp: add quirk for Fiberstone GPON-ONU-34-20BI
-
-Fiberstone GPON-ONU-34-20B can operate at 2500base-X, but report 1.2GBd
-NRZ in their EEPROM.
-
-The module also require the ignore tx fault fixup similar to Huawei MA5671A
-as it gets disabled on error messages with serial redirection enabled.
-
-Signed-off-by: Christian Marangi <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Paolo Abeni <[email protected]>
----
- drivers/net/phy/sfp.c | 5 +++++
- 1 file changed, 5 insertions(+)
-
---- a/drivers/net/phy/sfp.c
-+++ b/drivers/net/phy/sfp.c
-@@ -368,6 +368,13 @@ static const struct sfp_quirk sfp_quirks
-               .modes = sfp_quirk_2500basex,
-               .fixup = sfp_fixup_long_startup,
-       }, {
-+              // Fiberstore GPON-ONU-34-20BI can operate at 2500base-X, but report 1.2GBd
-+              // NRZ in their EEPROM
-+              .vendor = "FS",
-+              .part = "GPON-ONU-34-20BI",
-+              .modes = sfp_quirk_2500basex,
-+              .fixup = sfp_fixup_ignore_tx_fault,
-+      }, {
-               .vendor = "HALNy",
-               .part = "HL-GSFP",
-               .fixup = sfp_fixup_halny_gsfp,
diff --git a/target/linux/generic/backport-5.15/800-v6.0-0001-dt-bindings-leds-add-Broadcom-s-BCM63138-controller.patch b/target/linux/generic/backport-5.15/800-v6.0-0001-dt-bindings-leds-add-Broadcom-s-BCM63138-controller.patch
deleted file mode 100644 (file)
index b1072ce..0000000
+++ /dev/null
@@ -1,125 +0,0 @@
-From 13344f8ce8a0d98aa7f5d69ce3b47393c73a343b Mon Sep 17 00:00:00 2001
-From: =?UTF-8?q?Rafa=C5=82=20Mi=C5=82ecki?= <[email protected]>
-Date: Mon, 27 Dec 2021 15:59:04 +0100
-Subject: [PATCH] dt-bindings: leds: add Broadcom's BCM63138 controller
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-Broadcom used 2 LEDs hardware blocks for their BCM63xx SoCs:
-1. Older one (BCM6318, BCM6328, BCM6362, BCM63268, BCM6838)
-2. Newer one (BCM6848, BCM6858, BCM63138, BCM63148, BCM63381, BCM68360)
-
-The newer one was also later also used on BCM4908 SoC.
-
-Old block is already documented in the leds-bcm6328.yaml. This binding
-documents the new one which uses different registers & programming. It's
-first used in BCM63138 thus the binding name.
-
-Signed-off-by: Rafał Miłecki <[email protected]>
-Reviewed-by: Rob Herring <[email protected]>
-Reviewed-by: Florian Fainelli <[email protected]>
-Signed-off-by: Pavel Machek <[email protected]>
----
- .../bindings/leds/leds-bcm63138.yaml          | 95 +++++++++++++++++++
- 1 file changed, 95 insertions(+)
- create mode 100644 Documentation/devicetree/bindings/leds/leds-bcm63138.yaml
-
---- /dev/null
-+++ b/Documentation/devicetree/bindings/leds/leds-bcm63138.yaml
-@@ -0,0 +1,95 @@
-+# SPDX-License-Identifier: GPL-2.0-only OR BSD-2-Clause
-+%YAML 1.2
-+---
-+$id: http://devicetree.org/schemas/leds/leds-bcm63138.yaml#
-+$schema: http://devicetree.org/meta-schemas/core.yaml#
-+
-+title: Broadcom's BCM63138 LEDs controller
-+
-+maintainers:
-+  - Rafał Miłecki <[email protected]>
-+
-+description: |
-+  This LEDs controller was first used on BCM63138 and later reused on BCM4908,
-+  BCM6848, BCM6858, BCM63138, BCM63148, BCM63381 and BCM68360 SoCs.
-+
-+  It supports up to 32 LEDs that can be connected parallelly or serially. It
-+  also includes limited support for hardware blinking.
-+
-+  Binding serially connected LEDs isn't documented yet.
-+
-+properties:
-+  compatible:
-+    oneOf:
-+      - items:
-+          - enum:
-+              - brcm,bcm4908-leds
-+              - brcm,bcm6848-leds
-+              - brcm,bcm6858-leds
-+              - brcm,bcm63148-leds
-+              - brcm,bcm63381-leds
-+              - brcm,bcm68360-leds
-+          - const: brcm,bcm63138-leds
-+      - const: brcm,bcm63138-leds
-+
-+  reg:
-+    maxItems: 1
-+
-+  "#address-cells":
-+    const: 1
-+
-+  "#size-cells":
-+    const: 0
-+
-+patternProperties:
-+  "^led@[a-f0-9]+$":
-+    type: object
-+
-+    $ref: common.yaml#
-+
-+    properties:
-+      reg:
-+        maxItems: 1
-+        description: LED pin number
-+
-+      active-low:
-+        type: boolean
-+        description: Makes LED active low.
-+
-+    required:
-+      - reg
-+
-+    unevaluatedProperties: false
-+
-+required:
-+  - reg
-+  - "#address-cells"
-+  - "#size-cells"
-+
-+additionalProperties: false
-+
-+examples:
-+  - |
-+    #include <dt-bindings/leds/common.h>
-+
-+    leds@ff800800 {
-+        compatible = "brcm,bcm4908-leds", "brcm,bcm63138-leds";
-+        reg = <0xff800800 0xdc>;
-+
-+        #address-cells = <1>;
-+        #size-cells = <0>;
-+
-+        led@0 {
-+            reg = <0x0>;
-+            function = LED_FUNCTION_POWER;
-+            color = <LED_COLOR_ID_GREEN>;
-+            default-state = "on";
-+        };
-+
-+        led@3 {
-+            reg = <0x3>;
-+            function = LED_FUNCTION_STATUS;
-+            color = <LED_COLOR_ID_GREEN>;
-+            active-low;
-+        };
-+    };
diff --git a/target/linux/generic/backport-5.15/800-v6.0-0002-leds-bcm63138-add-support-for-BCM63138-controller.patch b/target/linux/generic/backport-5.15/800-v6.0-0002-leds-bcm63138-add-support-for-BCM63138-controller.patch
deleted file mode 100644 (file)
index 3765845..0000000
+++ /dev/null
@@ -1,356 +0,0 @@
-From a0ba692072d89075d0a75c7ad9df31f2c1ee9a1c Mon Sep 17 00:00:00 2001
-From: =?UTF-8?q?Rafa=C5=82=20Mi=C5=82ecki?= <[email protected]>
-Date: Mon, 27 Dec 2021 15:59:05 +0100
-Subject: [PATCH] leds: bcm63138: add support for BCM63138 controller
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-It's a new controller first introduced in BCM63138 SoC. Later it was
-also used in BCM4908, some BCM68xx and some BCM63xxx SoCs.
-
-Signed-off-by: Rafał Miłecki <[email protected]>
-Reviewed-by: Florian Fainelli <[email protected]>
-Signed-off-by: Pavel Machek <[email protected]>
----
- drivers/leds/blink/Kconfig         |  12 ++
- drivers/leds/blink/Makefile        |   1 +
- drivers/leds/blink/leds-bcm63138.c | 308 +++++++++++++++++++++++++++++
- 3 files changed, 321 insertions(+)
- create mode 100644 drivers/leds/blink/leds-bcm63138.c
-
---- a/drivers/leds/blink/Kconfig
-+++ b/drivers/leds/blink/Kconfig
-@@ -1,3 +1,15 @@
-+config LEDS_BCM63138
-+      tristate "LED Support for Broadcom BCM63138 SoC"
-+      depends on LEDS_CLASS
-+      depends on ARCH_BCM4908 || ARCH_BCM_5301X || BCM63XX || COMPILE_TEST
-+      depends on HAS_IOMEM
-+      depends on OF
-+      default ARCH_BCM4908
-+      help
-+        This option enables support for LED controller that is part of
-+        BCM63138 SoC. The same hardware block is known to be also used
-+        in BCM4908, BCM6848, BCM6858, BCM63148, BCM63381 and BCM68360.
-+
- config LEDS_LGM
-        tristate "LED support for LGM SoC series"
-        depends on X86 || COMPILE_TEST
---- a/drivers/leds/blink/Makefile
-+++ b/drivers/leds/blink/Makefile
-@@ -1,2 +1,3 @@
- # SPDX-License-Identifier: GPL-2.0
-+obj-$(CONFIG_LEDS_BCM63138)   += leds-bcm63138.o
- obj-$(CONFIG_LEDS_LGM)        += leds-lgm-sso.o
---- /dev/null
-+++ b/drivers/leds/blink/leds-bcm63138.c
-@@ -0,0 +1,308 @@
-+// SPDX-License-Identifier: GPL-2.0-only
-+/*
-+ * Copyright (C) 2021 Rafał Miłecki <[email protected]>
-+ */
-+#include <linux/delay.h>
-+#include <linux/io.h>
-+#include <linux/leds.h>
-+#include <linux/module.h>
-+#include <linux/of.h>
-+#include <linux/pinctrl/consumer.h>
-+#include <linux/platform_device.h>
-+#include <linux/spinlock.h>
-+
-+#define BCM63138_MAX_LEDS                             32
-+#define BCM63138_MAX_BRIGHTNESS                               9
-+
-+#define BCM63138_LED_BITS                             4                               /* how many bits control a single LED */
-+#define BCM63138_LED_MASK                             ((1 << BCM63138_LED_BITS) - 1)  /* 0xf */
-+#define BCM63138_LEDS_PER_REG                         (32 / BCM63138_LED_BITS)        /* 8 */
-+
-+#define BCM63138_GLB_CTRL                             0x00
-+#define  BCM63138_GLB_CTRL_SERIAL_LED_DATA_PPOL               0x00000002
-+#define  BCM63138_GLB_CTRL_SERIAL_LED_EN_POL          0x00000008
-+#define BCM63138_MASK                                 0x04
-+#define BCM63138_HW_LED_EN                            0x08
-+#define BCM63138_SERIAL_LED_SHIFT_SEL                 0x0c
-+#define BCM63138_FLASH_RATE_CTRL1                     0x10
-+#define BCM63138_FLASH_RATE_CTRL2                     0x14
-+#define BCM63138_FLASH_RATE_CTRL3                     0x18
-+#define BCM63138_FLASH_RATE_CTRL4                     0x1c
-+#define BCM63138_BRIGHT_CTRL1                         0x20
-+#define BCM63138_BRIGHT_CTRL2                         0x24
-+#define BCM63138_BRIGHT_CTRL3                         0x28
-+#define BCM63138_BRIGHT_CTRL4                         0x2c
-+#define BCM63138_POWER_LED_CFG                                0x30
-+#define BCM63138_HW_POLARITY                          0xb4
-+#define BCM63138_SW_DATA                              0xb8
-+#define BCM63138_SW_POLARITY                          0xbc
-+#define BCM63138_PARALLEL_LED_POLARITY                        0xc0
-+#define BCM63138_SERIAL_LED_POLARITY                  0xc4
-+#define BCM63138_HW_LED_STATUS                                0xc8
-+#define BCM63138_FLASH_CTRL_STATUS                    0xcc
-+#define BCM63138_FLASH_BRT_CTRL                               0xd0
-+#define BCM63138_FLASH_P_LED_OUT_STATUS                       0xd4
-+#define BCM63138_FLASH_S_LED_OUT_STATUS                       0xd8
-+
-+struct bcm63138_leds {
-+      struct device *dev;
-+      void __iomem *base;
-+      spinlock_t lock;
-+};
-+
-+struct bcm63138_led {
-+      struct bcm63138_leds *leds;
-+      struct led_classdev cdev;
-+      u32 pin;
-+      bool active_low;
-+};
-+
-+/*
-+ * I/O access
-+ */
-+
-+static void bcm63138_leds_write(struct bcm63138_leds *leds, unsigned int reg,
-+                              u32 data)
-+{
-+      writel(data, leds->base + reg);
-+}
-+
-+static unsigned long bcm63138_leds_read(struct bcm63138_leds *leds,
-+                                      unsigned int reg)
-+{
-+      return readl(leds->base + reg);
-+}
-+
-+static void bcm63138_leds_update_bits(struct bcm63138_leds *leds,
-+                                    unsigned int reg, u32 mask, u32 val)
-+{
-+      WARN_ON(val & ~mask);
-+
-+      bcm63138_leds_write(leds, reg, (bcm63138_leds_read(leds, reg) & ~mask) | (val & mask));
-+}
-+
-+/*
-+ * Helpers
-+ */
-+
-+static void bcm63138_leds_set_flash_rate(struct bcm63138_leds *leds,
-+                                       struct bcm63138_led *led,
-+                                       u8 value)
-+{
-+      int reg_offset = (led->pin >> fls((BCM63138_LEDS_PER_REG - 1))) * 4;
-+      int shift = (led->pin & (BCM63138_LEDS_PER_REG - 1)) * BCM63138_LED_BITS;
-+
-+      bcm63138_leds_update_bits(leds, BCM63138_FLASH_RATE_CTRL1 + reg_offset,
-+                                BCM63138_LED_MASK << shift, value << shift);
-+}
-+
-+static void bcm63138_leds_set_bright(struct bcm63138_leds *leds,
-+                                   struct bcm63138_led *led,
-+                                   u8 value)
-+{
-+      int reg_offset = (led->pin >> fls((BCM63138_LEDS_PER_REG - 1))) * 4;
-+      int shift = (led->pin & (BCM63138_LEDS_PER_REG - 1)) * BCM63138_LED_BITS;
-+
-+      bcm63138_leds_update_bits(leds, BCM63138_BRIGHT_CTRL1 + reg_offset,
-+                                BCM63138_LED_MASK << shift, value << shift);
-+}
-+
-+static void bcm63138_leds_enable_led(struct bcm63138_leds *leds,
-+                                   struct bcm63138_led *led,
-+                                   enum led_brightness value)
-+{
-+      u32 bit = BIT(led->pin);
-+
-+      bcm63138_leds_update_bits(leds, BCM63138_SW_DATA, bit,
-+                                value == LED_OFF ? 0 : bit);
-+}
-+
-+/*
-+ * API callbacks
-+ */
-+
-+static void bcm63138_leds_brightness_set(struct led_classdev *led_cdev,
-+                                       enum led_brightness value)
-+{
-+      struct bcm63138_led *led = container_of(led_cdev, struct bcm63138_led, cdev);
-+      struct bcm63138_leds *leds = led->leds;
-+      unsigned long flags;
-+
-+      spin_lock_irqsave(&leds->lock, flags);
-+
-+      bcm63138_leds_enable_led(leds, led, value);
-+      if (!value)
-+              bcm63138_leds_set_flash_rate(leds, led, 0);
-+      else
-+              bcm63138_leds_set_bright(leds, led, value);
-+
-+      spin_unlock_irqrestore(&leds->lock, flags);
-+}
-+
-+static int bcm63138_leds_blink_set(struct led_classdev *led_cdev,
-+                                 unsigned long *delay_on,
-+                                 unsigned long *delay_off)
-+{
-+      struct bcm63138_led *led = container_of(led_cdev, struct bcm63138_led, cdev);
-+      struct bcm63138_leds *leds = led->leds;
-+      unsigned long flags;
-+      u8 value;
-+
-+      if (!*delay_on && !*delay_off) {
-+              *delay_on = 640;
-+              *delay_off = 640;
-+      }
-+
-+      if (*delay_on != *delay_off) {
-+              dev_dbg(led_cdev->dev, "Blinking at unequal delays is not supported\n");
-+              return -EINVAL;
-+      }
-+
-+      switch (*delay_on) {
-+      case 1152 ... 1408: /* 1280 ms ± 10% */
-+              value = 0x7;
-+              break;
-+      case 576 ... 704: /* 640 ms ± 10% */
-+              value = 0x6;
-+              break;
-+      case 288 ... 352: /* 320 ms ± 10% */
-+              value = 0x5;
-+              break;
-+      case 126 ... 154: /* 140 ms ± 10% */
-+              value = 0x4;
-+              break;
-+      case 59 ... 72: /* 65 ms ± 10% */
-+              value = 0x3;
-+              break;
-+      default:
-+              dev_dbg(led_cdev->dev, "Blinking delay value %lu is unsupported\n",
-+                      *delay_on);
-+              return -EINVAL;
-+      }
-+
-+      spin_lock_irqsave(&leds->lock, flags);
-+
-+      bcm63138_leds_enable_led(leds, led, BCM63138_MAX_BRIGHTNESS);
-+      bcm63138_leds_set_flash_rate(leds, led, value);
-+
-+      spin_unlock_irqrestore(&leds->lock, flags);
-+
-+      return 0;
-+}
-+
-+/*
-+ * LED driver
-+ */
-+
-+static void bcm63138_leds_create_led(struct bcm63138_leds *leds,
-+                                   struct device_node *np)
-+{
-+      struct led_init_data init_data = {
-+              .fwnode = of_fwnode_handle(np),
-+      };
-+      struct device *dev = leds->dev;
-+      struct bcm63138_led *led;
-+      struct pinctrl *pinctrl;
-+      u32 bit;
-+      int err;
-+
-+      led = devm_kzalloc(dev, sizeof(*led), GFP_KERNEL);
-+      if (!led) {
-+              dev_err(dev, "Failed to alloc LED\n");
-+              return;
-+      }
-+
-+      led->leds = leds;
-+
-+      if (of_property_read_u32(np, "reg", &led->pin)) {
-+              dev_err(dev, "Missing \"reg\" property in %pOF\n", np);
-+              goto err_free;
-+      }
-+
-+      if (led->pin >= BCM63138_MAX_LEDS) {
-+              dev_err(dev, "Invalid \"reg\" value %d\n", led->pin);
-+              goto err_free;
-+      }
-+
-+      led->active_low = of_property_read_bool(np, "active-low");
-+
-+      led->cdev.max_brightness = BCM63138_MAX_BRIGHTNESS;
-+      led->cdev.brightness_set = bcm63138_leds_brightness_set;
-+      led->cdev.blink_set = bcm63138_leds_blink_set;
-+
-+      err = devm_led_classdev_register_ext(dev, &led->cdev, &init_data);
-+      if (err) {
-+              dev_err(dev, "Failed to register LED %pOF: %d\n", np, err);
-+              goto err_free;
-+      }
-+
-+      pinctrl = devm_pinctrl_get_select_default(led->cdev.dev);
-+      if (IS_ERR(pinctrl) && PTR_ERR(pinctrl) != -ENODEV) {
-+              dev_warn(led->cdev.dev, "Failed to select %pOF pinctrl: %ld\n",
-+                       np, PTR_ERR(pinctrl));
-+      }
-+
-+      bit = BIT(led->pin);
-+      bcm63138_leds_update_bits(leds, BCM63138_PARALLEL_LED_POLARITY, bit,
-+                                led->active_low ? 0 : bit);
-+      bcm63138_leds_update_bits(leds, BCM63138_HW_LED_EN, bit, 0);
-+      bcm63138_leds_set_flash_rate(leds, led, 0);
-+      bcm63138_leds_enable_led(leds, led, led->cdev.brightness);
-+
-+      return;
-+
-+err_free:
-+      devm_kfree(dev, led);
-+}
-+
-+static int bcm63138_leds_probe(struct platform_device *pdev)
-+{
-+      struct device_node *np = dev_of_node(&pdev->dev);
-+      struct device *dev = &pdev->dev;
-+      struct bcm63138_leds *leds;
-+      struct device_node *child;
-+
-+      leds = devm_kzalloc(dev, sizeof(*leds), GFP_KERNEL);
-+      if (!leds)
-+              return -ENOMEM;
-+
-+      leds->dev = dev;
-+
-+      leds->base = devm_platform_ioremap_resource(pdev, 0);
-+      if (IS_ERR(leds->base))
-+              return PTR_ERR(leds->base);
-+
-+      spin_lock_init(&leds->lock);
-+
-+      bcm63138_leds_write(leds, BCM63138_GLB_CTRL,
-+                          BCM63138_GLB_CTRL_SERIAL_LED_DATA_PPOL |
-+                          BCM63138_GLB_CTRL_SERIAL_LED_EN_POL);
-+      bcm63138_leds_write(leds, BCM63138_HW_LED_EN, 0);
-+      bcm63138_leds_write(leds, BCM63138_SERIAL_LED_POLARITY, 0);
-+      bcm63138_leds_write(leds, BCM63138_PARALLEL_LED_POLARITY, 0);
-+
-+      for_each_available_child_of_node(np, child) {
-+              bcm63138_leds_create_led(leds, child);
-+      }
-+
-+      return 0;
-+}
-+
-+static const struct of_device_id bcm63138_leds_of_match_table[] = {
-+      { .compatible = "brcm,bcm63138-leds", },
-+      { },
-+};
-+
-+static struct platform_driver bcm63138_leds_driver = {
-+      .probe = bcm63138_leds_probe,
-+      .driver = {
-+              .name = "leds-bcm63xxx",
-+              .of_match_table = bcm63138_leds_of_match_table,
-+      },
-+};
-+
-+module_platform_driver(bcm63138_leds_driver);
-+
-+MODULE_AUTHOR("Rafał Miłecki");
-+MODULE_LICENSE("GPL");
-+MODULE_DEVICE_TABLE(of, bcm63138_leds_of_match_table);
diff --git a/target/linux/generic/backport-5.15/801-v6.0-0001-dt-bindings-leds-leds-bcm63138-unify-full-stops-in-d.patch b/target/linux/generic/backport-5.15/801-v6.0-0001-dt-bindings-leds-leds-bcm63138-unify-full-stops-in-d.patch
deleted file mode 100644 (file)
index 483826a..0000000
+++ /dev/null
@@ -1,30 +0,0 @@
-From 13b64a0c19059b38150c79d65d350ae44034c5df Mon Sep 17 00:00:00 2001
-From: =?UTF-8?q?Rafa=C5=82=20Mi=C5=82ecki?= <[email protected]>
-Date: Sun, 17 Jul 2022 14:42:46 +0200
-Subject: [PATCH] dt-bindings: leds: leds-bcm63138: unify full stops in
- descriptions
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-Description of "reg" doesn't have full stop at the end. It makes sense
-as it's a one-sentence only. Use the same style for "active-low".
-
-Reported-by: Pavel Machek <[email protected]>
-Signed-off-by: Rafał Miłecki <[email protected]>
-Signed-off-by: Pavel Machek <[email protected]>
----
- Documentation/devicetree/bindings/leds/leds-bcm63138.yaml | 2 +-
- 1 file changed, 1 insertion(+), 1 deletion(-)
-
---- a/Documentation/devicetree/bindings/leds/leds-bcm63138.yaml
-+++ b/Documentation/devicetree/bindings/leds/leds-bcm63138.yaml
-@@ -54,7 +54,7 @@ patternProperties:
-       active-low:
-         type: boolean
--        description: Makes LED active low.
-+        description: Makes LED active low
-     required:
-       - reg
diff --git a/target/linux/generic/backport-5.15/801-v6.0-0002-leds-add-help-info-about-BCM63138-module-name.patch b/target/linux/generic/backport-5.15/801-v6.0-0002-leds-add-help-info-about-BCM63138-module-name.patch
deleted file mode 100644 (file)
index 5430b1f..0000000
+++ /dev/null
@@ -1,28 +0,0 @@
-From bcc607cdbb1f931111196699426f0cb83bfb296a Mon Sep 17 00:00:00 2001
-From: =?UTF-8?q?Rafa=C5=82=20Mi=C5=82ecki?= <[email protected]>
-Date: Sun, 17 Jul 2022 14:42:47 +0200
-Subject: [PATCH] leds: add help info about BCM63138 module name
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-It's what we do for all other LEDs drivers.
-
-Reported-by: Pavel Machek <[email protected]>
-Signed-off-by: Rafał Miłecki <[email protected]>
-Signed-off-by: Pavel Machek <[email protected]>
----
- drivers/leds/blink/Kconfig | 2 ++
- 1 file changed, 2 insertions(+)
-
---- a/drivers/leds/blink/Kconfig
-+++ b/drivers/leds/blink/Kconfig
-@@ -10,6 +10,8 @@ config LEDS_BCM63138
-         BCM63138 SoC. The same hardware block is known to be also used
-         in BCM4908, BCM6848, BCM6858, BCM63148, BCM63381 and BCM68360.
-+        If compiled as module it will be called leds-bcm63138.
-+
- config LEDS_LGM
-        tristate "LED support for LGM SoC series"
-        depends on X86 || COMPILE_TEST
diff --git a/target/linux/generic/backport-5.15/801-v6.0-0003-leds-leds-bcm63138-get-rid-of-LED_OFF.patch b/target/linux/generic/backport-5.15/801-v6.0-0003-leds-leds-bcm63138-get-rid-of-LED_OFF.patch
deleted file mode 100644 (file)
index e125a54..0000000
+++ /dev/null
@@ -1,30 +0,0 @@
-From 92cfc71ee2ddfb499ed53e21b28bdf8739bc70bc Mon Sep 17 00:00:00 2001
-From: =?UTF-8?q?Rafa=C5=82=20Mi=C5=82ecki?= <[email protected]>
-Date: Sun, 17 Jul 2022 14:42:48 +0200
-Subject: [PATCH] leds: leds-bcm63138: get rid of LED_OFF
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-The whole "enum led_brightness" is marked as obsolete. Replace it with a
-(non-)zero check.
-
-Reported-by: Pavel Machek <[email protected]>
-Signed-off-by: Rafał Miłecki <[email protected]>
-Signed-off-by: Pavel Machek <[email protected]>
----
- drivers/leds/blink/leds-bcm63138.c | 3 +--
- 1 file changed, 1 insertion(+), 2 deletions(-)
-
---- a/drivers/leds/blink/leds-bcm63138.c
-+++ b/drivers/leds/blink/leds-bcm63138.c
-@@ -113,8 +113,7 @@ static void bcm63138_leds_enable_led(str
- {
-       u32 bit = BIT(led->pin);
--      bcm63138_leds_update_bits(leds, BCM63138_SW_DATA, bit,
--                                value == LED_OFF ? 0 : bit);
-+      bcm63138_leds_update_bits(leds, BCM63138_SW_DATA, bit, value ? bit : 0);
- }
- /*
diff --git a/target/linux/generic/backport-5.15/802-v5.16-0001-nvmem-core-rework-nvmem-cell-instance-creation.patch b/target/linux/generic/backport-5.15/802-v5.16-0001-nvmem-core-rework-nvmem-cell-instance-creation.patch
deleted file mode 100644 (file)
index ebab8c7..0000000
+++ /dev/null
@@ -1,456 +0,0 @@
-From 7ae6478b304bc004c3139b422665b0e23b57f05c Mon Sep 17 00:00:00 2001
-From: Srinivas Kandagatla <[email protected]>
-Date: Wed, 13 Oct 2021 14:19:55 +0100
-Subject: [PATCH] nvmem: core: rework nvmem cell instance creation
-
-In the existing design, we do not create a instance per nvmem cell consumer
-but we directly refer cell from nvmem cell list that are added to provider.
-
-However this design has some limitations when consumers want to assign name
-or connection id the nvmem cell instance, ex: via "nvmem-cell-names" or
-id in nvmem_cell_get(id).
-
-Having a name associated with nvmem cell consumer instance will help
-provider drivers in performing post processing of nvmem cell data if required
-before data is seen by the consumers. This is pretty normal with some vendors
-storing nvmem cells like mac-address in a vendor specific data layouts that
-are not directly usable by the consumer drivers.
-
-With this patch nvmem cell will be created dynamically during nvmem_cell_get
-and destroyed in nvmem_cell_put, allowing consumers to associate name with
-nvmem cell consumer instance.
-
-With this patch a new struct nvmem_cell_entry replaces struct nvmem_cell
-for storing nvmem cell information within the core.
-This patch does not change nvmem-consumer interface based on nvmem_cell.
-
-Tested-by: Joakim Zhang <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/core.c | 165 +++++++++++++++++++++++++++----------------
- 1 file changed, 105 insertions(+), 60 deletions(-)
-
---- a/drivers/nvmem/core.c
-+++ b/drivers/nvmem/core.c
-@@ -45,8 +45,7 @@ struct nvmem_device {
- #define to_nvmem_device(d) container_of(d, struct nvmem_device, dev)
- #define FLAG_COMPAT           BIT(0)
--
--struct nvmem_cell {
-+struct nvmem_cell_entry {
-       const char              *name;
-       int                     offset;
-       int                     bytes;
-@@ -57,6 +56,11 @@ struct nvmem_cell {
-       struct list_head        node;
- };
-+struct nvmem_cell {
-+      struct nvmem_cell_entry *entry;
-+      const char              *id;
-+};
-+
- static DEFINE_MUTEX(nvmem_mutex);
- static DEFINE_IDA(nvmem_ida);
-@@ -424,7 +428,7 @@ static struct bus_type nvmem_bus_type =
-       .name           = "nvmem",
- };
--static void nvmem_cell_drop(struct nvmem_cell *cell)
-+static void nvmem_cell_entry_drop(struct nvmem_cell_entry *cell)
- {
-       blocking_notifier_call_chain(&nvmem_notifier, NVMEM_CELL_REMOVE, cell);
-       mutex_lock(&nvmem_mutex);
-@@ -437,13 +441,13 @@ static void nvmem_cell_drop(struct nvmem
- static void nvmem_device_remove_all_cells(const struct nvmem_device *nvmem)
- {
--      struct nvmem_cell *cell, *p;
-+      struct nvmem_cell_entry *cell, *p;
-       list_for_each_entry_safe(cell, p, &nvmem->cells, node)
--              nvmem_cell_drop(cell);
-+              nvmem_cell_entry_drop(cell);
- }
--static void nvmem_cell_add(struct nvmem_cell *cell)
-+static void nvmem_cell_entry_add(struct nvmem_cell_entry *cell)
- {
-       mutex_lock(&nvmem_mutex);
-       list_add_tail(&cell->node, &cell->nvmem->cells);
-@@ -451,9 +455,9 @@ static void nvmem_cell_add(struct nvmem_
-       blocking_notifier_call_chain(&nvmem_notifier, NVMEM_CELL_ADD, cell);
- }
--static int nvmem_cell_info_to_nvmem_cell_nodup(struct nvmem_device *nvmem,
--                                      const struct nvmem_cell_info *info,
--                                      struct nvmem_cell *cell)
-+static int nvmem_cell_info_to_nvmem_cell_entry_nodup(struct nvmem_device *nvmem,
-+                                                   const struct nvmem_cell_info *info,
-+                                                   struct nvmem_cell_entry *cell)
- {
-       cell->nvmem = nvmem;
-       cell->offset = info->offset;
-@@ -477,13 +481,13 @@ static int nvmem_cell_info_to_nvmem_cell
-       return 0;
- }
--static int nvmem_cell_info_to_nvmem_cell(struct nvmem_device *nvmem,
--                              const struct nvmem_cell_info *info,
--                              struct nvmem_cell *cell)
-+static int nvmem_cell_info_to_nvmem_cell_entry(struct nvmem_device *nvmem,
-+                                             const struct nvmem_cell_info *info,
-+                                             struct nvmem_cell_entry *cell)
- {
-       int err;
--      err = nvmem_cell_info_to_nvmem_cell_nodup(nvmem, info, cell);
-+      err = nvmem_cell_info_to_nvmem_cell_entry_nodup(nvmem, info, cell);
-       if (err)
-               return err;
-@@ -507,7 +511,7 @@ static int nvmem_add_cells(struct nvmem_
-                   const struct nvmem_cell_info *info,
-                   int ncells)
- {
--      struct nvmem_cell **cells;
-+      struct nvmem_cell_entry **cells;
-       int i, rval;
-       cells = kcalloc(ncells, sizeof(*cells), GFP_KERNEL);
-@@ -521,13 +525,13 @@ static int nvmem_add_cells(struct nvmem_
-                       goto err;
-               }
--              rval = nvmem_cell_info_to_nvmem_cell(nvmem, &info[i], cells[i]);
-+              rval = nvmem_cell_info_to_nvmem_cell_entry(nvmem, &info[i], cells[i]);
-               if (rval) {
-                       kfree(cells[i]);
-                       goto err;
-               }
--              nvmem_cell_add(cells[i]);
-+              nvmem_cell_entry_add(cells[i]);
-       }
-       /* remove tmp array */
-@@ -536,7 +540,7 @@ static int nvmem_add_cells(struct nvmem_
-       return 0;
- err:
-       while (i--)
--              nvmem_cell_drop(cells[i]);
-+              nvmem_cell_entry_drop(cells[i]);
-       kfree(cells);
-@@ -573,7 +577,7 @@ static int nvmem_add_cells_from_table(st
- {
-       const struct nvmem_cell_info *info;
-       struct nvmem_cell_table *table;
--      struct nvmem_cell *cell;
-+      struct nvmem_cell_entry *cell;
-       int rval = 0, i;
-       mutex_lock(&nvmem_cell_mutex);
-@@ -588,15 +592,13 @@ static int nvmem_add_cells_from_table(st
-                                       goto out;
-                               }
--                              rval = nvmem_cell_info_to_nvmem_cell(nvmem,
--                                                                   info,
--                                                                   cell);
-+                              rval = nvmem_cell_info_to_nvmem_cell_entry(nvmem, info, cell);
-                               if (rval) {
-                                       kfree(cell);
-                                       goto out;
-                               }
--                              nvmem_cell_add(cell);
-+                              nvmem_cell_entry_add(cell);
-                       }
-               }
-       }
-@@ -606,10 +608,10 @@ out:
-       return rval;
- }
--static struct nvmem_cell *
--nvmem_find_cell_by_name(struct nvmem_device *nvmem, const char *cell_id)
-+static struct nvmem_cell_entry *
-+nvmem_find_cell_entry_by_name(struct nvmem_device *nvmem, const char *cell_id)
- {
--      struct nvmem_cell *iter, *cell = NULL;
-+      struct nvmem_cell_entry *iter, *cell = NULL;
-       mutex_lock(&nvmem_mutex);
-       list_for_each_entry(iter, &nvmem->cells, node) {
-@@ -680,7 +682,7 @@ static int nvmem_add_cells_from_of(struc
- {
-       struct device_node *parent, *child;
-       struct device *dev = &nvmem->dev;
--      struct nvmem_cell *cell;
-+      struct nvmem_cell_entry *cell;
-       const __be32 *addr;
-       int len;
-@@ -729,7 +731,7 @@ static int nvmem_add_cells_from_of(struc
-               }
-               cell->np = of_node_get(child);
--              nvmem_cell_add(cell);
-+              nvmem_cell_entry_add(cell);
-       }
-       return 0;
-@@ -1142,9 +1144,33 @@ struct nvmem_device *devm_nvmem_device_g
- }
- EXPORT_SYMBOL_GPL(devm_nvmem_device_get);
-+static struct nvmem_cell *nvmem_create_cell(struct nvmem_cell_entry *entry, const char *id)
-+{
-+      struct nvmem_cell *cell;
-+      const char *name = NULL;
-+
-+      cell = kzalloc(sizeof(*cell), GFP_KERNEL);
-+      if (!cell)
-+              return ERR_PTR(-ENOMEM);
-+
-+      if (id) {
-+              name = kstrdup_const(id, GFP_KERNEL);
-+              if (!name) {
-+                      kfree(cell);
-+                      return ERR_PTR(-ENOMEM);
-+              }
-+      }
-+
-+      cell->id = name;
-+      cell->entry = entry;
-+
-+      return cell;
-+}
-+
- static struct nvmem_cell *
- nvmem_cell_get_from_lookup(struct device *dev, const char *con_id)
- {
-+      struct nvmem_cell_entry *cell_entry;
-       struct nvmem_cell *cell = ERR_PTR(-ENOENT);
-       struct nvmem_cell_lookup *lookup;
-       struct nvmem_device *nvmem;
-@@ -1169,11 +1195,15 @@ nvmem_cell_get_from_lookup(struct device
-                               break;
-                       }
--                      cell = nvmem_find_cell_by_name(nvmem,
--                                                     lookup->cell_name);
--                      if (!cell) {
-+                      cell_entry = nvmem_find_cell_entry_by_name(nvmem,
-+                                                                 lookup->cell_name);
-+                      if (!cell_entry) {
-                               __nvmem_device_put(nvmem);
-                               cell = ERR_PTR(-ENOENT);
-+                      } else {
-+                              cell = nvmem_create_cell(cell_entry, con_id);
-+                              if (IS_ERR(cell))
-+                                      __nvmem_device_put(nvmem);
-                       }
-                       break;
-               }
-@@ -1184,10 +1214,10 @@ nvmem_cell_get_from_lookup(struct device
- }
- #if IS_ENABLED(CONFIG_OF)
--static struct nvmem_cell *
--nvmem_find_cell_by_node(struct nvmem_device *nvmem, struct device_node *np)
-+static struct nvmem_cell_entry *
-+nvmem_find_cell_entry_by_node(struct nvmem_device *nvmem, struct device_node *np)
- {
--      struct nvmem_cell *iter, *cell = NULL;
-+      struct nvmem_cell_entry *iter, *cell = NULL;
-       mutex_lock(&nvmem_mutex);
-       list_for_each_entry(iter, &nvmem->cells, node) {
-@@ -1217,6 +1247,7 @@ struct nvmem_cell *of_nvmem_cell_get(str
- {
-       struct device_node *cell_np, *nvmem_np;
-       struct nvmem_device *nvmem;
-+      struct nvmem_cell_entry *cell_entry;
-       struct nvmem_cell *cell;
-       int index = 0;
-@@ -1237,12 +1268,16 @@ struct nvmem_cell *of_nvmem_cell_get(str
-       if (IS_ERR(nvmem))
-               return ERR_CAST(nvmem);
--      cell = nvmem_find_cell_by_node(nvmem, cell_np);
--      if (!cell) {
-+      cell_entry = nvmem_find_cell_entry_by_node(nvmem, cell_np);
-+      if (!cell_entry) {
-               __nvmem_device_put(nvmem);
-               return ERR_PTR(-ENOENT);
-       }
-+      cell = nvmem_create_cell(cell_entry, id);
-+      if (IS_ERR(cell))
-+              __nvmem_device_put(nvmem);
-+
-       return cell;
- }
- EXPORT_SYMBOL_GPL(of_nvmem_cell_get);
-@@ -1348,13 +1383,17 @@ EXPORT_SYMBOL(devm_nvmem_cell_put);
-  */
- void nvmem_cell_put(struct nvmem_cell *cell)
- {
--      struct nvmem_device *nvmem = cell->nvmem;
-+      struct nvmem_device *nvmem = cell->entry->nvmem;
-+
-+      if (cell->id)
-+              kfree_const(cell->id);
-+      kfree(cell);
-       __nvmem_device_put(nvmem);
- }
- EXPORT_SYMBOL_GPL(nvmem_cell_put);
--static void nvmem_shift_read_buffer_in_place(struct nvmem_cell *cell, void *buf)
-+static void nvmem_shift_read_buffer_in_place(struct nvmem_cell_entry *cell, void *buf)
- {
-       u8 *p, *b;
-       int i, extra, bit_offset = cell->bit_offset;
-@@ -1388,8 +1427,8 @@ static void nvmem_shift_read_buffer_in_p
- }
- static int __nvmem_cell_read(struct nvmem_device *nvmem,
--                    struct nvmem_cell *cell,
--                    void *buf, size_t *len)
-+                    struct nvmem_cell_entry *cell,
-+                    void *buf, size_t *len, const char *id)
- {
-       int rc;
-@@ -1420,18 +1459,18 @@ static int __nvmem_cell_read(struct nvme
-  */
- void *nvmem_cell_read(struct nvmem_cell *cell, size_t *len)
- {
--      struct nvmem_device *nvmem = cell->nvmem;
-+      struct nvmem_device *nvmem = cell->entry->nvmem;
-       u8 *buf;
-       int rc;
-       if (!nvmem)
-               return ERR_PTR(-EINVAL);
--      buf = kzalloc(cell->bytes, GFP_KERNEL);
-+      buf = kzalloc(cell->entry->bytes, GFP_KERNEL);
-       if (!buf)
-               return ERR_PTR(-ENOMEM);
--      rc = __nvmem_cell_read(nvmem, cell, buf, len);
-+      rc = __nvmem_cell_read(nvmem, cell->entry, buf, len, cell->id);
-       if (rc) {
-               kfree(buf);
-               return ERR_PTR(rc);
-@@ -1441,7 +1480,7 @@ void *nvmem_cell_read(struct nvmem_cell
- }
- EXPORT_SYMBOL_GPL(nvmem_cell_read);
--static void *nvmem_cell_prepare_write_buffer(struct nvmem_cell *cell,
-+static void *nvmem_cell_prepare_write_buffer(struct nvmem_cell_entry *cell,
-                                            u8 *_buf, int len)
- {
-       struct nvmem_device *nvmem = cell->nvmem;
-@@ -1494,16 +1533,7 @@ err:
-       return ERR_PTR(rc);
- }
--/**
-- * nvmem_cell_write() - Write to a given nvmem cell
-- *
-- * @cell: nvmem cell to be written.
-- * @buf: Buffer to be written.
-- * @len: length of buffer to be written to nvmem cell.
-- *
-- * Return: length of bytes written or negative on failure.
-- */
--int nvmem_cell_write(struct nvmem_cell *cell, void *buf, size_t len)
-+static int __nvmem_cell_entry_write(struct nvmem_cell_entry *cell, void *buf, size_t len)
- {
-       struct nvmem_device *nvmem = cell->nvmem;
-       int rc;
-@@ -1529,6 +1559,21 @@ int nvmem_cell_write(struct nvmem_cell *
-       return len;
- }
-+
-+/**
-+ * nvmem_cell_write() - Write to a given nvmem cell
-+ *
-+ * @cell: nvmem cell to be written.
-+ * @buf: Buffer to be written.
-+ * @len: length of buffer to be written to nvmem cell.
-+ *
-+ * Return: length of bytes written or negative on failure.
-+ */
-+int nvmem_cell_write(struct nvmem_cell *cell, void *buf, size_t len)
-+{
-+      return __nvmem_cell_entry_write(cell->entry, buf, len);
-+}
-+
- EXPORT_SYMBOL_GPL(nvmem_cell_write);
- static int nvmem_cell_read_common(struct device *dev, const char *cell_id,
-@@ -1631,7 +1676,7 @@ static const void *nvmem_cell_read_varia
-       if (IS_ERR(cell))
-               return cell;
--      nbits = cell->nbits;
-+      nbits = cell->entry->nbits;
-       buf = nvmem_cell_read(cell, len);
-       nvmem_cell_put(cell);
-       if (IS_ERR(buf))
-@@ -1727,18 +1772,18 @@ EXPORT_SYMBOL_GPL(nvmem_cell_read_variab
- ssize_t nvmem_device_cell_read(struct nvmem_device *nvmem,
-                          struct nvmem_cell_info *info, void *buf)
- {
--      struct nvmem_cell cell;
-+      struct nvmem_cell_entry cell;
-       int rc;
-       ssize_t len;
-       if (!nvmem)
-               return -EINVAL;
--      rc = nvmem_cell_info_to_nvmem_cell_nodup(nvmem, info, &cell);
-+      rc = nvmem_cell_info_to_nvmem_cell_entry_nodup(nvmem, info, &cell);
-       if (rc)
-               return rc;
--      rc = __nvmem_cell_read(nvmem, &cell, buf, &len);
-+      rc = __nvmem_cell_read(nvmem, &cell, buf, &len, NULL);
-       if (rc)
-               return rc;
-@@ -1758,17 +1803,17 @@ EXPORT_SYMBOL_GPL(nvmem_device_cell_read
- int nvmem_device_cell_write(struct nvmem_device *nvmem,
-                           struct nvmem_cell_info *info, void *buf)
- {
--      struct nvmem_cell cell;
-+      struct nvmem_cell_entry cell;
-       int rc;
-       if (!nvmem)
-               return -EINVAL;
--      rc = nvmem_cell_info_to_nvmem_cell_nodup(nvmem, info, &cell);
-+      rc = nvmem_cell_info_to_nvmem_cell_entry_nodup(nvmem, info, &cell);
-       if (rc)
-               return rc;
--      return nvmem_cell_write(&cell, buf, cell.bytes);
-+      return __nvmem_cell_entry_write(&cell, buf, cell.bytes);
- }
- EXPORT_SYMBOL_GPL(nvmem_device_cell_write);
diff --git a/target/linux/generic/backport-5.15/802-v5.16-0002-nvmem-core-add-nvmem-cell-post-processing-callback.patch b/target/linux/generic/backport-5.15/802-v5.16-0002-nvmem-core-add-nvmem-cell-post-processing-callback.patch
deleted file mode 100644 (file)
index df264ad..0000000
+++ /dev/null
@@ -1,82 +0,0 @@
-From 5008062f1c3f5af3acf86164aa6fcc77b0c7bdce Mon Sep 17 00:00:00 2001
-From: Srinivas Kandagatla <[email protected]>
-Date: Wed, 13 Oct 2021 14:19:56 +0100
-Subject: [PATCH] nvmem: core: add nvmem cell post processing callback
-
-Some NVMEM providers have certain nvmem cells encoded, which requires
-post processing before actually using it.
-
-For example mac-address is stored in either in ascii or delimited or reverse-order.
-
-Having a post-process callback hook to provider drivers would enable them to
-do this vendor specific post processing before nvmem consumers see it.
-
-Tested-by: Joakim Zhang <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/core.c           | 9 +++++++++
- include/linux/nvmem-provider.h | 5 +++++
- 2 files changed, 14 insertions(+)
-
---- a/drivers/nvmem/core.c
-+++ b/drivers/nvmem/core.c
-@@ -38,6 +38,7 @@ struct nvmem_device {
-       unsigned int            nkeepout;
-       nvmem_reg_read_t        reg_read;
-       nvmem_reg_write_t       reg_write;
-+      nvmem_cell_post_process_t cell_post_process;
-       struct gpio_desc        *wp_gpio;
-       void *priv;
- };
-@@ -799,6 +800,7 @@ struct nvmem_device *nvmem_register(cons
-       nvmem->type = config->type;
-       nvmem->reg_read = config->reg_read;
-       nvmem->reg_write = config->reg_write;
-+      nvmem->cell_post_process = config->cell_post_process;
-       nvmem->keepout = config->keepout;
-       nvmem->nkeepout = config->nkeepout;
-       if (config->of_node)
-@@ -1441,6 +1443,13 @@ static int __nvmem_cell_read(struct nvme
-       if (cell->bit_offset || cell->nbits)
-               nvmem_shift_read_buffer_in_place(cell, buf);
-+      if (nvmem->cell_post_process) {
-+              rc = nvmem->cell_post_process(nvmem->priv, id,
-+                                            cell->offset, buf, cell->bytes);
-+              if (rc)
-+                      return rc;
-+      }
-+
-       if (len)
-               *len = cell->bytes;
---- a/include/linux/nvmem-provider.h
-+++ b/include/linux/nvmem-provider.h
-@@ -19,6 +19,9 @@ typedef int (*nvmem_reg_read_t)(void *pr
-                               void *val, size_t bytes);
- typedef int (*nvmem_reg_write_t)(void *priv, unsigned int offset,
-                                void *val, size_t bytes);
-+/* used for vendor specific post processing of cell data */
-+typedef int (*nvmem_cell_post_process_t)(void *priv, const char *id, unsigned int offset,
-+                                        void *buf, size_t bytes);
- enum nvmem_type {
-       NVMEM_TYPE_UNKNOWN = 0,
-@@ -62,6 +65,7 @@ struct nvmem_keepout {
-  * @no_of_node:       Device should not use the parent's of_node even if it's !NULL.
-  * @reg_read: Callback to read data.
-  * @reg_write:        Callback to write data.
-+ * @cell_post_process:        Callback for vendor specific post processing of cell data
-  * @size:     Device size.
-  * @word_size:        Minimum read/write access granularity.
-  * @stride:   Minimum read/write access stride.
-@@ -92,6 +96,7 @@ struct nvmem_config {
-       bool                    no_of_node;
-       nvmem_reg_read_t        reg_read;
-       nvmem_reg_write_t       reg_write;
-+      nvmem_cell_post_process_t cell_post_process;
-       int     size;
-       int     word_size;
-       int     stride;
diff --git a/target/linux/generic/backport-5.15/802-v5.16-0003-nvmem-imx-ocotp-add-support-for-post-processing.patch b/target/linux/generic/backport-5.15/802-v5.16-0003-nvmem-imx-ocotp-add-support-for-post-processing.patch
deleted file mode 100644 (file)
index ee19228..0000000
+++ /dev/null
@@ -1,92 +0,0 @@
-From d0221a780cbc99fec6c27a98dba2828dc5735c00 Mon Sep 17 00:00:00 2001
-From: Srinivas Kandagatla <[email protected]>
-Date: Wed, 13 Oct 2021 14:19:57 +0100
-Subject: [PATCH] nvmem: imx-ocotp: add support for post processing
-
-Add .cell_post_process callback for imx-ocotp to deal with MAC address,
-since MAC address need to be reversed byte for some i.MX SoCs.
-
-Tested-by: Joakim Zhang <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/imx-ocotp.c | 25 +++++++++++++++++++++++++
- 1 file changed, 25 insertions(+)
-
---- a/drivers/nvmem/imx-ocotp.c
-+++ b/drivers/nvmem/imx-ocotp.c
-@@ -97,6 +97,7 @@ struct ocotp_params {
-       unsigned int bank_address_words;
-       void (*set_timing)(struct ocotp_priv *priv);
-       struct ocotp_ctrl_reg ctrl;
-+      bool reverse_mac_address;
- };
- static int imx_ocotp_wait_for_busy(struct ocotp_priv *priv, u32 flags)
-@@ -221,6 +222,25 @@ read_end:
-       return ret;
- }
-+static int imx_ocotp_cell_pp(void *context, const char *id, unsigned int offset,
-+                           void *data, size_t bytes)
-+{
-+      struct ocotp_priv *priv = context;
-+
-+      /* Deal with some post processing of nvmem cell data */
-+      if (id && !strcmp(id, "mac-address")) {
-+              if (priv->params->reverse_mac_address) {
-+                      u8 *buf = data;
-+                      int i;
-+
-+                      for (i = 0; i < bytes/2; i++)
-+                              swap(buf[i], buf[bytes - i - 1]);
-+              }
-+      }
-+
-+      return 0;
-+}
-+
- static void imx_ocotp_set_imx6_timing(struct ocotp_priv *priv)
- {
-       unsigned long clk_rate;
-@@ -468,6 +488,7 @@ static struct nvmem_config imx_ocotp_nvm
-       .stride = 1,
-       .reg_read = imx_ocotp_read,
-       .reg_write = imx_ocotp_write,
-+      .cell_post_process = imx_ocotp_cell_pp,
- };
- static const struct ocotp_params imx6q_params = {
-@@ -530,6 +551,7 @@ static const struct ocotp_params imx8mq_
-       .bank_address_words = 0,
-       .set_timing = imx_ocotp_set_imx6_timing,
-       .ctrl = IMX_OCOTP_BM_CTRL_DEFAULT,
-+      .reverse_mac_address = true,
- };
- static const struct ocotp_params imx8mm_params = {
-@@ -537,6 +559,7 @@ static const struct ocotp_params imx8mm_
-       .bank_address_words = 0,
-       .set_timing = imx_ocotp_set_imx6_timing,
-       .ctrl = IMX_OCOTP_BM_CTRL_DEFAULT,
-+      .reverse_mac_address = true,
- };
- static const struct ocotp_params imx8mn_params = {
-@@ -544,6 +567,7 @@ static const struct ocotp_params imx8mn_
-       .bank_address_words = 0,
-       .set_timing = imx_ocotp_set_imx6_timing,
-       .ctrl = IMX_OCOTP_BM_CTRL_DEFAULT,
-+      .reverse_mac_address = true,
- };
- static const struct ocotp_params imx8mp_params = {
-@@ -551,6 +575,7 @@ static const struct ocotp_params imx8mp_
-       .bank_address_words = 0,
-       .set_timing = imx_ocotp_set_imx6_timing,
-       .ctrl = IMX_OCOTP_BM_CTRL_8MP,
-+      .reverse_mac_address = true,
- };
- static const struct of_device_id imx_ocotp_dt_ids[] = {
diff --git a/target/linux/generic/backport-5.15/803-v5.17-0002-nvmem-mtk-efuse-support-minimum-one-byte-access-stri.patch b/target/linux/generic/backport-5.15/803-v5.17-0002-nvmem-mtk-efuse-support-minimum-one-byte-access-stri.patch
deleted file mode 100644 (file)
index 785bfe5..0000000
+++ /dev/null
@@ -1,47 +0,0 @@
-From 98e2c4efae214fb7086cac9117616eb6ea11475d Mon Sep 17 00:00:00 2001
-From: Chunfeng Yun <[email protected]>
-Date: Thu, 9 Dec 2021 17:42:34 +0000
-Subject: [PATCH] nvmem: mtk-efuse: support minimum one byte access stride and
- granularity
-
-In order to support nvmem bits property, should support minimum 1 byte
-read stride and minimum 1 byte read granularity at the same time.
-
-Signed-off-by: Chunfeng Yun <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/mtk-efuse.c | 13 +++++++------
- 1 file changed, 7 insertions(+), 6 deletions(-)
-
---- a/drivers/nvmem/mtk-efuse.c
-+++ b/drivers/nvmem/mtk-efuse.c
-@@ -19,11 +19,12 @@ static int mtk_reg_read(void *context,
-                       unsigned int reg, void *_val, size_t bytes)
- {
-       struct mtk_efuse_priv *priv = context;
--      u32 *val = _val;
--      int i = 0, words = bytes / 4;
-+      void __iomem *addr = priv->base + reg;
-+      u8 *val = _val;
-+      int i;
--      while (words--)
--              *val++ = readl(priv->base + reg + (i++ * 4));
-+      for (i = 0; i < bytes; i++, val++)
-+              *val = readb(addr + i);
-       return 0;
- }
-@@ -45,8 +46,8 @@ static int mtk_efuse_probe(struct platfo
-       if (IS_ERR(priv->base))
-               return PTR_ERR(priv->base);
--      econfig.stride = 4;
--      econfig.word_size = 4;
-+      econfig.stride = 1;
-+      econfig.word_size = 1;
-       econfig.reg_read = mtk_reg_read;
-       econfig.size = resource_size(res);
-       econfig.priv = priv;
diff --git a/target/linux/generic/backport-5.15/804-v5.18-0001-nvmem-core-Remove-unused-devm_nvmem_unregister.patch b/target/linux/generic/backport-5.15/804-v5.18-0001-nvmem-core-Remove-unused-devm_nvmem_unregister.patch
deleted file mode 100644 (file)
index ca5357c..0000000
+++ /dev/null
@@ -1,72 +0,0 @@
-From 190fae468592bc2f0efc8b928920f8f712b5831e Mon Sep 17 00:00:00 2001
-From: Andy Shevchenko <[email protected]>
-Date: Sun, 20 Feb 2022 15:15:15 +0000
-Subject: [PATCH] nvmem: core: Remove unused devm_nvmem_unregister()
-
-There are no users and seems no will come of the devm_nvmem_unregister().
-Remove the function and remove the unused devm_nvmem_match() along with it.
-
-Signed-off-by: Andy Shevchenko <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/core.c           | 22 ----------------------
- include/linux/nvmem-provider.h |  8 --------
- 2 files changed, 30 deletions(-)
-
---- a/drivers/nvmem/core.c
-+++ b/drivers/nvmem/core.c
-@@ -943,28 +943,6 @@ struct nvmem_device *devm_nvmem_register
- }
- EXPORT_SYMBOL_GPL(devm_nvmem_register);
--static int devm_nvmem_match(struct device *dev, void *res, void *data)
--{
--      struct nvmem_device **r = res;
--
--      return *r == data;
--}
--
--/**
-- * devm_nvmem_unregister() - Unregister previously registered managed nvmem
-- * device.
-- *
-- * @dev: Device that uses the nvmem device.
-- * @nvmem: Pointer to previously registered nvmem device.
-- *
-- * Return: Will be negative on error or zero on success.
-- */
--int devm_nvmem_unregister(struct device *dev, struct nvmem_device *nvmem)
--{
--      return devres_release(dev, devm_nvmem_release, devm_nvmem_match, nvmem);
--}
--EXPORT_SYMBOL(devm_nvmem_unregister);
--
- static struct nvmem_device *__nvmem_device_get(void *data,
-                       int (*match)(struct device *dev, const void *data))
- {
---- a/include/linux/nvmem-provider.h
-+++ b/include/linux/nvmem-provider.h
-@@ -133,8 +133,6 @@ void nvmem_unregister(struct nvmem_devic
- struct nvmem_device *devm_nvmem_register(struct device *dev,
-                                        const struct nvmem_config *cfg);
--int devm_nvmem_unregister(struct device *dev, struct nvmem_device *nvmem);
--
- void nvmem_add_cell_table(struct nvmem_cell_table *table);
- void nvmem_del_cell_table(struct nvmem_cell_table *table);
-@@ -153,12 +151,6 @@ devm_nvmem_register(struct device *dev,
-       return nvmem_register(c);
- }
--static inline int
--devm_nvmem_unregister(struct device *dev, struct nvmem_device *nvmem)
--{
--      return -EOPNOTSUPP;
--}
--
- static inline void nvmem_add_cell_table(struct nvmem_cell_table *table) {}
- static inline void nvmem_del_cell_table(struct nvmem_cell_table *table) {}
diff --git a/target/linux/generic/backport-5.15/804-v5.18-0002-nvmem-core-Use-devm_add_action_or_reset.patch b/target/linux/generic/backport-5.15/804-v5.18-0002-nvmem-core-Use-devm_add_action_or_reset.patch
deleted file mode 100644 (file)
index b71a0a3..0000000
+++ /dev/null
@@ -1,58 +0,0 @@
-From 5825b2c6762611e67ccaf3ccf64485365a120f0b Mon Sep 17 00:00:00 2001
-From: Andy Shevchenko <[email protected]>
-Date: Sun, 20 Feb 2022 15:15:16 +0000
-Subject: [PATCH] nvmem: core: Use devm_add_action_or_reset()
-
-Slightly simplify the devm_nvmem_register() by using the
-devm_add_action_or_reset().
-
-Signed-off-by: Andy Shevchenko <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/core.c | 22 +++++++++-------------
- 1 file changed, 9 insertions(+), 13 deletions(-)
-
---- a/drivers/nvmem/core.c
-+++ b/drivers/nvmem/core.c
-@@ -905,9 +905,9 @@ void nvmem_unregister(struct nvmem_devic
- }
- EXPORT_SYMBOL_GPL(nvmem_unregister);
--static void devm_nvmem_release(struct device *dev, void *res)
-+static void devm_nvmem_unregister(void *nvmem)
- {
--      nvmem_unregister(*(struct nvmem_device **)res);
-+      nvmem_unregister(nvmem);
- }
- /**
-@@ -924,20 +924,16 @@ static void devm_nvmem_release(struct de
- struct nvmem_device *devm_nvmem_register(struct device *dev,
-                                        const struct nvmem_config *config)
- {
--      struct nvmem_device **ptr, *nvmem;
--
--      ptr = devres_alloc(devm_nvmem_release, sizeof(*ptr), GFP_KERNEL);
--      if (!ptr)
--              return ERR_PTR(-ENOMEM);
-+      struct nvmem_device *nvmem;
-+      int ret;
-       nvmem = nvmem_register(config);
-+      if (IS_ERR(nvmem))
-+              return nvmem;
--      if (!IS_ERR(nvmem)) {
--              *ptr = nvmem;
--              devres_add(dev, ptr);
--      } else {
--              devres_free(ptr);
--      }
-+      ret = devm_add_action_or_reset(dev, devm_nvmem_unregister, nvmem);
-+      if (ret)
-+              return ERR_PTR(ret);
-       return nvmem;
- }
diff --git a/target/linux/generic/backport-5.15/804-v5.18-0003-nvmem-core-Check-input-parameter-for-NULL-in-nvmem_u.patch b/target/linux/generic/backport-5.15/804-v5.18-0003-nvmem-core-Check-input-parameter-for-NULL-in-nvmem_u.patch
deleted file mode 100644 (file)
index 4f471f2..0000000
+++ /dev/null
@@ -1,30 +0,0 @@
-From 8c751e0d9a5264376935a84429a2d468c8877d99 Mon Sep 17 00:00:00 2001
-From: Andy Shevchenko <[email protected]>
-Date: Sun, 20 Feb 2022 15:15:17 +0000
-Subject: [PATCH] nvmem: core: Check input parameter for NULL in
- nvmem_unregister()
-
-nvmem_unregister() frees resources and standard pattern is to allow
-caller to not care if it's NULL or not. This will reduce burden on
-the callers to perform this check.
-
-Signed-off-by: Andy Shevchenko <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/core.c | 3 ++-
- 1 file changed, 2 insertions(+), 1 deletion(-)
-
---- a/drivers/nvmem/core.c
-+++ b/drivers/nvmem/core.c
-@@ -901,7 +901,8 @@ static void nvmem_device_release(struct
-  */
- void nvmem_unregister(struct nvmem_device *nvmem)
- {
--      kref_put(&nvmem->refcnt, nvmem_device_release);
-+      if (nvmem)
-+              kref_put(&nvmem->refcnt, nvmem_device_release);
- }
- EXPORT_SYMBOL_GPL(nvmem_unregister);
diff --git a/target/linux/generic/backport-5.15/804-v5.18-0004-nvmem-qfprom-fix-kerneldoc-warning.patch b/target/linux/generic/backport-5.15/804-v5.18-0004-nvmem-qfprom-fix-kerneldoc-warning.patch
deleted file mode 100644 (file)
index c98f8e9..0000000
+++ /dev/null
@@ -1,29 +0,0 @@
-From 05196facc052385960028ac634447ecf6c764ec3 Mon Sep 17 00:00:00 2001
-From: Srinivas Kandagatla <[email protected]>
-Date: Sun, 20 Feb 2022 15:15:18 +0000
-Subject: [PATCH] nvmem: qfprom: fix kerneldoc warning
-
-This patch fixes below kernel doc warning,
-warning: expecting prototype for qfprom_efuse_reg_write().
-Prototype was for qfprom_reg_write() instead
-
-No code changes.
-
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/qfprom.c | 2 +-
- 1 file changed, 1 insertion(+), 1 deletion(-)
-
---- a/drivers/nvmem/qfprom.c
-+++ b/drivers/nvmem/qfprom.c
-@@ -244,7 +244,7 @@ err_clk_prepared:
- }
- /**
-- * qfprom_efuse_reg_write() - Write to fuses.
-+ * qfprom_reg_write() - Write to fuses.
-  * @context: Our driver data.
-  * @reg:     The offset to write at.
-  * @_val:    Pointer to data to write.
diff --git a/target/linux/generic/backport-5.15/804-v5.18-0005-nvmem-sunxi_sid-Add-support-for-D1-variant.patch b/target/linux/generic/backport-5.15/804-v5.18-0005-nvmem-sunxi_sid-Add-support-for-D1-variant.patch
deleted file mode 100644 (file)
index 6aad6af..0000000
+++ /dev/null
@@ -1,38 +0,0 @@
-From 07ae4fde9efada7878e1383d6ccc7da70315ca23 Mon Sep 17 00:00:00 2001
-From: Samuel Holland <[email protected]>
-Date: Sun, 20 Feb 2022 15:15:20 +0000
-Subject: [PATCH] nvmem: sunxi_sid: Add support for D1 variant
-
-D1 has a smaller eFuse block than some other recent SoCs, and it no
-longer requires a workaround to read the eFuse data.
-
-Signed-off-by: Samuel Holland <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/sunxi_sid.c | 6 ++++++
- 1 file changed, 6 insertions(+)
-
---- a/drivers/nvmem/sunxi_sid.c
-+++ b/drivers/nvmem/sunxi_sid.c
-@@ -184,6 +184,11 @@ static const struct sunxi_sid_cfg sun8i_
-       .need_register_readout = true,
- };
-+static const struct sunxi_sid_cfg sun20i_d1_cfg = {
-+      .value_offset = 0x200,
-+      .size = 0x100,
-+};
-+
- static const struct sunxi_sid_cfg sun50i_a64_cfg = {
-       .value_offset = 0x200,
-       .size = 0x100,
-@@ -200,6 +205,7 @@ static const struct of_device_id sunxi_s
-       { .compatible = "allwinner,sun7i-a20-sid", .data = &sun7i_a20_cfg },
-       { .compatible = "allwinner,sun8i-a83t-sid", .data = &sun50i_a64_cfg },
-       { .compatible = "allwinner,sun8i-h3-sid", .data = &sun8i_h3_cfg },
-+      { .compatible = "allwinner,sun20i-d1-sid", .data = &sun20i_d1_cfg },
-       { .compatible = "allwinner,sun50i-a64-sid", .data = &sun50i_a64_cfg },
-       { .compatible = "allwinner,sun50i-h5-sid", .data = &sun50i_a64_cfg },
-       { .compatible = "allwinner,sun50i-h6-sid", .data = &sun50i_h6_cfg },
diff --git a/target/linux/generic/backport-5.15/804-v5.18-0006-nvmem-meson-mx-efuse-replace-unnecessary-devm_kstrdu.patch b/target/linux/generic/backport-5.15/804-v5.18-0006-nvmem-meson-mx-efuse-replace-unnecessary-devm_kstrdu.patch
deleted file mode 100644 (file)
index a73b42c..0000000
+++ /dev/null
@@ -1,28 +0,0 @@
-From 4dc8d89faed9bb05f116fa1794fc955b14910386 Mon Sep 17 00:00:00 2001
-From: Xiaoke Wang <[email protected]>
-Date: Sun, 20 Feb 2022 15:15:21 +0000
-Subject: [PATCH] nvmem: meson-mx-efuse: replace unnecessary devm_kstrdup()
-
-Replace unnecessary devm_kstrdup() so to avoid redundant memory allocation.
-
-Suggested-by: Martin Blumenstingl <[email protected]>
-Signed-off-by: Xiaoke Wang <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/meson-mx-efuse.c | 3 +--
- 1 file changed, 1 insertion(+), 2 deletions(-)
-
---- a/drivers/nvmem/meson-mx-efuse.c
-+++ b/drivers/nvmem/meson-mx-efuse.c
-@@ -209,8 +209,7 @@ static int meson_mx_efuse_probe(struct p
-       if (IS_ERR(efuse->base))
-               return PTR_ERR(efuse->base);
--      efuse->config.name = devm_kstrdup(&pdev->dev, drvdata->name,
--                                        GFP_KERNEL);
-+      efuse->config.name = drvdata->name;
-       efuse->config.owner = THIS_MODULE;
-       efuse->config.dev = &pdev->dev;
-       efuse->config.priv = efuse;
diff --git a/target/linux/generic/backport-5.15/804-v5.18-0007-nvmem-add-driver-for-Layerscape-SFP-Security-Fuse-Pr.patch b/target/linux/generic/backport-5.15/804-v5.18-0007-nvmem-add-driver-for-Layerscape-SFP-Security-Fuse-Pr.patch
deleted file mode 100644 (file)
index 6afb68b..0000000
+++ /dev/null
@@ -1,139 +0,0 @@
-From f78451012b9e159afdba31c3eb69f223a9f42adc Mon Sep 17 00:00:00 2001
-From: Michael Walle <[email protected]>
-Date: Sun, 20 Feb 2022 15:15:23 +0000
-Subject: [PATCH] nvmem: add driver for Layerscape SFP (Security Fuse
- Processor)
-
-Add support for the Security Fuse Processor found on Layerscape SoCs.
-This driver implements basic read access.
-
-Signed-off-by: Michael Walle <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/Kconfig          | 12 +++++
- drivers/nvmem/Makefile         |  2 +
- drivers/nvmem/layerscape-sfp.c | 89 ++++++++++++++++++++++++++++++++++
- 3 files changed, 103 insertions(+)
- create mode 100644 drivers/nvmem/layerscape-sfp.c
-
---- a/drivers/nvmem/Kconfig
-+++ b/drivers/nvmem/Kconfig
-@@ -300,4 +300,16 @@ config NVMEM_BRCM_NVRAM
-         This driver provides support for Broadcom's NVRAM that can be accessed
-         using I/O mapping.
-+config NVMEM_LAYERSCAPE_SFP
-+      tristate "Layerscape SFP (Security Fuse Processor) support"
-+      depends on ARCH_LAYERSCAPE || COMPILE_TEST
-+      depends on HAS_IOMEM
-+      help
-+        This driver provides support to read the eFuses on Freescale
-+        Layerscape SoC's. For example, the vendor provides a per part
-+        unique ID there.
-+
-+        This driver can also be built as a module. If so, the module
-+        will be called layerscape-sfp.
-+
- endif
---- a/drivers/nvmem/Makefile
-+++ b/drivers/nvmem/Makefile
-@@ -61,3 +61,5 @@ obj-$(CONFIG_NVMEM_RMEM)     += nvmem-rmem.
- nvmem-rmem-y                  := rmem.o
- obj-$(CONFIG_NVMEM_BRCM_NVRAM)        += nvmem_brcm_nvram.o
- nvmem_brcm_nvram-y            := brcm_nvram.o
-+obj-$(CONFIG_NVMEM_LAYERSCAPE_SFP)    += nvmem-layerscape-sfp.o
-+nvmem-layerscape-sfp-y                := layerscape-sfp.o
---- /dev/null
-+++ b/drivers/nvmem/layerscape-sfp.c
-@@ -0,0 +1,89 @@
-+// SPDX-License-Identifier: GPL-2.0-only
-+/*
-+ * Layerscape SFP driver
-+ *
-+ * Copyright (c) 2022 Michael Walle <[email protected]>
-+ *
-+ */
-+
-+#include <linux/device.h>
-+#include <linux/io.h>
-+#include <linux/mod_devicetable.h>
-+#include <linux/module.h>
-+#include <linux/nvmem-provider.h>
-+#include <linux/platform_device.h>
-+#include <linux/property.h>
-+
-+#define LAYERSCAPE_SFP_OTP_OFFSET     0x0200
-+
-+struct layerscape_sfp_priv {
-+      void __iomem *base;
-+};
-+
-+struct layerscape_sfp_data {
-+      int size;
-+};
-+
-+static int layerscape_sfp_read(void *context, unsigned int offset, void *val,
-+                             size_t bytes)
-+{
-+      struct layerscape_sfp_priv *priv = context;
-+
-+      memcpy_fromio(val, priv->base + LAYERSCAPE_SFP_OTP_OFFSET + offset,
-+                    bytes);
-+
-+      return 0;
-+}
-+
-+static struct nvmem_config layerscape_sfp_nvmem_config = {
-+      .name = "fsl-sfp",
-+      .reg_read = layerscape_sfp_read,
-+};
-+
-+static int layerscape_sfp_probe(struct platform_device *pdev)
-+{
-+      const struct layerscape_sfp_data *data;
-+      struct layerscape_sfp_priv *priv;
-+      struct nvmem_device *nvmem;
-+
-+      priv = devm_kzalloc(&pdev->dev, sizeof(*priv), GFP_KERNEL);
-+      if (!priv)
-+              return -ENOMEM;
-+
-+      priv->base = devm_platform_ioremap_resource(pdev, 0);
-+      if (IS_ERR(priv->base))
-+              return PTR_ERR(priv->base);
-+
-+      data = device_get_match_data(&pdev->dev);
-+
-+      layerscape_sfp_nvmem_config.size = data->size;
-+      layerscape_sfp_nvmem_config.dev = &pdev->dev;
-+      layerscape_sfp_nvmem_config.priv = priv;
-+
-+      nvmem = devm_nvmem_register(&pdev->dev, &layerscape_sfp_nvmem_config);
-+
-+      return PTR_ERR_OR_ZERO(nvmem);
-+}
-+
-+static const struct layerscape_sfp_data ls1028a_data = {
-+      .size = 0x88,
-+};
-+
-+static const struct of_device_id layerscape_sfp_dt_ids[] = {
-+      { .compatible = "fsl,ls1028a-sfp", .data = &ls1028a_data },
-+      {},
-+};
-+MODULE_DEVICE_TABLE(of, layerscape_sfp_dt_ids);
-+
-+static struct platform_driver layerscape_sfp_driver = {
-+      .probe  = layerscape_sfp_probe,
-+      .driver = {
-+              .name   = "layerscape_sfp",
-+              .of_match_table = layerscape_sfp_dt_ids,
-+      },
-+};
-+module_platform_driver(layerscape_sfp_driver);
-+
-+MODULE_AUTHOR("Michael Walle <[email protected]>");
-+MODULE_DESCRIPTION("Layerscape Security Fuse Processor driver");
-+MODULE_LICENSE("GPL");
diff --git a/target/linux/generic/backport-5.15/804-v5.18-0008-nvmem-qfprom-Increase-fuse-blow-timeout-to-prevent-w.patch b/target/linux/generic/backport-5.15/804-v5.18-0008-nvmem-qfprom-Increase-fuse-blow-timeout-to-prevent-w.patch
deleted file mode 100644 (file)
index 74bd4a7..0000000
+++ /dev/null
@@ -1,32 +0,0 @@
-From bc5c75e0a5a9400f81a987cc720100ac475fa4d8 Mon Sep 17 00:00:00 2001
-From: Knox Chiou <[email protected]>
-Date: Wed, 23 Feb 2022 22:35:00 +0000
-Subject: [PATCH] nvmem: qfprom: Increase fuse blow timeout to prevent write
- fail
-
-sc7180 blow fuses got slightly chances to hit qfprom_reg_write timeout.
-Current timeout is simply too low. Since blowing fuses is a
-very rare operation, so the risk associated with overestimating this
-number is low.
-Increase fuse blow timeout from 1ms to 10ms.
-
-Reviewed-by: Douglas Anderson <[email protected]>
-Signed-off-by: Knox Chiou <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/qfprom.c | 2 +-
- 1 file changed, 1 insertion(+), 1 deletion(-)
-
---- a/drivers/nvmem/qfprom.c
-+++ b/drivers/nvmem/qfprom.c
-@@ -22,7 +22,7 @@
- /* Amount of time required to hold charge to blow fuse in micro-seconds */
- #define QFPROM_FUSE_BLOW_POLL_US      100
--#define QFPROM_FUSE_BLOW_TIMEOUT_US   1000
-+#define QFPROM_FUSE_BLOW_TIMEOUT_US   10000
- #define QFPROM_BLOW_STATUS_OFFSET     0x048
- #define QFPROM_BLOW_STATUS_BUSY               0x1
diff --git a/target/linux/generic/backport-5.15/804-v5.18-0009-nvmem-Add-driver-for-OCOTP-in-Sunplus-SP7021.patch b/target/linux/generic/backport-5.15/804-v5.18-0009-nvmem-Add-driver-for-OCOTP-in-Sunplus-SP7021.patch
deleted file mode 100644 (file)
index ac77fc9..0000000
+++ /dev/null
@@ -1,291 +0,0 @@
-From 8747ec2e9762ed9ae53b3a590938f454b6a1abdf Mon Sep 17 00:00:00 2001
-From: Vincent Shih <[email protected]>
-Date: Wed, 23 Feb 2022 22:35:01 +0000
-Subject: [PATCH] nvmem: Add driver for OCOTP in Sunplus SP7021
-
-Add driver for OCOTP in Sunplus SP7021
-
-Signed-off-by: Vincent Shih <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- MAINTAINERS                   |   5 +
- drivers/nvmem/Kconfig         |  12 ++
- drivers/nvmem/Makefile        |   2 +
- drivers/nvmem/sunplus-ocotp.c | 228 ++++++++++++++++++++++++++++++++++
- 4 files changed, 247 insertions(+)
- create mode 100644 drivers/nvmem/sunplus-ocotp.c
-
---- a/MAINTAINERS
-+++ b/MAINTAINERS
-@@ -17966,6 +17966,11 @@ L:    [email protected]
- S:    Maintained
- F:    drivers/net/ethernet/dlink/sundance.c
-+SUNPLUS OCOTP DRIVER
-+M:    Vincent Shih <[email protected]>
-+S:    Maintained
-+F:    drivers/nvmem/sunplus-ocotp.c
-+
- SUPERH
- M:    Yoshinori Sato <[email protected]>
- M:    Rich Felker <[email protected]>
---- a/drivers/nvmem/Kconfig
-+++ b/drivers/nvmem/Kconfig
-@@ -312,4 +312,16 @@ config NVMEM_LAYERSCAPE_SFP
-         This driver can also be built as a module. If so, the module
-         will be called layerscape-sfp.
-+config NVMEM_SUNPLUS_OCOTP
-+      tristate "Sunplus SoC OTP support"
-+      depends on SOC_SP7021 || COMPILE_TEST
-+      depends on HAS_IOMEM
-+      help
-+        This is a driver for the On-chip OTP controller (OCOTP) available
-+        on Sunplus SoCs. It provides access to 128 bytes of one-time
-+        programmable eFuse.
-+
-+        This driver can also be built as a module. If so, the module
-+        will be called nvmem-sunplus-ocotp.
-+
- endif
---- a/drivers/nvmem/Makefile
-+++ b/drivers/nvmem/Makefile
-@@ -63,3 +63,5 @@ obj-$(CONFIG_NVMEM_BRCM_NVRAM)       += nvmem_
- nvmem_brcm_nvram-y            := brcm_nvram.o
- obj-$(CONFIG_NVMEM_LAYERSCAPE_SFP)    += nvmem-layerscape-sfp.o
- nvmem-layerscape-sfp-y                := layerscape-sfp.o
-+obj-$(CONFIG_NVMEM_SUNPLUS_OCOTP)     += nvmem_sunplus_ocotp.o
-+nvmem_sunplus_ocotp-y         := sunplus-ocotp.o
---- /dev/null
-+++ b/drivers/nvmem/sunplus-ocotp.c
-@@ -0,0 +1,228 @@
-+// SPDX-License-Identifier: GPL-2.0
-+
-+/*
-+ * The OCOTP driver for Sunplus       SP7021
-+ *
-+ * Copyright (C) 2019 Sunplus Technology Inc., All rights reserved.
-+ */
-+
-+#include <linux/bitfield.h>
-+#include <linux/clk.h>
-+#include <linux/delay.h>
-+#include <linux/device.h>
-+#include <linux/io.h>
-+#include <linux/iopoll.h>
-+#include <linux/module.h>
-+#include <linux/nvmem-provider.h>
-+#include <linux/of_device.h>
-+#include <linux/platform_device.h>
-+
-+/*
-+ * OTP memory
-+ * Each bank contains 4 words (32 bits).
-+ * Bank 0 starts at offset 0 from the base.
-+ */
-+
-+#define OTP_WORDS_PER_BANK            4
-+#define OTP_WORD_SIZE                 sizeof(u32)
-+#define OTP_BIT_ADDR_OF_BANK          (8 * OTP_WORD_SIZE * OTP_WORDS_PER_BANK)
-+#define QAC628_OTP_NUM_BANKS          8
-+#define QAC628_OTP_SIZE                       (QAC628_OTP_NUM_BANKS * OTP_WORDS_PER_BANK * OTP_WORD_SIZE)
-+#define OTP_READ_TIMEOUT_US           200000
-+
-+/* HB_GPIO */
-+#define ADDRESS_8_DATA                        0x20
-+
-+/* OTP_RX */
-+#define OTP_CONTROL_2                 0x48
-+#define OTP_RD_PERIOD                 GENMASK(15, 8)
-+#define OTP_RD_PERIOD_MASK            ~GENMASK(15, 8)
-+#define CPU_CLOCK                     FIELD_PREP(OTP_RD_PERIOD, 30)
-+#define SEL_BAK_KEY2                  BIT(5)
-+#define SEL_BAK_KEY2_MASK             ~BIT(5)
-+#define SW_TRIM_EN                    BIT(4)
-+#define SW_TRIM_EN_MASK                       ~BIT(4)
-+#define SEL_BAK_KEY                   BIT(3)
-+#define SEL_BAK_KEY_MASK              ~BIT(3)
-+#define OTP_READ                      BIT(2)
-+#define OTP_LOAD_SECURE_DATA          BIT(1)
-+#define OTP_LOAD_SECURE_DATA_MASK     ~BIT(1)
-+#define OTP_DO_CRC                    BIT(0)
-+#define OTP_DO_CRC_MASK                       ~BIT(0)
-+#define OTP_STATUS                    0x4c
-+#define OTP_READ_DONE                 BIT(4)
-+#define OTP_READ_DONE_MASK            ~BIT(4)
-+#define OTP_LOAD_SECURE_DONE_MASK     ~BIT(2)
-+#define OTP_READ_ADDRESS              0x50
-+
-+enum base_type {
-+      HB_GPIO,
-+      OTPRX,
-+      BASEMAX,
-+};
-+
-+struct sp_ocotp_priv {
-+      struct device *dev;
-+      void __iomem *base[BASEMAX];
-+      struct clk *clk;
-+};
-+
-+struct sp_ocotp_data {
-+      int size;
-+};
-+
-+const struct sp_ocotp_data  sp_otp_v0 = {
-+      .size = QAC628_OTP_SIZE,
-+};
-+
-+static int sp_otp_read_real(struct sp_ocotp_priv *otp, int addr, char *value)
-+{
-+      unsigned int addr_data;
-+      unsigned int byte_shift;
-+      unsigned int status;
-+      int ret;
-+
-+      addr_data = addr % (OTP_WORD_SIZE * OTP_WORDS_PER_BANK);
-+      addr_data = addr_data / OTP_WORD_SIZE;
-+
-+      byte_shift = addr % (OTP_WORD_SIZE * OTP_WORDS_PER_BANK);
-+      byte_shift = byte_shift % OTP_WORD_SIZE;
-+
-+      addr = addr / (OTP_WORD_SIZE * OTP_WORDS_PER_BANK);
-+      addr = addr * OTP_BIT_ADDR_OF_BANK;
-+
-+      writel(readl(otp->base[OTPRX] + OTP_STATUS) & OTP_READ_DONE_MASK &
-+             OTP_LOAD_SECURE_DONE_MASK, otp->base[OTPRX] + OTP_STATUS);
-+      writel(addr, otp->base[OTPRX] + OTP_READ_ADDRESS);
-+      writel(readl(otp->base[OTPRX] + OTP_CONTROL_2) | OTP_READ,
-+             otp->base[OTPRX] + OTP_CONTROL_2);
-+      writel(readl(otp->base[OTPRX] + OTP_CONTROL_2) & SEL_BAK_KEY2_MASK & SW_TRIM_EN_MASK
-+             & SEL_BAK_KEY_MASK & OTP_LOAD_SECURE_DATA_MASK & OTP_DO_CRC_MASK,
-+             otp->base[OTPRX] + OTP_CONTROL_2);
-+      writel((readl(otp->base[OTPRX] + OTP_CONTROL_2) & OTP_RD_PERIOD_MASK) | CPU_CLOCK,
-+             otp->base[OTPRX] + OTP_CONTROL_2);
-+
-+      ret = readl_poll_timeout(otp->base[OTPRX] + OTP_STATUS, status,
-+                               status & OTP_READ_DONE, 10, OTP_READ_TIMEOUT_US);
-+
-+      if (ret < 0)
-+              return ret;
-+
-+      *value = (readl(otp->base[HB_GPIO] + ADDRESS_8_DATA + addr_data * OTP_WORD_SIZE)
-+                >> (8 * byte_shift)) & 0xff;
-+
-+      return ret;
-+}
-+
-+static int sp_ocotp_read(void *priv, unsigned int offset, void *value, size_t bytes)
-+{
-+      struct sp_ocotp_priv *otp = priv;
-+      unsigned int addr;
-+      char *buf = value;
-+      char val[4];
-+      int ret;
-+
-+      ret = clk_enable(otp->clk);
-+      if (ret)
-+              return ret;
-+
-+      *buf = 0;
-+      for (addr = offset; addr < (offset + bytes); addr++) {
-+              ret = sp_otp_read_real(otp, addr, val);
-+              if (ret < 0) {
-+                      dev_err(otp->dev, "OTP read fail:%d at %d", ret, addr);
-+                      goto disable_clk;
-+              }
-+
-+              *buf++ = *val;
-+      }
-+
-+disable_clk:
-+      clk_disable(otp->clk);
-+
-+      return ret;
-+}
-+
-+static struct nvmem_config sp_ocotp_nvmem_config = {
-+      .name = "sp-ocotp",
-+      .read_only = true,
-+      .word_size = 1,
-+      .size = QAC628_OTP_SIZE,
-+      .stride = 1,
-+      .reg_read = sp_ocotp_read,
-+      .owner = THIS_MODULE,
-+};
-+
-+static int sp_ocotp_probe(struct platform_device *pdev)
-+{
-+      struct device *dev = &pdev->dev;
-+      struct nvmem_device *nvmem;
-+      struct sp_ocotp_priv *otp;
-+      struct resource *res;
-+      int ret;
-+
-+      otp = devm_kzalloc(dev, sizeof(*otp), GFP_KERNEL);
-+      if (!otp)
-+              return -ENOMEM;
-+
-+      otp->dev = dev;
-+
-+      res = platform_get_resource_byname(pdev, IORESOURCE_MEM, "hb_gpio");
-+      otp->base[HB_GPIO] = devm_ioremap_resource(dev, res);
-+      if (IS_ERR(otp->base[HB_GPIO]))
-+              return PTR_ERR(otp->base[HB_GPIO]);
-+
-+      res = platform_get_resource_byname(pdev, IORESOURCE_MEM, "otprx");
-+      otp->base[OTPRX] = devm_ioremap_resource(dev, res);
-+      if (IS_ERR(otp->base[OTPRX]))
-+              return PTR_ERR(otp->base[OTPRX]);
-+
-+      otp->clk = devm_clk_get(&pdev->dev, NULL);
-+      if (IS_ERR(otp->clk))
-+              return dev_err_probe(&pdev->dev, PTR_ERR(otp->clk),
-+                                              "devm_clk_get fail\n");
-+
-+      ret = clk_prepare(otp->clk);
-+      if (ret < 0) {
-+              dev_err(dev, "failed to prepare clk: %d\n", ret);
-+              return ret;
-+      }
-+
-+      sp_ocotp_nvmem_config.priv = otp;
-+      sp_ocotp_nvmem_config.dev = dev;
-+
-+      nvmem = devm_nvmem_register(dev, &sp_ocotp_nvmem_config);
-+      if (IS_ERR(nvmem))
-+              return dev_err_probe(&pdev->dev, PTR_ERR(nvmem),
-+                                              "register nvmem device fail\n");
-+
-+      platform_set_drvdata(pdev, nvmem);
-+
-+      dev_dbg(dev, "banks:%d x wpb:%d x wsize:%d = %d",
-+              (int)QAC628_OTP_NUM_BANKS, (int)OTP_WORDS_PER_BANK,
-+              (int)OTP_WORD_SIZE, (int)QAC628_OTP_SIZE);
-+
-+      dev_info(dev, "by Sunplus (C) 2020");
-+
-+      return 0;
-+}
-+
-+static const struct of_device_id sp_ocotp_dt_ids[] = {
-+      { .compatible = "sunplus,sp7021-ocotp", .data = &sp_otp_v0 },
-+      { }
-+};
-+MODULE_DEVICE_TABLE(of, sp_ocotp_dt_ids);
-+
-+static struct platform_driver sp_otp_driver = {
-+      .probe     = sp_ocotp_probe,
-+      .driver    = {
-+              .name           = "sunplus,sp7021-ocotp",
-+              .of_match_table = sp_ocotp_dt_ids,
-+      }
-+};
-+module_platform_driver(sp_otp_driver);
-+
-+MODULE_AUTHOR("Vincent Shih <[email protected]>");
-+MODULE_DESCRIPTION("Sunplus On-Chip OTP driver");
-+MODULE_LICENSE("GPL");
-+
diff --git a/target/linux/generic/backport-5.15/804-v5.18-0010-nvmem-brcm_nvram-parse-NVRAM-content-into-NVMEM-cell.patch b/target/linux/generic/backport-5.15/804-v5.18-0010-nvmem-brcm_nvram-parse-NVRAM-content-into-NVMEM-cell.patch
deleted file mode 100644 (file)
index 99781b3..0000000
+++ /dev/null
@@ -1,146 +0,0 @@
-From 6e977eaa8280e957b87904b536661550f2a6b3e8 Mon Sep 17 00:00:00 2001
-From: =?UTF-8?q?Rafa=C5=82=20Mi=C5=82ecki?= <[email protected]>
-Date: Fri, 25 Feb 2022 17:58:20 +0000
-Subject: [PATCH] nvmem: brcm_nvram: parse NVRAM content into NVMEM cells
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-NVRAM consist of header and NUL separated key-value pairs. Parse it and
-create NVMEM cell for every key-value entry.
-
-Signed-off-by: Rafał Miłecki <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/brcm_nvram.c | 90 ++++++++++++++++++++++++++++++++++++++
- 1 file changed, 90 insertions(+)
-
---- a/drivers/nvmem/brcm_nvram.c
-+++ b/drivers/nvmem/brcm_nvram.c
-@@ -6,12 +6,26 @@
- #include <linux/io.h>
- #include <linux/mod_devicetable.h>
- #include <linux/module.h>
-+#include <linux/nvmem-consumer.h>
- #include <linux/nvmem-provider.h>
- #include <linux/platform_device.h>
-+#include <linux/slab.h>
-+
-+#define NVRAM_MAGIC                   "FLSH"
- struct brcm_nvram {
-       struct device *dev;
-       void __iomem *base;
-+      struct nvmem_cell_info *cells;
-+      int ncells;
-+};
-+
-+struct brcm_nvram_header {
-+      char magic[4];
-+      __le32 len;
-+      __le32 crc_ver_init;    /* 0:7 crc, 8:15 ver, 16:31 sdram_init */
-+      __le32 config_refresh;  /* 0:15 sdram_config, 16:31 sdram_refresh */
-+      __le32 config_ncdl;     /* ncdl values for memc */
- };
- static int brcm_nvram_read(void *context, unsigned int offset, void *val,
-@@ -26,6 +40,75 @@ static int brcm_nvram_read(void *context
-       return 0;
- }
-+static int brcm_nvram_add_cells(struct brcm_nvram *priv, uint8_t *data,
-+                              size_t len)
-+{
-+      struct device *dev = priv->dev;
-+      char *var, *value, *eq;
-+      int idx;
-+
-+      priv->ncells = 0;
-+      for (var = data + sizeof(struct brcm_nvram_header);
-+           var < (char *)data + len && *var;
-+           var += strlen(var) + 1) {
-+              priv->ncells++;
-+      }
-+
-+      priv->cells = devm_kcalloc(dev, priv->ncells, sizeof(*priv->cells), GFP_KERNEL);
-+      if (!priv->cells)
-+              return -ENOMEM;
-+
-+      for (var = data + sizeof(struct brcm_nvram_header), idx = 0;
-+           var < (char *)data + len && *var;
-+           var = value + strlen(value) + 1, idx++) {
-+              eq = strchr(var, '=');
-+              if (!eq)
-+                      break;
-+              *eq = '\0';
-+              value = eq + 1;
-+
-+              priv->cells[idx].name = devm_kstrdup(dev, var, GFP_KERNEL);
-+              if (!priv->cells[idx].name)
-+                      return -ENOMEM;
-+              priv->cells[idx].offset = value - (char *)data;
-+              priv->cells[idx].bytes = strlen(value);
-+      }
-+
-+      return 0;
-+}
-+
-+static int brcm_nvram_parse(struct brcm_nvram *priv)
-+{
-+      struct device *dev = priv->dev;
-+      struct brcm_nvram_header header;
-+      uint8_t *data;
-+      size_t len;
-+      int err;
-+
-+      memcpy_fromio(&header, priv->base, sizeof(header));
-+
-+      if (memcmp(header.magic, NVRAM_MAGIC, 4)) {
-+              dev_err(dev, "Invalid NVRAM magic\n");
-+              return -EINVAL;
-+      }
-+
-+      len = le32_to_cpu(header.len);
-+
-+      data = kcalloc(1, len, GFP_KERNEL);
-+      memcpy_fromio(data, priv->base, len);
-+      data[len - 1] = '\0';
-+
-+      err = brcm_nvram_add_cells(priv, data, len);
-+      if (err) {
-+              dev_err(dev, "Failed to add cells: %d\n", err);
-+              return err;
-+      }
-+
-+      kfree(data);
-+
-+      return 0;
-+}
-+
- static int brcm_nvram_probe(struct platform_device *pdev)
- {
-       struct nvmem_config config = {
-@@ -35,6 +118,7 @@ static int brcm_nvram_probe(struct platf
-       struct device *dev = &pdev->dev;
-       struct resource *res;
-       struct brcm_nvram *priv;
-+      int err;
-       priv = devm_kzalloc(dev, sizeof(*priv), GFP_KERNEL);
-       if (!priv)
-@@ -46,7 +130,13 @@ static int brcm_nvram_probe(struct platf
-       if (IS_ERR(priv->base))
-               return PTR_ERR(priv->base);
-+      err = brcm_nvram_parse(priv);
-+      if (err)
-+              return err;
-+
-       config.dev = dev;
-+      config.cells = priv->cells;
-+      config.ncells = priv->ncells;
-       config.priv = priv;
-       config.size = resource_size(res);
diff --git a/target/linux/generic/backport-5.15/805-v5.19-0001-nvmem-bcm-ocotp-mark-ACPI-device-ID-table-as-maybe-u.patch b/target/linux/generic/backport-5.15/805-v5.19-0001-nvmem-bcm-ocotp-mark-ACPI-device-ID-table-as-maybe-u.patch
deleted file mode 100644 (file)
index ef3107d..0000000
+++ /dev/null
@@ -1,32 +0,0 @@
-From 6bd0ffeaa389866089e9573b2298ae58d6359b75 Mon Sep 17 00:00:00 2001
-From: Krzysztof Kozlowski <[email protected]>
-Date: Mon, 21 Mar 2022 12:03:24 +0100
-Subject: [PATCH] nvmem: bcm-ocotp: mark ACPI device ID table as maybe unused
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-"bcm_otpc_acpi_ids" is used with ACPI_PTR, so a build with !CONFIG_ACPI
-has a warning:
-
-  drivers/nvmem/bcm-ocotp.c:247:36: error:
-    ‘bcm_otpc_acpi_ids’ defined but not used [-Werror=unused-const-variable=]
-
-Signed-off-by: Krzysztof Kozlowski <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/bcm-ocotp.c | 2 +-
- 1 file changed, 1 insertion(+), 1 deletion(-)
-
---- a/drivers/nvmem/bcm-ocotp.c
-+++ b/drivers/nvmem/bcm-ocotp.c
-@@ -244,7 +244,7 @@ static const struct of_device_id bcm_otp
- };
- MODULE_DEVICE_TABLE(of, bcm_otpc_dt_ids);
--static const struct acpi_device_id bcm_otpc_acpi_ids[] = {
-+static const struct acpi_device_id bcm_otpc_acpi_ids[] __maybe_unused = {
-       { .id = "BRCM0700", .driver_data = (kernel_ulong_t)&otp_map },
-       { .id = "BRCM0701", .driver_data = (kernel_ulong_t)&otp_map_v2 },
-       { /* sentinel */ }
diff --git a/target/linux/generic/backport-5.15/805-v5.19-0002-nvmem-sunplus-ocotp-staticize-sp_otp_v0.patch b/target/linux/generic/backport-5.15/805-v5.19-0002-nvmem-sunplus-ocotp-staticize-sp_otp_v0.patch
deleted file mode 100644 (file)
index a84d231..0000000
+++ /dev/null
@@ -1,30 +0,0 @@
-From 1066f8156351fcd997125257cea47cf805ba4f6d Mon Sep 17 00:00:00 2001
-From: Krzysztof Kozlowski <[email protected]>
-Date: Mon, 21 Mar 2022 12:03:25 +0100
-Subject: [PATCH] nvmem: sunplus-ocotp: staticize sp_otp_v0
-
-The "sp_otp_v0" file scope variable is not used outside, so make it
-static to fix warning:
-
-  drivers/nvmem/sunplus-ocotp.c:74:29: sparse:
-    sparse: symbol 'sp_otp_v0' was not declared. Should it be static?
-
-Reported-by: kernel test robot <[email protected]>
-Signed-off-by: Krzysztof Kozlowski <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/sunplus-ocotp.c | 2 +-
- 1 file changed, 1 insertion(+), 1 deletion(-)
-
---- a/drivers/nvmem/sunplus-ocotp.c
-+++ b/drivers/nvmem/sunplus-ocotp.c
-@@ -71,7 +71,7 @@ struct sp_ocotp_data {
-       int size;
- };
--const struct sp_ocotp_data  sp_otp_v0 = {
-+static const struct sp_ocotp_data sp_otp_v0 = {
-       .size = QAC628_OTP_SIZE,
- };
diff --git a/target/linux/generic/backport-5.15/805-v5.19-0003-nvmem-sunplus-ocotp-drop-useless-probe-confirmation.patch b/target/linux/generic/backport-5.15/805-v5.19-0003-nvmem-sunplus-ocotp-drop-useless-probe-confirmation.patch
deleted file mode 100644 (file)
index 886ebc1..0000000
+++ /dev/null
@@ -1,27 +0,0 @@
-From 874dfbcf219ccc42a2cbd187d087c7db82c3024b Mon Sep 17 00:00:00 2001
-From: Krzysztof Kozlowski <[email protected]>
-Date: Mon, 21 Mar 2022 12:03:26 +0100
-Subject: [PATCH] nvmem: sunplus-ocotp: drop useless probe confirmation
-
-Printing probe success is discouraged, because we can use tracing for
-this purpose.  Remove useless print message after Sunplus OCOTP driver
-probe.
-
-Signed-off-by: Krzysztof Kozlowski <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/sunplus-ocotp.c | 2 --
- 1 file changed, 2 deletions(-)
-
---- a/drivers/nvmem/sunplus-ocotp.c
-+++ b/drivers/nvmem/sunplus-ocotp.c
-@@ -202,8 +202,6 @@ static int sp_ocotp_probe(struct platfor
-               (int)QAC628_OTP_NUM_BANKS, (int)OTP_WORDS_PER_BANK,
-               (int)OTP_WORD_SIZE, (int)QAC628_OTP_SIZE);
--      dev_info(dev, "by Sunplus (C) 2020");
--
-       return 0;
- }
diff --git a/target/linux/generic/backport-5.15/805-v5.19-0004-nvmem-core-support-passing-DT-node-in-cell-info.patch b/target/linux/generic/backport-5.15/805-v5.19-0004-nvmem-core-support-passing-DT-node-in-cell-info.patch
deleted file mode 100644 (file)
index 3b1e761..0000000
+++ /dev/null
@@ -1,41 +0,0 @@
-From dbc2f62061c6bfba0aee93161ee3194dcee84bd0 Mon Sep 17 00:00:00 2001
-From: =?UTF-8?q?Rafa=C5=82=20Mi=C5=82ecki?= <[email protected]>
-Date: Fri, 29 Apr 2022 17:26:46 +0100
-Subject: [PATCH] nvmem: core: support passing DT node in cell info
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-Some hardware may have NVMEM cells described in Device Tree using
-individual nodes. Let drivers pass such nodes to the NVMEM subsystem so
-they can be later used by NVMEM consumers.
-
-Signed-off-by: Rafał Miłecki <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/core.c           | 1 +
- include/linux/nvmem-consumer.h | 1 +
- 2 files changed, 2 insertions(+)
-
---- a/drivers/nvmem/core.c
-+++ b/drivers/nvmem/core.c
-@@ -467,6 +467,7 @@ static int nvmem_cell_info_to_nvmem_cell
-       cell->bit_offset = info->bit_offset;
-       cell->nbits = info->nbits;
-+      cell->np = info->np;
-       if (cell->nbits)
-               cell->bytes = DIV_ROUND_UP(cell->nbits + cell->bit_offset,
---- a/include/linux/nvmem-consumer.h
-+++ b/include/linux/nvmem-consumer.h
-@@ -25,6 +25,7 @@ struct nvmem_cell_info {
-       unsigned int            bytes;
-       unsigned int            bit_offset;
-       unsigned int            nbits;
-+      struct device_node      *np;
- };
- /**
diff --git a/target/linux/generic/backport-5.15/805-v5.19-0005-nvmem-brcm_nvram-find-Device-Tree-nodes-for-NVMEM-ce.patch b/target/linux/generic/backport-5.15/805-v5.19-0005-nvmem-brcm_nvram-find-Device-Tree-nodes-for-NVMEM-ce.patch
deleted file mode 100644 (file)
index a9eacd9..0000000
+++ /dev/null
@@ -1,38 +0,0 @@
-From 207775f7e17b8fd0426a2ac4a5b81e4e1d71849e Mon Sep 17 00:00:00 2001
-From: =?UTF-8?q?Rafa=C5=82=20Mi=C5=82ecki?= <[email protected]>
-Date: Fri, 29 Apr 2022 17:26:47 +0100
-Subject: [PATCH] nvmem: brcm_nvram: find Device Tree nodes for NVMEM cells
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-DT binding for Broadcom's NVRAM supports specifying NVMEM cells as NVMEM
-device (provider) subnodes. Look for such subnodes when collecing NVMEM
-cells. This allows NVMEM consumers to use NVRAM variables.
-
-Signed-off-by: Rafał Miłecki <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/brcm_nvram.c | 2 ++
- 1 file changed, 2 insertions(+)
-
---- a/drivers/nvmem/brcm_nvram.c
-+++ b/drivers/nvmem/brcm_nvram.c
-@@ -8,6 +8,7 @@
- #include <linux/module.h>
- #include <linux/nvmem-consumer.h>
- #include <linux/nvmem-provider.h>
-+#include <linux/of.h>
- #include <linux/platform_device.h>
- #include <linux/slab.h>
-@@ -72,6 +73,7 @@ static int brcm_nvram_add_cells(struct b
-                       return -ENOMEM;
-               priv->cells[idx].offset = value - (char *)data;
-               priv->cells[idx].bytes = strlen(value);
-+              priv->cells[idx].np = of_get_child_by_name(dev->of_node, priv->cells[idx].name);
-       }
-       return 0;
diff --git a/target/linux/generic/backport-5.15/805-v5.19-0006-nvmem-Add-Apple-eFuse-driver.patch b/target/linux/generic/backport-5.15/805-v5.19-0006-nvmem-Add-Apple-eFuse-driver.patch
deleted file mode 100644 (file)
index ebeb6f5..0000000
+++ /dev/null
@@ -1,130 +0,0 @@
-From b6b7ef932ae838209254f016ecf8862d716a5ced Mon Sep 17 00:00:00 2001
-From: Sven Peter <[email protected]>
-Date: Fri, 29 Apr 2022 17:26:50 +0100
-Subject: [PATCH] nvmem: Add Apple eFuse driver
-
-Apple SoCs contain eFuses used to store factory-programmed data such
-as calibration values for the PCIe or the Type-C PHY. They are organized
-as 32bit values exposed as MMIO.
-
-Signed-off-by: Sven Peter <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/Kconfig        | 12 ++++++
- drivers/nvmem/Makefile       |  2 +
- drivers/nvmem/apple-efuses.c | 80 ++++++++++++++++++++++++++++++++++++
- 3 files changed, 94 insertions(+)
- create mode 100644 drivers/nvmem/apple-efuses.c
-
---- a/drivers/nvmem/Kconfig
-+++ b/drivers/nvmem/Kconfig
-@@ -324,4 +324,16 @@ config NVMEM_SUNPLUS_OCOTP
-         This driver can also be built as a module. If so, the module
-         will be called nvmem-sunplus-ocotp.
-+config NVMEM_APPLE_EFUSES
-+      tristate "Apple eFuse support"
-+      depends on ARCH_APPLE || COMPILE_TEST
-+      default ARCH_APPLE
-+      help
-+        Say y here to enable support for reading eFuses on Apple SoCs
-+        such as the M1. These are e.g. used to store factory programmed
-+        calibration data required for the PCIe or the USB-C PHY.
-+
-+        This driver can also be built as a module. If so, the module will
-+        be called nvmem-apple-efuses.
-+
- endif
---- a/drivers/nvmem/Makefile
-+++ b/drivers/nvmem/Makefile
-@@ -65,3 +65,5 @@ obj-$(CONFIG_NVMEM_LAYERSCAPE_SFP)   += nv
- nvmem-layerscape-sfp-y                := layerscape-sfp.o
- obj-$(CONFIG_NVMEM_SUNPLUS_OCOTP)     += nvmem_sunplus_ocotp.o
- nvmem_sunplus_ocotp-y         := sunplus-ocotp.o
-+obj-$(CONFIG_NVMEM_APPLE_EFUSES)      += nvmem-apple-efuses.o
-+nvmem-apple-efuses-y          := apple-efuses.o
---- /dev/null
-+++ b/drivers/nvmem/apple-efuses.c
-@@ -0,0 +1,80 @@
-+// SPDX-License-Identifier: GPL-2.0-only
-+/*
-+ * Apple SoC eFuse driver
-+ *
-+ * Copyright (C) The Asahi Linux Contributors
-+ */
-+
-+#include <linux/io.h>
-+#include <linux/mod_devicetable.h>
-+#include <linux/module.h>
-+#include <linux/nvmem-provider.h>
-+#include <linux/platform_device.h>
-+
-+struct apple_efuses_priv {
-+      void __iomem *fuses;
-+};
-+
-+static int apple_efuses_read(void *context, unsigned int offset, void *val,
-+                           size_t bytes)
-+{
-+      struct apple_efuses_priv *priv = context;
-+      u32 *dst = val;
-+
-+      while (bytes >= sizeof(u32)) {
-+              *dst++ = readl_relaxed(priv->fuses + offset);
-+              bytes -= sizeof(u32);
-+              offset += sizeof(u32);
-+      }
-+
-+      return 0;
-+}
-+
-+static int apple_efuses_probe(struct platform_device *pdev)
-+{
-+      struct apple_efuses_priv *priv;
-+      struct resource *res;
-+      struct nvmem_config config = {
-+              .dev = &pdev->dev,
-+              .read_only = true,
-+              .reg_read = apple_efuses_read,
-+              .stride = sizeof(u32),
-+              .word_size = sizeof(u32),
-+              .name = "apple_efuses_nvmem",
-+              .id = NVMEM_DEVID_AUTO,
-+              .root_only = true,
-+      };
-+
-+      priv = devm_kzalloc(config.dev, sizeof(*priv), GFP_KERNEL);
-+      if (!priv)
-+              return -ENOMEM;
-+
-+      priv->fuses = devm_platform_get_and_ioremap_resource(pdev, 0, &res);
-+      if (IS_ERR(priv->fuses))
-+              return PTR_ERR(priv->fuses);
-+
-+      config.priv = priv;
-+      config.size = resource_size(res);
-+
-+      return PTR_ERR_OR_ZERO(devm_nvmem_register(config.dev, &config));
-+}
-+
-+static const struct of_device_id apple_efuses_of_match[] = {
-+      { .compatible = "apple,efuses", },
-+      {}
-+};
-+
-+MODULE_DEVICE_TABLE(of, apple_efuses_of_match);
-+
-+static struct platform_driver apple_efuses_driver = {
-+      .driver = {
-+              .name = "apple_efuses",
-+              .of_match_table = apple_efuses_of_match,
-+      },
-+      .probe = apple_efuses_probe,
-+};
-+
-+module_platform_driver(apple_efuses_driver);
-+
-+MODULE_AUTHOR("Sven Peter <[email protected]>");
-+MODULE_LICENSE("GPL");
diff --git a/target/linux/generic/backport-5.15/805-v5.19-0007-nvmem-qfprom-using-pm_runtime_resume_and_get-instead.patch b/target/linux/generic/backport-5.15/805-v5.19-0007-nvmem-qfprom-using-pm_runtime_resume_and_get-instead.patch
deleted file mode 100644 (file)
index cd51d97..0000000
+++ /dev/null
@@ -1,31 +0,0 @@
-From 517f6e2641a2802dce5a5aa0d18c7d37a35678d2 Mon Sep 17 00:00:00 2001
-From: Minghao Chi <[email protected]>
-Date: Fri, 29 Apr 2022 17:26:54 +0100
-Subject: [PATCH] nvmem: qfprom: using pm_runtime_resume_and_get instead of
- pm_runtime_get_sync
-
-Using pm_runtime_resume_and_get is more appropriate
-for simplifing code
-
-Reported-by: Zeal Robot <[email protected]>
-Signed-off-by: Minghao Chi <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/qfprom.c | 3 +--
- 1 file changed, 1 insertion(+), 2 deletions(-)
-
---- a/drivers/nvmem/qfprom.c
-+++ b/drivers/nvmem/qfprom.c
-@@ -217,9 +217,8 @@ static int qfprom_enable_fuse_blowing(co
-               goto err_clk_rate_set;
-       }
--      ret = pm_runtime_get_sync(priv->dev);
-+      ret = pm_runtime_resume_and_get(priv->dev);
-       if (ret < 0) {
--              pm_runtime_put_noidle(priv->dev);
-               dev_err(priv->dev, "Failed to enable power-domain\n");
-               goto err_reg_enable;
-       }
diff --git a/target/linux/generic/backport-5.15/805-v5.19-0008-nvmem-sfp-Use-regmap.patch b/target/linux/generic/backport-5.15/805-v5.19-0008-nvmem-sfp-Use-regmap.patch
deleted file mode 100644 (file)
index e187238..0000000
+++ /dev/null
@@ -1,109 +0,0 @@
-From 943eadbdb11314b41eacbcc484dfb7f93e271ff4 Mon Sep 17 00:00:00 2001
-From: Sean Anderson <[email protected]>
-Date: Fri, 29 Apr 2022 17:27:00 +0100
-Subject: [PATCH] nvmem: sfp: Use regmap
-
-This converts the SFP driver to use regmap. This will allow easily
-supporting devices with different endians. We disallow byte-level
-access, as regmap_bulk_read doesn't support it (and it's unclear what
-the correct result would be when we have an endianness difference).
-
-Signed-off-by: Sean Anderson <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/Kconfig          |  1 +
- drivers/nvmem/layerscape-sfp.c | 30 ++++++++++++++++++++++--------
- 2 files changed, 23 insertions(+), 8 deletions(-)
-
---- a/drivers/nvmem/Kconfig
-+++ b/drivers/nvmem/Kconfig
-@@ -304,6 +304,7 @@ config NVMEM_LAYERSCAPE_SFP
-       tristate "Layerscape SFP (Security Fuse Processor) support"
-       depends on ARCH_LAYERSCAPE || COMPILE_TEST
-       depends on HAS_IOMEM
-+      select REGMAP_MMIO
-       help
-         This driver provides support to read the eFuses on Freescale
-         Layerscape SoC's. For example, the vendor provides a per part
---- a/drivers/nvmem/layerscape-sfp.c
-+++ b/drivers/nvmem/layerscape-sfp.c
-@@ -13,15 +13,17 @@
- #include <linux/nvmem-provider.h>
- #include <linux/platform_device.h>
- #include <linux/property.h>
-+#include <linux/regmap.h>
- #define LAYERSCAPE_SFP_OTP_OFFSET     0x0200
- struct layerscape_sfp_priv {
--      void __iomem *base;
-+      struct regmap *regmap;
- };
- struct layerscape_sfp_data {
-       int size;
-+      enum regmap_endian endian;
- };
- static int layerscape_sfp_read(void *context, unsigned int offset, void *val,
-@@ -29,15 +31,16 @@ static int layerscape_sfp_read(void *con
- {
-       struct layerscape_sfp_priv *priv = context;
--      memcpy_fromio(val, priv->base + LAYERSCAPE_SFP_OTP_OFFSET + offset,
--                    bytes);
--
--      return 0;
-+      return regmap_bulk_read(priv->regmap,
-+                              LAYERSCAPE_SFP_OTP_OFFSET + offset, val,
-+                              bytes / 4);
- }
- static struct nvmem_config layerscape_sfp_nvmem_config = {
-       .name = "fsl-sfp",
-       .reg_read = layerscape_sfp_read,
-+      .word_size = 4,
-+      .stride = 4,
- };
- static int layerscape_sfp_probe(struct platform_device *pdev)
-@@ -45,16 +48,26 @@ static int layerscape_sfp_probe(struct p
-       const struct layerscape_sfp_data *data;
-       struct layerscape_sfp_priv *priv;
-       struct nvmem_device *nvmem;
-+      struct regmap_config config = { 0 };
-+      void __iomem *base;
-       priv = devm_kzalloc(&pdev->dev, sizeof(*priv), GFP_KERNEL);
-       if (!priv)
-               return -ENOMEM;
--      priv->base = devm_platform_ioremap_resource(pdev, 0);
--      if (IS_ERR(priv->base))
--              return PTR_ERR(priv->base);
-+      base = devm_platform_ioremap_resource(pdev, 0);
-+      if (IS_ERR(base))
-+              return PTR_ERR(base);
-       data = device_get_match_data(&pdev->dev);
-+      config.reg_bits = 32;
-+      config.reg_stride = 4;
-+      config.val_bits = 32;
-+      config.val_format_endian = data->endian;
-+      config.max_register = LAYERSCAPE_SFP_OTP_OFFSET + data->size - 4;
-+      priv->regmap = devm_regmap_init_mmio(&pdev->dev, base, &config);
-+      if (IS_ERR(priv->regmap))
-+              return PTR_ERR(priv->regmap);
-       layerscape_sfp_nvmem_config.size = data->size;
-       layerscape_sfp_nvmem_config.dev = &pdev->dev;
-@@ -67,6 +80,7 @@ static int layerscape_sfp_probe(struct p
- static const struct layerscape_sfp_data ls1028a_data = {
-       .size = 0x88,
-+      .endian = REGMAP_ENDIAN_LITTLE,
- };
- static const struct of_device_id layerscape_sfp_dt_ids[] = {
diff --git a/target/linux/generic/backport-5.15/805-v5.19-0009-nvmem-sfp-Add-support-for-TA-2.1-devices.patch b/target/linux/generic/backport-5.15/805-v5.19-0009-nvmem-sfp-Add-support-for-TA-2.1-devices.patch
deleted file mode 100644 (file)
index ee00098..0000000
+++ /dev/null
@@ -1,38 +0,0 @@
-From 33a1c6618677fe33f8e84cb7bedc45abbce89a50 Mon Sep 17 00:00:00 2001
-From: Sean Anderson <[email protected]>
-Date: Fri, 29 Apr 2022 17:27:01 +0100
-Subject: [PATCH] nvmem: sfp: Add support for TA 2.1 devices
-
-This adds support for Trust Architecture (TA) 2.1 devices to the SFP driver.
-There are few differences between TA 2.1 and TA 3.0, especially for
-read-only support, so just re-use the existing data.
-
-Signed-off-by: Sean Anderson <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/layerscape-sfp.c | 6 ++++++
- 1 file changed, 6 insertions(+)
-
---- a/drivers/nvmem/layerscape-sfp.c
-+++ b/drivers/nvmem/layerscape-sfp.c
-@@ -78,12 +78,18 @@ static int layerscape_sfp_probe(struct p
-       return PTR_ERR_OR_ZERO(nvmem);
- }
-+static const struct layerscape_sfp_data ls1021a_data = {
-+      .size = 0x88,
-+      .endian = REGMAP_ENDIAN_BIG,
-+};
-+
- static const struct layerscape_sfp_data ls1028a_data = {
-       .size = 0x88,
-       .endian = REGMAP_ENDIAN_LITTLE,
- };
- static const struct of_device_id layerscape_sfp_dt_ids[] = {
-+      { .compatible = "fsl,ls1021a-sfp", .data = &ls1021a_data },
-       { .compatible = "fsl,ls1028a-sfp", .data = &ls1028a_data },
-       {},
- };
diff --git a/target/linux/generic/backport-5.15/806-v6.0-0001-nvmem-microchip-otpc-add-support.patch b/target/linux/generic/backport-5.15/806-v6.0-0001-nvmem-microchip-otpc-add-support.patch
deleted file mode 100644 (file)
index f54ba7e..0000000
+++ /dev/null
@@ -1,389 +0,0 @@
-From 98830350d3fc824c1ff5c338140fe20f041a5916 Mon Sep 17 00:00:00 2001
-From: Claudiu Beznea <[email protected]>
-Date: Wed, 6 Jul 2022 11:06:22 +0100
-Subject: [PATCH] nvmem: microchip-otpc: add support
-
-Add support for Microchip OTP controller available on SAMA7G5. The OTPC
-controls the access to a non-volatile memory. The memory behind OTPC is
-organized into packets, packets are composed by a fixed length header
-(4 bytes long) and a variable length payload (payload length is available
-in the header). When software request the data at an offset in memory
-the OTPC will return (via header + data registers) the whole packet that
-has a word at that offset. For the OTP memory layout like below:
-
-offset  OTP Memory layout
-
-         .           .
-         .    ...    .
-         .           .
-0x0E     +-----------+ <--- packet X
-         | header  X |
-0x12     +-----------+
-         | payload X |
-0x16     |           |
-         |           |
-0x1A     |           |
-         +-----------+
-         .           .
-         .    ...    .
-         .           .
-
-if user requests data at address 0x16 the data started at 0x0E will be
-returned by controller. User will be able to fetch the whole packet
-starting at 0x0E (or parts of the packet) via proper registers. The same
-packet will be returned if software request the data at offset 0x0E or
-0x12 or 0x1A.
-
-The OTP will be populated by Microchip with at least 2 packets first one
-being boot configuration packet and the 2nd one being temperature
-calibration packet. The packet order will be preserved b/w different chip
-revisions but the packet sizes may change.
-
-For the above reasons and to keep the same software able to work on all
-chip variants the read function of the driver is working with a packet
-id instead of an offset in OTP memory.
-
-Signed-off-by: Claudiu Beznea <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- MAINTAINERS                    |   8 +
- drivers/nvmem/Kconfig          |   7 +
- drivers/nvmem/Makefile         |   2 +
- drivers/nvmem/microchip-otpc.c | 288 +++++++++++++++++++++++++++++++++
- 4 files changed, 305 insertions(+)
- create mode 100644 drivers/nvmem/microchip-otpc.c
-
---- a/MAINTAINERS
-+++ b/MAINTAINERS
-@@ -12365,6 +12365,14 @@ S:    Supported
- F:    Documentation/devicetree/bindings/mtd/atmel-nand.txt
- F:    drivers/mtd/nand/raw/atmel/*
-+MICROCHIP OTPC DRIVER
-+M:    Claudiu Beznea <[email protected]>
-+L:    [email protected] (moderated for non-subscribers)
-+S:    Supported
-+F:    Documentation/devicetree/bindings/nvmem/microchip,sama7g5-otpc.yaml
-+F:    drivers/nvmem/microchip-otpc.c
-+F:    dt-bindings/nvmem/microchip,sama7g5-otpc.h
-+
- MICROCHIP PWM DRIVER
- M:    Claudiu Beznea <[email protected]>
- L:    [email protected] (moderated for non-subscribers)
---- a/drivers/nvmem/Kconfig
-+++ b/drivers/nvmem/Kconfig
-@@ -107,6 +107,13 @@ config MTK_EFUSE
-         This driver can also be built as a module. If so, the module
-         will be called efuse-mtk.
-+config MICROCHIP_OTPC
-+      tristate "Microchip OTPC support"
-+      depends on ARCH_AT91 || COMPILE_TEST
-+      help
-+        This driver enable the OTP controller available on Microchip SAMA7G5
-+        SoCs. It controlls the access to the OTP memory connected to it.
-+
- config NVMEM_NINTENDO_OTP
-       tristate "Nintendo Wii and Wii U OTP Support"
-       depends on WII || COMPILE_TEST
---- a/drivers/nvmem/Makefile
-+++ b/drivers/nvmem/Makefile
-@@ -67,3 +67,5 @@ obj-$(CONFIG_NVMEM_SUNPLUS_OCOTP)    += nvm
- nvmem_sunplus_ocotp-y         := sunplus-ocotp.o
- obj-$(CONFIG_NVMEM_APPLE_EFUSES)      += nvmem-apple-efuses.o
- nvmem-apple-efuses-y          := apple-efuses.o
-+obj-$(CONFIG_MICROCHIP_OTPC)  += nvmem-microchip-otpc.o
-+nvmem-microchip-otpc-y                := microchip-otpc.o
---- /dev/null
-+++ b/drivers/nvmem/microchip-otpc.c
-@@ -0,0 +1,288 @@
-+// SPDX-License-Identifier: GPL-2.0
-+/*
-+ * OTP Memory controller
-+ *
-+ * Copyright (C) 2022 Microchip Technology Inc. and its subsidiaries
-+ *
-+ * Author: Claudiu Beznea <[email protected]>
-+ */
-+
-+#include <linux/bitfield.h>
-+#include <linux/iopoll.h>
-+#include <linux/module.h>
-+#include <linux/nvmem-provider.h>
-+#include <linux/of.h>
-+#include <linux/platform_device.h>
-+
-+#define MCHP_OTPC_CR                  (0x0)
-+#define MCHP_OTPC_CR_READ             BIT(6)
-+#define MCHP_OTPC_MR                  (0x4)
-+#define MCHP_OTPC_MR_ADDR             GENMASK(31, 16)
-+#define MCHP_OTPC_AR                  (0x8)
-+#define MCHP_OTPC_SR                  (0xc)
-+#define MCHP_OTPC_SR_READ             BIT(6)
-+#define MCHP_OTPC_HR                  (0x20)
-+#define MCHP_OTPC_HR_SIZE             GENMASK(15, 8)
-+#define MCHP_OTPC_DR                  (0x24)
-+
-+#define MCHP_OTPC_NAME                        "mchp-otpc"
-+#define MCHP_OTPC_SIZE                        (11 * 1024)
-+
-+/**
-+ * struct mchp_otpc - OTPC private data structure
-+ * @base: base address
-+ * @dev: struct device pointer
-+ * @packets: list of packets in OTP memory
-+ * @npackets: number of packets in OTP memory
-+ */
-+struct mchp_otpc {
-+      void __iomem *base;
-+      struct device *dev;
-+      struct list_head packets;
-+      u32 npackets;
-+};
-+
-+/**
-+ * struct mchp_otpc_packet - OTPC packet data structure
-+ * @list: list head
-+ * @id: packet ID
-+ * @offset: packet offset (in words) in OTP memory
-+ */
-+struct mchp_otpc_packet {
-+      struct list_head list;
-+      u32 id;
-+      u32 offset;
-+};
-+
-+static struct mchp_otpc_packet *mchp_otpc_id_to_packet(struct mchp_otpc *otpc,
-+                                                     u32 id)
-+{
-+      struct mchp_otpc_packet *packet;
-+
-+      if (id >= otpc->npackets)
-+              return NULL;
-+
-+      list_for_each_entry(packet, &otpc->packets, list) {
-+              if (packet->id == id)
-+                      return packet;
-+      }
-+
-+      return NULL;
-+}
-+
-+static int mchp_otpc_prepare_read(struct mchp_otpc *otpc,
-+                                unsigned int offset)
-+{
-+      u32 tmp;
-+
-+      /* Set address. */
-+      tmp = readl_relaxed(otpc->base + MCHP_OTPC_MR);
-+      tmp &= ~MCHP_OTPC_MR_ADDR;
-+      tmp |= FIELD_PREP(MCHP_OTPC_MR_ADDR, offset);
-+      writel_relaxed(tmp, otpc->base + MCHP_OTPC_MR);
-+
-+      /* Set read. */
-+      tmp = readl_relaxed(otpc->base + MCHP_OTPC_CR);
-+      tmp |= MCHP_OTPC_CR_READ;
-+      writel_relaxed(tmp, otpc->base + MCHP_OTPC_CR);
-+
-+      /* Wait for packet to be transferred into temporary buffers. */
-+      return read_poll_timeout(readl_relaxed, tmp, !(tmp & MCHP_OTPC_SR_READ),
-+                               10000, 2000, false, otpc->base + MCHP_OTPC_SR);
-+}
-+
-+/*
-+ * OTPC memory is organized into packets. Each packets contains a header and
-+ * a payload. Header is 4 bytes long and contains the size of the payload.
-+ * Payload size varies. The memory footprint is something as follows:
-+ *
-+ * Memory offset  Memory footprint     Packet ID
-+ * -------------  ----------------     ---------
-+ *
-+ * 0x0            +------------+   <-- packet 0
-+ *                | header  0  |
-+ * 0x4            +------------+
-+ *                | payload 0  |
-+ *                .            .
-+ *                .    ...     .
-+ *                .            .
-+ * offset1        +------------+   <-- packet 1
-+ *                | header  1  |
-+ * offset1 + 0x4  +------------+
-+ *                | payload 1  |
-+ *                .            .
-+ *                .    ...     .
-+ *                .            .
-+ * offset2        +------------+   <-- packet 2
-+ *                .            .
-+ *                .    ...     .
-+ *                .            .
-+ * offsetN        +------------+   <-- packet N
-+ *                | header  N  |
-+ * offsetN + 0x4  +------------+
-+ *                | payload N  |
-+ *                .            .
-+ *                .    ...     .
-+ *                .            .
-+ *                +------------+
-+ *
-+ * where offset1, offset2, offsetN depends on the size of payload 0, payload 1,
-+ * payload N-1.
-+ *
-+ * The access to memory is done on a per packet basis: the control registers
-+ * need to be updated with an offset address (within a packet range) and the
-+ * data registers will be update by controller with information contained by
-+ * that packet. E.g. if control registers are updated with any address within
-+ * the range [offset1, offset2) the data registers are updated by controller
-+ * with packet 1. Header data is accessible though MCHP_OTPC_HR register.
-+ * Payload data is accessible though MCHP_OTPC_DR and MCHP_OTPC_AR registers.
-+ * There is no direct mapping b/w the offset requested by software and the
-+ * offset returned by hardware.
-+ *
-+ * For this, the read function will return the first requested bytes in the
-+ * packet. The user will have to be aware of the memory footprint before doing
-+ * the read request.
-+ */
-+static int mchp_otpc_read(void *priv, unsigned int off, void *val,
-+                        size_t bytes)
-+{
-+      struct mchp_otpc *otpc = priv;
-+      struct mchp_otpc_packet *packet;
-+      u32 *buf = val;
-+      u32 offset;
-+      size_t len = 0;
-+      int ret, payload_size;
-+
-+      /*
-+       * We reach this point with off being multiple of stride = 4 to
-+       * be able to cross the subsystem. Inside the driver we use continuous
-+       * unsigned integer numbers for packet id, thus devide off by 4
-+       * before passing it to mchp_otpc_id_to_packet().
-+       */
-+      packet = mchp_otpc_id_to_packet(otpc, off / 4);
-+      if (!packet)
-+              return -EINVAL;
-+      offset = packet->offset;
-+
-+      while (len < bytes) {
-+              ret = mchp_otpc_prepare_read(otpc, offset);
-+              if (ret)
-+                      return ret;
-+
-+              /* Read and save header content. */
-+              *buf++ = readl_relaxed(otpc->base + MCHP_OTPC_HR);
-+              len += sizeof(*buf);
-+              offset++;
-+              if (len >= bytes)
-+                      break;
-+
-+              /* Read and save payload content. */
-+              payload_size = FIELD_GET(MCHP_OTPC_HR_SIZE, *(buf - 1));
-+              writel_relaxed(0UL, otpc->base + MCHP_OTPC_AR);
-+              do {
-+                      *buf++ = readl_relaxed(otpc->base + MCHP_OTPC_DR);
-+                      len += sizeof(*buf);
-+                      offset++;
-+                      payload_size--;
-+              } while (payload_size >= 0 && len < bytes);
-+      }
-+
-+      return 0;
-+}
-+
-+static int mchp_otpc_init_packets_list(struct mchp_otpc *otpc, u32 *size)
-+{
-+      struct mchp_otpc_packet *packet;
-+      u32 word, word_pos = 0, id = 0, npackets = 0, payload_size;
-+      int ret;
-+
-+      INIT_LIST_HEAD(&otpc->packets);
-+      *size = 0;
-+
-+      while (*size < MCHP_OTPC_SIZE) {
-+              ret = mchp_otpc_prepare_read(otpc, word_pos);
-+              if (ret)
-+                      return ret;
-+
-+              word = readl_relaxed(otpc->base + MCHP_OTPC_HR);
-+              payload_size = FIELD_GET(MCHP_OTPC_HR_SIZE, word);
-+              if (!payload_size)
-+                      break;
-+
-+              packet = devm_kzalloc(otpc->dev, sizeof(*packet), GFP_KERNEL);
-+              if (!packet)
-+                      return -ENOMEM;
-+
-+              packet->id = id++;
-+              packet->offset = word_pos;
-+              INIT_LIST_HEAD(&packet->list);
-+              list_add_tail(&packet->list, &otpc->packets);
-+
-+              /* Count size by adding header and paload sizes. */
-+              *size += 4 * (payload_size + 1);
-+              /* Next word: this packet (header, payload) position + 1. */
-+              word_pos += payload_size + 2;
-+
-+              npackets++;
-+      }
-+
-+      otpc->npackets = npackets;
-+
-+      return 0;
-+}
-+
-+static struct nvmem_config mchp_nvmem_config = {
-+      .name = MCHP_OTPC_NAME,
-+      .type = NVMEM_TYPE_OTP,
-+      .read_only = true,
-+      .word_size = 4,
-+      .stride = 4,
-+      .reg_read = mchp_otpc_read,
-+};
-+
-+static int mchp_otpc_probe(struct platform_device *pdev)
-+{
-+      struct nvmem_device *nvmem;
-+      struct mchp_otpc *otpc;
-+      u32 size;
-+      int ret;
-+
-+      otpc = devm_kzalloc(&pdev->dev, sizeof(*otpc), GFP_KERNEL);
-+      if (!otpc)
-+              return -ENOMEM;
-+
-+      otpc->base = devm_platform_ioremap_resource(pdev, 0);
-+      if (IS_ERR(otpc->base))
-+              return PTR_ERR(otpc->base);
-+
-+      otpc->dev = &pdev->dev;
-+      ret = mchp_otpc_init_packets_list(otpc, &size);
-+      if (ret)
-+              return ret;
-+
-+      mchp_nvmem_config.dev = otpc->dev;
-+      mchp_nvmem_config.size = size;
-+      mchp_nvmem_config.priv = otpc;
-+      nvmem = devm_nvmem_register(&pdev->dev, &mchp_nvmem_config);
-+
-+      return PTR_ERR_OR_ZERO(nvmem);
-+}
-+
-+static const struct of_device_id __maybe_unused mchp_otpc_ids[] = {
-+      { .compatible = "microchip,sama7g5-otpc", },
-+      { },
-+};
-+MODULE_DEVICE_TABLE(of, mchp_otpc_ids);
-+
-+static struct platform_driver mchp_otpc_driver = {
-+      .probe = mchp_otpc_probe,
-+      .driver = {
-+              .name = MCHP_OTPC_NAME,
-+              .of_match_table = of_match_ptr(mchp_otpc_ids),
-+      },
-+};
-+module_platform_driver(mchp_otpc_driver);
-+
-+MODULE_AUTHOR("Claudiu Beznea <[email protected]>");
-+MODULE_DESCRIPTION("Microchip SAMA7G5 OTPC driver");
-+MODULE_LICENSE("GPL");
diff --git a/target/linux/generic/backport-5.15/806-v6.0-0002-nvmem-mtk-efuse-Simplify-with-devm_platform_get_and_.patch b/target/linux/generic/backport-5.15/806-v6.0-0002-nvmem-mtk-efuse-Simplify-with-devm_platform_get_and_.patch
deleted file mode 100644 (file)
index 6a4126b..0000000
+++ /dev/null
@@ -1,32 +0,0 @@
-From f5c97da8037b18d1256a58459fa96ed68e50fb41 Mon Sep 17 00:00:00 2001
-From: AngeloGioacchino Del Regno <[email protected]>
-Date: Wed, 6 Jul 2022 11:06:27 +0100
-Subject: [PATCH] nvmem: mtk-efuse: Simplify with
- devm_platform_get_and_ioremap_resource()
-
-Convert platform_get_resource(), devm_ioremap_resource() to a single
-call to devm_platform_get_and_ioremap_resource(), as this is exactly
-what this function does.
-
-No functional changes.
-
-Signed-off-by: AngeloGioacchino Del Regno <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/mtk-efuse.c | 3 +--
- 1 file changed, 1 insertion(+), 2 deletions(-)
-
---- a/drivers/nvmem/mtk-efuse.c
-+++ b/drivers/nvmem/mtk-efuse.c
-@@ -41,8 +41,7 @@ static int mtk_efuse_probe(struct platfo
-       if (!priv)
-               return -ENOMEM;
--      res = platform_get_resource(pdev, IORESOURCE_MEM, 0);
--      priv->base = devm_ioremap_resource(dev, res);
-+      priv->base = devm_platform_get_and_ioremap_resource(pdev, 0, &res);
-       if (IS_ERR(priv->base))
-               return PTR_ERR(priv->base);
diff --git a/target/linux/generic/backport-5.15/807-v6.1-0002-nvmem-add-driver-handling-U-Boot-environment-variabl.patch b/target/linux/generic/backport-5.15/807-v6.1-0002-nvmem-add-driver-handling-U-Boot-environment-variabl.patch
deleted file mode 100644 (file)
index 9138807..0000000
+++ /dev/null
@@ -1,286 +0,0 @@
-From d5542923f200f95bddf524f36fd495f78aa28e3c Mon Sep 17 00:00:00 2001
-From: =?UTF-8?q?Rafa=C5=82=20Mi=C5=82ecki?= <[email protected]>
-Date: Fri, 16 Sep 2022 13:20:48 +0100
-Subject: [PATCH] nvmem: add driver handling U-Boot environment variables
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-U-Boot stores its setup as environment variables. It's a list of
-key-value pairs stored on flash device with a custom header.
-
-This commit adds an NVMEM driver that:
-1. Provides NVMEM access to environment vars binary data
-2. Extracts variables as NVMEM cells
-
-Current Linux's NVMEM sysfs API allows reading whole NVMEM data block.
-It can be used by user-space tools for reading U-Boot env vars block
-without the hassle of finding its location. Parsing will still need to
-be re-done there.
-
-Kernel-parsed NVMEM cells can be read however by Linux drivers. This may
-be useful for Ethernet drivers for reading device MAC address which is
-often stored as U-Boot env variable.
-
-Reviewed-by: Ahmad Fatoum <[email protected]>
-Signed-off-by: Rafał Miłecki <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- MAINTAINERS                |   1 +
- drivers/nvmem/Kconfig      |  13 +++
- drivers/nvmem/Makefile     |   2 +
- drivers/nvmem/u-boot-env.c | 218 +++++++++++++++++++++++++++++++++++++
- 4 files changed, 234 insertions(+)
- create mode 100644 drivers/nvmem/u-boot-env.c
-
---- a/drivers/nvmem/Kconfig
-+++ b/drivers/nvmem/Kconfig
-@@ -344,4 +344,17 @@ config NVMEM_APPLE_EFUSES
-         This driver can also be built as a module. If so, the module will
-         be called nvmem-apple-efuses.
-+config NVMEM_U_BOOT_ENV
-+      tristate "U-Boot environment variables support"
-+      depends on OF && MTD
-+      select CRC32
-+      help
-+        U-Boot stores its setup as environment variables. This driver adds
-+        support for verifying & exporting such data. It also exposes variables
-+        as NVMEM cells so they can be referenced by other drivers.
-+
-+        Currently this drivers works only with env variables on top of MTD.
-+
-+        If compiled as module it will be called nvmem_u-boot-env.
-+
- endif
---- a/drivers/nvmem/Makefile
-+++ b/drivers/nvmem/Makefile
-@@ -69,3 +69,5 @@ obj-$(CONFIG_NVMEM_APPLE_EFUSES)     += nvme
- nvmem-apple-efuses-y          := apple-efuses.o
- obj-$(CONFIG_MICROCHIP_OTPC)  += nvmem-microchip-otpc.o
- nvmem-microchip-otpc-y                := microchip-otpc.o
-+obj-$(CONFIG_NVMEM_U_BOOT_ENV)        += nvmem_u-boot-env.o
-+nvmem_u-boot-env-y            := u-boot-env.o
---- /dev/null
-+++ b/drivers/nvmem/u-boot-env.c
-@@ -0,0 +1,218 @@
-+// SPDX-License-Identifier: GPL-2.0-only
-+/*
-+ * Copyright (C) 2022 Rafał Miłecki <[email protected]>
-+ */
-+
-+#include <linux/crc32.h>
-+#include <linux/mod_devicetable.h>
-+#include <linux/module.h>
-+#include <linux/mtd/mtd.h>
-+#include <linux/nvmem-consumer.h>
-+#include <linux/nvmem-provider.h>
-+#include <linux/of_device.h>
-+#include <linux/platform_device.h>
-+#include <linux/slab.h>
-+
-+enum u_boot_env_format {
-+      U_BOOT_FORMAT_SINGLE,
-+      U_BOOT_FORMAT_REDUNDANT,
-+};
-+
-+struct u_boot_env {
-+      struct device *dev;
-+      enum u_boot_env_format format;
-+
-+      struct mtd_info *mtd;
-+
-+      /* Cells */
-+      struct nvmem_cell_info *cells;
-+      int ncells;
-+};
-+
-+struct u_boot_env_image_single {
-+      __le32 crc32;
-+      uint8_t data[];
-+} __packed;
-+
-+struct u_boot_env_image_redundant {
-+      __le32 crc32;
-+      u8 mark;
-+      uint8_t data[];
-+} __packed;
-+
-+static int u_boot_env_read(void *context, unsigned int offset, void *val,
-+                         size_t bytes)
-+{
-+      struct u_boot_env *priv = context;
-+      struct device *dev = priv->dev;
-+      size_t bytes_read;
-+      int err;
-+
-+      err = mtd_read(priv->mtd, offset, bytes, &bytes_read, val);
-+      if (err && !mtd_is_bitflip(err)) {
-+              dev_err(dev, "Failed to read from mtd: %d\n", err);
-+              return err;
-+      }
-+
-+      if (bytes_read != bytes) {
-+              dev_err(dev, "Failed to read %zu bytes\n", bytes);
-+              return -EIO;
-+      }
-+
-+      return 0;
-+}
-+
-+static int u_boot_env_add_cells(struct u_boot_env *priv, uint8_t *buf,
-+                              size_t data_offset, size_t data_len)
-+{
-+      struct device *dev = priv->dev;
-+      char *data = buf + data_offset;
-+      char *var, *value, *eq;
-+      int idx;
-+
-+      priv->ncells = 0;
-+      for (var = data; var < data + data_len && *var; var += strlen(var) + 1)
-+              priv->ncells++;
-+
-+      priv->cells = devm_kcalloc(dev, priv->ncells, sizeof(*priv->cells), GFP_KERNEL);
-+      if (!priv->cells)
-+              return -ENOMEM;
-+
-+      for (var = data, idx = 0;
-+           var < data + data_len && *var;
-+           var = value + strlen(value) + 1, idx++) {
-+              eq = strchr(var, '=');
-+              if (!eq)
-+                      break;
-+              *eq = '\0';
-+              value = eq + 1;
-+
-+              priv->cells[idx].name = devm_kstrdup(dev, var, GFP_KERNEL);
-+              if (!priv->cells[idx].name)
-+                      return -ENOMEM;
-+              priv->cells[idx].offset = data_offset + value - data;
-+              priv->cells[idx].bytes = strlen(value);
-+      }
-+
-+      if (WARN_ON(idx != priv->ncells))
-+              priv->ncells = idx;
-+
-+      return 0;
-+}
-+
-+static int u_boot_env_parse(struct u_boot_env *priv)
-+{
-+      struct device *dev = priv->dev;
-+      size_t crc32_data_offset;
-+      size_t crc32_data_len;
-+      size_t crc32_offset;
-+      size_t data_offset;
-+      size_t data_len;
-+      uint32_t crc32;
-+      uint32_t calc;
-+      size_t bytes;
-+      uint8_t *buf;
-+      int err;
-+
-+      buf = kcalloc(1, priv->mtd->size, GFP_KERNEL);
-+      if (!buf) {
-+              err = -ENOMEM;
-+              goto err_out;
-+      }
-+
-+      err = mtd_read(priv->mtd, 0, priv->mtd->size, &bytes, buf);
-+      if ((err && !mtd_is_bitflip(err)) || bytes != priv->mtd->size) {
-+              dev_err(dev, "Failed to read from mtd: %d\n", err);
-+              goto err_kfree;
-+      }
-+
-+      switch (priv->format) {
-+      case U_BOOT_FORMAT_SINGLE:
-+              crc32_offset = offsetof(struct u_boot_env_image_single, crc32);
-+              crc32_data_offset = offsetof(struct u_boot_env_image_single, data);
-+              data_offset = offsetof(struct u_boot_env_image_single, data);
-+              break;
-+      case U_BOOT_FORMAT_REDUNDANT:
-+              crc32_offset = offsetof(struct u_boot_env_image_redundant, crc32);
-+              crc32_data_offset = offsetof(struct u_boot_env_image_redundant, mark);
-+              data_offset = offsetof(struct u_boot_env_image_redundant, data);
-+              break;
-+      }
-+      crc32 = le32_to_cpu(*(uint32_t *)(buf + crc32_offset));
-+      crc32_data_len = priv->mtd->size - crc32_data_offset;
-+      data_len = priv->mtd->size - data_offset;
-+
-+      calc = crc32(~0, buf + crc32_data_offset, crc32_data_len) ^ ~0L;
-+      if (calc != crc32) {
-+              dev_err(dev, "Invalid calculated CRC32: 0x%08x (expected: 0x%08x)\n", calc, crc32);
-+              err = -EINVAL;
-+              goto err_kfree;
-+      }
-+
-+      buf[priv->mtd->size - 1] = '\0';
-+      err = u_boot_env_add_cells(priv, buf, data_offset, data_len);
-+      if (err)
-+              dev_err(dev, "Failed to add cells: %d\n", err);
-+
-+err_kfree:
-+      kfree(buf);
-+err_out:
-+      return err;
-+}
-+
-+static int u_boot_env_probe(struct platform_device *pdev)
-+{
-+      struct nvmem_config config = {
-+              .name = "u-boot-env",
-+              .reg_read = u_boot_env_read,
-+      };
-+      struct device *dev = &pdev->dev;
-+      struct device_node *np = dev->of_node;
-+      struct u_boot_env *priv;
-+      int err;
-+
-+      priv = devm_kzalloc(dev, sizeof(*priv), GFP_KERNEL);
-+      if (!priv)
-+              return -ENOMEM;
-+      priv->dev = dev;
-+
-+      priv->format = (uintptr_t)of_device_get_match_data(dev);
-+
-+      priv->mtd = of_get_mtd_device_by_node(np);
-+      if (IS_ERR(priv->mtd)) {
-+              dev_err_probe(dev, PTR_ERR(priv->mtd), "Failed to get %pOF MTD\n", np);
-+              return PTR_ERR(priv->mtd);
-+      }
-+
-+      err = u_boot_env_parse(priv);
-+      if (err)
-+              return err;
-+
-+      config.dev = dev;
-+      config.cells = priv->cells;
-+      config.ncells = priv->ncells;
-+      config.priv = priv;
-+      config.size = priv->mtd->size;
-+
-+      return PTR_ERR_OR_ZERO(devm_nvmem_register(dev, &config));
-+}
-+
-+static const struct of_device_id u_boot_env_of_match_table[] = {
-+      { .compatible = "u-boot,env", .data = (void *)U_BOOT_FORMAT_SINGLE, },
-+      { .compatible = "u-boot,env-redundant-bool", .data = (void *)U_BOOT_FORMAT_REDUNDANT, },
-+      { .compatible = "u-boot,env-redundant-count", .data = (void *)U_BOOT_FORMAT_REDUNDANT, },
-+      {},
-+};
-+
-+static struct platform_driver u_boot_env_driver = {
-+      .probe = u_boot_env_probe,
-+      .driver = {
-+              .name = "u_boot_env",
-+              .of_match_table = u_boot_env_of_match_table,
-+      },
-+};
-+module_platform_driver(u_boot_env_driver);
-+
-+MODULE_AUTHOR("Rafał Miłecki");
-+MODULE_LICENSE("GPL");
-+MODULE_DEVICE_TABLE(of, u_boot_env_of_match_table);
diff --git a/target/linux/generic/backport-5.15/807-v6.1-0004-nvmem-brcm_nvram-Use-kzalloc-for-allocating-only-one.patch b/target/linux/generic/backport-5.15/807-v6.1-0004-nvmem-brcm_nvram-Use-kzalloc-for-allocating-only-one.patch
deleted file mode 100644 (file)
index 48ad63f..0000000
+++ /dev/null
@@ -1,29 +0,0 @@
-From d3524bb5b9a0c567b853a0024526afe87dde01ed Mon Sep 17 00:00:00 2001
-From: Kenneth Lee <[email protected]>
-Date: Fri, 16 Sep 2022 13:20:52 +0100
-Subject: [PATCH] nvmem: brcm_nvram: Use kzalloc for allocating only one
- element
-
-Use kzalloc(...) rather than kcalloc(1, ...) because the number of
-elements we are specifying in this case is 1, so kzalloc would
-accomplish the same thing and we can simplify.
-
-Signed-off-by: Kenneth Lee <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/brcm_nvram.c | 2 +-
- 1 file changed, 1 insertion(+), 1 deletion(-)
-
---- a/drivers/nvmem/brcm_nvram.c
-+++ b/drivers/nvmem/brcm_nvram.c
-@@ -96,7 +96,7 @@ static int brcm_nvram_parse(struct brcm_
-       len = le32_to_cpu(header.len);
--      data = kcalloc(1, len, GFP_KERNEL);
-+      data = kzalloc(len, GFP_KERNEL);
-       memcpy_fromio(data, priv->base, len);
-       data[len - 1] = '\0';
diff --git a/target/linux/generic/backport-5.15/807-v6.1-0005-nvmem-prefix-all-symbols-with-NVMEM_.patch b/target/linux/generic/backport-5.15/807-v6.1-0005-nvmem-prefix-all-symbols-with-NVMEM_.patch
deleted file mode 100644 (file)
index 4410fc4..0000000
+++ /dev/null
@@ -1,281 +0,0 @@
-From 28fc7c986f01fdcfd28af648be2597624cac0e27 Mon Sep 17 00:00:00 2001
-From: =?UTF-8?q?Rafa=C5=82=20Mi=C5=82ecki?= <[email protected]>
-Date: Fri, 16 Sep 2022 13:20:54 +0100
-Subject: [PATCH] nvmem: prefix all symbols with NVMEM_
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-This unifies all NVMEM symbols. They follow one style now.
-
-Reviewed-by: Matthias Brugger <[email protected]>
-Acked-by: Arnd Bergmann <[email protected]>
-Signed-off-by: Rafał Miłecki <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- arch/arm/configs/multi_v7_defconfig |  6 +++---
- arch/arm/configs/qcom_defconfig     |  2 +-
- arch/arm64/configs/defconfig        | 10 +++++-----
- arch/mips/configs/ci20_defconfig    |  2 +-
- drivers/cpufreq/Kconfig.arm         |  2 +-
- drivers/nvmem/Kconfig               | 24 ++++++++++++------------
- drivers/nvmem/Makefile              | 24 ++++++++++++------------
- drivers/soc/mediatek/Kconfig        |  2 +-
- drivers/thermal/qcom/Kconfig        |  2 +-
- 9 files changed, 37 insertions(+), 37 deletions(-)
-
---- a/arch/arm/configs/multi_v7_defconfig
-+++ b/arch/arm/configs/multi_v7_defconfig
-@@ -1124,10 +1124,10 @@ CONFIG_TI_PIPE3=y
- CONFIG_TWL4030_USB=m
- CONFIG_RAS=y
- CONFIG_NVMEM_IMX_OCOTP=y
--CONFIG_ROCKCHIP_EFUSE=m
-+CONFIG_NVMEM_ROCKCHIP_EFUSE=m
- CONFIG_NVMEM_SUNXI_SID=y
- CONFIG_NVMEM_VF610_OCOTP=y
--CONFIG_MESON_MX_EFUSE=m
-+CONFIG_NVMEM_MESON_MX_EFUSE=m
- CONFIG_NVMEM_RMEM=m
- CONFIG_FSI=m
- CONFIG_FSI_MASTER_GPIO=m
---- a/arch/arm/configs/qcom_defconfig
-+++ b/arch/arm/configs/qcom_defconfig
-@@ -274,7 +274,7 @@ CONFIG_PHY_QCOM_USB_HS=y
- CONFIG_PHY_QCOM_USB_HSIC=y
- CONFIG_PHY_QCOM_QMP=y
- CONFIG_PHY_QCOM_USB_SNPS_FEMTO_V2=y
--CONFIG_QCOM_QFPROM=y
-+CONFIG_NVMEM_QCOM_QFPROM=y
- CONFIG_INTERCONNECT=y
- CONFIG_INTERCONNECT_QCOM=y
- CONFIG_INTERCONNECT_QCOM_MSM8974=m
---- a/arch/arm64/configs/defconfig
-+++ b/arch/arm64/configs/defconfig
-@@ -1135,11 +1135,11 @@ CONFIG_QCOM_L3_PMU=y
- CONFIG_NVMEM_IMX_OCOTP=y
- CONFIG_NVMEM_IMX_OCOTP_SCU=y
- CONFIG_QCOM_QFPROM=y
--CONFIG_MTK_EFUSE=y
--CONFIG_ROCKCHIP_EFUSE=y
-+CONFIG_NVMEM_MTK_EFUSE=y
-+CONFIG_NVMEM_ROCKCHIP_EFUSE=y
- CONFIG_NVMEM_SUNXI_SID=y
--CONFIG_UNIPHIER_EFUSE=y
--CONFIG_MESON_EFUSE=m
-+CONFIG_NVMEM_UNIPHIER_EFUSE=y
-+CONFIG_NVMEM_MESON_EFUSE=m
- CONFIG_NVMEM_RMEM=m
- CONFIG_FPGA=y
- CONFIG_FPGA_MGR_STRATIX10_SOC=m
---- a/arch/mips/configs/ci20_defconfig
-+++ b/arch/mips/configs/ci20_defconfig
-@@ -137,7 +137,7 @@ CONFIG_MEMORY=y
- CONFIG_JZ4780_NEMC=y
- CONFIG_PWM=y
- CONFIG_PWM_JZ4740=m
--CONFIG_JZ4780_EFUSE=y
-+CONFIG_NVMEM_JZ4780_EFUSE=y
- CONFIG_JZ4770_PHY=y
- CONFIG_EXT4_FS=y
- # CONFIG_DNOTIFY is not set
---- a/drivers/cpufreq/Kconfig.arm
-+++ b/drivers/cpufreq/Kconfig.arm
-@@ -153,7 +153,7 @@ config ARM_OMAP2PLUS_CPUFREQ
- config ARM_QCOM_CPUFREQ_NVMEM
-       tristate "Qualcomm nvmem based CPUFreq"
-       depends on ARCH_QCOM
--      depends on QCOM_QFPROM
-+      depends on NVMEM_QCOM_QFPROM
-       depends on QCOM_SMEM
-       select PM_OPP
-       help
---- a/drivers/nvmem/Kconfig
-+++ b/drivers/nvmem/Kconfig
-@@ -52,7 +52,7 @@ config NVMEM_IMX_OCOTP_SCU
-         This is a driver for the SCU On-Chip OTP Controller (OCOTP)
-         available on i.MX8 SoCs.
--config JZ4780_EFUSE
-+config NVMEM_JZ4780_EFUSE
-       tristate "JZ4780 EFUSE Memory Support"
-       depends on MACH_INGENIC || COMPILE_TEST
-       depends on HAS_IOMEM
-@@ -96,7 +96,7 @@ config NVMEM_MXS_OCOTP
-         This driver can also be built as a module. If so, the module
-         will be called nvmem-mxs-ocotp.
--config MTK_EFUSE
-+config NVMEM_MTK_EFUSE
-       tristate "Mediatek SoCs EFUSE support"
-       depends on ARCH_MEDIATEK || COMPILE_TEST
-       depends on HAS_IOMEM
-@@ -107,7 +107,7 @@ config MTK_EFUSE
-         This driver can also be built as a module. If so, the module
-         will be called efuse-mtk.
--config MICROCHIP_OTPC
-+config NVMEM_MICROCHIP_OTPC
-       tristate "Microchip OTPC support"
-       depends on ARCH_AT91 || COMPILE_TEST
-       help
-@@ -126,7 +126,7 @@ config NVMEM_NINTENDO_OTP
-         This driver can also be built as a module. If so, the module
-         will be called nvmem-nintendo-otp.
--config QCOM_QFPROM
-+config NVMEM_QCOM_QFPROM
-       tristate "QCOM QFPROM Support"
-       depends on ARCH_QCOM || COMPILE_TEST
-       depends on HAS_IOMEM
-@@ -145,7 +145,7 @@ config NVMEM_SPMI_SDAM
-         Qualcomm Technologies, Inc. PMICs. It provides the clients
-         an interface to read/write to the SDAM module's shared memory.
--config ROCKCHIP_EFUSE
-+config NVMEM_ROCKCHIP_EFUSE
-       tristate "Rockchip eFuse Support"
-       depends on ARCH_ROCKCHIP || COMPILE_TEST
-       depends on HAS_IOMEM
-@@ -156,7 +156,7 @@ config ROCKCHIP_EFUSE
-         This driver can also be built as a module. If so, the module
-         will be called nvmem_rockchip_efuse.
--config ROCKCHIP_OTP
-+config NVMEM_ROCKCHIP_OTP
-       tristate "Rockchip OTP controller support"
-       depends on ARCH_ROCKCHIP || COMPILE_TEST
-       depends on HAS_IOMEM
-@@ -199,7 +199,7 @@ config NVMEM_SUNXI_SID
-         This driver can also be built as a module. If so, the module
-         will be called nvmem_sunxi_sid.
--config UNIPHIER_EFUSE
-+config NVMEM_UNIPHIER_EFUSE
-       tristate "UniPhier SoCs eFuse support"
-       depends on ARCH_UNIPHIER || COMPILE_TEST
-       depends on HAS_IOMEM
-@@ -221,7 +221,7 @@ config NVMEM_VF610_OCOTP
-         This driver can also be build as a module. If so, the module will
-         be called nvmem-vf610-ocotp.
--config MESON_EFUSE
-+config NVMEM_MESON_EFUSE
-       tristate "Amlogic Meson GX eFuse Support"
-       depends on (ARCH_MESON || COMPILE_TEST) && MESON_SM
-       help
-@@ -231,7 +231,7 @@ config MESON_EFUSE
-         This driver can also be built as a module. If so, the module
-         will be called nvmem_meson_efuse.
--config MESON_MX_EFUSE
-+config NVMEM_MESON_MX_EFUSE
-       tristate "Amlogic Meson6/Meson8/Meson8b eFuse Support"
-       depends on ARCH_MESON || COMPILE_TEST
-       help
-@@ -251,13 +251,13 @@ config NVMEM_SNVS_LPGPR
-         This driver can also be built as a module. If so, the module
-         will be called nvmem-snvs-lpgpr.
--config RAVE_SP_EEPROM
-+config NVMEM_RAVE_SP_EEPROM
-       tristate "Rave SP EEPROM Support"
-       depends on RAVE_SP_CORE
-       help
-         Say y here to enable Rave SP EEPROM support.
--config SC27XX_EFUSE
-+config NVMEM_SC27XX_EFUSE
-       tristate "Spreadtrum SC27XX eFuse Support"
-       depends on MFD_SC27XX_PMIC || COMPILE_TEST
-       depends on HAS_IOMEM
-@@ -278,7 +278,7 @@ config NVMEM_ZYNQMP
-         If sure, say yes. If unsure, say no.
--config SPRD_EFUSE
-+config NVMEM_SPRD_EFUSE
-       tristate "Spreadtrum SoC eFuse Support"
-       depends on ARCH_SPRD || COMPILE_TEST
-       depends on HAS_IOMEM
---- a/drivers/nvmem/Makefile
-+++ b/drivers/nvmem/Makefile
-@@ -15,7 +15,7 @@ obj-$(CONFIG_NVMEM_IMX_OCOTP)        += nvmem-i
- nvmem-imx-ocotp-y             := imx-ocotp.o
- obj-$(CONFIG_NVMEM_IMX_OCOTP_SCU)     += nvmem-imx-ocotp-scu.o
- nvmem-imx-ocotp-scu-y         := imx-ocotp-scu.o
--obj-$(CONFIG_JZ4780_EFUSE)            += nvmem_jz4780_efuse.o
-+obj-$(CONFIG_NVMEM_JZ4780_EFUSE)              += nvmem_jz4780_efuse.o
- nvmem_jz4780_efuse-y          := jz4780-efuse.o
- obj-$(CONFIG_NVMEM_LPC18XX_EEPROM)    += nvmem_lpc18xx_eeprom.o
- nvmem_lpc18xx_eeprom-y        := lpc18xx_eeprom.o
-@@ -25,37 +25,37 @@ obj-$(CONFIG_NVMEM_MXS_OCOTP)      += nvmem-m
- nvmem-mxs-ocotp-y             := mxs-ocotp.o
- obj-$(CONFIG_NVMEM_NINTENDO_OTP)      += nvmem-nintendo-otp.o
- nvmem-nintendo-otp-y          := nintendo-otp.o
--obj-$(CONFIG_MTK_EFUSE)               += nvmem_mtk-efuse.o
-+obj-$(CONFIG_NVMEM_MTK_EFUSE)         += nvmem_mtk-efuse.o
- nvmem_mtk-efuse-y             := mtk-efuse.o
--obj-$(CONFIG_QCOM_QFPROM)     += nvmem_qfprom.o
-+obj-$(CONFIG_NVMEM_QCOM_QFPROM)       += nvmem_qfprom.o
- nvmem_qfprom-y                        := qfprom.o
- obj-$(CONFIG_NVMEM_SPMI_SDAM) += nvmem_qcom-spmi-sdam.o
- nvmem_qcom-spmi-sdam-y                += qcom-spmi-sdam.o
--obj-$(CONFIG_ROCKCHIP_EFUSE)  += nvmem_rockchip_efuse.o
-+obj-$(CONFIG_NVMEM_ROCKCHIP_EFUSE)    += nvmem_rockchip_efuse.o
- nvmem_rockchip_efuse-y                := rockchip-efuse.o
--obj-$(CONFIG_ROCKCHIP_OTP)    += nvmem-rockchip-otp.o
-+obj-$(CONFIG_NVMEM_ROCKCHIP_OTP)      += nvmem-rockchip-otp.o
- nvmem-rockchip-otp-y          := rockchip-otp.o
- obj-$(CONFIG_NVMEM_SUNXI_SID) += nvmem_sunxi_sid.o
- nvmem_stm32_romem-y           := stm32-romem.o
- obj-$(CONFIG_NVMEM_STM32_ROMEM) += nvmem_stm32_romem.o
- nvmem_sunxi_sid-y             := sunxi_sid.o
--obj-$(CONFIG_UNIPHIER_EFUSE)  += nvmem-uniphier-efuse.o
-+obj-$(CONFIG_NVMEM_UNIPHIER_EFUSE)    += nvmem-uniphier-efuse.o
- nvmem-uniphier-efuse-y                := uniphier-efuse.o
- obj-$(CONFIG_NVMEM_VF610_OCOTP)       += nvmem-vf610-ocotp.o
- nvmem-vf610-ocotp-y           := vf610-ocotp.o
--obj-$(CONFIG_MESON_EFUSE)     += nvmem_meson_efuse.o
-+obj-$(CONFIG_NVMEM_MESON_EFUSE)       += nvmem_meson_efuse.o
- nvmem_meson_efuse-y           := meson-efuse.o
--obj-$(CONFIG_MESON_MX_EFUSE)  += nvmem_meson_mx_efuse.o
-+obj-$(CONFIG_NVMEM_MESON_MX_EFUSE)    += nvmem_meson_mx_efuse.o
- nvmem_meson_mx_efuse-y                := meson-mx-efuse.o
- obj-$(CONFIG_NVMEM_SNVS_LPGPR)        += nvmem_snvs_lpgpr.o
- nvmem_snvs_lpgpr-y            := snvs_lpgpr.o
--obj-$(CONFIG_RAVE_SP_EEPROM)  += nvmem-rave-sp-eeprom.o
-+obj-$(CONFIG_NVMEM_RAVE_SP_EEPROM)    += nvmem-rave-sp-eeprom.o
- nvmem-rave-sp-eeprom-y                := rave-sp-eeprom.o
--obj-$(CONFIG_SC27XX_EFUSE)    += nvmem-sc27xx-efuse.o
-+obj-$(CONFIG_NVMEM_SC27XX_EFUSE)      += nvmem-sc27xx-efuse.o
- nvmem-sc27xx-efuse-y          := sc27xx-efuse.o
- obj-$(CONFIG_NVMEM_ZYNQMP)    += nvmem_zynqmp_nvmem.o
- nvmem_zynqmp_nvmem-y          := zynqmp_nvmem.o
--obj-$(CONFIG_SPRD_EFUSE)      += nvmem_sprd_efuse.o
-+obj-$(CONFIG_NVMEM_SPRD_EFUSE)        += nvmem_sprd_efuse.o
- nvmem_sprd_efuse-y            := sprd-efuse.o
- obj-$(CONFIG_NVMEM_RMEM)      += nvmem-rmem.o
- nvmem-rmem-y                  := rmem.o
-@@ -67,7 +67,7 @@ obj-$(CONFIG_NVMEM_SUNPLUS_OCOTP)    += nvm
- nvmem_sunplus_ocotp-y         := sunplus-ocotp.o
- obj-$(CONFIG_NVMEM_APPLE_EFUSES)      += nvmem-apple-efuses.o
- nvmem-apple-efuses-y          := apple-efuses.o
--obj-$(CONFIG_MICROCHIP_OTPC)  += nvmem-microchip-otpc.o
-+obj-$(CONFIG_NVMEM_MICROCHIP_OTPC)    += nvmem-microchip-otpc.o
- nvmem-microchip-otpc-y                := microchip-otpc.o
- obj-$(CONFIG_NVMEM_U_BOOT_ENV)        += nvmem_u-boot-env.o
- nvmem_u-boot-env-y            := u-boot-env.o
---- a/drivers/thermal/qcom/Kconfig
-+++ b/drivers/thermal/qcom/Kconfig
-@@ -1,7 +1,7 @@
- # SPDX-License-Identifier: GPL-2.0-only
- config QCOM_TSENS
-       tristate "Qualcomm TSENS Temperature Alarm"
--      depends on QCOM_QFPROM
-+      depends on NVMEM_QCOM_QFPROM
-       depends on ARCH_QCOM || COMPILE_TEST
-       help
-         This enables the thermal sysfs driver for the TSENS device. It shows
diff --git a/target/linux/generic/backport-5.15/807-v6.1-0006-nvmem-sort-config-symbols-alphabetically.patch b/target/linux/generic/backport-5.15/807-v6.1-0006-nvmem-sort-config-symbols-alphabetically.patch
deleted file mode 100644 (file)
index 4e45524..0000000
+++ /dev/null
@@ -1,535 +0,0 @@
-From a06d9e5a63b7c2f622c908cd9600ce735e70f7c6 Mon Sep 17 00:00:00 2001
-From: =?UTF-8?q?Rafa=C5=82=20Mi=C5=82ecki?= <[email protected]>
-Date: Fri, 16 Sep 2022 13:20:55 +0100
-Subject: [PATCH] nvmem: sort config symbols alphabetically
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-1. Match what most subsystems do
-2. Simplify maintenance a bit
-3. Reduce amount of conflicts for new drivers patches
-
-While at it unify indent level in Makefile.
-
-Signed-off-by: Rafał Miłecki <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/Kconfig  | 300 +++++++++++++++++++++--------------------
- drivers/nvmem/Makefile | 114 ++++++++--------
- 2 files changed, 208 insertions(+), 206 deletions(-)
-
---- a/drivers/nvmem/Kconfig
-+++ b/drivers/nvmem/Kconfig
-@@ -21,6 +21,40 @@ config NVMEM_SYSFS
-        This interface is mostly used by userspace applications to
-        read/write directly into nvmem.
-+# Devices
-+
-+config NVMEM_APPLE_EFUSES
-+      tristate "Apple eFuse support"
-+      depends on ARCH_APPLE || COMPILE_TEST
-+      default ARCH_APPLE
-+      help
-+        Say y here to enable support for reading eFuses on Apple SoCs
-+        such as the M1. These are e.g. used to store factory programmed
-+        calibration data required for the PCIe or the USB-C PHY.
-+
-+        This driver can also be built as a module. If so, the module will
-+        be called nvmem-apple-efuses.
-+
-+config NVMEM_BCM_OCOTP
-+      tristate "Broadcom On-Chip OTP Controller support"
-+      depends on ARCH_BCM_IPROC || COMPILE_TEST
-+      depends on HAS_IOMEM
-+      default ARCH_BCM_IPROC
-+      help
-+        Say y here to enable read/write access to the Broadcom OTP
-+        controller.
-+
-+        This driver can also be built as a module. If so, the module
-+        will be called nvmem-bcm-ocotp.
-+
-+config NVMEM_BRCM_NVRAM
-+      tristate "Broadcom's NVRAM support"
-+      depends on ARCH_BCM_5301X || COMPILE_TEST
-+      depends on HAS_IOMEM
-+      help
-+        This driver provides support for Broadcom's NVRAM that can be accessed
-+        using I/O mapping.
-+
- config NVMEM_IMX_IIM
-       tristate "i.MX IC Identification Module support"
-       depends on ARCH_MXC || COMPILE_TEST
-@@ -64,6 +98,19 @@ config NVMEM_JZ4780_EFUSE
-         To compile this driver as a module, choose M here: the module
-         will be called nvmem_jz4780_efuse.
-+config NVMEM_LAYERSCAPE_SFP
-+      tristate "Layerscape SFP (Security Fuse Processor) support"
-+      depends on ARCH_LAYERSCAPE || COMPILE_TEST
-+      depends on HAS_IOMEM
-+      select REGMAP_MMIO
-+      help
-+        This driver provides support to read the eFuses on Freescale
-+        Layerscape SoC's. For example, the vendor provides a per part
-+        unique ID there.
-+
-+        This driver can also be built as a module. If so, the module
-+        will be called layerscape-sfp.
-+
- config NVMEM_LPC18XX_EEPROM
-       tristate "NXP LPC18XX EEPROM Memory Support"
-       depends on ARCH_LPC18XX || COMPILE_TEST
-@@ -84,17 +131,32 @@ config NVMEM_LPC18XX_OTP
-         To compile this driver as a module, choose M here: the module
-         will be called nvmem_lpc18xx_otp.
--config NVMEM_MXS_OCOTP
--      tristate "Freescale MXS On-Chip OTP Memory Support"
--      depends on ARCH_MXS || COMPILE_TEST
--      depends on HAS_IOMEM
-+config NVMEM_MESON_EFUSE
-+      tristate "Amlogic Meson GX eFuse Support"
-+      depends on (ARCH_MESON || COMPILE_TEST) && MESON_SM
-       help
--        If you say Y here, you will get readonly access to the
--        One Time Programmable memory pages that are stored
--        on the Freescale i.MX23/i.MX28 processor.
-+        This is a driver to retrieve specific values from the eFuse found on
-+        the Amlogic Meson GX SoCs.
-         This driver can also be built as a module. If so, the module
--        will be called nvmem-mxs-ocotp.
-+        will be called nvmem_meson_efuse.
-+
-+config NVMEM_MESON_MX_EFUSE
-+      tristate "Amlogic Meson6/Meson8/Meson8b eFuse Support"
-+      depends on ARCH_MESON || COMPILE_TEST
-+      help
-+        This is a driver to retrieve specific values from the eFuse found on
-+        the Amlogic Meson6, Meson8 and Meson8b SoCs.
-+
-+        This driver can also be built as a module. If so, the module
-+        will be called nvmem_meson_mx_efuse.
-+
-+config NVMEM_MICROCHIP_OTPC
-+      tristate "Microchip OTPC support"
-+      depends on ARCH_AT91 || COMPILE_TEST
-+      help
-+        This driver enable the OTP controller available on Microchip SAMA7G5
-+        SoCs. It controlls the access to the OTP memory connected to it.
- config NVMEM_MTK_EFUSE
-       tristate "Mediatek SoCs EFUSE support"
-@@ -107,12 +169,17 @@ config NVMEM_MTK_EFUSE
-         This driver can also be built as a module. If so, the module
-         will be called efuse-mtk.
--config NVMEM_MICROCHIP_OTPC
--      tristate "Microchip OTPC support"
--      depends on ARCH_AT91 || COMPILE_TEST
-+config NVMEM_MXS_OCOTP
-+      tristate "Freescale MXS On-Chip OTP Memory Support"
-+      depends on ARCH_MXS || COMPILE_TEST
-+      depends on HAS_IOMEM
-       help
--        This driver enable the OTP controller available on Microchip SAMA7G5
--        SoCs. It controlls the access to the OTP memory connected to it.
-+        If you say Y here, you will get readonly access to the
-+        One Time Programmable memory pages that are stored
-+        on the Freescale i.MX23/i.MX28 processor.
-+
-+        This driver can also be built as a module. If so, the module
-+        will be called nvmem-mxs-ocotp.
- config NVMEM_NINTENDO_OTP
-       tristate "Nintendo Wii and Wii U OTP Support"
-@@ -137,13 +204,21 @@ config NVMEM_QCOM_QFPROM
-         This driver can also be built as a module. If so, the module
-         will be called nvmem_qfprom.
--config NVMEM_SPMI_SDAM
--      tristate "SPMI SDAM Support"
--      depends on SPMI
-+config NVMEM_RAVE_SP_EEPROM
-+      tristate "Rave SP EEPROM Support"
-+      depends on RAVE_SP_CORE
-       help
--        This driver supports the Shared Direct Access Memory Module on
--        Qualcomm Technologies, Inc. PMICs. It provides the clients
--        an interface to read/write to the SDAM module's shared memory.
-+        Say y here to enable Rave SP EEPROM support.
-+
-+config NVMEM_RMEM
-+      tristate "Reserved Memory Based Driver Support"
-+      depends on HAS_IOMEM
-+      help
-+        This driver maps reserved memory into an nvmem device. It might be
-+        useful to expose information left by firmware in memory.
-+
-+        This driver can also be built as a module. If so, the module
-+        will be called nvmem-rmem.
- config NVMEM_ROCKCHIP_EFUSE
-       tristate "Rockchip eFuse Support"
-@@ -167,79 +242,16 @@ config NVMEM_ROCKCHIP_OTP
-         This driver can also be built as a module. If so, the module
-         will be called nvmem_rockchip_otp.
--config NVMEM_BCM_OCOTP
--      tristate "Broadcom On-Chip OTP Controller support"
--      depends on ARCH_BCM_IPROC || COMPILE_TEST
--      depends on HAS_IOMEM
--      default ARCH_BCM_IPROC
--      help
--        Say y here to enable read/write access to the Broadcom OTP
--        controller.
--
--        This driver can also be built as a module. If so, the module
--        will be called nvmem-bcm-ocotp.
--
--config NVMEM_STM32_ROMEM
--      tristate "STMicroelectronics STM32 factory-programmed memory support"
--      depends on ARCH_STM32 || COMPILE_TEST
--      help
--        Say y here to enable read-only access for STMicroelectronics STM32
--        factory-programmed memory area.
--
--        This driver can also be built as a module. If so, the module
--        will be called nvmem-stm32-romem.
--
--config NVMEM_SUNXI_SID
--      tristate "Allwinner SoCs SID support"
--      depends on ARCH_SUNXI
--      help
--        This is a driver for the 'security ID' available on various Allwinner
--        devices.
--
--        This driver can also be built as a module. If so, the module
--        will be called nvmem_sunxi_sid.
--
--config NVMEM_UNIPHIER_EFUSE
--      tristate "UniPhier SoCs eFuse support"
--      depends on ARCH_UNIPHIER || COMPILE_TEST
--      depends on HAS_IOMEM
--      help
--        This is a simple driver to dump specified values of UniPhier SoC
--        from eFuse.
--
--        This driver can also be built as a module. If so, the module
--        will be called nvmem-uniphier-efuse.
--
--config NVMEM_VF610_OCOTP
--      tristate "VF610 SoC OCOTP support"
--      depends on SOC_VF610 || COMPILE_TEST
-+config NVMEM_SC27XX_EFUSE
-+      tristate "Spreadtrum SC27XX eFuse Support"
-+      depends on MFD_SC27XX_PMIC || COMPILE_TEST
-       depends on HAS_IOMEM
-       help
--        This is a driver for the 'OCOTP' peripheral available on Vybrid
--        devices like VF5xx and VF6xx.
--
--        This driver can also be build as a module. If so, the module will
--        be called nvmem-vf610-ocotp.
--
--config NVMEM_MESON_EFUSE
--      tristate "Amlogic Meson GX eFuse Support"
--      depends on (ARCH_MESON || COMPILE_TEST) && MESON_SM
--      help
--        This is a driver to retrieve specific values from the eFuse found on
--        the Amlogic Meson GX SoCs.
--
--        This driver can also be built as a module. If so, the module
--        will be called nvmem_meson_efuse.
--
--config NVMEM_MESON_MX_EFUSE
--      tristate "Amlogic Meson6/Meson8/Meson8b eFuse Support"
--      depends on ARCH_MESON || COMPILE_TEST
--      help
--        This is a driver to retrieve specific values from the eFuse found on
--        the Amlogic Meson6, Meson8 and Meson8b SoCs.
-+        This is a simple driver to dump specified values of Spreadtrum
-+        SC27XX PMICs from eFuse.
-         This driver can also be built as a module. If so, the module
--        will be called nvmem_meson_mx_efuse.
-+        will be called nvmem-sc27xx-efuse.
- config NVMEM_SNVS_LPGPR
-       tristate "Support for Low Power General Purpose Register"
-@@ -251,32 +263,13 @@ config NVMEM_SNVS_LPGPR
-         This driver can also be built as a module. If so, the module
-         will be called nvmem-snvs-lpgpr.
--config NVMEM_RAVE_SP_EEPROM
--      tristate "Rave SP EEPROM Support"
--      depends on RAVE_SP_CORE
--      help
--        Say y here to enable Rave SP EEPROM support.
--
--config NVMEM_SC27XX_EFUSE
--      tristate "Spreadtrum SC27XX eFuse Support"
--      depends on MFD_SC27XX_PMIC || COMPILE_TEST
--      depends on HAS_IOMEM
--      help
--        This is a simple driver to dump specified values of Spreadtrum
--        SC27XX PMICs from eFuse.
--
--        This driver can also be built as a module. If so, the module
--        will be called nvmem-sc27xx-efuse.
--
--config NVMEM_ZYNQMP
--      bool "Xilinx ZYNQMP SoC nvmem firmware support"
--      depends on ARCH_ZYNQMP
-+config NVMEM_SPMI_SDAM
-+      tristate "SPMI SDAM Support"
-+      depends on SPMI
-       help
--        This is a driver to access hardware related data like
--        soc revision, IDCODE... etc by using the firmware
--        interface.
--
--        If sure, say yes. If unsure, say no.
-+        This driver supports the Shared Direct Access Memory Module on
-+        Qualcomm Technologies, Inc. PMICs. It provides the clients
-+        an interface to read/write to the SDAM module's shared memory.
- config NVMEM_SPRD_EFUSE
-       tristate "Spreadtrum SoC eFuse Support"
-@@ -289,36 +282,15 @@ config NVMEM_SPRD_EFUSE
-         This driver can also be built as a module. If so, the module
-         will be called nvmem-sprd-efuse.
--config NVMEM_RMEM
--      tristate "Reserved Memory Based Driver Support"
--      depends on HAS_IOMEM
--      help
--        This driver maps reserved memory into an nvmem device. It might be
--        useful to expose information left by firmware in memory.
--
--        This driver can also be built as a module. If so, the module
--        will be called nvmem-rmem.
--
--config NVMEM_BRCM_NVRAM
--      tristate "Broadcom's NVRAM support"
--      depends on ARCH_BCM_5301X || COMPILE_TEST
--      depends on HAS_IOMEM
--      help
--        This driver provides support for Broadcom's NVRAM that can be accessed
--        using I/O mapping.
--
--config NVMEM_LAYERSCAPE_SFP
--      tristate "Layerscape SFP (Security Fuse Processor) support"
--      depends on ARCH_LAYERSCAPE || COMPILE_TEST
--      depends on HAS_IOMEM
--      select REGMAP_MMIO
-+config NVMEM_STM32_ROMEM
-+      tristate "STMicroelectronics STM32 factory-programmed memory support"
-+      depends on ARCH_STM32 || COMPILE_TEST
-       help
--        This driver provides support to read the eFuses on Freescale
--        Layerscape SoC's. For example, the vendor provides a per part
--        unique ID there.
-+        Say y here to enable read-only access for STMicroelectronics STM32
-+        factory-programmed memory area.
-         This driver can also be built as a module. If so, the module
--        will be called layerscape-sfp.
-+        will be called nvmem-stm32-romem.
- config NVMEM_SUNPLUS_OCOTP
-       tristate "Sunplus SoC OTP support"
-@@ -332,17 +304,15 @@ config NVMEM_SUNPLUS_OCOTP
-         This driver can also be built as a module. If so, the module
-         will be called nvmem-sunplus-ocotp.
--config NVMEM_APPLE_EFUSES
--      tristate "Apple eFuse support"
--      depends on ARCH_APPLE || COMPILE_TEST
--      default ARCH_APPLE
-+config NVMEM_SUNXI_SID
-+      tristate "Allwinner SoCs SID support"
-+      depends on ARCH_SUNXI
-       help
--        Say y here to enable support for reading eFuses on Apple SoCs
--        such as the M1. These are e.g. used to store factory programmed
--        calibration data required for the PCIe or the USB-C PHY.
-+        This is a driver for the 'security ID' available on various Allwinner
-+        devices.
--        This driver can also be built as a module. If so, the module will
--        be called nvmem-apple-efuses.
-+        This driver can also be built as a module. If so, the module
-+        will be called nvmem_sunxi_sid.
- config NVMEM_U_BOOT_ENV
-       tristate "U-Boot environment variables support"
-@@ -357,4 +327,36 @@ config NVMEM_U_BOOT_ENV
-         If compiled as module it will be called nvmem_u-boot-env.
-+config NVMEM_UNIPHIER_EFUSE
-+      tristate "UniPhier SoCs eFuse support"
-+      depends on ARCH_UNIPHIER || COMPILE_TEST
-+      depends on HAS_IOMEM
-+      help
-+        This is a simple driver to dump specified values of UniPhier SoC
-+        from eFuse.
-+
-+        This driver can also be built as a module. If so, the module
-+        will be called nvmem-uniphier-efuse.
-+
-+config NVMEM_VF610_OCOTP
-+      tristate "VF610 SoC OCOTP support"
-+      depends on SOC_VF610 || COMPILE_TEST
-+      depends on HAS_IOMEM
-+      help
-+        This is a driver for the 'OCOTP' peripheral available on Vybrid
-+        devices like VF5xx and VF6xx.
-+
-+        This driver can also be build as a module. If so, the module will
-+        be called nvmem-vf610-ocotp.
-+
-+config NVMEM_ZYNQMP
-+      bool "Xilinx ZYNQMP SoC nvmem firmware support"
-+      depends on ARCH_ZYNQMP
-+      help
-+        This is a driver to access hardware related data like
-+        soc revision, IDCODE... etc by using the firmware
-+        interface.
-+
-+        If sure, say yes. If unsure, say no.
-+
- endif
---- a/drivers/nvmem/Makefile
-+++ b/drivers/nvmem/Makefile
-@@ -7,67 +7,67 @@ obj-$(CONFIG_NVMEM)          += nvmem_core.o
- nvmem_core-y                  := core.o
- # Devices
--obj-$(CONFIG_NVMEM_BCM_OCOTP) += nvmem-bcm-ocotp.o
--nvmem-bcm-ocotp-y             := bcm-ocotp.o
--obj-$(CONFIG_NVMEM_IMX_IIM)   += nvmem-imx-iim.o
--nvmem-imx-iim-y                       := imx-iim.o
--obj-$(CONFIG_NVMEM_IMX_OCOTP) += nvmem-imx-ocotp.o
--nvmem-imx-ocotp-y             := imx-ocotp.o
-+obj-$(CONFIG_NVMEM_APPLE_EFUSES)      += nvmem-apple-efuses.o
-+nvmem-apple-efuses-y                  := apple-efuses.o
-+obj-$(CONFIG_NVMEM_BCM_OCOTP)         += nvmem-bcm-ocotp.o
-+nvmem-bcm-ocotp-y                     := bcm-ocotp.o
-+obj-$(CONFIG_NVMEM_BRCM_NVRAM)                += nvmem_brcm_nvram.o
-+nvmem_brcm_nvram-y                    := brcm_nvram.o
-+obj-$(CONFIG_NVMEM_IMX_IIM)           += nvmem-imx-iim.o
-+nvmem-imx-iim-y                               := imx-iim.o
-+obj-$(CONFIG_NVMEM_IMX_OCOTP)         += nvmem-imx-ocotp.o
-+nvmem-imx-ocotp-y                     := imx-ocotp.o
- obj-$(CONFIG_NVMEM_IMX_OCOTP_SCU)     += nvmem-imx-ocotp-scu.o
--nvmem-imx-ocotp-scu-y         := imx-ocotp-scu.o
--obj-$(CONFIG_NVMEM_JZ4780_EFUSE)              += nvmem_jz4780_efuse.o
--nvmem_jz4780_efuse-y          := jz4780-efuse.o
-+nvmem-imx-ocotp-scu-y                 := imx-ocotp-scu.o
-+obj-$(CONFIG_NVMEM_JZ4780_EFUSE)      += nvmem_jz4780_efuse.o
-+nvmem_jz4780_efuse-y                  := jz4780-efuse.o
-+obj-$(CONFIG_NVMEM_LAYERSCAPE_SFP)    += nvmem-layerscape-sfp.o
-+nvmem-layerscape-sfp-y                        := layerscape-sfp.o
- obj-$(CONFIG_NVMEM_LPC18XX_EEPROM)    += nvmem_lpc18xx_eeprom.o
--nvmem_lpc18xx_eeprom-y        := lpc18xx_eeprom.o
--obj-$(CONFIG_NVMEM_LPC18XX_OTP)       += nvmem_lpc18xx_otp.o
--nvmem_lpc18xx_otp-y           := lpc18xx_otp.o
--obj-$(CONFIG_NVMEM_MXS_OCOTP) += nvmem-mxs-ocotp.o
--nvmem-mxs-ocotp-y             := mxs-ocotp.o
--obj-$(CONFIG_NVMEM_NINTENDO_OTP)      += nvmem-nintendo-otp.o
--nvmem-nintendo-otp-y          := nintendo-otp.o
-+nvmem_lpc18xx_eeprom-y                        := lpc18xx_eeprom.o
-+obj-$(CONFIG_NVMEM_LPC18XX_OTP)               += nvmem_lpc18xx_otp.o
-+nvmem_lpc18xx_otp-y                   := lpc18xx_otp.o
-+obj-$(CONFIG_NVMEM_MESON_EFUSE)               += nvmem_meson_efuse.o
-+nvmem_meson_efuse-y                   := meson-efuse.o
-+obj-$(CONFIG_NVMEM_MESON_MX_EFUSE)    += nvmem_meson_mx_efuse.o
-+nvmem_meson_mx_efuse-y                        := meson-mx-efuse.o
-+obj-$(CONFIG_NVMEM_MICROCHIP_OTPC)    += nvmem-microchip-otpc.o
-+nvmem-microchip-otpc-y                        := microchip-otpc.o
- obj-$(CONFIG_NVMEM_MTK_EFUSE)         += nvmem_mtk-efuse.o
--nvmem_mtk-efuse-y             := mtk-efuse.o
--obj-$(CONFIG_NVMEM_QCOM_QFPROM)       += nvmem_qfprom.o
--nvmem_qfprom-y                        := qfprom.o
--obj-$(CONFIG_NVMEM_SPMI_SDAM) += nvmem_qcom-spmi-sdam.o
--nvmem_qcom-spmi-sdam-y                += qcom-spmi-sdam.o
-+nvmem_mtk-efuse-y                     := mtk-efuse.o
-+obj-$(CONFIG_NVMEM_MXS_OCOTP)         += nvmem-mxs-ocotp.o
-+nvmem-mxs-ocotp-y                     := mxs-ocotp.o
-+obj-$(CONFIG_NVMEM_NINTENDO_OTP)      += nvmem-nintendo-otp.o
-+nvmem-nintendo-otp-y                  := nintendo-otp.o
-+obj-$(CONFIG_NVMEM_QCOM_QFPROM)               += nvmem_qfprom.o
-+nvmem_qfprom-y                                := qfprom.o
-+obj-$(CONFIG_NVMEM_RAVE_SP_EEPROM)    += nvmem-rave-sp-eeprom.o
-+nvmem-rave-sp-eeprom-y                        := rave-sp-eeprom.o
-+obj-$(CONFIG_NVMEM_RMEM)              += nvmem-rmem.o
-+nvmem-rmem-y                          := rmem.o
- obj-$(CONFIG_NVMEM_ROCKCHIP_EFUSE)    += nvmem_rockchip_efuse.o
--nvmem_rockchip_efuse-y                := rockchip-efuse.o
-+nvmem_rockchip_efuse-y                        := rockchip-efuse.o
- obj-$(CONFIG_NVMEM_ROCKCHIP_OTP)      += nvmem-rockchip-otp.o
--nvmem-rockchip-otp-y          := rockchip-otp.o
--obj-$(CONFIG_NVMEM_SUNXI_SID) += nvmem_sunxi_sid.o
--nvmem_stm32_romem-y           := stm32-romem.o
--obj-$(CONFIG_NVMEM_STM32_ROMEM) += nvmem_stm32_romem.o
--nvmem_sunxi_sid-y             := sunxi_sid.o
--obj-$(CONFIG_NVMEM_UNIPHIER_EFUSE)    += nvmem-uniphier-efuse.o
--nvmem-uniphier-efuse-y                := uniphier-efuse.o
--obj-$(CONFIG_NVMEM_VF610_OCOTP)       += nvmem-vf610-ocotp.o
--nvmem-vf610-ocotp-y           := vf610-ocotp.o
--obj-$(CONFIG_NVMEM_MESON_EFUSE)       += nvmem_meson_efuse.o
--nvmem_meson_efuse-y           := meson-efuse.o
--obj-$(CONFIG_NVMEM_MESON_MX_EFUSE)    += nvmem_meson_mx_efuse.o
--nvmem_meson_mx_efuse-y                := meson-mx-efuse.o
--obj-$(CONFIG_NVMEM_SNVS_LPGPR)        += nvmem_snvs_lpgpr.o
--nvmem_snvs_lpgpr-y            := snvs_lpgpr.o
--obj-$(CONFIG_NVMEM_RAVE_SP_EEPROM)    += nvmem-rave-sp-eeprom.o
--nvmem-rave-sp-eeprom-y                := rave-sp-eeprom.o
-+nvmem-rockchip-otp-y                  := rockchip-otp.o
- obj-$(CONFIG_NVMEM_SC27XX_EFUSE)      += nvmem-sc27xx-efuse.o
--nvmem-sc27xx-efuse-y          := sc27xx-efuse.o
--obj-$(CONFIG_NVMEM_ZYNQMP)    += nvmem_zynqmp_nvmem.o
--nvmem_zynqmp_nvmem-y          := zynqmp_nvmem.o
--obj-$(CONFIG_NVMEM_SPRD_EFUSE)        += nvmem_sprd_efuse.o
--nvmem_sprd_efuse-y            := sprd-efuse.o
--obj-$(CONFIG_NVMEM_RMEM)      += nvmem-rmem.o
--nvmem-rmem-y                  := rmem.o
--obj-$(CONFIG_NVMEM_BRCM_NVRAM)        += nvmem_brcm_nvram.o
--nvmem_brcm_nvram-y            := brcm_nvram.o
--obj-$(CONFIG_NVMEM_LAYERSCAPE_SFP)    += nvmem-layerscape-sfp.o
--nvmem-layerscape-sfp-y                := layerscape-sfp.o
-+nvmem-sc27xx-efuse-y                  := sc27xx-efuse.o
-+obj-$(CONFIG_NVMEM_SNVS_LPGPR)                += nvmem_snvs_lpgpr.o
-+nvmem_snvs_lpgpr-y                    := snvs_lpgpr.o
-+obj-$(CONFIG_NVMEM_SPMI_SDAM)         += nvmem_qcom-spmi-sdam.o
-+nvmem_qcom-spmi-sdam-y                        += qcom-spmi-sdam.o
-+obj-$(CONFIG_NVMEM_SPRD_EFUSE)                += nvmem_sprd_efuse.o
-+nvmem_sprd_efuse-y                    := sprd-efuse.o
-+obj-$(CONFIG_NVMEM_STM32_ROMEM)               += nvmem_stm32_romem.o
-+nvmem_stm32_romem-y                   := stm32-romem.o
- obj-$(CONFIG_NVMEM_SUNPLUS_OCOTP)     += nvmem_sunplus_ocotp.o
--nvmem_sunplus_ocotp-y         := sunplus-ocotp.o
--obj-$(CONFIG_NVMEM_APPLE_EFUSES)      += nvmem-apple-efuses.o
--nvmem-apple-efuses-y          := apple-efuses.o
--obj-$(CONFIG_NVMEM_MICROCHIP_OTPC)    += nvmem-microchip-otpc.o
--nvmem-microchip-otpc-y                := microchip-otpc.o
--obj-$(CONFIG_NVMEM_U_BOOT_ENV)        += nvmem_u-boot-env.o
--nvmem_u-boot-env-y            := u-boot-env.o
-+nvmem_sunplus_ocotp-y                 := sunplus-ocotp.o
-+obj-$(CONFIG_NVMEM_SUNXI_SID)         += nvmem_sunxi_sid.o
-+nvmem_sunxi_sid-y                     := sunxi_sid.o
-+obj-$(CONFIG_NVMEM_U_BOOT_ENV)                += nvmem_u-boot-env.o
-+nvmem_u-boot-env-y                    := u-boot-env.o
-+obj-$(CONFIG_NVMEM_UNIPHIER_EFUSE)    += nvmem-uniphier-efuse.o
-+nvmem-uniphier-efuse-y                        := uniphier-efuse.o
-+obj-$(CONFIG_NVMEM_VF610_OCOTP)               += nvmem-vf610-ocotp.o
-+nvmem-vf610-ocotp-y                   := vf610-ocotp.o
-+obj-$(CONFIG_NVMEM_ZYNQMP)            += nvmem_zynqmp_nvmem.o
-+nvmem_zynqmp_nvmem-y                  := zynqmp_nvmem.o
diff --git a/target/linux/generic/backport-5.15/807-v6.1-0007-nvmem-u-boot-env-find-Device-Tree-nodes-for-NVMEM-ce.patch b/target/linux/generic/backport-5.15/807-v6.1-0007-nvmem-u-boot-env-find-Device-Tree-nodes-for-NVMEM-ce.patch
deleted file mode 100644 (file)
index e0a082a..0000000
+++ /dev/null
@@ -1,31 +0,0 @@
-From d4d432670f7dee0a5432fcffcfc8699b25181ace Mon Sep 17 00:00:00 2001
-From: =?UTF-8?q?Rafa=C5=82=20Mi=C5=82ecki?= <[email protected]>
-Date: Fri, 16 Sep 2022 13:20:57 +0100
-Subject: [PATCH] nvmem: u-boot-env: find Device Tree nodes for NVMEM cells
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-DT binding allows specifying NVMEM cells as NVMEM device (provider)
-subnodes. Looks for such subnodes when building NVMEM cells.
-
-This allows NVMEM consumers to use U-Boot environment variables.
-
-Signed-off-by: Rafał Miłecki <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/u-boot-env.c | 1 +
- 1 file changed, 1 insertion(+)
-
---- a/drivers/nvmem/u-boot-env.c
-+++ b/drivers/nvmem/u-boot-env.c
-@@ -92,6 +92,7 @@ static int u_boot_env_add_cells(struct u
-                       return -ENOMEM;
-               priv->cells[idx].offset = data_offset + value - data;
-               priv->cells[idx].bytes = strlen(value);
-+              priv->cells[idx].np = of_get_child_by_name(dev->of_node, priv->cells[idx].name);
-       }
-       if (WARN_ON(idx != priv->ncells))
diff --git a/target/linux/generic/backport-5.15/807-v6.1-0008-nvmem-lan9662-otp-add-support.patch b/target/linux/generic/backport-5.15/807-v6.1-0008-nvmem-lan9662-otp-add-support.patch
deleted file mode 100644 (file)
index 945c612..0000000
+++ /dev/null
@@ -1,274 +0,0 @@
-From 9e8f208ad5229ddda97cd4a83ecf89c735d99592 Mon Sep 17 00:00:00 2001
-From: Horatiu Vultur <[email protected]>
-Date: Fri, 16 Sep 2022 13:20:59 +0100
-Subject: [PATCH] nvmem: lan9662-otp: add support
-
-Add support for OTP controller available on LAN9662. The OTPC controls
-the access to a non-volatile memory. The size of the memory is 8KB.
-The OTPC can access the memory based on an offset.
-Implement both the read and the write functionality.
-
-Signed-off-by: Horatiu Vultur <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/Kconfig        |   8 ++
- drivers/nvmem/Makefile       |   2 +
- drivers/nvmem/lan9662-otpc.c | 222 +++++++++++++++++++++++++++++++++++
- 3 files changed, 232 insertions(+)
- create mode 100644 drivers/nvmem/lan9662-otpc.c
-
---- a/drivers/nvmem/Kconfig
-+++ b/drivers/nvmem/Kconfig
-@@ -98,6 +98,14 @@ config NVMEM_JZ4780_EFUSE
-         To compile this driver as a module, choose M here: the module
-         will be called nvmem_jz4780_efuse.
-+config NVMEM_LAN9662_OTPC
-+      tristate "Microchip LAN9662 OTP controller support"
-+      depends on SOC_LAN966 || COMPILE_TEST
-+      depends on HAS_IOMEM
-+      help
-+        This driver enables the OTP controller available on Microchip LAN9662
-+        SoCs. It controls the access to the OTP memory connected to it.
-+
- config NVMEM_LAYERSCAPE_SFP
-       tristate "Layerscape SFP (Security Fuse Processor) support"
-       depends on ARCH_LAYERSCAPE || COMPILE_TEST
---- a/drivers/nvmem/Makefile
-+++ b/drivers/nvmem/Makefile
-@@ -21,6 +21,8 @@ obj-$(CONFIG_NVMEM_IMX_OCOTP_SCU)    += nvm
- nvmem-imx-ocotp-scu-y                 := imx-ocotp-scu.o
- obj-$(CONFIG_NVMEM_JZ4780_EFUSE)      += nvmem_jz4780_efuse.o
- nvmem_jz4780_efuse-y                  := jz4780-efuse.o
-+obj-$(CONFIG_NVMEM_LAN9662_OTPC)      += nvmem-lan9662-otpc.o
-+nvmem-lan9662-otpc-y          := lan9662-otpc.o
- obj-$(CONFIG_NVMEM_LAYERSCAPE_SFP)    += nvmem-layerscape-sfp.o
- nvmem-layerscape-sfp-y                        := layerscape-sfp.o
- obj-$(CONFIG_NVMEM_LPC18XX_EEPROM)    += nvmem_lpc18xx_eeprom.o
---- /dev/null
-+++ b/drivers/nvmem/lan9662-otpc.c
-@@ -0,0 +1,222 @@
-+// SPDX-License-Identifier: GPL-2.0
-+
-+#include <linux/iopoll.h>
-+#include <linux/module.h>
-+#include <linux/nvmem-provider.h>
-+#include <linux/of.h>
-+#include <linux/platform_device.h>
-+
-+#define OTP_OTP_PWR_DN(t)                     (t + 0x00)
-+#define OTP_OTP_PWR_DN_OTP_PWRDN_N            BIT(0)
-+#define OTP_OTP_ADDR_HI(t)                    (t + 0x04)
-+#define OTP_OTP_ADDR_LO(t)                    (t + 0x08)
-+#define OTP_OTP_PRGM_DATA(t)                  (t + 0x10)
-+#define OTP_OTP_PRGM_MODE(t)                  (t + 0x14)
-+#define OTP_OTP_PRGM_MODE_OTP_PGM_MODE_BYTE   BIT(0)
-+#define OTP_OTP_RD_DATA(t)                    (t + 0x18)
-+#define OTP_OTP_FUNC_CMD(t)                   (t + 0x20)
-+#define OTP_OTP_FUNC_CMD_OTP_PROGRAM          BIT(1)
-+#define OTP_OTP_FUNC_CMD_OTP_READ             BIT(0)
-+#define OTP_OTP_CMD_GO(t)                     (t + 0x28)
-+#define OTP_OTP_CMD_GO_OTP_GO                 BIT(0)
-+#define OTP_OTP_PASS_FAIL(t)                  (t + 0x2c)
-+#define OTP_OTP_PASS_FAIL_OTP_READ_PROHIBITED BIT(3)
-+#define OTP_OTP_PASS_FAIL_OTP_WRITE_PROHIBITED        BIT(2)
-+#define OTP_OTP_PASS_FAIL_OTP_FAIL            BIT(0)
-+#define OTP_OTP_STATUS(t)                     (t + 0x30)
-+#define OTP_OTP_STATUS_OTP_CPUMPEN            BIT(1)
-+#define OTP_OTP_STATUS_OTP_BUSY                       BIT(0)
-+
-+#define OTP_MEM_SIZE 8192
-+#define OTP_SLEEP_US 10
-+#define OTP_TIMEOUT_US 500000
-+
-+struct lan9662_otp {
-+      struct device *dev;
-+      void __iomem *base;
-+};
-+
-+static bool lan9662_otp_wait_flag_clear(void __iomem *reg, u32 flag)
-+{
-+      u32 val;
-+
-+      return readl_poll_timeout(reg, val, !(val & flag),
-+                                OTP_SLEEP_US, OTP_TIMEOUT_US);
-+}
-+
-+static int lan9662_otp_power(struct lan9662_otp *otp, bool up)
-+{
-+      void __iomem *pwrdn = OTP_OTP_PWR_DN(otp->base);
-+
-+      if (up) {
-+              writel(readl(pwrdn) & ~OTP_OTP_PWR_DN_OTP_PWRDN_N, pwrdn);
-+              if (lan9662_otp_wait_flag_clear(OTP_OTP_STATUS(otp->base),
-+                                              OTP_OTP_STATUS_OTP_CPUMPEN))
-+                      return -ETIMEDOUT;
-+      } else {
-+              writel(readl(pwrdn) | OTP_OTP_PWR_DN_OTP_PWRDN_N, pwrdn);
-+      }
-+
-+      return 0;
-+}
-+
-+static int lan9662_otp_execute(struct lan9662_otp *otp)
-+{
-+      if (lan9662_otp_wait_flag_clear(OTP_OTP_CMD_GO(otp->base),
-+                                      OTP_OTP_CMD_GO_OTP_GO))
-+              return -ETIMEDOUT;
-+
-+      if (lan9662_otp_wait_flag_clear(OTP_OTP_STATUS(otp->base),
-+                                      OTP_OTP_STATUS_OTP_BUSY))
-+              return -ETIMEDOUT;
-+
-+      return 0;
-+}
-+
-+static void lan9662_otp_set_address(struct lan9662_otp *otp, u32 offset)
-+{
-+      writel(0xff & (offset >> 8), OTP_OTP_ADDR_HI(otp->base));
-+      writel(0xff & offset, OTP_OTP_ADDR_LO(otp->base));
-+}
-+
-+static int lan9662_otp_read_byte(struct lan9662_otp *otp, u32 offset, u8 *dst)
-+{
-+      u32 pass;
-+      int rc;
-+
-+      lan9662_otp_set_address(otp, offset);
-+      writel(OTP_OTP_FUNC_CMD_OTP_READ, OTP_OTP_FUNC_CMD(otp->base));
-+      writel(OTP_OTP_CMD_GO_OTP_GO, OTP_OTP_CMD_GO(otp->base));
-+      rc = lan9662_otp_execute(otp);
-+      if (!rc) {
-+              pass = readl(OTP_OTP_PASS_FAIL(otp->base));
-+              if (pass & OTP_OTP_PASS_FAIL_OTP_READ_PROHIBITED)
-+                      return -EACCES;
-+              *dst = (u8) readl(OTP_OTP_RD_DATA(otp->base));
-+      }
-+      return rc;
-+}
-+
-+static int lan9662_otp_write_byte(struct lan9662_otp *otp, u32 offset, u8 data)
-+{
-+      u32 pass;
-+      int rc;
-+
-+      lan9662_otp_set_address(otp, offset);
-+      writel(OTP_OTP_PRGM_MODE_OTP_PGM_MODE_BYTE, OTP_OTP_PRGM_MODE(otp->base));
-+      writel(data, OTP_OTP_PRGM_DATA(otp->base));
-+      writel(OTP_OTP_FUNC_CMD_OTP_PROGRAM, OTP_OTP_FUNC_CMD(otp->base));
-+      writel(OTP_OTP_CMD_GO_OTP_GO, OTP_OTP_CMD_GO(otp->base));
-+
-+      rc = lan9662_otp_execute(otp);
-+      if (!rc) {
-+              pass = readl(OTP_OTP_PASS_FAIL(otp->base));
-+              if (pass & OTP_OTP_PASS_FAIL_OTP_WRITE_PROHIBITED)
-+                      return -EACCES;
-+              if (pass & OTP_OTP_PASS_FAIL_OTP_FAIL)
-+                      return -EIO;
-+      }
-+      return rc;
-+}
-+
-+static int lan9662_otp_read(void *context, unsigned int offset,
-+                          void *_val, size_t bytes)
-+{
-+      struct lan9662_otp *otp = context;
-+      u8 *val = _val;
-+      uint8_t data;
-+      int i, rc = 0;
-+
-+      lan9662_otp_power(otp, true);
-+      for (i = 0; i < bytes; i++) {
-+              rc = lan9662_otp_read_byte(otp, offset + i, &data);
-+              if (rc < 0)
-+                      break;
-+              *val++ = data;
-+      }
-+      lan9662_otp_power(otp, false);
-+
-+      return rc;
-+}
-+
-+static int lan9662_otp_write(void *context, unsigned int offset,
-+                           void *_val, size_t bytes)
-+{
-+      struct lan9662_otp *otp = context;
-+      u8 *val = _val;
-+      u8 data, newdata;
-+      int i, rc = 0;
-+
-+      lan9662_otp_power(otp, true);
-+      for (i = 0; i < bytes; i++) {
-+              /* Skip zero bytes */
-+              if (val[i]) {
-+                      rc = lan9662_otp_read_byte(otp, offset + i, &data);
-+                      if (rc < 0)
-+                              break;
-+
-+                      newdata = data | val[i];
-+                      if (newdata == data)
-+                              continue;
-+
-+                      rc = lan9662_otp_write_byte(otp, offset + i,
-+                                                    newdata);
-+                      if (rc < 0)
-+                              break;
-+              }
-+      }
-+      lan9662_otp_power(otp, false);
-+
-+      return rc;
-+}
-+
-+static struct nvmem_config otp_config = {
-+      .name = "lan9662-otp",
-+      .stride = 1,
-+      .word_size = 1,
-+      .reg_read = lan9662_otp_read,
-+      .reg_write = lan9662_otp_write,
-+      .size = OTP_MEM_SIZE,
-+};
-+
-+static int lan9662_otp_probe(struct platform_device *pdev)
-+{
-+      struct device *dev = &pdev->dev;
-+      struct nvmem_device *nvmem;
-+      struct lan9662_otp *otp;
-+
-+      otp = devm_kzalloc(&pdev->dev, sizeof(*otp), GFP_KERNEL);
-+      if (!otp)
-+              return -ENOMEM;
-+
-+      otp->dev = dev;
-+      otp->base = devm_platform_ioremap_resource(pdev, 0);
-+      if (IS_ERR(otp->base))
-+              return PTR_ERR(otp->base);
-+
-+      otp_config.priv = otp;
-+      otp_config.dev = dev;
-+
-+      nvmem = devm_nvmem_register(dev, &otp_config);
-+
-+      return PTR_ERR_OR_ZERO(nvmem);
-+}
-+
-+static const struct of_device_id lan9662_otp_match[] = {
-+      { .compatible = "microchip,lan9662-otp", },
-+      { },
-+};
-+MODULE_DEVICE_TABLE(of, lan9662_otp_match);
-+
-+static struct platform_driver lan9662_otp_driver = {
-+      .probe = lan9662_otp_probe,
-+      .driver = {
-+              .name = "lan9662-otp",
-+              .of_match_table = lan9662_otp_match,
-+      },
-+};
-+module_platform_driver(lan9662_otp_driver);
-+
-+MODULE_AUTHOR("Horatiu Vultur <[email protected]>");
-+MODULE_DESCRIPTION("lan9662 OTP driver");
-+MODULE_LICENSE("GPL");
diff --git a/target/linux/generic/backport-5.15/807-v6.1-0009-nvmem-u-boot-env-fix-crc32-casting-type.patch b/target/linux/generic/backport-5.15/807-v6.1-0009-nvmem-u-boot-env-fix-crc32-casting-type.patch
deleted file mode 100644 (file)
index 633a668..0000000
+++ /dev/null
@@ -1,32 +0,0 @@
-From 3717ca3e0cc8683f93b41d3f06ca79631eb58715 Mon Sep 17 00:00:00 2001
-From: =?UTF-8?q?Rafa=C5=82=20Mi=C5=82ecki?= <[email protected]>
-Date: Fri, 16 Sep 2022 13:21:00 +0100
-Subject: [PATCH] nvmem: u-boot-env: fix crc32 casting type
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-This fixes:
-drivers/nvmem/u-boot-env.c:141:17: sparse: sparse: cast to restricted __le32
-
-Fixes: d5542923f200 ("nvmem: add driver handling U-Boot environment variables")
-Reported-by: kernel test robot <[email protected]>
-Signed-off-by: Rafał Miłecki <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/u-boot-env.c | 2 +-
- 1 file changed, 1 insertion(+), 1 deletion(-)
-
---- a/drivers/nvmem/u-boot-env.c
-+++ b/drivers/nvmem/u-boot-env.c
-@@ -139,7 +139,7 @@ static int u_boot_env_parse(struct u_boo
-               data_offset = offsetof(struct u_boot_env_image_redundant, data);
-               break;
-       }
--      crc32 = le32_to_cpu(*(uint32_t *)(buf + crc32_offset));
-+      crc32 = le32_to_cpu(*(__le32 *)(buf + crc32_offset));
-       crc32_data_len = priv->mtd->size - crc32_data_offset;
-       data_len = priv->mtd->size - data_offset;
diff --git a/target/linux/generic/backport-5.15/807-v6.1-0010-nvmem-lan9662-otp-Fix-compatible-string.patch b/target/linux/generic/backport-5.15/807-v6.1-0010-nvmem-lan9662-otp-Fix-compatible-string.patch
deleted file mode 100644 (file)
index b663a13..0000000
+++ /dev/null
@@ -1,34 +0,0 @@
-From 1aeb122d214b92474c86fde00a03d6e2d69381b5 Mon Sep 17 00:00:00 2001
-From: Horatiu Vultur <[email protected]>
-Date: Wed, 28 Sep 2022 21:51:12 +0200
-Subject: [PATCH] nvmem: lan9662-otp: Fix compatible string
-
-The device tree bindings for lan9662-otp expects the compatible string
-to be one of following compatible strings:
-microchip,lan9662-otpc
-microchip,lan9668-otpc
-
-The problem is that the lan9662-otp driver contains the
-microchip,lan9662-otp compatible string instead of
-microchip,lan9662-otpc.
-Fix this by updating the compatible string in the driver.
-
-Fixes: 9e8f208ad5229d ("nvmem: lan9662-otp: add support")
-Signed-off-by: Horatiu Vultur <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/lan9662-otpc.c | 2 +-
- 1 file changed, 1 insertion(+), 1 deletion(-)
-
---- a/drivers/nvmem/lan9662-otpc.c
-+++ b/drivers/nvmem/lan9662-otpc.c
-@@ -203,7 +203,7 @@ static int lan9662_otp_probe(struct plat
- }
- static const struct of_device_id lan9662_otp_match[] = {
--      { .compatible = "microchip,lan9662-otp", },
-+      { .compatible = "microchip,lan9662-otpc", },
-       { },
- };
- MODULE_DEVICE_TABLE(of, lan9662_otp_match);
diff --git a/target/linux/generic/backport-5.15/807-v6.1-0011-nvmem-u-boot-env-fix-crc32_data_offset-on-redundant-.patch b/target/linux/generic/backport-5.15/807-v6.1-0011-nvmem-u-boot-env-fix-crc32_data_offset-on-redundant-.patch
deleted file mode 100644 (file)
index 967e891..0000000
+++ /dev/null
@@ -1,59 +0,0 @@
-From ee424f7d3960152f5f862bbb6943e59828dc7917 Mon Sep 17 00:00:00 2001
-From: Christian Lamparter <[email protected]>
-Date: Fri, 4 Nov 2022 17:52:03 +0100
-Subject: [PATCH] nvmem: u-boot-env: fix crc32_data_offset on redundant
- u-boot-env
-
-The Western Digital MyBook Live (PowerPC 464/APM82181)
-has a set of redundant u-boot-env. Loading up the driver
-the following error:
-
-| u_boot_env: Invalid calculated CRC32: 0x4f8f2c86 (expected: 0x98b14514)
-| u_boot_env: probe of partition@1e000 failed with error -22
-
-Looking up the userspace libubootenv utilities source [0],
-it looks like the "mark" or "flag" is not part of the
-crc32 sum... which is unfortunate :(
-
-|static int libuboot_load(struct uboot_ctx *ctx)
-|{
-|[...]
-|       if (ctx->redundant) {
-|              [...]
-|               offsetdata = offsetof(struct uboot_env_redund, data);
-|              [...]                                   //-----^^
-|       }
-|       usable_envsize = ctx->size - offsetdata;
-|       buf[0] = malloc(bufsize);
-|[...]
-|      for (i = 0; i < copies; i++) {
-|              data = (uint8_t *)(buf[i] + offsetdata);
-|               uint32_t crc;
-|
-|              ret = devread(ctx, i, buf[i]);
-|              [...]
-|              crc = *(uint32_t *)(buf[i] + offsetcrc);
-|               dev->crc = crc32(0, (uint8_t *)data, usable_envsize);
-|
-
-[0] https://github.com/sbabic/libubootenv/blob/master/src/uboot_env.c#L951
-
-Fixes: d5542923f200 ("nvmem: add driver handling U-Boot environment variables")
-Signed-off-by: Christian Lamparter <[email protected]>
-Link: https://lore.kernel.org/r/70a16eae113e08db2390b76e174f4837caa135c3.1667580636.git.chunkeey@gmail.com
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/u-boot-env.c | 2 +-
- 1 file changed, 1 insertion(+), 1 deletion(-)
-
---- a/drivers/nvmem/u-boot-env.c
-+++ b/drivers/nvmem/u-boot-env.c
-@@ -135,7 +135,7 @@ static int u_boot_env_parse(struct u_boo
-               break;
-       case U_BOOT_FORMAT_REDUNDANT:
-               crc32_offset = offsetof(struct u_boot_env_image_redundant, crc32);
--              crc32_data_offset = offsetof(struct u_boot_env_image_redundant, mark);
-+              crc32_data_offset = offsetof(struct u_boot_env_image_redundant, data);
-               data_offset = offsetof(struct u_boot_env_image_redundant, data);
-               break;
-       }
diff --git a/target/linux/generic/backport-5.15/807-v6.1-0013-nvmem-lan9662-otp-Change-return-type-of-lan9662_otp_.patch b/target/linux/generic/backport-5.15/807-v6.1-0013-nvmem-lan9662-otp-Change-return-type-of-lan9662_otp_.patch
deleted file mode 100644 (file)
index 0c842f0..0000000
+++ /dev/null
@@ -1,35 +0,0 @@
-From 022b68f271de0e53024e6d5e96fee8e76d25eb95 Mon Sep 17 00:00:00 2001
-From: Horatiu Vultur <[email protected]>
-Date: Fri, 18 Nov 2022 06:38:40 +0000
-Subject: [PATCH] nvmem: lan9662-otp: Change return type of
- lan9662_otp_wait_flag_clear()
-
-The blamed commit introduced the following smatch warning in the
-function lan9662_otp_wait_flag_clear:
-drivers/nvmem/lan9662-otpc.c:43 lan9662_otp_wait_flag_clear() warn: signedness bug returning '(-110)'
-
-Fix this by changing the return type of the function
-lan9662_otp_wait_flag_clear() to be int instead of bool.
-
-Fixes: 9e8f208ad5229d ("nvmem: lan9662-otp: add support")
-Reported-by: kernel test robot <[email protected]>
-Reported-by: Dan Carpenter <[email protected]>
-Signed-off-by: Horatiu Vultur <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/lan9662-otpc.c | 2 +-
- 1 file changed, 1 insertion(+), 1 deletion(-)
-
---- a/drivers/nvmem/lan9662-otpc.c
-+++ b/drivers/nvmem/lan9662-otpc.c
-@@ -36,7 +36,7 @@ struct lan9662_otp {
-       void __iomem *base;
- };
--static bool lan9662_otp_wait_flag_clear(void __iomem *reg, u32 flag)
-+static int lan9662_otp_wait_flag_clear(void __iomem *reg, u32 flag)
- {
-       u32 val;
diff --git a/target/linux/generic/backport-5.15/808-v6.2-0001-nvmem-stm32-move-STM32MP15_BSEC_NUM_LOWER-in-config.patch b/target/linux/generic/backport-5.15/808-v6.2-0001-nvmem-stm32-move-STM32MP15_BSEC_NUM_LOWER-in-config.patch
deleted file mode 100644 (file)
index 3375963..0000000
+++ /dev/null
@@ -1,82 +0,0 @@
-From fbfc4ca465a1f8d81bf2d67d95bf7fc67c3cf0c2 Mon Sep 17 00:00:00 2001
-From: Patrick Delaunay <[email protected]>
-Date: Fri, 18 Nov 2022 06:39:20 +0000
-Subject: [PATCH] nvmem: stm32: move STM32MP15_BSEC_NUM_LOWER in config
-
-Support STM32MP15_BSEC_NUM_LOWER in stm32 romem config to prepare
-the next SoC in STM32MP family.
-
-Signed-off-by: Patrick Delaunay <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/stm32-romem.c | 21 ++++++++++++++++-----
- 1 file changed, 16 insertions(+), 5 deletions(-)
-
---- a/drivers/nvmem/stm32-romem.c
-+++ b/drivers/nvmem/stm32-romem.c
-@@ -22,16 +22,15 @@
- /* shadow registers offest */
- #define STM32MP15_BSEC_DATA0          0x200
--/* 32 (x 32-bits) lower shadow registers */
--#define STM32MP15_BSEC_NUM_LOWER      32
--
- struct stm32_romem_cfg {
-       int size;
-+      u8 lower;
- };
- struct stm32_romem_priv {
-       void __iomem *base;
-       struct nvmem_config cfg;
-+      u8 lower;
- };
- static int stm32_romem_read(void *context, unsigned int offset, void *buf,
-@@ -85,7 +84,7 @@ static int stm32_bsec_read(void *context
-       for (i = roffset; (i < roffset + rbytes); i += 4) {
-               u32 otp = i >> 2;
--              if (otp < STM32MP15_BSEC_NUM_LOWER) {
-+              if (otp < priv->lower) {
-                       /* read lower data from shadow registers */
-                       val = readl_relaxed(
-                               priv->base + STM32MP15_BSEC_DATA0 + i);
-@@ -159,6 +158,8 @@ static int stm32_romem_probe(struct plat
-       priv->cfg.priv = priv;
-       priv->cfg.owner = THIS_MODULE;
-+      priv->lower = 0;
-+
-       cfg = (const struct stm32_romem_cfg *)
-               of_match_device(dev->driver->of_match_table, dev)->data;
-       if (!cfg) {
-@@ -167,6 +168,7 @@ static int stm32_romem_probe(struct plat
-               priv->cfg.reg_read = stm32_romem_read;
-       } else {
-               priv->cfg.size = cfg->size;
-+              priv->lower = cfg->lower;
-               priv->cfg.reg_read = stm32_bsec_read;
-               priv->cfg.reg_write = stm32_bsec_write;
-       }
-@@ -174,8 +176,17 @@ static int stm32_romem_probe(struct plat
-       return PTR_ERR_OR_ZERO(devm_nvmem_register(dev, &priv->cfg));
- }
-+/*
-+ * STM32MP15 BSEC OTP regions: 4096 OTP bits (with 3072 effective bits)
-+ * => 96 x 32-bits data words
-+ * - Lower: 1K bits, 2:1 redundancy, incremental bit programming
-+ *   => 32 (x 32-bits) lower shadow registers = words 0 to 31
-+ * - Upper: 2K bits, ECC protection, word programming only
-+ *   => 64 (x 32-bits) = words 32 to 95
-+ */
- static const struct stm32_romem_cfg stm32mp15_bsec_cfg = {
--      .size = 384, /* 96 x 32-bits data words */
-+      .size = 384,
-+      .lower = 32,
- };
- static const struct of_device_id stm32_romem_of_match[] = {
diff --git a/target/linux/generic/backport-5.15/808-v6.2-0002-nvmem-stm32-add-warning-when-upper-OTPs-are-updated.patch b/target/linux/generic/backport-5.15/808-v6.2-0002-nvmem-stm32-add-warning-when-upper-OTPs-are-updated.patch
deleted file mode 100644 (file)
index 5791df2..0000000
+++ /dev/null
@@ -1,34 +0,0 @@
-From d61784e6410f3df2028e6eb91b06ffed37a660e0 Mon Sep 17 00:00:00 2001
-From: Patrick Delaunay <[email protected]>
-Date: Fri, 18 Nov 2022 06:39:21 +0000
-Subject: [PATCH] nvmem: stm32: add warning when upper OTPs are updated
-
-As the upper OTPs are ECC protected, they support only one 32 bits word
-programming.
-For a second modification of this word, these ECC become invalid and
-this OTP will be no more accessible, the shadowed value is invalid.
-
-This patch adds a warning to indicate an upper OTP update, because this
-operation is dangerous as OTP is not locked by the driver after the first
-update to avoid a second update.
-
-Signed-off-by: Patrick Delaunay <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/stm32-romem.c | 3 +++
- 1 file changed, 3 insertions(+)
-
---- a/drivers/nvmem/stm32-romem.c
-+++ b/drivers/nvmem/stm32-romem.c
-@@ -132,6 +132,9 @@ static int stm32_bsec_write(void *contex
-               }
-       }
-+      if (offset + bytes >= priv->lower * 4)
-+              dev_warn(dev, "Update of upper OTPs with ECC protection (word programming, only once)\n");
-+
-       return 0;
- }
diff --git a/target/linux/generic/backport-5.15/808-v6.2-0003-nvmem-stm32-add-nvmem-type-attribute.patch b/target/linux/generic/backport-5.15/808-v6.2-0003-nvmem-stm32-add-nvmem-type-attribute.patch
deleted file mode 100644 (file)
index b83ad69..0000000
+++ /dev/null
@@ -1,26 +0,0 @@
-From a3816a7d7c097c1da46aad5f5d1e229b607dce04 Mon Sep 17 00:00:00 2001
-From: Patrick Delaunay <[email protected]>
-Date: Fri, 18 Nov 2022 06:39:22 +0000
-Subject: [PATCH] nvmem: stm32: add nvmem type attribute
-
-Inform NVMEM framework of type attribute for stm32-romem as NVMEM_TYPE_OTP
-so userspace is able to know how the data is stored in BSEC.
-
-Signed-off-by: Patrick Delaunay <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/stm32-romem.c | 1 +
- 1 file changed, 1 insertion(+)
-
---- a/drivers/nvmem/stm32-romem.c
-+++ b/drivers/nvmem/stm32-romem.c
-@@ -160,6 +160,7 @@ static int stm32_romem_probe(struct plat
-       priv->cfg.dev = dev;
-       priv->cfg.priv = priv;
-       priv->cfg.owner = THIS_MODULE;
-+      priv->cfg.type = NVMEM_TYPE_OTP;
-       priv->lower = 0;
diff --git a/target/linux/generic/backport-5.15/808-v6.2-0004-nvmem-stm32-fix-spelling-typo-in-comment.patch b/target/linux/generic/backport-5.15/808-v6.2-0004-nvmem-stm32-fix-spelling-typo-in-comment.patch
deleted file mode 100644 (file)
index 52ba1e6..0000000
+++ /dev/null
@@ -1,27 +0,0 @@
-From 06aac0e11960a7ddccc1888326b5906d017e0f24 Mon Sep 17 00:00:00 2001
-From: Jiangshan Yi <[email protected]>
-Date: Fri, 18 Nov 2022 06:39:24 +0000
-Subject: [PATCH] nvmem: stm32: fix spelling typo in comment
-
-Fix spelling typo in comment.
-
-Reported-by: k2ci <[email protected]>
-Signed-off-by: Jiangshan Yi <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/stm32-romem.c | 2 +-
- 1 file changed, 1 insertion(+), 1 deletion(-)
-
---- a/drivers/nvmem/stm32-romem.c
-+++ b/drivers/nvmem/stm32-romem.c
-@@ -19,7 +19,7 @@
- #define STM32_SMC_WRITE_SHADOW                0x03
- #define STM32_SMC_READ_OTP            0x04
--/* shadow registers offest */
-+/* shadow registers offset */
- #define STM32MP15_BSEC_DATA0          0x200
- struct stm32_romem_cfg {
diff --git a/target/linux/generic/backport-5.15/808-v6.2-0005-nvmem-Kconfig-Fix-spelling-mistake-controlls-control.patch b/target/linux/generic/backport-5.15/808-v6.2-0005-nvmem-Kconfig-Fix-spelling-mistake-controlls-control.patch
deleted file mode 100644 (file)
index 8f024f4..0000000
+++ /dev/null
@@ -1,27 +0,0 @@
-From fb817c4ef63e8cfb6e77ae4a2875ae854c80708f Mon Sep 17 00:00:00 2001
-From: Colin Ian King <[email protected]>
-Date: Fri, 18 Nov 2022 06:39:26 +0000
-Subject: [PATCH] nvmem: Kconfig: Fix spelling mistake "controlls" ->
- "controls"
-
-There is a spelling mistake in a Kconfig description. Fix it.
-
-Signed-off-by: Colin Ian King <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/Kconfig | 2 +-
- 1 file changed, 1 insertion(+), 1 deletion(-)
-
---- a/drivers/nvmem/Kconfig
-+++ b/drivers/nvmem/Kconfig
-@@ -164,7 +164,7 @@ config NVMEM_MICROCHIP_OTPC
-       depends on ARCH_AT91 || COMPILE_TEST
-       help
-         This driver enable the OTP controller available on Microchip SAMA7G5
--        SoCs. It controlls the access to the OTP memory connected to it.
-+        SoCs. It controls the access to the OTP memory connected to it.
- config NVMEM_MTK_EFUSE
-       tristate "Mediatek SoCs EFUSE support"
diff --git a/target/linux/generic/backport-5.15/808-v6.2-0006-nvmem-u-boot-env-add-Broadcom-format-support.patch b/target/linux/generic/backport-5.15/808-v6.2-0006-nvmem-u-boot-env-add-Broadcom-format-support.patch
deleted file mode 100644 (file)
index 861386a..0000000
+++ /dev/null
@@ -1,67 +0,0 @@
-From ada84d07af6097b2addd18262668ce6cb9e15206 Mon Sep 17 00:00:00 2001
-From: =?UTF-8?q?Rafa=C5=82=20Mi=C5=82ecki?= <[email protected]>
-Date: Fri, 18 Nov 2022 06:39:27 +0000
-Subject: [PATCH] nvmem: u-boot-env: add Broadcom format support
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-Broadcom uses U-Boot for a lot of their bcmbca familiy chipsets. They
-decided to store U-Boot environment data inside U-Boot partition and to
-use a custom header (with "uEnv" magic and env data length).
-
-Add support for Broadcom's specific binding and their custom format.
-
-Ref: 6b0584c19d87 ("dt-bindings: nvmem: u-boot,env: add Broadcom's variant binding")
-Signed-off-by: Rafał Miłecki <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/u-boot-env.c | 14 ++++++++++++++
- 1 file changed, 14 insertions(+)
-
---- a/drivers/nvmem/u-boot-env.c
-+++ b/drivers/nvmem/u-boot-env.c
-@@ -16,6 +16,7 @@
- enum u_boot_env_format {
-       U_BOOT_FORMAT_SINGLE,
-       U_BOOT_FORMAT_REDUNDANT,
-+      U_BOOT_FORMAT_BROADCOM,
- };
- struct u_boot_env {
-@@ -40,6 +41,13 @@ struct u_boot_env_image_redundant {
-       uint8_t data[];
- } __packed;
-+struct u_boot_env_image_broadcom {
-+      __le32 magic;
-+      __le32 len;
-+      __le32 crc32;
-+      uint8_t data[0];
-+} __packed;
-+
- static int u_boot_env_read(void *context, unsigned int offset, void *val,
-                          size_t bytes)
- {
-@@ -138,6 +146,11 @@ static int u_boot_env_parse(struct u_boo
-               crc32_data_offset = offsetof(struct u_boot_env_image_redundant, data);
-               data_offset = offsetof(struct u_boot_env_image_redundant, data);
-               break;
-+      case U_BOOT_FORMAT_BROADCOM:
-+              crc32_offset = offsetof(struct u_boot_env_image_broadcom, crc32);
-+              crc32_data_offset = offsetof(struct u_boot_env_image_broadcom, data);
-+              data_offset = offsetof(struct u_boot_env_image_broadcom, data);
-+              break;
-       }
-       crc32 = le32_to_cpu(*(__le32 *)(buf + crc32_offset));
-       crc32_data_len = priv->mtd->size - crc32_data_offset;
-@@ -202,6 +215,7 @@ static const struct of_device_id u_boot_
-       { .compatible = "u-boot,env", .data = (void *)U_BOOT_FORMAT_SINGLE, },
-       { .compatible = "u-boot,env-redundant-bool", .data = (void *)U_BOOT_FORMAT_REDUNDANT, },
-       { .compatible = "u-boot,env-redundant-count", .data = (void *)U_BOOT_FORMAT_REDUNDANT, },
-+      { .compatible = "brcm,env", .data = (void *)U_BOOT_FORMAT_BROADCOM, },
-       {},
- };
diff --git a/target/linux/generic/backport-5.15/808-v6.2-0007-nvmem-brcm_nvram-Add-check-for-kzalloc.patch b/target/linux/generic/backport-5.15/808-v6.2-0007-nvmem-brcm_nvram-Add-check-for-kzalloc.patch
deleted file mode 100644 (file)
index 14108b5..0000000
+++ /dev/null
@@ -1,30 +0,0 @@
-From b0576ade3aaf24b376ea1a4406ae138e2a22b0c0 Mon Sep 17 00:00:00 2001
-From: Jiasheng Jiang <[email protected]>
-Date: Fri, 27 Jan 2023 10:40:06 +0000
-Subject: [PATCH] nvmem: brcm_nvram: Add check for kzalloc
-
-Add the check for the return value of kzalloc in order to avoid
-NULL pointer dereference.
-
-Fixes: 6e977eaa8280 ("nvmem: brcm_nvram: parse NVRAM content into NVMEM cells")
-Signed-off-by: Jiasheng Jiang <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/brcm_nvram.c | 3 +++
- 1 file changed, 3 insertions(+)
-
---- a/drivers/nvmem/brcm_nvram.c
-+++ b/drivers/nvmem/brcm_nvram.c
-@@ -97,6 +97,9 @@ static int brcm_nvram_parse(struct brcm_
-       len = le32_to_cpu(header.len);
-       data = kzalloc(len, GFP_KERNEL);
-+      if (!data)
-+              return -ENOMEM;
-+
-       memcpy_fromio(data, priv->base, len);
-       data[len - 1] = '\0';
diff --git a/target/linux/generic/backport-5.15/808-v6.2-0008-nvmem-sunxi_sid-Always-use-32-bit-MMIO-reads.patch b/target/linux/generic/backport-5.15/808-v6.2-0008-nvmem-sunxi_sid-Always-use-32-bit-MMIO-reads.patch
deleted file mode 100644 (file)
index 632b01c..0000000
+++ /dev/null
@@ -1,55 +0,0 @@
-From c151d5ed8e8fe0474bd61dce7f2076ca5916c683 Mon Sep 17 00:00:00 2001
-From: Samuel Holland <[email protected]>
-Date: Fri, 27 Jan 2023 10:40:07 +0000
-Subject: [PATCH] nvmem: sunxi_sid: Always use 32-bit MMIO reads
-
-The SID SRAM on at least some SoCs (A64 and D1) returns different values
-when read with bus cycles narrower than 32 bits. This is not immediately
-obvious, because memcpy_fromio() uses word-size accesses as long as
-enough data is being copied.
-
-The vendor driver always uses 32-bit MMIO reads, so do the same here.
-This is faster than the register-based method, which is currently used
-as a workaround on A64. And it fixes the values returned on D1, where
-the SRAM method was being used.
-
-The special case for the last word is needed to maintain .word_size == 1
-for sysfs ABI compatibility, as noted previously in commit de2a3eaea552
-("nvmem: sunxi_sid: Optimize register read-out method").
-
-Fixes: 07ae4fde9efa ("nvmem: sunxi_sid: Add support for D1 variant")
-Tested-by: Heiko Stuebner <[email protected]>
-Signed-off-by: Samuel Holland <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/sunxi_sid.c | 15 ++++++++++++++-
- 1 file changed, 14 insertions(+), 1 deletion(-)
-
---- a/drivers/nvmem/sunxi_sid.c
-+++ b/drivers/nvmem/sunxi_sid.c
-@@ -41,8 +41,21 @@ static int sunxi_sid_read(void *context,
-                         void *val, size_t bytes)
- {
-       struct sunxi_sid *sid = context;
-+      u32 word;
--      memcpy_fromio(val, sid->base + sid->value_offset + offset, bytes);
-+      /* .stride = 4 so offset is guaranteed to be aligned */
-+      __ioread32_copy(val, sid->base + sid->value_offset + offset, bytes / 4);
-+
-+      val += round_down(bytes, 4);
-+      offset += round_down(bytes, 4);
-+      bytes = bytes % 4;
-+
-+      if (!bytes)
-+              return 0;
-+
-+      /* Handle any trailing bytes */
-+      word = readl_relaxed(sid->base + sid->value_offset + offset);
-+      memcpy(val, &word, bytes);
-       return 0;
- }
diff --git a/target/linux/generic/backport-5.15/808-v6.2-0013-nvmem-core-fix-device-node-refcounting.patch b/target/linux/generic/backport-5.15/808-v6.2-0013-nvmem-core-fix-device-node-refcounting.patch
deleted file mode 100644 (file)
index a229c30..0000000
+++ /dev/null
@@ -1,48 +0,0 @@
-From edcf2fb660526b5ed29f93bd17328a2b4835c8b2 Mon Sep 17 00:00:00 2001
-From: Michael Walle <[email protected]>
-Date: Fri, 27 Jan 2023 10:40:12 +0000
-Subject: [PATCH] nvmem: core: fix device node refcounting
-
-In of_nvmem_cell_get(), of_get_next_parent() is used on cell_np. This
-will decrement the refcount on cell_np, but cell_np is still used later
-in the code. Use of_get_parent() instead and of_node_put() in the
-appropriate places.
-
-Fixes: 69aba7948cbe ("nvmem: Add a simple NVMEM framework for consumers")
-Fixes: 7ae6478b304b ("nvmem: core: rework nvmem cell instance creation")
-Signed-off-by: Michael Walle <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/core.c | 11 ++++++++---
- 1 file changed, 8 insertions(+), 3 deletions(-)
-
---- a/drivers/nvmem/core.c
-+++ b/drivers/nvmem/core.c
-@@ -1237,16 +1237,21 @@ struct nvmem_cell *of_nvmem_cell_get(str
-       if (!cell_np)
-               return ERR_PTR(-ENOENT);
--      nvmem_np = of_get_next_parent(cell_np);
--      if (!nvmem_np)
-+      nvmem_np = of_get_parent(cell_np);
-+      if (!nvmem_np) {
-+              of_node_put(cell_np);
-               return ERR_PTR(-EINVAL);
-+      }
-       nvmem = __nvmem_device_get(nvmem_np, device_match_of_node);
-       of_node_put(nvmem_np);
--      if (IS_ERR(nvmem))
-+      if (IS_ERR(nvmem)) {
-+              of_node_put(cell_np);
-               return ERR_CAST(nvmem);
-+      }
-       cell_entry = nvmem_find_cell_entry_by_node(nvmem, cell_np);
-+      of_node_put(cell_np);
-       if (!cell_entry) {
-               __nvmem_device_put(nvmem);
-               return ERR_PTR(-ENOENT);
diff --git a/target/linux/generic/backport-5.15/809-v6.3-0001-nvmem-core-remove-spurious-white-space.patch b/target/linux/generic/backport-5.15/809-v6.3-0001-nvmem-core-remove-spurious-white-space.patch
deleted file mode 100644 (file)
index 01400fd..0000000
+++ /dev/null
@@ -1,26 +0,0 @@
-From 2e8dc541ae207349b51c65391be625ffe1f86e0c Mon Sep 17 00:00:00 2001
-From: "Russell King (Oracle)" <[email protected]>
-Date: Mon, 6 Feb 2023 13:43:41 +0000
-Subject: [PATCH] nvmem: core: remove spurious white space
-
-Remove a spurious white space in for the ida_alloc() call.
-
-Signed-off-by: Russell King (Oracle) <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/core.c | 2 +-
- 1 file changed, 1 insertion(+), 1 deletion(-)
-
---- a/drivers/nvmem/core.c
-+++ b/drivers/nvmem/core.c
-@@ -764,7 +764,7 @@ struct nvmem_device *nvmem_register(cons
-       if (!nvmem)
-               return ERR_PTR(-ENOMEM);
--      rval  = ida_alloc(&nvmem_ida, GFP_KERNEL);
-+      rval = ida_alloc(&nvmem_ida, GFP_KERNEL);
-       if (rval < 0) {
-               kfree(nvmem);
-               return ERR_PTR(rval);
diff --git a/target/linux/generic/backport-5.15/809-v6.3-0002-nvmem-core-add-an-index-parameter-to-the-cell.patch b/target/linux/generic/backport-5.15/809-v6.3-0002-nvmem-core-add-an-index-parameter-to-the-cell.patch
deleted file mode 100644 (file)
index 454d3bf..0000000
+++ /dev/null
@@ -1,180 +0,0 @@
-From 5d8e6e6c10a3d37486d263b16ddc15991a7e4a88 Mon Sep 17 00:00:00 2001
-From: Michael Walle <[email protected]>
-Date: Mon, 6 Feb 2023 13:43:46 +0000
-Subject: [PATCH] nvmem: core: add an index parameter to the cell
-
-Sometimes a cell can represend multiple values. For example, a base
-ethernet address stored in the NVMEM can be expanded into multiple
-discreet ones by adding an offset.
-
-For this use case, introduce an index parameter which is then used to
-distiguish between values. This parameter will then be passed to the
-post process hook which can then use it to create different values
-during reading.
-
-At the moment, there is only support for the device tree path. You can
-add the index to the phandle, e.g.
-
-  &net {
-          nvmem-cells = <&base_mac_address 2>;
-          nvmem-cell-names = "mac-address";
-  };
-
-  &nvmem_provider {
-          base_mac_address: base-mac-address@0 {
-                  #nvmem-cell-cells = <1>;
-                  reg = <0 6>;
-          };
-  };
-
-Signed-off-by: Michael Walle <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/core.c           | 37 ++++++++++++++++++++++++----------
- drivers/nvmem/imx-ocotp.c      |  4 ++--
- include/linux/nvmem-provider.h |  4 ++--
- 3 files changed, 30 insertions(+), 15 deletions(-)
-
---- a/drivers/nvmem/core.c
-+++ b/drivers/nvmem/core.c
-@@ -60,6 +60,7 @@ struct nvmem_cell_entry {
- struct nvmem_cell {
-       struct nvmem_cell_entry *entry;
-       const char              *id;
-+      int                     index;
- };
- static DEFINE_MUTEX(nvmem_mutex);
-@@ -1122,7 +1123,8 @@ struct nvmem_device *devm_nvmem_device_g
- }
- EXPORT_SYMBOL_GPL(devm_nvmem_device_get);
--static struct nvmem_cell *nvmem_create_cell(struct nvmem_cell_entry *entry, const char *id)
-+static struct nvmem_cell *nvmem_create_cell(struct nvmem_cell_entry *entry,
-+                                          const char *id, int index)
- {
-       struct nvmem_cell *cell;
-       const char *name = NULL;
-@@ -1141,6 +1143,7 @@ static struct nvmem_cell *nvmem_create_c
-       cell->id = name;
-       cell->entry = entry;
-+      cell->index = index;
-       return cell;
- }
-@@ -1179,7 +1182,7 @@ nvmem_cell_get_from_lookup(struct device
-                               __nvmem_device_put(nvmem);
-                               cell = ERR_PTR(-ENOENT);
-                       } else {
--                              cell = nvmem_create_cell(cell_entry, con_id);
-+                              cell = nvmem_create_cell(cell_entry, con_id, 0);
-                               if (IS_ERR(cell))
-                                       __nvmem_device_put(nvmem);
-                       }
-@@ -1227,15 +1230,27 @@ struct nvmem_cell *of_nvmem_cell_get(str
-       struct nvmem_device *nvmem;
-       struct nvmem_cell_entry *cell_entry;
-       struct nvmem_cell *cell;
-+      struct of_phandle_args cell_spec;
-       int index = 0;
-+      int cell_index = 0;
-+      int ret;
-       /* if cell name exists, find index to the name */
-       if (id)
-               index = of_property_match_string(np, "nvmem-cell-names", id);
--      cell_np = of_parse_phandle(np, "nvmem-cells", index);
--      if (!cell_np)
--              return ERR_PTR(-ENOENT);
-+      ret = of_parse_phandle_with_optional_args(np, "nvmem-cells",
-+                                                "#nvmem-cell-cells",
-+                                                index, &cell_spec);
-+      if (ret)
-+              return ERR_PTR(ret);
-+
-+      if (cell_spec.args_count > 1)
-+              return ERR_PTR(-EINVAL);
-+
-+      cell_np = cell_spec.np;
-+      if (cell_spec.args_count)
-+              cell_index = cell_spec.args[0];
-       nvmem_np = of_get_parent(cell_np);
-       if (!nvmem_np) {
-@@ -1257,7 +1272,7 @@ struct nvmem_cell *of_nvmem_cell_get(str
-               return ERR_PTR(-ENOENT);
-       }
--      cell = nvmem_create_cell(cell_entry, id);
-+      cell = nvmem_create_cell(cell_entry, id, cell_index);
-       if (IS_ERR(cell))
-               __nvmem_device_put(nvmem);
-@@ -1410,8 +1425,8 @@ static void nvmem_shift_read_buffer_in_p
- }
- static int __nvmem_cell_read(struct nvmem_device *nvmem,
--                    struct nvmem_cell_entry *cell,
--                    void *buf, size_t *len, const char *id)
-+                           struct nvmem_cell_entry *cell,
-+                           void *buf, size_t *len, const char *id, int index)
- {
-       int rc;
-@@ -1425,7 +1440,7 @@ static int __nvmem_cell_read(struct nvme
-               nvmem_shift_read_buffer_in_place(cell, buf);
-       if (nvmem->cell_post_process) {
--              rc = nvmem->cell_post_process(nvmem->priv, id,
-+              rc = nvmem->cell_post_process(nvmem->priv, id, index,
-                                             cell->offset, buf, cell->bytes);
-               if (rc)
-                       return rc;
-@@ -1460,7 +1475,7 @@ void *nvmem_cell_read(struct nvmem_cell
-       if (!buf)
-               return ERR_PTR(-ENOMEM);
--      rc = __nvmem_cell_read(nvmem, cell->entry, buf, len, cell->id);
-+      rc = __nvmem_cell_read(nvmem, cell->entry, buf, len, cell->id, cell->index);
-       if (rc) {
-               kfree(buf);
-               return ERR_PTR(rc);
-@@ -1773,7 +1788,7 @@ ssize_t nvmem_device_cell_read(struct nv
-       if (rc)
-               return rc;
--      rc = __nvmem_cell_read(nvmem, &cell, buf, &len, NULL);
-+      rc = __nvmem_cell_read(nvmem, &cell, buf, &len, NULL, 0);
-       if (rc)
-               return rc;
---- a/drivers/nvmem/imx-ocotp.c
-+++ b/drivers/nvmem/imx-ocotp.c
-@@ -222,8 +222,8 @@ read_end:
-       return ret;
- }
--static int imx_ocotp_cell_pp(void *context, const char *id, unsigned int offset,
--                           void *data, size_t bytes)
-+static int imx_ocotp_cell_pp(void *context, const char *id, int index,
-+                           unsigned int offset, void *data, size_t bytes)
- {
-       struct ocotp_priv *priv = context;
---- a/include/linux/nvmem-provider.h
-+++ b/include/linux/nvmem-provider.h
-@@ -20,8 +20,8 @@ typedef int (*nvmem_reg_read_t)(void *pr
- typedef int (*nvmem_reg_write_t)(void *priv, unsigned int offset,
-                                void *val, size_t bytes);
- /* used for vendor specific post processing of cell data */
--typedef int (*nvmem_cell_post_process_t)(void *priv, const char *id, unsigned int offset,
--                                        void *buf, size_t bytes);
-+typedef int (*nvmem_cell_post_process_t)(void *priv, const char *id, int index,
-+                                       unsigned int offset, void *buf, size_t bytes);
- enum nvmem_type {
-       NVMEM_TYPE_UNKNOWN = 0,
diff --git a/target/linux/generic/backport-5.15/809-v6.3-0003-nvmem-core-move-struct-nvmem_cell_info-to-nvmem-prov.patch b/target/linux/generic/backport-5.15/809-v6.3-0003-nvmem-core-move-struct-nvmem_cell_info-to-nvmem-prov.patch
deleted file mode 100644 (file)
index f3829b3..0000000
+++ /dev/null
@@ -1,78 +0,0 @@
-From fbd03d27776c6121a483921601418e3c8f0ff37e Mon Sep 17 00:00:00 2001
-From: Michael Walle <[email protected]>
-Date: Mon, 6 Feb 2023 13:43:47 +0000
-Subject: [PATCH] nvmem: core: move struct nvmem_cell_info to nvmem-provider.h
-
-struct nvmem_cell_info is used to describe a cell. Thus this should
-really be in the nvmem-provider's header. There are two (unused) nvmem
-access methods which use the nvmem_cell_info to describe the cell to be
-accesses. One can argue, that they will create a cell before accessing,
-thus they are both a provider and a consumer.
-
-struct nvmem_cell_info will get used more and more by nvmem-providers,
-don't force them to also include the consumer header, although they are
-not.
-
-Signed-off-by: Michael Walle <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- include/linux/nvmem-consumer.h | 10 +---------
- include/linux/nvmem-provider.h | 19 ++++++++++++++++++-
- 2 files changed, 19 insertions(+), 10 deletions(-)
-
---- a/include/linux/nvmem-consumer.h
-+++ b/include/linux/nvmem-consumer.h
-@@ -18,15 +18,7 @@ struct device_node;
- /* consumer cookie */
- struct nvmem_cell;
- struct nvmem_device;
--
--struct nvmem_cell_info {
--      const char              *name;
--      unsigned int            offset;
--      unsigned int            bytes;
--      unsigned int            bit_offset;
--      unsigned int            nbits;
--      struct device_node      *np;
--};
-+struct nvmem_cell_info;
- /**
-  * struct nvmem_cell_lookup - cell lookup entry
---- a/include/linux/nvmem-provider.h
-+++ b/include/linux/nvmem-provider.h
-@@ -14,7 +14,6 @@
- #include <linux/gpio/consumer.h>
- struct nvmem_device;
--struct nvmem_cell_info;
- typedef int (*nvmem_reg_read_t)(void *priv, unsigned int offset,
-                               void *val, size_t bytes);
- typedef int (*nvmem_reg_write_t)(void *priv, unsigned int offset,
-@@ -48,6 +47,24 @@ struct nvmem_keepout {
- };
- /**
-+ * struct nvmem_cell_info - NVMEM cell description
-+ * @name:     Name.
-+ * @offset:   Offset within the NVMEM device.
-+ * @bytes:    Length of the cell.
-+ * @bit_offset:       Bit offset if cell is smaller than a byte.
-+ * @nbits:    Number of bits.
-+ * @np:               Optional device_node pointer.
-+ */
-+struct nvmem_cell_info {
-+      const char              *name;
-+      unsigned int            offset;
-+      unsigned int            bytes;
-+      unsigned int            bit_offset;
-+      unsigned int            nbits;
-+      struct device_node      *np;
-+};
-+
-+/**
-  * struct nvmem_config - NVMEM device configuration
-  *
-  * @dev:      Parent device.
diff --git a/target/linux/generic/backport-5.15/809-v6.3-0004-nvmem-core-drop-the-removal-of-the-cells-in-nvmem_ad.patch b/target/linux/generic/backport-5.15/809-v6.3-0004-nvmem-core-drop-the-removal-of-the-cells-in-nvmem_ad.patch
deleted file mode 100644 (file)
index 8f996ea..0000000
+++ /dev/null
@@ -1,65 +0,0 @@
-From cc5bdd323dde6494623f3ffe3a5b887fa21cd375 Mon Sep 17 00:00:00 2001
-From: Michael Walle <[email protected]>
-Date: Mon, 6 Feb 2023 13:43:48 +0000
-Subject: [PATCH] nvmem: core: drop the removal of the cells in
- nvmem_add_cells()
-
-If nvmem_add_cells() fails, the whole nvmem_register() will fail
-and the cells will then be removed anyway. This is a preparation
-to introduce a nvmem_add_one_cell() which can then be used by
-nvmem_add_cells().
-
-This is then the same to what nvmem_add_cells_from_table() and
-nvmem_add_cells_from_of() do.
-
-Signed-off-by: Michael Walle <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/core.c | 14 ++++----------
- 1 file changed, 4 insertions(+), 10 deletions(-)
-
---- a/drivers/nvmem/core.c
-+++ b/drivers/nvmem/core.c
-@@ -515,7 +515,7 @@ static int nvmem_add_cells(struct nvmem_
-                   int ncells)
- {
-       struct nvmem_cell_entry **cells;
--      int i, rval;
-+      int i, rval = 0;
-       cells = kcalloc(ncells, sizeof(*cells), GFP_KERNEL);
-       if (!cells)
-@@ -525,28 +525,22 @@ static int nvmem_add_cells(struct nvmem_
-               cells[i] = kzalloc(sizeof(**cells), GFP_KERNEL);
-               if (!cells[i]) {
-                       rval = -ENOMEM;
--                      goto err;
-+                      goto out;
-               }
-               rval = nvmem_cell_info_to_nvmem_cell_entry(nvmem, &info[i], cells[i]);
-               if (rval) {
-                       kfree(cells[i]);
--                      goto err;
-+                      goto out;
-               }
-               nvmem_cell_entry_add(cells[i]);
-       }
-+out:
-       /* remove tmp array */
-       kfree(cells);
--      return 0;
--err:
--      while (i--)
--              nvmem_cell_entry_drop(cells[i]);
--
--      kfree(cells);
--
-       return rval;
- }
diff --git a/target/linux/generic/backport-5.15/809-v6.3-0005-nvmem-core-add-nvmem_add_one_cell.patch b/target/linux/generic/backport-5.15/809-v6.3-0005-nvmem-core-add-nvmem_add_one_cell.patch
deleted file mode 100644 (file)
index 711ce22..0000000
+++ /dev/null
@@ -1,122 +0,0 @@
-From 2ded6830d376d5e7bf43d59f7f7fdf1a59abc676 Mon Sep 17 00:00:00 2001
-From: Michael Walle <[email protected]>
-Date: Mon, 6 Feb 2023 13:43:49 +0000
-Subject: [PATCH] nvmem: core: add nvmem_add_one_cell()
-
-Add a new function to add exactly one cell. This will be used by the
-nvmem layout drivers to add custom cells. In contrast to the
-nvmem_add_cells(), this has the advantage that we don't have to assemble
-a list of cells on runtime.
-
-Signed-off-by: Michael Walle <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/core.c           | 59 ++++++++++++++++++++--------------
- include/linux/nvmem-provider.h |  8 +++++
- 2 files changed, 43 insertions(+), 24 deletions(-)
-
---- a/drivers/nvmem/core.c
-+++ b/drivers/nvmem/core.c
-@@ -502,6 +502,36 @@ static int nvmem_cell_info_to_nvmem_cell
- }
- /**
-+ * nvmem_add_one_cell() - Add one cell information to an nvmem device
-+ *
-+ * @nvmem: nvmem device to add cells to.
-+ * @info: nvmem cell info to add to the device
-+ *
-+ * Return: 0 or negative error code on failure.
-+ */
-+int nvmem_add_one_cell(struct nvmem_device *nvmem,
-+                     const struct nvmem_cell_info *info)
-+{
-+      struct nvmem_cell_entry *cell;
-+      int rval;
-+
-+      cell = kzalloc(sizeof(*cell), GFP_KERNEL);
-+      if (!cell)
-+              return -ENOMEM;
-+
-+      rval = nvmem_cell_info_to_nvmem_cell_entry(nvmem, info, cell);
-+      if (rval) {
-+              kfree(cell);
-+              return rval;
-+      }
-+
-+      nvmem_cell_entry_add(cell);
-+
-+      return 0;
-+}
-+EXPORT_SYMBOL_GPL(nvmem_add_one_cell);
-+
-+/**
-  * nvmem_add_cells() - Add cell information to an nvmem device
-  *
-  * @nvmem: nvmem device to add cells to.
-@@ -514,34 +544,15 @@ static int nvmem_add_cells(struct nvmem_
-                   const struct nvmem_cell_info *info,
-                   int ncells)
- {
--      struct nvmem_cell_entry **cells;
--      int i, rval = 0;
--
--      cells = kcalloc(ncells, sizeof(*cells), GFP_KERNEL);
--      if (!cells)
--              return -ENOMEM;
-+      int i, rval;
-       for (i = 0; i < ncells; i++) {
--              cells[i] = kzalloc(sizeof(**cells), GFP_KERNEL);
--              if (!cells[i]) {
--                      rval = -ENOMEM;
--                      goto out;
--              }
--
--              rval = nvmem_cell_info_to_nvmem_cell_entry(nvmem, &info[i], cells[i]);
--              if (rval) {
--                      kfree(cells[i]);
--                      goto out;
--              }
--
--              nvmem_cell_entry_add(cells[i]);
-+              rval = nvmem_add_one_cell(nvmem, &info[i]);
-+              if (rval)
-+                      return rval;
-       }
--out:
--      /* remove tmp array */
--      kfree(cells);
--
--      return rval;
-+      return 0;
- }
- /**
---- a/include/linux/nvmem-provider.h
-+++ b/include/linux/nvmem-provider.h
-@@ -153,6 +153,9 @@ struct nvmem_device *devm_nvmem_register
- void nvmem_add_cell_table(struct nvmem_cell_table *table);
- void nvmem_del_cell_table(struct nvmem_cell_table *table);
-+int nvmem_add_one_cell(struct nvmem_device *nvmem,
-+                     const struct nvmem_cell_info *info);
-+
- #else
- static inline struct nvmem_device *nvmem_register(const struct nvmem_config *c)
-@@ -170,6 +173,11 @@ devm_nvmem_register(struct device *dev,
- static inline void nvmem_add_cell_table(struct nvmem_cell_table *table) {}
- static inline void nvmem_del_cell_table(struct nvmem_cell_table *table) {}
-+static inline int nvmem_add_one_cell(struct nvmem_device *nvmem,
-+                                   const struct nvmem_cell_info *info)
-+{
-+      return -EOPNOTSUPP;
-+}
- #endif /* CONFIG_NVMEM */
- #endif  /* ifndef _LINUX_NVMEM_PROVIDER_H */
diff --git a/target/linux/generic/backport-5.15/809-v6.3-0006-nvmem-core-use-nvmem_add_one_cell-in-nvmem_add_cells.patch b/target/linux/generic/backport-5.15/809-v6.3-0006-nvmem-core-use-nvmem_add_one_cell-in-nvmem_add_cells.patch
deleted file mode 100644 (file)
index e1791e5..0000000
+++ /dev/null
@@ -1,93 +0,0 @@
-From 50014d659617dc58780a5d31ceb76c82779a9d8b Mon Sep 17 00:00:00 2001
-From: Michael Walle <[email protected]>
-Date: Mon, 6 Feb 2023 13:43:50 +0000
-Subject: [PATCH] nvmem: core: use nvmem_add_one_cell() in
- nvmem_add_cells_from_of()
-
-Convert nvmem_add_cells_from_of() to use the new nvmem_add_one_cell().
-This will remove duplicate code and it will make it possible to add a
-hook to a nvmem layout in between, which can change fields before the
-cell is finally added.
-
-Signed-off-by: Michael Walle <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/core.c | 45 ++++++++++++++------------------------------
- 1 file changed, 14 insertions(+), 31 deletions(-)
-
---- a/drivers/nvmem/core.c
-+++ b/drivers/nvmem/core.c
-@@ -688,15 +688,14 @@ static int nvmem_validate_keepouts(struc
- static int nvmem_add_cells_from_of(struct nvmem_device *nvmem)
- {
--      struct device_node *parent, *child;
-       struct device *dev = &nvmem->dev;
--      struct nvmem_cell_entry *cell;
-+      struct device_node *child;
-       const __be32 *addr;
--      int len;
-+      int len, ret;
--      parent = dev->of_node;
-+      for_each_child_of_node(dev->of_node, child) {
-+              struct nvmem_cell_info info = {0};
--      for_each_child_of_node(parent, child) {
-               addr = of_get_property(child, "reg", &len);
-               if (!addr)
-                       continue;
-@@ -706,40 +705,24 @@ static int nvmem_add_cells_from_of(struc
-                       return -EINVAL;
-               }
--              cell = kzalloc(sizeof(*cell), GFP_KERNEL);
--              if (!cell) {
--                      of_node_put(child);
--                      return -ENOMEM;
--              }
--
--              cell->nvmem = nvmem;
--              cell->offset = be32_to_cpup(addr++);
--              cell->bytes = be32_to_cpup(addr);
--              cell->name = kasprintf(GFP_KERNEL, "%pOFn", child);
-+              info.offset = be32_to_cpup(addr++);
-+              info.bytes = be32_to_cpup(addr);
-+              info.name = kasprintf(GFP_KERNEL, "%pOFn", child);
-               addr = of_get_property(child, "bits", &len);
-               if (addr && len == (2 * sizeof(u32))) {
--                      cell->bit_offset = be32_to_cpup(addr++);
--                      cell->nbits = be32_to_cpup(addr);
-+                      info.bit_offset = be32_to_cpup(addr++);
-+                      info.nbits = be32_to_cpup(addr);
-               }
--              if (cell->nbits)
--                      cell->bytes = DIV_ROUND_UP(
--                                      cell->nbits + cell->bit_offset,
--                                      BITS_PER_BYTE);
--
--              if (!IS_ALIGNED(cell->offset, nvmem->stride)) {
--                      dev_err(dev, "cell %s unaligned to nvmem stride %d\n",
--                              cell->name, nvmem->stride);
--                      /* Cells already added will be freed later. */
--                      kfree_const(cell->name);
--                      kfree(cell);
-+              info.np = of_node_get(child);
-+
-+              ret = nvmem_add_one_cell(nvmem, &info);
-+              kfree(info.name);
-+              if (ret) {
-                       of_node_put(child);
--                      return -EINVAL;
-+                      return ret;
-               }
--
--              cell->np = of_node_get(child);
--              nvmem_cell_entry_add(cell);
-       }
-       return 0;
diff --git a/target/linux/generic/backport-5.15/809-v6.3-0007-nvmem-stm32-add-OP-TEE-support-for-STM32MP13x.patch b/target/linux/generic/backport-5.15/809-v6.3-0007-nvmem-stm32-add-OP-TEE-support-for-STM32MP13x.patch
deleted file mode 100644 (file)
index 172a78b..0000000
+++ /dev/null
@@ -1,562 +0,0 @@
-From 6a0bc3522e746025e2d9a63ab2cb5d7062c2d39c Mon Sep 17 00:00:00 2001
-From: Patrick Delaunay <[email protected]>
-Date: Mon, 6 Feb 2023 13:43:51 +0000
-Subject: [PATCH] nvmem: stm32: add OP-TEE support for STM32MP13x
-
-For boot with OP-TEE on STM32MP13, the communication with the secure
-world no more use STMicroelectronics SMC but communication with the
-STM32MP BSEC TA, for data access (read/write) or lock operation:
-- all the request are sent to OP-TEE trusted application,
-- for upper OTP with ECC protection and with word programming only
-  each OTP are permanently locked when programmed to avoid ECC error
-  on the second write operation
-
-Signed-off-by: Patrick Delaunay <[email protected]>
-Reviewed-by: Etienne Carriere <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/Kconfig               |  11 +
- drivers/nvmem/Makefile              |   1 +
- drivers/nvmem/stm32-bsec-optee-ta.c | 298 ++++++++++++++++++++++++++++
- drivers/nvmem/stm32-bsec-optee-ta.h |  80 ++++++++
- drivers/nvmem/stm32-romem.c         |  54 ++++-
- 5 files changed, 441 insertions(+), 3 deletions(-)
- create mode 100644 drivers/nvmem/stm32-bsec-optee-ta.c
- create mode 100644 drivers/nvmem/stm32-bsec-optee-ta.h
-
---- a/drivers/nvmem/Kconfig
-+++ b/drivers/nvmem/Kconfig
-@@ -290,9 +290,20 @@ config NVMEM_SPRD_EFUSE
-         This driver can also be built as a module. If so, the module
-         will be called nvmem-sprd-efuse.
-+config NVMEM_STM32_BSEC_OPTEE_TA
-+      bool "STM32MP BSEC OP-TEE TA support for nvmem-stm32-romem driver"
-+      depends on OPTEE
-+      help
-+        Say y here to enable the accesses to STM32MP SoC OTPs by the OP-TEE
-+        trusted application STM32MP BSEC.
-+
-+        This library is a used by stm32-romem driver or included in the module
-+        called nvmem-stm32-romem.
-+
- config NVMEM_STM32_ROMEM
-       tristate "STMicroelectronics STM32 factory-programmed memory support"
-       depends on ARCH_STM32 || COMPILE_TEST
-+      imply NVMEM_STM32_BSEC_OPTEE_TA
-       help
-         Say y here to enable read-only access for STMicroelectronics STM32
-         factory-programmed memory area.
---- a/drivers/nvmem/Makefile
-+++ b/drivers/nvmem/Makefile
-@@ -61,6 +61,7 @@ obj-$(CONFIG_NVMEM_SPRD_EFUSE)               += nvmem
- nvmem_sprd_efuse-y                    := sprd-efuse.o
- obj-$(CONFIG_NVMEM_STM32_ROMEM)               += nvmem_stm32_romem.o
- nvmem_stm32_romem-y                   := stm32-romem.o
-+nvmem_stm32_romem-$(CONFIG_NVMEM_STM32_BSEC_OPTEE_TA) += stm32-bsec-optee-ta.o
- obj-$(CONFIG_NVMEM_SUNPLUS_OCOTP)     += nvmem_sunplus_ocotp.o
- nvmem_sunplus_ocotp-y                 := sunplus-ocotp.o
- obj-$(CONFIG_NVMEM_SUNXI_SID)         += nvmem_sunxi_sid.o
---- /dev/null
-+++ b/drivers/nvmem/stm32-bsec-optee-ta.c
-@@ -0,0 +1,298 @@
-+// SPDX-License-Identifier: GPL-2.0-or-later
-+/*
-+ * OP-TEE STM32MP BSEC PTA interface, used by STM32 ROMEM driver
-+ *
-+ * Copyright (C) 2022, STMicroelectronics - All Rights Reserved
-+ */
-+
-+#include <linux/tee_drv.h>
-+
-+#include "stm32-bsec-optee-ta.h"
-+
-+/*
-+ * Read OTP memory
-+ *
-+ * [in]               value[0].a              OTP start offset in byte
-+ * [in]               value[0].b              Access type (0:shadow, 1:fuse, 2:lock)
-+ * [out]      memref[1].buffer        Output buffer to store read values
-+ * [out]      memref[1].size          Size of OTP to be read
-+ *
-+ * Return codes:
-+ * TEE_SUCCESS - Invoke command success
-+ * TEE_ERROR_BAD_PARAMETERS - Incorrect input param
-+ * TEE_ERROR_ACCESS_DENIED - OTP not accessible by caller
-+ */
-+#define PTA_BSEC_READ_MEM             0x0
-+
-+/*
-+ * Write OTP memory
-+ *
-+ * [in]               value[0].a              OTP start offset in byte
-+ * [in]               value[0].b              Access type (0:shadow, 1:fuse, 2:lock)
-+ * [in]               memref[1].buffer        Input buffer to read values
-+ * [in]               memref[1].size          Size of OTP to be written
-+ *
-+ * Return codes:
-+ * TEE_SUCCESS - Invoke command success
-+ * TEE_ERROR_BAD_PARAMETERS - Incorrect input param
-+ * TEE_ERROR_ACCESS_DENIED - OTP not accessible by caller
-+ */
-+#define PTA_BSEC_WRITE_MEM            0x1
-+
-+/* value of PTA_BSEC access type = value[in] b */
-+#define SHADOW_ACCESS 0
-+#define FUSE_ACCESS   1
-+#define LOCK_ACCESS   2
-+
-+/* Bitfield definition for LOCK status */
-+#define LOCK_PERM                     BIT(30)
-+
-+/* OP-TEE STM32MP BSEC TA UUID */
-+static const uuid_t stm32mp_bsec_ta_uuid =
-+      UUID_INIT(0x94cf71ad, 0x80e6, 0x40b5,
-+                0xa7, 0xc6, 0x3d, 0xc5, 0x01, 0xeb, 0x28, 0x03);
-+
-+/*
-+ * Check whether this driver supports the BSEC TA in the TEE instance
-+ * represented by the params (ver/data) to this function.
-+ */
-+static int stm32_bsec_optee_ta_match(struct tee_ioctl_version_data *ver,
-+                                   const void *data)
-+{
-+      /* Currently this driver only supports GP compliant, OP-TEE based TA */
-+      if ((ver->impl_id == TEE_IMPL_ID_OPTEE) &&
-+              (ver->gen_caps & TEE_GEN_CAP_GP))
-+              return 1;
-+      else
-+              return 0;
-+}
-+
-+/* Open a session to OP-TEE for STM32MP BSEC TA */
-+static int stm32_bsec_ta_open_session(struct tee_context *ctx, u32 *id)
-+{
-+      struct tee_ioctl_open_session_arg sess_arg;
-+      int rc;
-+
-+      memset(&sess_arg, 0, sizeof(sess_arg));
-+      export_uuid(sess_arg.uuid, &stm32mp_bsec_ta_uuid);
-+      sess_arg.clnt_login = TEE_IOCTL_LOGIN_REE_KERNEL;
-+      sess_arg.num_params = 0;
-+
-+      rc = tee_client_open_session(ctx, &sess_arg, NULL);
-+      if ((rc < 0) || (sess_arg.ret != 0)) {
-+              pr_err("%s: tee_client_open_session failed err:%#x, ret:%#x\n",
-+                     __func__, sess_arg.ret, rc);
-+              if (!rc)
-+                      rc = -EINVAL;
-+      } else {
-+              *id = sess_arg.session;
-+      }
-+
-+      return rc;
-+}
-+
-+/* close a session to OP-TEE for STM32MP BSEC TA */
-+static void stm32_bsec_ta_close_session(void *ctx, u32 id)
-+{
-+      tee_client_close_session(ctx, id);
-+}
-+
-+/* stm32_bsec_optee_ta_open() - initialize the STM32MP BSEC TA */
-+int stm32_bsec_optee_ta_open(struct tee_context **ctx)
-+{
-+      struct tee_context *tee_ctx;
-+      u32 session_id;
-+      int rc;
-+
-+      /* Open context with TEE driver */
-+      tee_ctx = tee_client_open_context(NULL, stm32_bsec_optee_ta_match, NULL, NULL);
-+      if (IS_ERR(tee_ctx)) {
-+              rc = PTR_ERR(tee_ctx);
-+              if (rc == -ENOENT)
-+                      return -EPROBE_DEFER;
-+              pr_err("%s: tee_client_open_context failed (%d)\n", __func__, rc);
-+
-+              return rc;
-+      }
-+
-+      /* Check STM32MP BSEC TA presence */
-+      rc = stm32_bsec_ta_open_session(tee_ctx, &session_id);
-+      if (rc) {
-+              tee_client_close_context(tee_ctx);
-+              return rc;
-+      }
-+
-+      stm32_bsec_ta_close_session(tee_ctx, session_id);
-+
-+      *ctx = tee_ctx;
-+
-+      return 0;
-+}
-+
-+/* stm32_bsec_optee_ta_open() - release the PTA STM32MP BSEC TA */
-+void stm32_bsec_optee_ta_close(void *ctx)
-+{
-+      tee_client_close_context(ctx);
-+}
-+
-+/* stm32_bsec_optee_ta_read() - nvmem read access using PTA client driver */
-+int stm32_bsec_optee_ta_read(struct tee_context *ctx, unsigned int offset,
-+                           void *buf, size_t bytes)
-+{
-+      struct tee_shm *shm;
-+      struct tee_ioctl_invoke_arg arg;
-+      struct tee_param param[2];
-+      u8 *shm_buf;
-+      u32 start, num_bytes;
-+      int ret;
-+      u32 session_id;
-+
-+      ret = stm32_bsec_ta_open_session(ctx, &session_id);
-+      if (ret)
-+              return ret;
-+
-+      memset(&arg, 0, sizeof(arg));
-+      memset(&param, 0, sizeof(param));
-+
-+      arg.func = PTA_BSEC_READ_MEM;
-+      arg.session = session_id;
-+      arg.num_params = 2;
-+
-+      /* align access on 32bits */
-+      start = ALIGN_DOWN(offset, 4);
-+      num_bytes = round_up(offset + bytes - start, 4);
-+      param[0].attr = TEE_IOCTL_PARAM_ATTR_TYPE_VALUE_INPUT;
-+      param[0].u.value.a = start;
-+      param[0].u.value.b = SHADOW_ACCESS;
-+
-+      shm = tee_shm_alloc_kernel_buf(ctx, num_bytes);
-+      if (IS_ERR(shm)) {
-+              ret = PTR_ERR(shm);
-+              goto out_tee_session;
-+      }
-+
-+      param[1].attr = TEE_IOCTL_PARAM_ATTR_TYPE_MEMREF_OUTPUT;
-+      param[1].u.memref.shm = shm;
-+      param[1].u.memref.size = num_bytes;
-+
-+      ret = tee_client_invoke_func(ctx, &arg, param);
-+      if (ret < 0 || arg.ret != 0) {
-+              pr_err("TA_BSEC invoke failed TEE err:%#x, ret:%#x\n",
-+                      arg.ret, ret);
-+              if (!ret)
-+                      ret = -EIO;
-+      }
-+      if (!ret) {
-+              shm_buf = tee_shm_get_va(shm, 0);
-+              if (IS_ERR(shm_buf)) {
-+                      ret = PTR_ERR(shm_buf);
-+                      pr_err("tee_shm_get_va failed for transmit (%d)\n", ret);
-+              } else {
-+                      /* read data from 32 bits aligned buffer */
-+                      memcpy(buf, &shm_buf[offset % 4], bytes);
-+              }
-+      }
-+
-+      tee_shm_free(shm);
-+
-+out_tee_session:
-+      stm32_bsec_ta_close_session(ctx, session_id);
-+
-+      return ret;
-+}
-+
-+/* stm32_bsec_optee_ta_write() - nvmem write access using PTA client driver */
-+int stm32_bsec_optee_ta_write(struct tee_context *ctx, unsigned int lower,
-+                            unsigned int offset, void *buf, size_t bytes)
-+{     struct tee_shm *shm;
-+      struct tee_ioctl_invoke_arg arg;
-+      struct tee_param param[2];
-+      u8 *shm_buf;
-+      int ret;
-+      u32 session_id;
-+
-+      ret = stm32_bsec_ta_open_session(ctx, &session_id);
-+      if (ret)
-+              return ret;
-+
-+      /* Allow only writing complete 32-bits aligned words */
-+      if ((bytes % 4) || (offset % 4))
-+              return -EINVAL;
-+
-+      memset(&arg, 0, sizeof(arg));
-+      memset(&param, 0, sizeof(param));
-+
-+      arg.func = PTA_BSEC_WRITE_MEM;
-+      arg.session = session_id;
-+      arg.num_params = 2;
-+
-+      param[0].attr = TEE_IOCTL_PARAM_ATTR_TYPE_VALUE_INPUT;
-+      param[0].u.value.a = offset;
-+      param[0].u.value.b = FUSE_ACCESS;
-+
-+      shm = tee_shm_alloc_kernel_buf(ctx, bytes);
-+      if (IS_ERR(shm)) {
-+              ret = PTR_ERR(shm);
-+              goto out_tee_session;
-+      }
-+
-+      param[1].attr = TEE_IOCTL_PARAM_ATTR_TYPE_MEMREF_INPUT;
-+      param[1].u.memref.shm = shm;
-+      param[1].u.memref.size = bytes;
-+
-+      shm_buf = tee_shm_get_va(shm, 0);
-+      if (IS_ERR(shm_buf)) {
-+              ret = PTR_ERR(shm_buf);
-+              pr_err("tee_shm_get_va failed for transmit (%d)\n", ret);
-+              tee_shm_free(shm);
-+
-+              goto out_tee_session;
-+      }
-+
-+      memcpy(shm_buf, buf, bytes);
-+
-+      ret = tee_client_invoke_func(ctx, &arg, param);
-+      if (ret < 0 || arg.ret != 0) {
-+              pr_err("TA_BSEC invoke failed TEE err:%#x, ret:%#x\n", arg.ret, ret);
-+              if (!ret)
-+                      ret = -EIO;
-+      }
-+      pr_debug("Write OTPs %d to %zu, ret=%d\n", offset / 4, (offset + bytes) / 4, ret);
-+
-+      /* Lock the upper OTPs with ECC protection, word programming only */
-+      if (!ret && ((offset + bytes) >= (lower * 4))) {
-+              u32 start, nb_lock;
-+              u32 *lock = (u32 *)shm_buf;
-+              int i;
-+
-+              /*
-+               * don't lock the lower OTPs, no ECC protection and incremental
-+               * bit programming, a second write is allowed
-+               */
-+              start = max_t(u32, offset, lower * 4);
-+              nb_lock = (offset + bytes - start) / 4;
-+
-+              param[0].u.value.a = start;
-+              param[0].u.value.b = LOCK_ACCESS;
-+              param[1].u.memref.size = nb_lock * 4;
-+
-+              for (i = 0; i < nb_lock; i++)
-+                      lock[i] = LOCK_PERM;
-+
-+              ret = tee_client_invoke_func(ctx, &arg, param);
-+              if (ret < 0 || arg.ret != 0) {
-+                      pr_err("TA_BSEC invoke failed TEE err:%#x, ret:%#x\n", arg.ret, ret);
-+                      if (!ret)
-+                              ret = -EIO;
-+              }
-+              pr_debug("Lock upper OTPs %d to %d, ret=%d\n",
-+                       start / 4, start / 4 + nb_lock, ret);
-+      }
-+
-+      tee_shm_free(shm);
-+
-+out_tee_session:
-+      stm32_bsec_ta_close_session(ctx, session_id);
-+
-+      return ret;
-+}
---- /dev/null
-+++ b/drivers/nvmem/stm32-bsec-optee-ta.h
-@@ -0,0 +1,80 @@
-+/* SPDX-License-Identifier: GPL-2.0-or-later */
-+/*
-+ * OP-TEE STM32MP BSEC PTA interface, used by STM32 ROMEM driver
-+ *
-+ * Copyright (C) 2022, STMicroelectronics - All Rights Reserved
-+ */
-+
-+#if IS_ENABLED(CONFIG_NVMEM_STM32_BSEC_OPTEE_TA)
-+/**
-+ * stm32_bsec_optee_ta_open() - initialize the STM32 BSEC TA
-+ * @ctx: the OP-TEE context on success
-+ *
-+ * Return:
-+ *    On success, 0. On failure, -errno.
-+ */
-+int stm32_bsec_optee_ta_open(struct tee_context **ctx);
-+
-+/**
-+ * stm32_bsec_optee_ta_close() - release the STM32 BSEC TA
-+ * @ctx: the OP-TEE context
-+ *
-+ * This function used to clean the OP-TEE resources initialized in
-+ * stm32_bsec_optee_ta_open(); it can be used as callback to
-+ * devm_add_action_or_reset()
-+ */
-+void stm32_bsec_optee_ta_close(void *ctx);
-+
-+/**
-+ * stm32_bsec_optee_ta_read() - nvmem read access using TA client driver
-+ * @ctx: the OP-TEE context provided by stm32_bsec_optee_ta_open
-+ * @offset: nvmem offset
-+ * @buf: buffer to fill with nvem values
-+ * @bytes: number of bytes to read
-+ *
-+ * Return:
-+ *    On success, 0. On failure, -errno.
-+ */
-+int stm32_bsec_optee_ta_read(struct tee_context *ctx, unsigned int offset,
-+                           void *buf, size_t bytes);
-+
-+/**
-+ * stm32_bsec_optee_ta_write() - nvmem write access using TA client driver
-+ * @ctx: the OP-TEE context provided by stm32_bsec_optee_ta_open
-+ * @lower: number of lower OTP, not protected by ECC
-+ * @offset: nvmem offset
-+ * @buf: buffer with nvem values
-+ * @bytes: number of bytes to write
-+ *
-+ * Return:
-+ *    On success, 0. On failure, -errno.
-+ */
-+int stm32_bsec_optee_ta_write(struct tee_context *ctx, unsigned int lower,
-+                            unsigned int offset, void *buf, size_t bytes);
-+
-+#else
-+
-+static inline int stm32_bsec_optee_ta_open(struct tee_context **ctx)
-+{
-+      return -EOPNOTSUPP;
-+}
-+
-+static inline void stm32_bsec_optee_ta_close(void *ctx)
-+{
-+}
-+
-+static inline int stm32_bsec_optee_ta_read(struct tee_context *ctx,
-+                                         unsigned int offset, void *buf,
-+                                         size_t bytes)
-+{
-+      return -EOPNOTSUPP;
-+}
-+
-+static inline int stm32_bsec_optee_ta_write(struct tee_context *ctx,
-+                                          unsigned int lower,
-+                                          unsigned int offset, void *buf,
-+                                          size_t bytes)
-+{
-+      return -EOPNOTSUPP;
-+}
-+#endif /* CONFIG_NVMEM_STM32_BSEC_OPTEE_TA */
---- a/drivers/nvmem/stm32-romem.c
-+++ b/drivers/nvmem/stm32-romem.c
-@@ -11,6 +11,9 @@
- #include <linux/module.h>
- #include <linux/nvmem-provider.h>
- #include <linux/of_device.h>
-+#include <linux/tee_drv.h>
-+
-+#include "stm32-bsec-optee-ta.h"
- /* BSEC secure service access from non-secure */
- #define STM32_SMC_BSEC                        0x82001003
-@@ -25,12 +28,14 @@
- struct stm32_romem_cfg {
-       int size;
-       u8 lower;
-+      bool ta;
- };
- struct stm32_romem_priv {
-       void __iomem *base;
-       struct nvmem_config cfg;
-       u8 lower;
-+      struct tee_context *ctx;
- };
- static int stm32_romem_read(void *context, unsigned int offset, void *buf,
-@@ -138,12 +143,29 @@ static int stm32_bsec_write(void *contex
-       return 0;
- }
-+static int stm32_bsec_pta_read(void *context, unsigned int offset, void *buf,
-+                             size_t bytes)
-+{
-+      struct stm32_romem_priv *priv = context;
-+
-+      return stm32_bsec_optee_ta_read(priv->ctx, offset, buf, bytes);
-+}
-+
-+static int stm32_bsec_pta_write(void *context, unsigned int offset, void *buf,
-+                              size_t bytes)
-+{
-+      struct stm32_romem_priv *priv = context;
-+
-+      return stm32_bsec_optee_ta_write(priv->ctx, priv->lower, offset, buf, bytes);
-+}
-+
- static int stm32_romem_probe(struct platform_device *pdev)
- {
-       const struct stm32_romem_cfg *cfg;
-       struct device *dev = &pdev->dev;
-       struct stm32_romem_priv *priv;
-       struct resource *res;
-+      int rc;
-       priv = devm_kzalloc(dev, sizeof(*priv), GFP_KERNEL);
-       if (!priv)
-@@ -173,15 +195,31 @@ static int stm32_romem_probe(struct plat
-       } else {
-               priv->cfg.size = cfg->size;
-               priv->lower = cfg->lower;
--              priv->cfg.reg_read = stm32_bsec_read;
--              priv->cfg.reg_write = stm32_bsec_write;
-+              if (cfg->ta) {
-+                      rc = stm32_bsec_optee_ta_open(&priv->ctx);
-+                      /* wait for OP-TEE client driver to be up and ready */
-+                      if (rc)
-+                              return rc;
-+              }
-+              if (priv->ctx) {
-+                      rc = devm_add_action_or_reset(dev, stm32_bsec_optee_ta_close, priv->ctx);
-+                      if (rc) {
-+                              dev_err(dev, "devm_add_action_or_reset() failed (%d)\n", rc);
-+                              return rc;
-+                      }
-+                      priv->cfg.reg_read = stm32_bsec_pta_read;
-+                      priv->cfg.reg_write = stm32_bsec_pta_write;
-+              } else {
-+                      priv->cfg.reg_read = stm32_bsec_read;
-+                      priv->cfg.reg_write = stm32_bsec_write;
-+              }
-       }
-       return PTR_ERR_OR_ZERO(devm_nvmem_register(dev, &priv->cfg));
- }
- /*
-- * STM32MP15 BSEC OTP regions: 4096 OTP bits (with 3072 effective bits)
-+ * STM32MP15/13 BSEC OTP regions: 4096 OTP bits (with 3072 effective bits)
-  * => 96 x 32-bits data words
-  * - Lower: 1K bits, 2:1 redundancy, incremental bit programming
-  *   => 32 (x 32-bits) lower shadow registers = words 0 to 31
-@@ -191,6 +229,13 @@ static int stm32_romem_probe(struct plat
- static const struct stm32_romem_cfg stm32mp15_bsec_cfg = {
-       .size = 384,
-       .lower = 32,
-+      .ta = false,
-+};
-+
-+static const struct stm32_romem_cfg stm32mp13_bsec_cfg = {
-+      .size = 384,
-+      .lower = 32,
-+      .ta = true,
- };
- static const struct of_device_id stm32_romem_of_match[] = {
-@@ -198,7 +243,10 @@ static const struct of_device_id stm32_r
-               .compatible = "st,stm32mp15-bsec",
-               .data = (void *)&stm32mp15_bsec_cfg,
-       }, {
-+              .compatible = "st,stm32mp13-bsec",
-+              .data = (void *)&stm32mp13_bsec_cfg,
-       },
-+      { /* sentinel */ },
- };
- MODULE_DEVICE_TABLE(of, stm32_romem_of_match);
diff --git a/target/linux/generic/backport-5.15/809-v6.3-0008-nvmem-stm32-detect-bsec-pta-presence-for-STM32MP15x.patch b/target/linux/generic/backport-5.15/809-v6.3-0008-nvmem-stm32-detect-bsec-pta-presence-for-STM32MP15x.patch
deleted file mode 100644 (file)
index cea8e93..0000000
+++ /dev/null
@@ -1,85 +0,0 @@
-From df2f34ef1d924125ffaf29dfdaf7cdbd3183c321 Mon Sep 17 00:00:00 2001
-From: Patrick Delaunay <[email protected]>
-Date: Mon, 6 Feb 2023 13:43:52 +0000
-Subject: [PATCH] nvmem: stm32: detect bsec pta presence for STM32MP15x
-
-On STM32MP15x SoC, the SMC backend is optional when OP-TEE is used;
-the PTA BSEC should be used as it is done on STM32MP13x platform,
-but the BSEC SMC can be also used: it is a legacy mode in OP-TEE,
-not recommended but used in previous OP-TEE firmware.
-
-The presence of OP-TEE is dynamically detected in STM32MP15x device tree
-and the supported NVMEM backend is dynamically detected:
-- PTA with stm32_bsec_pta_find
-- SMC with stm32_bsec_check
-
-With OP-TEE but without PTA and SMC detection, the probe is deferred for
-STM32MP15x devices.
-
-On STM32MP13x platform, only the PTA is supported with cfg->ta = true
-and this detection is skipped.
-
-Signed-off-by: Patrick Delaunay <[email protected]>
-Reviewed-by: Etienne Carriere <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/stm32-romem.c | 38 +++++++++++++++++++++++++++++++++----
- 1 file changed, 34 insertions(+), 4 deletions(-)
-
---- a/drivers/nvmem/stm32-romem.c
-+++ b/drivers/nvmem/stm32-romem.c
-@@ -159,6 +159,31 @@ static int stm32_bsec_pta_write(void *co
-       return stm32_bsec_optee_ta_write(priv->ctx, priv->lower, offset, buf, bytes);
- }
-+static bool stm32_bsec_smc_check(void)
-+{
-+      u32 val;
-+      int ret;
-+
-+      /* check that the OP-TEE support the BSEC SMC (legacy mode) */
-+      ret = stm32_bsec_smc(STM32_SMC_READ_SHADOW, 0, 0, &val);
-+
-+      return !ret;
-+}
-+
-+static bool optee_presence_check(void)
-+{
-+      struct device_node *np;
-+      bool tee_detected = false;
-+
-+      /* check that the OP-TEE node is present and available. */
-+      np = of_find_compatible_node(NULL, NULL, "linaro,optee-tz");
-+      if (np && of_device_is_available(np))
-+              tee_detected = true;
-+      of_node_put(np);
-+
-+      return tee_detected;
-+}
-+
- static int stm32_romem_probe(struct platform_device *pdev)
- {
-       const struct stm32_romem_cfg *cfg;
-@@ -195,11 +220,16 @@ static int stm32_romem_probe(struct plat
-       } else {
-               priv->cfg.size = cfg->size;
-               priv->lower = cfg->lower;
--              if (cfg->ta) {
-+              if (cfg->ta || optee_presence_check()) {
-                       rc = stm32_bsec_optee_ta_open(&priv->ctx);
--                      /* wait for OP-TEE client driver to be up and ready */
--                      if (rc)
--                              return rc;
-+                      if (rc) {
-+                              /* wait for OP-TEE client driver to be up and ready */
-+                              if (rc == -EPROBE_DEFER)
-+                                      return -EPROBE_DEFER;
-+                              /* BSEC PTA is required or SMC not supported */
-+                              if (cfg->ta || !stm32_bsec_smc_check())
-+                                      return rc;
-+                      }
-               }
-               if (priv->ctx) {
-                       rc = devm_add_action_or_reset(dev, stm32_bsec_optee_ta_close, priv->ctx);
diff --git a/target/linux/generic/backport-5.15/809-v6.3-0009-nvmem-rave-sp-eeprm-fix-kernel-doc-bad-line-warning.patch b/target/linux/generic/backport-5.15/809-v6.3-0009-nvmem-rave-sp-eeprm-fix-kernel-doc-bad-line-warning.patch
deleted file mode 100644 (file)
index 9d6275a..0000000
+++ /dev/null
@@ -1,32 +0,0 @@
-From 3e5ac22aa564026e99defc3a8e02082521a5b231 Mon Sep 17 00:00:00 2001
-From: Randy Dunlap <[email protected]>
-Date: Mon, 6 Feb 2023 13:43:53 +0000
-Subject: [PATCH] nvmem: rave-sp-eeprm: fix kernel-doc bad line warning
-
-Convert an empty line to " *" to avoid a kernel-doc warning:
-
-drivers/nvmem/rave-sp-eeprom.c:48: warning: bad line:
-
-Signed-off-by: Randy Dunlap <[email protected]>
-Cc: Srinivas Kandagatla <[email protected]>
-Cc: Andrey Vostrikov <[email protected]>
-Cc: Nikita Yushchenko <[email protected]>
-Cc: Andrey Smirnov <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/rave-sp-eeprom.c | 2 +-
- 1 file changed, 1 insertion(+), 1 deletion(-)
-
---- a/drivers/nvmem/rave-sp-eeprom.c
-+++ b/drivers/nvmem/rave-sp-eeprom.c
-@@ -45,7 +45,7 @@ enum rave_sp_eeprom_header_size {
-  * @type:     Access type (see enum rave_sp_eeprom_access_type)
-  * @success:  Success flag (Success = 1, Failure = 0)
-  * @data:     Read data
--
-+ *
-  * Note this structure corresponds to RSP_*_EEPROM payload from RAVE
-  * SP ICD
-  */
diff --git a/target/linux/generic/backport-5.15/809-v6.3-0010-nvmem-qcom-spmi-sdam-register-at-device-init-time.patch b/target/linux/generic/backport-5.15/809-v6.3-0010-nvmem-qcom-spmi-sdam-register-at-device-init-time.patch
deleted file mode 100644 (file)
index 1ab9e60..0000000
+++ /dev/null
@@ -1,43 +0,0 @@
-From eb7dda20f42a9137e9ee53d5ed3b743d49338cb5 Mon Sep 17 00:00:00 2001
-From: Johan Hovold <[email protected]>
-Date: Mon, 6 Feb 2023 13:43:54 +0000
-Subject: [PATCH] nvmem: qcom-spmi-sdam: register at device init time
-
-There are currently no in-tree users of the Qualcomm SDAM nvmem driver
-and there is generally no point in registering a driver that can be
-built as a module at subsys init time.
-
-Register the driver at the normal device init time instead and let
-driver core sort out the probe order.
-
-Signed-off-by: Johan Hovold <[email protected]>
-Reviewed-by: Bjorn Andersson <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/qcom-spmi-sdam.c | 13 +------------
- 1 file changed, 1 insertion(+), 12 deletions(-)
-
---- a/drivers/nvmem/qcom-spmi-sdam.c
-+++ b/drivers/nvmem/qcom-spmi-sdam.c
-@@ -175,18 +175,7 @@ static struct platform_driver sdam_drive
-       },
-       .probe          = sdam_probe,
- };
--
--static int __init sdam_init(void)
--{
--      return platform_driver_register(&sdam_driver);
--}
--subsys_initcall(sdam_init);
--
--static void __exit sdam_exit(void)
--{
--      return platform_driver_unregister(&sdam_driver);
--}
--module_exit(sdam_exit);
-+module_platform_driver(sdam_driver);
- MODULE_DESCRIPTION("QCOM SPMI SDAM driver");
- MODULE_LICENSE("GPL v2");
diff --git a/target/linux/generic/backport-5.15/809-v6.3-0011-nvmem-stm32-fix-OPTEE-dependency.patch b/target/linux/generic/backport-5.15/809-v6.3-0011-nvmem-stm32-fix-OPTEE-dependency.patch
deleted file mode 100644 (file)
index dcf704c..0000000
+++ /dev/null
@@ -1,46 +0,0 @@
-From 1dc7e37bb0ec1c997fac82031332a38c7610352f Mon Sep 17 00:00:00 2001
-From: Arnd Bergmann <[email protected]>
-Date: Mon, 6 Feb 2023 13:43:56 +0000
-Subject: [PATCH] nvmem: stm32: fix OPTEE dependency
-
-The stm32 nvmem driver fails to link as built-in when OPTEE
-is a loadable module:
-
-aarch64-linux-ld: drivers/nvmem/stm32-bsec-optee-ta.o: in function `stm32_bsec:
-stm32-bsec-optee-ta.c:(.text+0xc8): undefined reference to `tee_client_open_session'
-aarch64-linux-ld: drivers/nvmem/stm32-bsec-optee-ta.o: in function `stm32_bsec:
-stm32-bsec-optee-ta.c:(.text+0x1fc): undefined reference to `tee_client_open_context'
-
-Change the CONFIG_NVMEM_STM32_ROMEM definition so it can only
-be built-in if OPTEE is either built-in or disabled, and
-make NVMEM_STM32_BSEC_OPTEE_TA a hidden symbol instead.
-
-Signed-off-by: Arnd Bergmann <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/Kconfig | 5 ++---
- 1 file changed, 2 insertions(+), 3 deletions(-)
-
---- a/drivers/nvmem/Kconfig
-+++ b/drivers/nvmem/Kconfig
-@@ -291,8 +291,7 @@ config NVMEM_SPRD_EFUSE
-         will be called nvmem-sprd-efuse.
- config NVMEM_STM32_BSEC_OPTEE_TA
--      bool "STM32MP BSEC OP-TEE TA support for nvmem-stm32-romem driver"
--      depends on OPTEE
-+      def_bool NVMEM_STM32_ROMEM && OPTEE
-       help
-         Say y here to enable the accesses to STM32MP SoC OTPs by the OP-TEE
-         trusted application STM32MP BSEC.
-@@ -303,7 +302,7 @@ config NVMEM_STM32_BSEC_OPTEE_TA
- config NVMEM_STM32_ROMEM
-       tristate "STMicroelectronics STM32 factory-programmed memory support"
-       depends on ARCH_STM32 || COMPILE_TEST
--      imply NVMEM_STM32_BSEC_OPTEE_TA
-+      depends on OPTEE || !OPTEE
-       help
-         Say y here to enable read-only access for STMicroelectronics STM32
-         factory-programmed memory area.
diff --git a/target/linux/generic/backport-5.15/810-v5.17-net-qmi_wwan-add-ZTE-MF286D-modem-19d2-1485.patch b/target/linux/generic/backport-5.15/810-v5.17-net-qmi_wwan-add-ZTE-MF286D-modem-19d2-1485.patch
deleted file mode 100644 (file)
index dbd734e..0000000
+++ /dev/null
@@ -1,59 +0,0 @@
-From 078c6a1cbd4cd7496048786beec2e312577bebbf Mon Sep 17 00:00:00 2001
-From: Pawel Dembicki <[email protected]>
-Date: Tue, 11 Jan 2022 23:11:32 +0100
-Subject: [PATCH 1/1] net: qmi_wwan: add ZTE MF286D modem 19d2:1485
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-Modem from ZTE MF286D is an Qualcomm MDM9250 based 3G/4G modem.
-
-T:  Bus=02 Lev=01 Prnt=01 Port=00 Cnt=01 Dev#=  3 Spd=5000 MxCh= 0
-D:  Ver= 3.00 Cls=00(>ifc ) Sub=00 Prot=00 MxPS= 9 #Cfgs=  1
-P:  Vendor=19d2 ProdID=1485 Rev=52.87
-S:  Manufacturer=ZTE,Incorporated
-S:  Product=ZTE Technologies MSM
-S:  SerialNumber=MF286DZTED000000
-C:* #Ifs= 7 Cfg#= 1 Atr=80 MxPwr=896mA
-A:  FirstIf#= 0 IfCount= 2 Cls=02(comm.) Sub=06 Prot=00
-I:* If#= 0 Alt= 0 #EPs= 1 Cls=02(comm.) Sub=02 Prot=ff Driver=rndis_host
-E:  Ad=82(I) Atr=03(Int.) MxPS=   8 Ivl=32ms
-I:* If#= 1 Alt= 0 #EPs= 2 Cls=0a(data ) Sub=00 Prot=00 Driver=rndis_host
-E:  Ad=81(I) Atr=02(Bulk) MxPS=1024 Ivl=0ms
-E:  Ad=01(O) Atr=02(Bulk) MxPS=1024 Ivl=0ms
-I:* If#= 2 Alt= 0 #EPs= 2 Cls=ff(vend.) Sub=ff Prot=ff Driver=option
-E:  Ad=83(I) Atr=02(Bulk) MxPS=1024 Ivl=0ms
-E:  Ad=02(O) Atr=02(Bulk) MxPS=1024 Ivl=0ms
-I:* If#= 3 Alt= 0 #EPs= 3 Cls=ff(vend.) Sub=ff Prot=ff Driver=option
-E:  Ad=85(I) Atr=03(Int.) MxPS=  10 Ivl=32ms
-E:  Ad=84(I) Atr=02(Bulk) MxPS=1024 Ivl=0ms
-E:  Ad=03(O) Atr=02(Bulk) MxPS=1024 Ivl=0ms
-I:* If#= 4 Alt= 0 #EPs= 3 Cls=ff(vend.) Sub=ff Prot=ff Driver=option
-E:  Ad=87(I) Atr=03(Int.) MxPS=  10 Ivl=32ms
-E:  Ad=86(I) Atr=02(Bulk) MxPS=1024 Ivl=0ms
-E:  Ad=04(O) Atr=02(Bulk) MxPS=1024 Ivl=0ms
-I:* If#= 5 Alt= 0 #EPs= 3 Cls=ff(vend.) Sub=ff Prot=ff Driver=qmi_wwan
-E:  Ad=88(I) Atr=03(Int.) MxPS=   8 Ivl=32ms
-E:  Ad=8e(I) Atr=02(Bulk) MxPS=1024 Ivl=0ms
-E:  Ad=0f(O) Atr=02(Bulk) MxPS=1024 Ivl=0ms
-I:* If#= 6 Alt= 0 #EPs= 2 Cls=ff(vend.) Sub=42 Prot=01 Driver=usbfs
-E:  Ad=05(O) Atr=02(Bulk) MxPS=1024 Ivl=0ms
-E:  Ad=89(I) Atr=02(Bulk) MxPS=1024 Ivl=0ms
-
-Signed-off-by: Pawel Dembicki <[email protected]>
-Acked-by: Bjørn Mork <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/usb/qmi_wwan.c | 1 +
- 1 file changed, 1 insertion(+)
-
---- a/drivers/net/usb/qmi_wwan.c
-+++ b/drivers/net/usb/qmi_wwan.c
-@@ -1317,6 +1317,7 @@ static const struct usb_device_id produc
-       {QMI_FIXED_INTF(0x19d2, 0x1426, 2)},    /* ZTE MF91 */
-       {QMI_FIXED_INTF(0x19d2, 0x1428, 2)},    /* Telewell TW-LTE 4G v2 */
-       {QMI_FIXED_INTF(0x19d2, 0x1432, 3)},    /* ZTE ME3620 */
-+      {QMI_FIXED_INTF(0x19d2, 0x1485, 5)},    /* ZTE MF286D */
-       {QMI_FIXED_INTF(0x19d2, 0x2002, 4)},    /* ZTE (Vodafone) K3765-Z */
-       {QMI_FIXED_INTF(0x2001, 0x7e16, 3)},    /* D-Link DWM-221 */
-       {QMI_FIXED_INTF(0x2001, 0x7e19, 4)},    /* D-Link DWM-221 B1 */
diff --git a/target/linux/generic/backport-5.15/811-v6.4-0001-nvmem-xilinx-zynqmp-make-modular.patch b/target/linux/generic/backport-5.15/811-v6.4-0001-nvmem-xilinx-zynqmp-make-modular.patch
deleted file mode 100644 (file)
index 8328e87..0000000
+++ /dev/null
@@ -1,35 +0,0 @@
-From bcd1fe07def0f070eb5f31594620aaee6f81d31a Mon Sep 17 00:00:00 2001
-From: Nick Alcock <[email protected]>
-Date: Tue, 4 Apr 2023 18:21:11 +0100
-Subject: [PATCH] nvmem: xilinx: zynqmp: make modular
-
-This driver has a MODULE_LICENSE but is not tristate so cannot be
-built as a module, unlike all its peers: make it modular to match.
-
-Signed-off-by: Nick Alcock <[email protected]>
-Suggested-by: Michal Simek <[email protected]>
-Cc: Luis Chamberlain <[email protected]>
-Cc: Hitomi Hasegawa <[email protected]>
-Cc: Srinivas Kandagatla <[email protected]>
-Cc: Michal Simek <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/Kconfig | 2 +-
- 1 file changed, 1 insertion(+), 1 deletion(-)
-
---- a/drivers/nvmem/Kconfig
-+++ b/drivers/nvmem/Kconfig
-@@ -368,7 +368,7 @@ config NVMEM_VF610_OCOTP
-         be called nvmem-vf610-ocotp.
- config NVMEM_ZYNQMP
--      bool "Xilinx ZYNQMP SoC nvmem firmware support"
-+      tristate "Xilinx ZYNQMP SoC nvmem firmware support"
-       depends on ARCH_ZYNQMP
-       help
-         This is a driver to access hardware related data like
diff --git a/target/linux/generic/backport-5.15/811-v6.4-0002-nvmem-core-introduce-NVMEM-layouts.patch b/target/linux/generic/backport-5.15/811-v6.4-0002-nvmem-core-introduce-NVMEM-layouts.patch
deleted file mode 100644 (file)
index 23518d2..0000000
+++ /dev/null
@@ -1,387 +0,0 @@
-From 266570f496b90dea8fda893c2cf7c28d63ae2bd9 Mon Sep 17 00:00:00 2001
-From: Michael Walle <[email protected]>
-Date: Tue, 4 Apr 2023 18:21:21 +0100
-Subject: [PATCH] nvmem: core: introduce NVMEM layouts
-
-NVMEM layouts are used to generate NVMEM cells during runtime. Think of
-an EEPROM with a well-defined conent. For now, the content can be
-described by a device tree or a board file. But this only works if the
-offsets and lengths are static and don't change. One could also argue
-that putting the layout of the EEPROM in the device tree is the wrong
-place. Instead, the device tree should just have a specific compatible
-string.
-
-Right now there are two use cases:
- (1) The NVMEM cell needs special processing. E.g. if it only specifies
-     a base MAC address offset and you need to add an offset, or it
-     needs to parse a MAC from ASCII format or some proprietary format.
-     (Post processing of cells is added in a later commit).
- (2) u-boot environment parsing. The cells don't have a particular
-     offset but it needs parsing the content to determine the offsets
-     and length.
-
-Co-developed-by: Miquel Raynal <[email protected]>
-Signed-off-by: Miquel Raynal <[email protected]>
-Signed-off-by: Michael Walle <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- Documentation/driver-api/nvmem.rst |  15 ++++
- drivers/nvmem/Kconfig              |   4 +
- drivers/nvmem/Makefile             |   1 +
- drivers/nvmem/core.c               | 120 +++++++++++++++++++++++++++++
- drivers/nvmem/layouts/Kconfig      |   5 ++
- drivers/nvmem/layouts/Makefile     |   4 +
- include/linux/nvmem-consumer.h     |   7 ++
- include/linux/nvmem-provider.h     |  51 ++++++++++++
- 8 files changed, 207 insertions(+)
- create mode 100644 drivers/nvmem/layouts/Kconfig
- create mode 100644 drivers/nvmem/layouts/Makefile
-
---- a/Documentation/driver-api/nvmem.rst
-+++ b/Documentation/driver-api/nvmem.rst
-@@ -189,3 +189,18 @@ ex::
- =====================
- See Documentation/devicetree/bindings/nvmem/nvmem.txt
-+
-+8. NVMEM layouts
-+================
-+
-+NVMEM layouts are yet another mechanism to create cells. With the device
-+tree binding it is possible to specify simple cells by using an offset
-+and a length. Sometimes, the cells doesn't have a static offset, but
-+the content is still well defined, e.g. tag-length-values. In this case,
-+the NVMEM device content has to be first parsed and the cells need to
-+be added accordingly. Layouts let you read the content of the NVMEM device
-+and let you add cells dynamically.
-+
-+Another use case for layouts is the post processing of cells. With layouts,
-+it is possible to associate a custom post processing hook to a cell. It
-+even possible to add this hook to cells not created by the layout itself.
---- a/drivers/nvmem/Kconfig
-+++ b/drivers/nvmem/Kconfig
-@@ -21,6 +21,10 @@ config NVMEM_SYSFS
-        This interface is mostly used by userspace applications to
-        read/write directly into nvmem.
-+# Layouts
-+
-+source "drivers/nvmem/layouts/Kconfig"
-+
- # Devices
- config NVMEM_APPLE_EFUSES
---- a/drivers/nvmem/Makefile
-+++ b/drivers/nvmem/Makefile
-@@ -5,6 +5,7 @@
- obj-$(CONFIG_NVMEM)           += nvmem_core.o
- nvmem_core-y                  := core.o
-+obj-y                         += layouts/
- # Devices
- obj-$(CONFIG_NVMEM_APPLE_EFUSES)      += nvmem-apple-efuses.o
---- a/drivers/nvmem/core.c
-+++ b/drivers/nvmem/core.c
-@@ -40,6 +40,7 @@ struct nvmem_device {
-       nvmem_reg_write_t       reg_write;
-       nvmem_cell_post_process_t cell_post_process;
-       struct gpio_desc        *wp_gpio;
-+      struct nvmem_layout     *layout;
-       void *priv;
- };
-@@ -74,6 +75,9 @@ static LIST_HEAD(nvmem_lookup_list);
- static BLOCKING_NOTIFIER_HEAD(nvmem_notifier);
-+static DEFINE_SPINLOCK(nvmem_layout_lock);
-+static LIST_HEAD(nvmem_layouts);
-+
- static int __nvmem_reg_read(struct nvmem_device *nvmem, unsigned int offset,
-                           void *val, size_t bytes)
- {
-@@ -728,6 +732,101 @@ static int nvmem_add_cells_from_of(struc
-       return 0;
- }
-+int __nvmem_layout_register(struct nvmem_layout *layout, struct module *owner)
-+{
-+      layout->owner = owner;
-+
-+      spin_lock(&nvmem_layout_lock);
-+      list_add(&layout->node, &nvmem_layouts);
-+      spin_unlock(&nvmem_layout_lock);
-+
-+      return 0;
-+}
-+EXPORT_SYMBOL_GPL(__nvmem_layout_register);
-+
-+void nvmem_layout_unregister(struct nvmem_layout *layout)
-+{
-+      spin_lock(&nvmem_layout_lock);
-+      list_del(&layout->node);
-+      spin_unlock(&nvmem_layout_lock);
-+}
-+EXPORT_SYMBOL_GPL(nvmem_layout_unregister);
-+
-+static struct nvmem_layout *nvmem_layout_get(struct nvmem_device *nvmem)
-+{
-+      struct device_node *layout_np, *np = nvmem->dev.of_node;
-+      struct nvmem_layout *l, *layout = NULL;
-+
-+      layout_np = of_get_child_by_name(np, "nvmem-layout");
-+      if (!layout_np)
-+              return NULL;
-+
-+      spin_lock(&nvmem_layout_lock);
-+
-+      list_for_each_entry(l, &nvmem_layouts, node) {
-+              if (of_match_node(l->of_match_table, layout_np)) {
-+                      if (try_module_get(l->owner))
-+                              layout = l;
-+
-+                      break;
-+              }
-+      }
-+
-+      spin_unlock(&nvmem_layout_lock);
-+      of_node_put(layout_np);
-+
-+      return layout;
-+}
-+
-+static void nvmem_layout_put(struct nvmem_layout *layout)
-+{
-+      if (layout)
-+              module_put(layout->owner);
-+}
-+
-+static int nvmem_add_cells_from_layout(struct nvmem_device *nvmem)
-+{
-+      struct nvmem_layout *layout = nvmem->layout;
-+      int ret;
-+
-+      if (layout && layout->add_cells) {
-+              ret = layout->add_cells(&nvmem->dev, nvmem, layout);
-+              if (ret)
-+                      return ret;
-+      }
-+
-+      return 0;
-+}
-+
-+#if IS_ENABLED(CONFIG_OF)
-+/**
-+ * of_nvmem_layout_get_container() - Get OF node to layout container.
-+ *
-+ * @nvmem: nvmem device.
-+ *
-+ * Return: a node pointer with refcount incremented or NULL if no
-+ * container exists. Use of_node_put() on it when done.
-+ */
-+struct device_node *of_nvmem_layout_get_container(struct nvmem_device *nvmem)
-+{
-+      return of_get_child_by_name(nvmem->dev.of_node, "nvmem-layout");
-+}
-+EXPORT_SYMBOL_GPL(of_nvmem_layout_get_container);
-+#endif
-+
-+const void *nvmem_layout_get_match_data(struct nvmem_device *nvmem,
-+                                      struct nvmem_layout *layout)
-+{
-+      struct device_node __maybe_unused *layout_np;
-+      const struct of_device_id *match;
-+
-+      layout_np = of_nvmem_layout_get_container(nvmem);
-+      match = of_match_node(layout->of_match_table, layout_np);
-+
-+      return match ? match->data : NULL;
-+}
-+EXPORT_SYMBOL_GPL(nvmem_layout_get_match_data);
-+
- /**
-  * nvmem_register() - Register a nvmem device for given nvmem_config.
-  * Also creates a binary entry in /sys/bus/nvmem/devices/dev-name/nvmem
-@@ -834,6 +933,12 @@ struct nvmem_device *nvmem_register(cons
-                       goto err_put_device;
-       }
-+      /*
-+       * If the driver supplied a layout by config->layout, the module
-+       * pointer will be NULL and nvmem_layout_put() will be a noop.
-+       */
-+      nvmem->layout = config->layout ?: nvmem_layout_get(nvmem);
-+
-       if (config->cells) {
-               rval = nvmem_add_cells(nvmem, config->cells, config->ncells);
-               if (rval)
-@@ -854,12 +959,17 @@ struct nvmem_device *nvmem_register(cons
-       if (rval)
-               goto err_remove_cells;
-+      rval = nvmem_add_cells_from_layout(nvmem);
-+      if (rval)
-+              goto err_remove_cells;
-+
-       blocking_notifier_call_chain(&nvmem_notifier, NVMEM_ADD, nvmem);
-       return nvmem;
- err_remove_cells:
-       nvmem_device_remove_all_cells(nvmem);
-+      nvmem_layout_put(nvmem->layout);
-       if (config->compat)
-               nvmem_sysfs_remove_compat(nvmem, config);
- err_put_device:
-@@ -881,6 +991,7 @@ static void nvmem_device_release(struct
-               device_remove_bin_file(nvmem->base_dev, &nvmem->eeprom);
-       nvmem_device_remove_all_cells(nvmem);
-+      nvmem_layout_put(nvmem->layout);
-       device_unregister(&nvmem->dev);
- }
-@@ -1246,6 +1357,15 @@ struct nvmem_cell *of_nvmem_cell_get(str
-               return ERR_PTR(-EINVAL);
-       }
-+      /* nvmem layouts produce cells within the nvmem-layout container */
-+      if (of_node_name_eq(nvmem_np, "nvmem-layout")) {
-+              nvmem_np = of_get_next_parent(nvmem_np);
-+              if (!nvmem_np) {
-+                      of_node_put(cell_np);
-+                      return ERR_PTR(-EINVAL);
-+              }
-+      }
-+
-       nvmem = __nvmem_device_get(nvmem_np, device_match_of_node);
-       of_node_put(nvmem_np);
-       if (IS_ERR(nvmem)) {
---- /dev/null
-+++ b/drivers/nvmem/layouts/Kconfig
-@@ -0,0 +1,5 @@
-+# SPDX-License-Identifier: GPL-2.0
-+
-+menu "Layout Types"
-+
-+endmenu
---- /dev/null
-+++ b/drivers/nvmem/layouts/Makefile
-@@ -0,0 +1,4 @@
-+# SPDX-License-Identifier: GPL-2.0
-+#
-+# Makefile for nvmem layouts.
-+#
---- a/include/linux/nvmem-consumer.h
-+++ b/include/linux/nvmem-consumer.h
-@@ -239,6 +239,7 @@ struct nvmem_cell *of_nvmem_cell_get(str
-                                    const char *id);
- struct nvmem_device *of_nvmem_device_get(struct device_node *np,
-                                        const char *name);
-+struct device_node *of_nvmem_layout_get_container(struct nvmem_device *nvmem);
- #else
- static inline struct nvmem_cell *of_nvmem_cell_get(struct device_node *np,
-                                                  const char *id)
-@@ -251,6 +252,12 @@ static inline struct nvmem_device *of_nv
- {
-       return ERR_PTR(-EOPNOTSUPP);
- }
-+
-+static inline struct device_node *
-+of_nvmem_layout_get_container(struct nvmem_device *nvmem)
-+{
-+      return ERR_PTR(-EOPNOTSUPP);
-+}
- #endif /* CONFIG_NVMEM && CONFIG_OF */
- #endif  /* ifndef _LINUX_NVMEM_CONSUMER_H */
---- a/include/linux/nvmem-provider.h
-+++ b/include/linux/nvmem-provider.h
-@@ -88,6 +88,7 @@ struct nvmem_cell_info {
-  * @stride:   Minimum read/write access stride.
-  * @priv:     User context passed to read/write callbacks.
-  * @ignore_wp:  Write Protect pin is managed by the provider.
-+ * @layout:   Fixed layout associated with this nvmem device.
-  *
-  * Note: A default "nvmem<id>" name will be assigned to the device if
-  * no name is specified in its configuration. In such case "<id>" is
-@@ -109,6 +110,7 @@ struct nvmem_config {
-       bool                    read_only;
-       bool                    root_only;
-       bool                    ignore_wp;
-+      struct nvmem_layout     *layout;
-       struct device_node      *of_node;
-       bool                    no_of_node;
-       nvmem_reg_read_t        reg_read;
-@@ -142,6 +144,33 @@ struct nvmem_cell_table {
-       struct list_head        node;
- };
-+/**
-+ * struct nvmem_layout - NVMEM layout definitions
-+ *
-+ * @name:             Layout name.
-+ * @of_match_table:   Open firmware match table.
-+ * @add_cells:                Will be called if a nvmem device is found which
-+ *                    has this layout. The function will add layout
-+ *                    specific cells with nvmem_add_one_cell().
-+ * @owner:            Pointer to struct module.
-+ * @node:             List node.
-+ *
-+ * A nvmem device can hold a well defined structure which can just be
-+ * evaluated during runtime. For example a TLV list, or a list of "name=val"
-+ * pairs. A nvmem layout can parse the nvmem device and add appropriate
-+ * cells.
-+ */
-+struct nvmem_layout {
-+      const char *name;
-+      const struct of_device_id *of_match_table;
-+      int (*add_cells)(struct device *dev, struct nvmem_device *nvmem,
-+                       struct nvmem_layout *layout);
-+
-+      /* private */
-+      struct module *owner;
-+      struct list_head node;
-+};
-+
- #if IS_ENABLED(CONFIG_NVMEM)
- struct nvmem_device *nvmem_register(const struct nvmem_config *cfg);
-@@ -156,6 +185,14 @@ void nvmem_del_cell_table(struct nvmem_c
- int nvmem_add_one_cell(struct nvmem_device *nvmem,
-                      const struct nvmem_cell_info *info);
-+int __nvmem_layout_register(struct nvmem_layout *layout, struct module *owner);
-+#define nvmem_layout_register(layout) \
-+      __nvmem_layout_register(layout, THIS_MODULE)
-+void nvmem_layout_unregister(struct nvmem_layout *layout);
-+
-+const void *nvmem_layout_get_match_data(struct nvmem_device *nvmem,
-+                                      struct nvmem_layout *layout);
-+
- #else
- static inline struct nvmem_device *nvmem_register(const struct nvmem_config *c)
-@@ -179,5 +216,19 @@ static inline int nvmem_add_one_cell(str
-       return -EOPNOTSUPP;
- }
-+static inline int nvmem_layout_register(struct nvmem_layout *layout)
-+{
-+      return -EOPNOTSUPP;
-+}
-+
-+static inline void nvmem_layout_unregister(struct nvmem_layout *layout) {}
-+
-+static inline const void *
-+nvmem_layout_get_match_data(struct nvmem_device *nvmem,
-+                          struct nvmem_layout *layout)
-+{
-+      return NULL;
-+}
-+
- #endif /* CONFIG_NVMEM */
- #endif  /* ifndef _LINUX_NVMEM_PROVIDER_H */
diff --git a/target/linux/generic/backport-5.15/811-v6.4-0003-nvmem-core-handle-the-absence-of-expected-layouts.patch b/target/linux/generic/backport-5.15/811-v6.4-0003-nvmem-core-handle-the-absence-of-expected-layouts.patch
deleted file mode 100644 (file)
index 6fa7b63..0000000
+++ /dev/null
@@ -1,61 +0,0 @@
-From 6468a6f45148fb5e95c86b4efebf63f9abcd2137 Mon Sep 17 00:00:00 2001
-From: Miquel Raynal <[email protected]>
-Date: Tue, 4 Apr 2023 18:21:22 +0100
-Subject: [PATCH] nvmem: core: handle the absence of expected layouts
-
-Make nvmem_layout_get() return -EPROBE_DEFER while the expected layout
-is not available. This condition cannot be triggered today as nvmem
-layout drivers are initialed as part of an early init call, but soon
-these drivers will be converted into modules and be initialized with a
-standard priority, so the unavailability of the drivers might become a
-reality that must be taken care of.
-
-Let's anticipate this by telling the caller the layout might not yet be
-available. A probe deferral is requested in this case.
-
-Please note this does not affect any nvmem device not using layouts,
-because an early check against the "nvmem-layout" container presence
-will return NULL in this case.
-
-Signed-off-by: Miquel Raynal <[email protected]>
-Tested-by: Michael Walle <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/core.c | 10 +++++++++-
- 1 file changed, 9 insertions(+), 1 deletion(-)
-
---- a/drivers/nvmem/core.c
-+++ b/drivers/nvmem/core.c
-@@ -755,7 +755,7 @@ EXPORT_SYMBOL_GPL(nvmem_layout_unregiste
- static struct nvmem_layout *nvmem_layout_get(struct nvmem_device *nvmem)
- {
-       struct device_node *layout_np, *np = nvmem->dev.of_node;
--      struct nvmem_layout *l, *layout = NULL;
-+      struct nvmem_layout *l, *layout = ERR_PTR(-EPROBE_DEFER);
-       layout_np = of_get_child_by_name(np, "nvmem-layout");
-       if (!layout_np)
-@@ -938,6 +938,13 @@ struct nvmem_device *nvmem_register(cons
-        * pointer will be NULL and nvmem_layout_put() will be a noop.
-        */
-       nvmem->layout = config->layout ?: nvmem_layout_get(nvmem);
-+      if (IS_ERR(nvmem->layout)) {
-+              rval = PTR_ERR(nvmem->layout);
-+              nvmem->layout = NULL;
-+
-+              if (rval == -EPROBE_DEFER)
-+                      goto err_teardown_compat;
-+      }
-       if (config->cells) {
-               rval = nvmem_add_cells(nvmem, config->cells, config->ncells);
-@@ -970,6 +977,7 @@ struct nvmem_device *nvmem_register(cons
- err_remove_cells:
-       nvmem_device_remove_all_cells(nvmem);
-       nvmem_layout_put(nvmem->layout);
-+err_teardown_compat:
-       if (config->compat)
-               nvmem_sysfs_remove_compat(nvmem, config);
- err_put_device:
diff --git a/target/linux/generic/backport-5.15/811-v6.4-0004-nvmem-core-request-layout-modules-loading.patch b/target/linux/generic/backport-5.15/811-v6.4-0004-nvmem-core-request-layout-modules-loading.patch
deleted file mode 100644 (file)
index b934166..0000000
+++ /dev/null
@@ -1,52 +0,0 @@
-From b1c37bec1ccfe5ccab72bc0ddc0dfa45c43e2de2 Mon Sep 17 00:00:00 2001
-From: Miquel Raynal <[email protected]>
-Date: Tue, 4 Apr 2023 18:21:23 +0100
-Subject: [PATCH] nvmem: core: request layout modules loading
-
-When a storage device like an eeprom or an mtd device probes, it
-registers an nvmem device if the nvmem subsystem has been enabled (bool
-symbol). During nvmem registration, if the device is using layouts to
-expose dynamic nvmem cells, the core will first try to get a reference
-over the layout driver callbacks. In practice there is not relationship
-that can be described between the storage driver and the nvmem
-layout. So there is no way we can enforce both drivers will be built-in
-or both will be modules. If the storage device driver is built-in but
-the layout is built as a module, instead of badly failing with an
-endless probe deferral loop, lets just make a modprobe call in case the
-driver was made available in an initramfs with
-of_device_node_request_module(), and offer a fully functional system to
-the user.
-
-Signed-off-by: Miquel Raynal <[email protected]>
-Tested-by: Michael Walle <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/core.c | 8 ++++++++
- 1 file changed, 8 insertions(+)
-
---- a/drivers/nvmem/core.c
-+++ b/drivers/nvmem/core.c
-@@ -17,6 +17,7 @@
- #include <linux/nvmem-provider.h>
- #include <linux/gpio/consumer.h>
- #include <linux/of.h>
-+#include <linux/of_device.h>
- #include <linux/slab.h>
- struct nvmem_device {
-@@ -761,6 +762,13 @@ static struct nvmem_layout *nvmem_layout
-       if (!layout_np)
-               return NULL;
-+      /*
-+       * In case the nvmem device was built-in while the layout was built as a
-+       * module, we shall manually request the layout driver loading otherwise
-+       * we'll never have any match.
-+       */
-+      of_request_module(layout_np);
-+
-       spin_lock(&nvmem_layout_lock);
-       list_for_each_entry(l, &nvmem_layouts, node) {
diff --git a/target/linux/generic/backport-5.15/811-v6.4-0005-nvmem-core-add-per-cell-post-processing.patch b/target/linux/generic/backport-5.15/811-v6.4-0005-nvmem-core-add-per-cell-post-processing.patch
deleted file mode 100644 (file)
index 53628cd..0000000
+++ /dev/null
@@ -1,86 +0,0 @@
-From 345ec382cd4b736c36e01f155d08c913b225b736 Mon Sep 17 00:00:00 2001
-From: Michael Walle <[email protected]>
-Date: Tue, 4 Apr 2023 18:21:24 +0100
-Subject: [PATCH] nvmem: core: add per-cell post processing
-
-Instead of relying on the name the consumer is using for the cell, like
-it is done for the nvmem .cell_post_process configuration parameter,
-provide a per-cell post processing hook. This can then be populated by
-the NVMEM provider (or the NVMEM layout) when adding the cell.
-
-Signed-off-by: Michael Walle <[email protected]>
-Signed-off-by: Miquel Raynal <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/core.c           | 17 +++++++++++++++++
- include/linux/nvmem-provider.h |  3 +++
- 2 files changed, 20 insertions(+)
-
---- a/drivers/nvmem/core.c
-+++ b/drivers/nvmem/core.c
-@@ -54,6 +54,7 @@ struct nvmem_cell_entry {
-       int                     bytes;
-       int                     bit_offset;
-       int                     nbits;
-+      nvmem_cell_post_process_t read_post_process;
-       struct device_node      *np;
-       struct nvmem_device     *nvmem;
-       struct list_head        node;
-@@ -470,6 +471,7 @@ static int nvmem_cell_info_to_nvmem_cell
-       cell->offset = info->offset;
-       cell->bytes = info->bytes;
-       cell->name = info->name;
-+      cell->read_post_process = info->read_post_process;
-       cell->bit_offset = info->bit_offset;
-       cell->nbits = info->nbits;
-@@ -1563,6 +1565,13 @@ static int __nvmem_cell_read(struct nvme
-       if (cell->bit_offset || cell->nbits)
-               nvmem_shift_read_buffer_in_place(cell, buf);
-+      if (cell->read_post_process) {
-+              rc = cell->read_post_process(nvmem->priv, id, index,
-+                                           cell->offset, buf, cell->bytes);
-+              if (rc)
-+                      return rc;
-+      }
-+
-       if (nvmem->cell_post_process) {
-               rc = nvmem->cell_post_process(nvmem->priv, id, index,
-                                             cell->offset, buf, cell->bytes);
-@@ -1671,6 +1680,14 @@ static int __nvmem_cell_entry_write(stru
-           (cell->bit_offset == 0 && len != cell->bytes))
-               return -EINVAL;
-+      /*
-+       * Any cells which have a read_post_process hook are read-only because
-+       * we cannot reverse the operation and it might affect other cells,
-+       * too.
-+       */
-+      if (cell->read_post_process)
-+              return -EINVAL;
-+
-       if (cell->bit_offset || cell->nbits) {
-               buf = nvmem_cell_prepare_write_buffer(cell, buf, len);
-               if (IS_ERR(buf))
---- a/include/linux/nvmem-provider.h
-+++ b/include/linux/nvmem-provider.h
-@@ -54,6 +54,8 @@ struct nvmem_keepout {
-  * @bit_offset:       Bit offset if cell is smaller than a byte.
-  * @nbits:    Number of bits.
-  * @np:               Optional device_node pointer.
-+ * @read_post_process:        Callback for optional post processing of cell data
-+ *                    on reads.
-  */
- struct nvmem_cell_info {
-       const char              *name;
-@@ -62,6 +64,7 @@ struct nvmem_cell_info {
-       unsigned int            bit_offset;
-       unsigned int            nbits;
-       struct device_node      *np;
-+      nvmem_cell_post_process_t read_post_process;
- };
- /**
diff --git a/target/linux/generic/backport-5.15/811-v6.4-0006-nvmem-core-allow-to-modify-a-cell-before-adding-it.patch b/target/linux/generic/backport-5.15/811-v6.4-0006-nvmem-core-allow-to-modify-a-cell-before-adding-it.patch
deleted file mode 100644 (file)
index 3299014..0000000
+++ /dev/null
@@ -1,59 +0,0 @@
-From de12c9691501ccba41a154c223869f82be4c12fd Mon Sep 17 00:00:00 2001
-From: Michael Walle <[email protected]>
-Date: Tue, 4 Apr 2023 18:21:25 +0100
-Subject: [PATCH] nvmem: core: allow to modify a cell before adding it
-
-Provide a way to modify a cell before it will get added. This is useful
-to attach a custom post processing hook via a layout.
-
-Signed-off-by: Michael Walle <[email protected]>
-Signed-off-by: Miquel Raynal <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/core.c           | 4 ++++
- include/linux/nvmem-provider.h | 5 +++++
- 2 files changed, 9 insertions(+)
-
---- a/drivers/nvmem/core.c
-+++ b/drivers/nvmem/core.c
-@@ -695,6 +695,7 @@ static int nvmem_validate_keepouts(struc
- static int nvmem_add_cells_from_of(struct nvmem_device *nvmem)
- {
-+      struct nvmem_layout *layout = nvmem->layout;
-       struct device *dev = &nvmem->dev;
-       struct device_node *child;
-       const __be32 *addr;
-@@ -724,6 +725,9 @@ static int nvmem_add_cells_from_of(struc
-               info.np = of_node_get(child);
-+              if (layout && layout->fixup_cell_info)
-+                      layout->fixup_cell_info(nvmem, layout, &info);
-+
-               ret = nvmem_add_one_cell(nvmem, &info);
-               kfree(info.name);
-               if (ret) {
---- a/include/linux/nvmem-provider.h
-+++ b/include/linux/nvmem-provider.h
-@@ -155,6 +155,8 @@ struct nvmem_cell_table {
-  * @add_cells:                Will be called if a nvmem device is found which
-  *                    has this layout. The function will add layout
-  *                    specific cells with nvmem_add_one_cell().
-+ * @fixup_cell_info:  Will be called before a cell is added. Can be
-+ *                    used to modify the nvmem_cell_info.
-  * @owner:            Pointer to struct module.
-  * @node:             List node.
-  *
-@@ -168,6 +170,9 @@ struct nvmem_layout {
-       const struct of_device_id *of_match_table;
-       int (*add_cells)(struct device *dev, struct nvmem_device *nvmem,
-                        struct nvmem_layout *layout);
-+      void (*fixup_cell_info)(struct nvmem_device *nvmem,
-+                              struct nvmem_layout *layout,
-+                              struct nvmem_cell_info *cell);
-       /* private */
-       struct module *owner;
diff --git a/target/linux/generic/backport-5.15/811-v6.4-0007-nvmem-imx-ocotp-replace-global-post-processing-with-.patch b/target/linux/generic/backport-5.15/811-v6.4-0007-nvmem-imx-ocotp-replace-global-post-processing-with-.patch
deleted file mode 100644 (file)
index 2a5fa61..0000000
+++ /dev/null
@@ -1,81 +0,0 @@
-From 6c56a82d7895a213a43182a5d01a21a906a79847 Mon Sep 17 00:00:00 2001
-From: Michael Walle <[email protected]>
-Date: Tue, 4 Apr 2023 18:21:26 +0100
-Subject: [PATCH] nvmem: imx-ocotp: replace global post processing with layouts
-
-In preparation of retiring the global post processing hook change this
-driver to use layouts. The layout will be supplied during registration
-and will be used to add the post processing hook to all added cells.
-
-Signed-off-by: Michael Walle <[email protected]>
-Tested-by: Michael Walle <[email protected]> # on kontron-pitx-imx8m
-Signed-off-by: Miquel Raynal <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/imx-ocotp.c | 30 +++++++++++++++++++-----------
- 1 file changed, 19 insertions(+), 11 deletions(-)
-
---- a/drivers/nvmem/imx-ocotp.c
-+++ b/drivers/nvmem/imx-ocotp.c
-@@ -225,18 +225,13 @@ read_end:
- static int imx_ocotp_cell_pp(void *context, const char *id, int index,
-                            unsigned int offset, void *data, size_t bytes)
- {
--      struct ocotp_priv *priv = context;
-+      u8 *buf = data;
-+      int i;
-       /* Deal with some post processing of nvmem cell data */
--      if (id && !strcmp(id, "mac-address")) {
--              if (priv->params->reverse_mac_address) {
--                      u8 *buf = data;
--                      int i;
--
--                      for (i = 0; i < bytes/2; i++)
--                              swap(buf[i], buf[bytes - i - 1]);
--              }
--      }
-+      if (id && !strcmp(id, "mac-address"))
-+              for (i = 0; i < bytes / 2; i++)
-+                      swap(buf[i], buf[bytes - i - 1]);
-       return 0;
- }
-@@ -488,7 +483,6 @@ static struct nvmem_config imx_ocotp_nvm
-       .stride = 1,
-       .reg_read = imx_ocotp_read,
-       .reg_write = imx_ocotp_write,
--      .cell_post_process = imx_ocotp_cell_pp,
- };
- static const struct ocotp_params imx6q_params = {
-@@ -595,6 +589,17 @@ static const struct of_device_id imx_oco
- };
- MODULE_DEVICE_TABLE(of, imx_ocotp_dt_ids);
-+static void imx_ocotp_fixup_cell_info(struct nvmem_device *nvmem,
-+                                    struct nvmem_layout *layout,
-+                                    struct nvmem_cell_info *cell)
-+{
-+      cell->read_post_process = imx_ocotp_cell_pp;
-+}
-+
-+struct nvmem_layout imx_ocotp_layout = {
-+      .fixup_cell_info = imx_ocotp_fixup_cell_info,
-+};
-+
- static int imx_ocotp_probe(struct platform_device *pdev)
- {
-       struct device *dev = &pdev->dev;
-@@ -619,6 +624,9 @@ static int imx_ocotp_probe(struct platfo
-       imx_ocotp_nvmem_config.size = 4 * priv->params->nregs;
-       imx_ocotp_nvmem_config.dev = dev;
-       imx_ocotp_nvmem_config.priv = priv;
-+      if (priv->params->reverse_mac_address)
-+              imx_ocotp_nvmem_config.layout = &imx_ocotp_layout;
-+
-       priv->config = &imx_ocotp_nvmem_config;
-       clk_prepare_enable(priv->clk);
diff --git a/target/linux/generic/backport-5.15/811-v6.4-0008-nvmem-cell-drop-global-cell_post_process.patch b/target/linux/generic/backport-5.15/811-v6.4-0008-nvmem-cell-drop-global-cell_post_process.patch
deleted file mode 100644 (file)
index eac202b..0000000
+++ /dev/null
@@ -1,68 +0,0 @@
-From 011e40a166fdaa65fb9946b7cd91efec85b70dbb Mon Sep 17 00:00:00 2001
-From: Michael Walle <[email protected]>
-Date: Tue, 4 Apr 2023 18:21:27 +0100
-Subject: [PATCH] nvmem: cell: drop global cell_post_process
-
-There are no users anymore for the global cell_post_process callback
-anymore. New users should use proper nvmem layouts.
-
-Signed-off-by: Michael Walle <[email protected]>
-Signed-off-by: Miquel Raynal <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/core.c           | 9 ---------
- include/linux/nvmem-provider.h | 2 --
- 2 files changed, 11 deletions(-)
-
---- a/drivers/nvmem/core.c
-+++ b/drivers/nvmem/core.c
-@@ -39,7 +39,6 @@ struct nvmem_device {
-       unsigned int            nkeepout;
-       nvmem_reg_read_t        reg_read;
-       nvmem_reg_write_t       reg_write;
--      nvmem_cell_post_process_t cell_post_process;
-       struct gpio_desc        *wp_gpio;
-       struct nvmem_layout     *layout;
-       void *priv;
-@@ -903,7 +902,6 @@ struct nvmem_device *nvmem_register(cons
-       nvmem->type = config->type;
-       nvmem->reg_read = config->reg_read;
-       nvmem->reg_write = config->reg_write;
--      nvmem->cell_post_process = config->cell_post_process;
-       nvmem->keepout = config->keepout;
-       nvmem->nkeepout = config->nkeepout;
-       if (config->of_node)
-@@ -1575,13 +1573,6 @@ static int __nvmem_cell_read(struct nvme
-               if (rc)
-                       return rc;
-       }
--
--      if (nvmem->cell_post_process) {
--              rc = nvmem->cell_post_process(nvmem->priv, id, index,
--                                            cell->offset, buf, cell->bytes);
--              if (rc)
--                      return rc;
--      }
-       if (len)
-               *len = cell->bytes;
---- a/include/linux/nvmem-provider.h
-+++ b/include/linux/nvmem-provider.h
-@@ -85,7 +85,6 @@ struct nvmem_cell_info {
-  * @no_of_node:       Device should not use the parent's of_node even if it's !NULL.
-  * @reg_read: Callback to read data.
-  * @reg_write:        Callback to write data.
-- * @cell_post_process:        Callback for vendor specific post processing of cell data
-  * @size:     Device size.
-  * @word_size:        Minimum read/write access granularity.
-  * @stride:   Minimum read/write access stride.
-@@ -118,7 +117,6 @@ struct nvmem_config {
-       bool                    no_of_node;
-       nvmem_reg_read_t        reg_read;
-       nvmem_reg_write_t       reg_write;
--      nvmem_cell_post_process_t cell_post_process;
-       int     size;
-       int     word_size;
-       int     stride;
diff --git a/target/linux/generic/backport-5.15/811-v6.4-0009-nvmem-core-provide-own-priv-pointer-in-post-process-.patch b/target/linux/generic/backport-5.15/811-v6.4-0009-nvmem-core-provide-own-priv-pointer-in-post-process-.patch
deleted file mode 100644 (file)
index 46b30a2..0000000
+++ /dev/null
@@ -1,76 +0,0 @@
-From 8a134fd9f9323f4c39ec27055b3d3723cfb5c1e9 Mon Sep 17 00:00:00 2001
-From: Michael Walle <[email protected]>
-Date: Tue, 4 Apr 2023 18:21:28 +0100
-Subject: [PATCH] nvmem: core: provide own priv pointer in post process
- callback
-
-It doesn't make any more sense to have a opaque pointer set up by the
-nvmem device. Usually, the layout isn't associated with a particular
-nvmem device. Instead, let the caller who set the post process callback
-provide the priv pointer.
-
-Signed-off-by: Michael Walle <[email protected]>
-Signed-off-by: Miquel Raynal <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/core.c           | 4 +++-
- include/linux/nvmem-provider.h | 5 ++++-
- 2 files changed, 7 insertions(+), 2 deletions(-)
-
---- a/drivers/nvmem/core.c
-+++ b/drivers/nvmem/core.c
-@@ -54,6 +54,7 @@ struct nvmem_cell_entry {
-       int                     bit_offset;
-       int                     nbits;
-       nvmem_cell_post_process_t read_post_process;
-+      void                    *priv;
-       struct device_node      *np;
-       struct nvmem_device     *nvmem;
-       struct list_head        node;
-@@ -471,6 +472,7 @@ static int nvmem_cell_info_to_nvmem_cell
-       cell->bytes = info->bytes;
-       cell->name = info->name;
-       cell->read_post_process = info->read_post_process;
-+      cell->priv = info->priv;
-       cell->bit_offset = info->bit_offset;
-       cell->nbits = info->nbits;
-@@ -1568,7 +1570,7 @@ static int __nvmem_cell_read(struct nvme
-               nvmem_shift_read_buffer_in_place(cell, buf);
-       if (cell->read_post_process) {
--              rc = cell->read_post_process(nvmem->priv, id, index,
-+              rc = cell->read_post_process(cell->priv, id, index,
-                                            cell->offset, buf, cell->bytes);
-               if (rc)
-                       return rc;
---- a/include/linux/nvmem-provider.h
-+++ b/include/linux/nvmem-provider.h
-@@ -20,7 +20,8 @@ typedef int (*nvmem_reg_write_t)(void *p
-                                void *val, size_t bytes);
- /* used for vendor specific post processing of cell data */
- typedef int (*nvmem_cell_post_process_t)(void *priv, const char *id, int index,
--                                       unsigned int offset, void *buf, size_t bytes);
-+                                       unsigned int offset, void *buf,
-+                                       size_t bytes);
- enum nvmem_type {
-       NVMEM_TYPE_UNKNOWN = 0,
-@@ -56,6 +57,7 @@ struct nvmem_keepout {
-  * @np:               Optional device_node pointer.
-  * @read_post_process:        Callback for optional post processing of cell data
-  *                    on reads.
-+ * @priv:     Opaque data passed to the read_post_process hook.
-  */
- struct nvmem_cell_info {
-       const char              *name;
-@@ -65,6 +67,7 @@ struct nvmem_cell_info {
-       unsigned int            nbits;
-       struct device_node      *np;
-       nvmem_cell_post_process_t read_post_process;
-+      void                    *priv;
- };
- /**
diff --git a/target/linux/generic/backport-5.15/811-v6.4-0010-nvmem-layouts-sl28vpd-Add-new-layout-driver.patch b/target/linux/generic/backport-5.15/811-v6.4-0010-nvmem-layouts-sl28vpd-Add-new-layout-driver.patch
deleted file mode 100644 (file)
index 7d97658..0000000
+++ /dev/null
@@ -1,215 +0,0 @@
-From d9fae023fe86069750092fc1c2f3a73e2fb18512 Mon Sep 17 00:00:00 2001
-From: Michael Walle <[email protected]>
-Date: Tue, 4 Apr 2023 18:21:29 +0100
-Subject: [PATCH] nvmem: layouts: sl28vpd: Add new layout driver
-
-This layout applies to the VPD of the Kontron sl28 boards. The VPD only
-contains a base MAC address. Therefore, we have to add an individual
-offset to it. This is done by taking the second argument of the nvmem
-phandle into account. Also this let us checking the VPD version and the
-checksum.
-
-Signed-off-by: Michael Walle <[email protected]>
-Signed-off-by: Miquel Raynal <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/layouts/Kconfig   |   9 ++
- drivers/nvmem/layouts/Makefile  |   2 +
- drivers/nvmem/layouts/sl28vpd.c | 165 ++++++++++++++++++++++++++++++++
- 3 files changed, 176 insertions(+)
- create mode 100644 drivers/nvmem/layouts/sl28vpd.c
-
---- a/drivers/nvmem/layouts/Kconfig
-+++ b/drivers/nvmem/layouts/Kconfig
-@@ -2,4 +2,13 @@
- menu "Layout Types"
-+config NVMEM_LAYOUT_SL28_VPD
-+      tristate "Kontron sl28 VPD layout support"
-+      select CRC8
-+      help
-+        Say Y here if you want to support the VPD layout of the Kontron
-+        SMARC-sAL28 boards.
-+
-+        If unsure, say N.
-+
- endmenu
---- a/drivers/nvmem/layouts/Makefile
-+++ b/drivers/nvmem/layouts/Makefile
-@@ -2,3 +2,5 @@
- #
- # Makefile for nvmem layouts.
- #
-+
-+obj-$(CONFIG_NVMEM_LAYOUT_SL28_VPD) += sl28vpd.o
---- /dev/null
-+++ b/drivers/nvmem/layouts/sl28vpd.c
-@@ -0,0 +1,165 @@
-+// SPDX-License-Identifier: GPL-2.0
-+
-+#include <linux/crc8.h>
-+#include <linux/etherdevice.h>
-+#include <linux/nvmem-consumer.h>
-+#include <linux/nvmem-provider.h>
-+#include <linux/of.h>
-+#include <uapi/linux/if_ether.h>
-+
-+#define SL28VPD_MAGIC 'V'
-+
-+struct sl28vpd_header {
-+      u8 magic;
-+      u8 version;
-+} __packed;
-+
-+struct sl28vpd_v1 {
-+      struct sl28vpd_header header;
-+      char serial_number[15];
-+      u8 base_mac_address[ETH_ALEN];
-+      u8 crc8;
-+} __packed;
-+
-+static int sl28vpd_mac_address_pp(void *priv, const char *id, int index,
-+                                unsigned int offset, void *buf,
-+                                size_t bytes)
-+{
-+      if (bytes != ETH_ALEN)
-+              return -EINVAL;
-+
-+      if (index < 0)
-+              return -EINVAL;
-+
-+      if (!is_valid_ether_addr(buf))
-+              return -EINVAL;
-+
-+      eth_addr_add(buf, index);
-+
-+      return 0;
-+}
-+
-+static const struct nvmem_cell_info sl28vpd_v1_entries[] = {
-+      {
-+              .name = "serial-number",
-+              .offset = offsetof(struct sl28vpd_v1, serial_number),
-+              .bytes = sizeof_field(struct sl28vpd_v1, serial_number),
-+      },
-+      {
-+              .name = "base-mac-address",
-+              .offset = offsetof(struct sl28vpd_v1, base_mac_address),
-+              .bytes = sizeof_field(struct sl28vpd_v1, base_mac_address),
-+              .read_post_process = sl28vpd_mac_address_pp,
-+      },
-+};
-+
-+static int sl28vpd_v1_check_crc(struct device *dev, struct nvmem_device *nvmem)
-+{
-+      struct sl28vpd_v1 data_v1;
-+      u8 table[CRC8_TABLE_SIZE];
-+      int ret;
-+      u8 crc;
-+
-+      crc8_populate_msb(table, 0x07);
-+
-+      ret = nvmem_device_read(nvmem, 0, sizeof(data_v1), &data_v1);
-+      if (ret < 0)
-+              return ret;
-+      else if (ret != sizeof(data_v1))
-+              return -EIO;
-+
-+      crc = crc8(table, (void *)&data_v1, sizeof(data_v1) - 1, 0);
-+
-+      if (crc != data_v1.crc8) {
-+              dev_err(dev,
-+                      "Checksum is invalid (got %02x, expected %02x).\n",
-+                      crc, data_v1.crc8);
-+              return -EINVAL;
-+      }
-+
-+      return 0;
-+}
-+
-+static int sl28vpd_add_cells(struct device *dev, struct nvmem_device *nvmem,
-+                           struct nvmem_layout *layout)
-+{
-+      const struct nvmem_cell_info *pinfo;
-+      struct nvmem_cell_info info = {0};
-+      struct device_node *layout_np;
-+      struct sl28vpd_header hdr;
-+      int ret, i;
-+
-+      /* check header */
-+      ret = nvmem_device_read(nvmem, 0, sizeof(hdr), &hdr);
-+      if (ret < 0)
-+              return ret;
-+      else if (ret != sizeof(hdr))
-+              return -EIO;
-+
-+      if (hdr.magic != SL28VPD_MAGIC) {
-+              dev_err(dev, "Invalid magic value (%02x)\n", hdr.magic);
-+              return -EINVAL;
-+      }
-+
-+      if (hdr.version != 1) {
-+              dev_err(dev, "Version %d is unsupported.\n", hdr.version);
-+              return -EINVAL;
-+      }
-+
-+      ret = sl28vpd_v1_check_crc(dev, nvmem);
-+      if (ret)
-+              return ret;
-+
-+      layout_np = of_nvmem_layout_get_container(nvmem);
-+      if (!layout_np)
-+              return -ENOENT;
-+
-+      for (i = 0; i < ARRAY_SIZE(sl28vpd_v1_entries); i++) {
-+              pinfo = &sl28vpd_v1_entries[i];
-+
-+              info.name = pinfo->name;
-+              info.offset = pinfo->offset;
-+              info.bytes = pinfo->bytes;
-+              info.read_post_process = pinfo->read_post_process;
-+              info.np = of_get_child_by_name(layout_np, pinfo->name);
-+
-+              ret = nvmem_add_one_cell(nvmem, &info);
-+              if (ret) {
-+                      of_node_put(layout_np);
-+                      return ret;
-+              }
-+      }
-+
-+      of_node_put(layout_np);
-+
-+      return 0;
-+}
-+
-+static const struct of_device_id sl28vpd_of_match_table[] = {
-+      { .compatible = "kontron,sl28-vpd" },
-+      {},
-+};
-+MODULE_DEVICE_TABLE(of, sl28vpd_of_match_table);
-+
-+struct nvmem_layout sl28vpd_layout = {
-+      .name = "sl28-vpd",
-+      .of_match_table = sl28vpd_of_match_table,
-+      .add_cells = sl28vpd_add_cells,
-+};
-+
-+static int __init sl28vpd_init(void)
-+{
-+      return nvmem_layout_register(&sl28vpd_layout);
-+}
-+
-+static void __exit sl28vpd_exit(void)
-+{
-+      nvmem_layout_unregister(&sl28vpd_layout);
-+}
-+
-+module_init(sl28vpd_init);
-+module_exit(sl28vpd_exit);
-+
-+MODULE_LICENSE("GPL");
-+MODULE_AUTHOR("Michael Walle <[email protected]>");
-+MODULE_DESCRIPTION("NVMEM layout driver for the VPD of Kontron sl28 boards");
diff --git a/target/linux/generic/backport-5.15/811-v6.4-0011-nvmem-layouts-onie-tlv-Add-new-layout-driver.patch b/target/linux/generic/backport-5.15/811-v6.4-0011-nvmem-layouts-onie-tlv-Add-new-layout-driver.patch
deleted file mode 100644 (file)
index ca8b4bc..0000000
+++ /dev/null
@@ -1,306 +0,0 @@
-From d3c0d12f6474216bf386101e2449cc73e5c5b61d Mon Sep 17 00:00:00 2001
-From: Miquel Raynal <[email protected]>
-Date: Tue, 4 Apr 2023 18:21:31 +0100
-Subject: [PATCH] nvmem: layouts: onie-tlv: Add new layout driver
-
-This layout applies on top of any non volatile storage device containing
-an ONIE table factory flashed. This table follows the tlv
-(type-length-value) organization described in the link below. We cannot
-afford using regular parsers because the content of these tables is
-manufacturer specific and must be dynamically discovered.
-
-Link: https://opencomputeproject.github.io/onie/design-spec/hw_requirements.html
-Signed-off-by: Miquel Raynal <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/layouts/Kconfig    |   9 ++
- drivers/nvmem/layouts/Makefile   |   1 +
- drivers/nvmem/layouts/onie-tlv.c | 257 +++++++++++++++++++++++++++++++
- 3 files changed, 267 insertions(+)
- create mode 100644 drivers/nvmem/layouts/onie-tlv.c
-
---- a/drivers/nvmem/layouts/Kconfig
-+++ b/drivers/nvmem/layouts/Kconfig
-@@ -11,4 +11,13 @@ config NVMEM_LAYOUT_SL28_VPD
-         If unsure, say N.
-+config NVMEM_LAYOUT_ONIE_TLV
-+      tristate "ONIE tlv support"
-+      select CRC32
-+      help
-+        Say Y here if you want to support the Open Compute Project ONIE
-+        Type-Length-Value standard table.
-+
-+        If unsure, say N.
-+
- endmenu
---- a/drivers/nvmem/layouts/Makefile
-+++ b/drivers/nvmem/layouts/Makefile
-@@ -4,3 +4,4 @@
- #
- obj-$(CONFIG_NVMEM_LAYOUT_SL28_VPD) += sl28vpd.o
-+obj-$(CONFIG_NVMEM_LAYOUT_ONIE_TLV) += onie-tlv.o
---- /dev/null
-+++ b/drivers/nvmem/layouts/onie-tlv.c
-@@ -0,0 +1,257 @@
-+// SPDX-License-Identifier: GPL-2.0-only
-+/*
-+ * ONIE tlv NVMEM cells provider
-+ *
-+ * Copyright (C) 2022 Open Compute Group ONIE
-+ * Author: Miquel Raynal <[email protected]>
-+ * Based on the nvmem driver written by: Vadym Kochan <[email protected]>
-+ * Inspired by the first layout written by: Rafał Miłecki <[email protected]>
-+ */
-+
-+#include <linux/crc32.h>
-+#include <linux/etherdevice.h>
-+#include <linux/nvmem-consumer.h>
-+#include <linux/nvmem-provider.h>
-+#include <linux/of.h>
-+
-+#define ONIE_TLV_MAX_LEN 2048
-+#define ONIE_TLV_CRC_FIELD_SZ 6
-+#define ONIE_TLV_CRC_SZ 4
-+#define ONIE_TLV_HDR_ID       "TlvInfo"
-+
-+struct onie_tlv_hdr {
-+      u8 id[8];
-+      u8 version;
-+      __be16 data_len;
-+} __packed;
-+
-+struct onie_tlv {
-+      u8 type;
-+      u8 len;
-+} __packed;
-+
-+static const char *onie_tlv_cell_name(u8 type)
-+{
-+      switch (type) {
-+      case 0x21:
-+              return "product-name";
-+      case 0x22:
-+              return "part-number";
-+      case 0x23:
-+              return "serial-number";
-+      case 0x24:
-+              return "mac-address";
-+      case 0x25:
-+              return "manufacture-date";
-+      case 0x26:
-+              return "device-version";
-+      case 0x27:
-+              return "label-revision";
-+      case 0x28:
-+              return "platform-name";
-+      case 0x29:
-+              return "onie-version";
-+      case 0x2A:
-+              return "num-macs";
-+      case 0x2B:
-+              return "manufacturer";
-+      case 0x2C:
-+              return "country-code";
-+      case 0x2D:
-+              return "vendor";
-+      case 0x2E:
-+              return "diag-version";
-+      case 0x2F:
-+              return "service-tag";
-+      case 0xFD:
-+              return "vendor-extension";
-+      case 0xFE:
-+              return "crc32";
-+      default:
-+              break;
-+      }
-+
-+      return NULL;
-+}
-+
-+static int onie_tlv_mac_read_cb(void *priv, const char *id, int index,
-+                              unsigned int offset, void *buf,
-+                              size_t bytes)
-+{
-+      eth_addr_add(buf, index);
-+
-+      return 0;
-+}
-+
-+static nvmem_cell_post_process_t onie_tlv_read_cb(u8 type, u8 *buf)
-+{
-+      switch (type) {
-+      case 0x24:
-+              return &onie_tlv_mac_read_cb;
-+      default:
-+              break;
-+      }
-+
-+      return NULL;
-+}
-+
-+static int onie_tlv_add_cells(struct device *dev, struct nvmem_device *nvmem,
-+                            size_t data_len, u8 *data)
-+{
-+      struct nvmem_cell_info cell = {};
-+      struct device_node *layout;
-+      struct onie_tlv tlv;
-+      unsigned int hdr_len = sizeof(struct onie_tlv_hdr);
-+      unsigned int offset = 0;
-+      int ret;
-+
-+      layout = of_nvmem_layout_get_container(nvmem);
-+      if (!layout)
-+              return -ENOENT;
-+
-+      while (offset < data_len) {
-+              memcpy(&tlv, data + offset, sizeof(tlv));
-+              if (offset + tlv.len >= data_len) {
-+                      dev_err(dev, "Out of bounds field (0x%x bytes at 0x%x)\n",
-+                              tlv.len, hdr_len + offset);
-+                      break;
-+              }
-+
-+              cell.name = onie_tlv_cell_name(tlv.type);
-+              if (!cell.name)
-+                      continue;
-+
-+              cell.offset = hdr_len + offset + sizeof(tlv.type) + sizeof(tlv.len);
-+              cell.bytes = tlv.len;
-+              cell.np = of_get_child_by_name(layout, cell.name);
-+              cell.read_post_process = onie_tlv_read_cb(tlv.type, data + offset + sizeof(tlv));
-+
-+              ret = nvmem_add_one_cell(nvmem, &cell);
-+              if (ret) {
-+                      of_node_put(layout);
-+                      return ret;
-+              }
-+
-+              offset += sizeof(tlv) + tlv.len;
-+      }
-+
-+      of_node_put(layout);
-+
-+      return 0;
-+}
-+
-+static bool onie_tlv_hdr_is_valid(struct device *dev, struct onie_tlv_hdr *hdr)
-+{
-+      if (memcmp(hdr->id, ONIE_TLV_HDR_ID, sizeof(hdr->id))) {
-+              dev_err(dev, "Invalid header\n");
-+              return false;
-+      }
-+
-+      if (hdr->version != 0x1) {
-+              dev_err(dev, "Invalid version number\n");
-+              return false;
-+      }
-+
-+      return true;
-+}
-+
-+static bool onie_tlv_crc_is_valid(struct device *dev, size_t table_len, u8 *table)
-+{
-+      struct onie_tlv crc_hdr;
-+      u32 read_crc, calc_crc;
-+      __be32 crc_be;
-+
-+      memcpy(&crc_hdr, table + table_len - ONIE_TLV_CRC_FIELD_SZ, sizeof(crc_hdr));
-+      if (crc_hdr.type != 0xfe || crc_hdr.len != ONIE_TLV_CRC_SZ) {
-+              dev_err(dev, "Invalid CRC field\n");
-+              return false;
-+      }
-+
-+      /* The table contains a JAMCRC, which is XOR'ed compared to the original
-+       * CRC32 implementation as known in the Ethernet world.
-+       */
-+      memcpy(&crc_be, table + table_len - ONIE_TLV_CRC_SZ, ONIE_TLV_CRC_SZ);
-+      read_crc = be32_to_cpu(crc_be);
-+      calc_crc = crc32(~0, table, table_len - ONIE_TLV_CRC_SZ) ^ 0xFFFFFFFF;
-+      if (read_crc != calc_crc) {
-+              dev_err(dev, "Invalid CRC read: 0x%08x, expected: 0x%08x\n",
-+                      read_crc, calc_crc);
-+              return false;
-+      }
-+
-+      return true;
-+}
-+
-+static int onie_tlv_parse_table(struct device *dev, struct nvmem_device *nvmem,
-+                              struct nvmem_layout *layout)
-+{
-+      struct onie_tlv_hdr hdr;
-+      size_t table_len, data_len, hdr_len;
-+      u8 *table, *data;
-+      int ret;
-+
-+      ret = nvmem_device_read(nvmem, 0, sizeof(hdr), &hdr);
-+      if (ret < 0)
-+              return ret;
-+
-+      if (!onie_tlv_hdr_is_valid(dev, &hdr)) {
-+              dev_err(dev, "Invalid ONIE TLV header\n");
-+              return -EINVAL;
-+      }
-+
-+      hdr_len = sizeof(hdr.id) + sizeof(hdr.version) + sizeof(hdr.data_len);
-+      data_len = be16_to_cpu(hdr.data_len);
-+      table_len = hdr_len + data_len;
-+      if (table_len > ONIE_TLV_MAX_LEN) {
-+              dev_err(dev, "Invalid ONIE TLV data length\n");
-+              return -EINVAL;
-+      }
-+
-+      table = devm_kmalloc(dev, table_len, GFP_KERNEL);
-+      if (!table)
-+              return -ENOMEM;
-+
-+      ret = nvmem_device_read(nvmem, 0, table_len, table);
-+      if (ret != table_len)
-+              return ret;
-+
-+      if (!onie_tlv_crc_is_valid(dev, table_len, table))
-+              return -EINVAL;
-+
-+      data = table + hdr_len;
-+      ret = onie_tlv_add_cells(dev, nvmem, data_len, data);
-+      if (ret)
-+              return ret;
-+
-+      return 0;
-+}
-+
-+static const struct of_device_id onie_tlv_of_match_table[] = {
-+      { .compatible = "onie,tlv-layout", },
-+      {},
-+};
-+MODULE_DEVICE_TABLE(of, onie_tlv_of_match_table);
-+
-+static struct nvmem_layout onie_tlv_layout = {
-+      .name = "ONIE tlv layout",
-+      .of_match_table = onie_tlv_of_match_table,
-+      .add_cells = onie_tlv_parse_table,
-+};
-+
-+static int __init onie_tlv_init(void)
-+{
-+      return nvmem_layout_register(&onie_tlv_layout);
-+}
-+
-+static void __exit onie_tlv_exit(void)
-+{
-+      nvmem_layout_unregister(&onie_tlv_layout);
-+}
-+
-+module_init(onie_tlv_init);
-+module_exit(onie_tlv_exit);
-+
-+MODULE_LICENSE("GPL");
-+MODULE_AUTHOR("Miquel Raynal <[email protected]>");
-+MODULE_DESCRIPTION("NVMEM layout driver for Onie TLV table parsing");
-+MODULE_ALIAS("NVMEM layout driver for Onie TLV table parsing");
diff --git a/target/linux/generic/backport-5.15/811-v6.4-0012-nvmem-stm32-romem-mark-OF-related-data-as-maybe-unus.patch b/target/linux/generic/backport-5.15/811-v6.4-0012-nvmem-stm32-romem-mark-OF-related-data-as-maybe-unus.patch
deleted file mode 100644 (file)
index 94a0911..0000000
+++ /dev/null
@@ -1,32 +0,0 @@
-From a4fb434ef96ace5af758ca2c52c3a3f8f3abc87c Mon Sep 17 00:00:00 2001
-From: Krzysztof Kozlowski <[email protected]>
-Date: Tue, 4 Apr 2023 18:21:34 +0100
-Subject: [PATCH] nvmem: stm32-romem: mark OF related data as maybe unused
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-The driver can be compile tested with !CONFIG_OF making certain data
-unused:
-
-  drivers/nvmem/stm32-romem.c:271:34: error: ‘stm32_romem_of_match’ defined but not used [-Werror=unused-const-variable=]
-
-Signed-off-by: Krzysztof Kozlowski <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/stm32-romem.c | 2 +-
- 1 file changed, 1 insertion(+), 1 deletion(-)
-
---- a/drivers/nvmem/stm32-romem.c
-+++ b/drivers/nvmem/stm32-romem.c
-@@ -268,7 +268,7 @@ static const struct stm32_romem_cfg stm3
-       .ta = true,
- };
--static const struct of_device_id stm32_romem_of_match[] = {
-+static const struct of_device_id stm32_romem_of_match[] __maybe_unused = {
-       { .compatible = "st,stm32f4-otp", }, {
-               .compatible = "st,stm32mp15-bsec",
-               .data = (void *)&stm32mp15_bsec_cfg,
diff --git a/target/linux/generic/backport-5.15/811-v6.4-0013-nvmem-mtk-efuse-Support-postprocessing-for-GPU-speed.patch b/target/linux/generic/backport-5.15/811-v6.4-0013-nvmem-mtk-efuse-Support-postprocessing-for-GPU-speed.patch
deleted file mode 100644 (file)
index abda402..0000000
+++ /dev/null
@@ -1,120 +0,0 @@
-From de6e05097f7db066afb0ad4c88b730949f7b7749 Mon Sep 17 00:00:00 2001
-From: AngeloGioacchino Del Regno <[email protected]>
-Date: Tue, 4 Apr 2023 18:21:35 +0100
-Subject: [PATCH] nvmem: mtk-efuse: Support postprocessing for GPU speed
- binning data
-
-On some MediaTek SoCs GPU speed binning data is available for read
-in the SoC's eFuse array but it has a format that is incompatible
-with what the OPP API expects, as we read a number from 0 to 7 but
-opp-supported-hw is expecting a bitmask to enable an OPP entry:
-being what we read limited to 0-7, it's straightforward to simply
-convert the value to BIT(value) as a post-processing action.
-
-So, introduce post-processing support and enable it by evaluating
-the newly introduced platform data's `uses_post_processing` member,
-currently enabled only for MT8186.
-
-Signed-off-by: AngeloGioacchino Del Regno <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/mtk-efuse.c | 53 +++++++++++++++++++++++++++++++++++++--
- 1 file changed, 51 insertions(+), 2 deletions(-)
-
---- a/drivers/nvmem/mtk-efuse.c
-+++ b/drivers/nvmem/mtk-efuse.c
-@@ -10,6 +10,11 @@
- #include <linux/io.h>
- #include <linux/nvmem-provider.h>
- #include <linux/platform_device.h>
-+#include <linux/property.h>
-+
-+struct mtk_efuse_pdata {
-+      bool uses_post_processing;
-+};
- struct mtk_efuse_priv {
-       void __iomem *base;
-@@ -29,6 +34,37 @@ static int mtk_reg_read(void *context,
-       return 0;
- }
-+static int mtk_efuse_gpu_speedbin_pp(void *context, const char *id, int index,
-+                                   unsigned int offset, void *data, size_t bytes)
-+{
-+      u8 *val = data;
-+
-+      if (val[0] < 8)
-+              val[0] = BIT(val[0]);
-+
-+      return 0;
-+}
-+
-+static void mtk_efuse_fixup_cell_info(struct nvmem_device *nvmem,
-+                                    struct nvmem_layout *layout,
-+                                    struct nvmem_cell_info *cell)
-+{
-+      size_t sz = strlen(cell->name);
-+
-+      /*
-+       * On some SoCs, the GPU speedbin is not read as bitmask but as
-+       * a number with range [0-7] (max 3 bits): post process to use
-+       * it in OPP tables to describe supported-hw.
-+       */
-+      if (cell->nbits <= 3 &&
-+          strncmp(cell->name, "gpu-speedbin", min(sz, strlen("gpu-speedbin"))) == 0)
-+              cell->read_post_process = mtk_efuse_gpu_speedbin_pp;
-+}
-+
-+static struct nvmem_layout mtk_efuse_layout = {
-+      .fixup_cell_info = mtk_efuse_fixup_cell_info,
-+};
-+
- static int mtk_efuse_probe(struct platform_device *pdev)
- {
-       struct device *dev = &pdev->dev;
-@@ -36,6 +72,7 @@ static int mtk_efuse_probe(struct platfo
-       struct nvmem_device *nvmem;
-       struct nvmem_config econfig = {};
-       struct mtk_efuse_priv *priv;
-+      const struct mtk_efuse_pdata *pdata;
-       priv = devm_kzalloc(dev, sizeof(*priv), GFP_KERNEL);
-       if (!priv)
-@@ -45,20 +82,32 @@ static int mtk_efuse_probe(struct platfo
-       if (IS_ERR(priv->base))
-               return PTR_ERR(priv->base);
-+      pdata = device_get_match_data(dev);
-       econfig.stride = 1;
-       econfig.word_size = 1;
-       econfig.reg_read = mtk_reg_read;
-       econfig.size = resource_size(res);
-       econfig.priv = priv;
-       econfig.dev = dev;
-+      if (pdata->uses_post_processing)
-+              econfig.layout = &mtk_efuse_layout;
-       nvmem = devm_nvmem_register(dev, &econfig);
-       return PTR_ERR_OR_ZERO(nvmem);
- }
-+static const struct mtk_efuse_pdata mtk_mt8186_efuse_pdata = {
-+      .uses_post_processing = true,
-+};
-+
-+static const struct mtk_efuse_pdata mtk_efuse_pdata = {
-+      .uses_post_processing = false,
-+};
-+
- static const struct of_device_id mtk_efuse_of_match[] = {
--      { .compatible = "mediatek,mt8173-efuse",},
--      { .compatible = "mediatek,efuse",},
-+      { .compatible = "mediatek,mt8173-efuse", .data = &mtk_efuse_pdata },
-+      { .compatible = "mediatek,mt8186-efuse", .data = &mtk_mt8186_efuse_pdata },
-+      { .compatible = "mediatek,efuse", .data = &mtk_efuse_pdata },
-       {/* sentinel */},
- };
- MODULE_DEVICE_TABLE(of, mtk_efuse_of_match);
diff --git a/target/linux/generic/backport-5.15/811-v6.4-0014-nvmem-bcm-ocotp-Use-devm_platform_ioremap_resource.patch b/target/linux/generic/backport-5.15/811-v6.4-0014-nvmem-bcm-ocotp-Use-devm_platform_ioremap_resource.patch
deleted file mode 100644 (file)
index a0874f7..0000000
+++ /dev/null
@@ -1,39 +0,0 @@
-From 1dc552fa33cf98af3e784dbc0500da93cae3b24a Mon Sep 17 00:00:00 2001
-From: Yang Li <[email protected]>
-Date: Tue, 4 Apr 2023 18:21:38 +0100
-Subject: [PATCH] nvmem: bcm-ocotp: Use devm_platform_ioremap_resource()
-
-According to commit 7945f929f1a7 ("drivers: provide
-devm_platform_ioremap_resource()"), convert platform_get_resource(),
-devm_ioremap_resource() to a single call to use
-devm_platform_ioremap_resource(), as this is exactly what this function
-does.
-
-Signed-off-by: Yang Li <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/bcm-ocotp.c | 4 +---
- 1 file changed, 1 insertion(+), 3 deletions(-)
-
---- a/drivers/nvmem/bcm-ocotp.c
-+++ b/drivers/nvmem/bcm-ocotp.c
-@@ -254,7 +254,6 @@ MODULE_DEVICE_TABLE(acpi, bcm_otpc_acpi_
- static int bcm_otpc_probe(struct platform_device *pdev)
- {
-       struct device *dev = &pdev->dev;
--      struct resource *res;
-       struct otpc_priv *priv;
-       struct nvmem_device *nvmem;
-       int err;
-@@ -269,8 +268,7 @@ static int bcm_otpc_probe(struct platfor
-               return -ENODEV;
-       /* Get OTP base address register. */
--      res = platform_get_resource(pdev, IORESOURCE_MEM, 0);
--      priv->base = devm_ioremap_resource(dev, res);
-+      priv->base = devm_platform_ioremap_resource(pdev, 0);
-       if (IS_ERR(priv->base)) {
-               dev_err(dev, "unable to map I/O memory\n");
-               return PTR_ERR(priv->base);
diff --git a/target/linux/generic/backport-5.15/811-v6.4-0015-nvmem-nintendo-otp-Use-devm_platform_ioremap_resourc.patch b/target/linux/generic/backport-5.15/811-v6.4-0015-nvmem-nintendo-otp-Use-devm_platform_ioremap_resourc.patch
deleted file mode 100644 (file)
index 890dacd..0000000
+++ /dev/null
@@ -1,39 +0,0 @@
-From 649409990d2e93fac657be7c6960c28a2c601d65 Mon Sep 17 00:00:00 2001
-From: Yang Li <[email protected]>
-Date: Tue, 4 Apr 2023 18:21:39 +0100
-Subject: [PATCH] nvmem: nintendo-otp: Use devm_platform_ioremap_resource()
-
-According to commit 7945f929f1a7 ("drivers: provide
-devm_platform_ioremap_resource()"), convert platform_get_resource(),
-devm_ioremap_resource() to a single call to use
-devm_platform_ioremap_resource(), as this is exactly what this function
-does.
-
-Signed-off-by: Yang Li <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/nintendo-otp.c | 4 +---
- 1 file changed, 1 insertion(+), 3 deletions(-)
-
---- a/drivers/nvmem/nintendo-otp.c
-+++ b/drivers/nvmem/nintendo-otp.c
-@@ -76,7 +76,6 @@ static int nintendo_otp_probe(struct pla
-       struct device *dev = &pdev->dev;
-       const struct of_device_id *of_id =
-               of_match_device(nintendo_otp_of_table, dev);
--      struct resource *res;
-       struct nvmem_device *nvmem;
-       struct nintendo_otp_priv *priv;
-@@ -92,8 +91,7 @@ static int nintendo_otp_probe(struct pla
-       if (!priv)
-               return -ENOMEM;
--      res = platform_get_resource(pdev, IORESOURCE_MEM, 0);
--      priv->regs = devm_ioremap_resource(dev, res);
-+      priv->regs = devm_platform_ioremap_resource(pdev, 0);
-       if (IS_ERR(priv->regs))
-               return PTR_ERR(priv->regs);
diff --git a/target/linux/generic/backport-5.15/811-v6.4-0016-nvmem-vf610-ocotp-Use-devm_platform_get_and_ioremap_.patch b/target/linux/generic/backport-5.15/811-v6.4-0016-nvmem-vf610-ocotp-Use-devm_platform_get_and_ioremap_.patch
deleted file mode 100644 (file)
index 3f5d3c1..0000000
+++ /dev/null
@@ -1,32 +0,0 @@
-From c2367aa60d5e34d48582362c6de34b4131d92be7 Mon Sep 17 00:00:00 2001
-From: Yang Li <[email protected]>
-Date: Tue, 4 Apr 2023 18:21:40 +0100
-Subject: [PATCH] nvmem: vf610-ocotp: Use
- devm_platform_get_and_ioremap_resource()
-
-According to commit 890cc39a8799 ("drivers: provide
-devm_platform_get_and_ioremap_resource()"), convert
-platform_get_resource(), devm_ioremap_resource() to a single
-call to devm_platform_get_and_ioremap_resource(), as this is exactly
-what this function does.
-
-Signed-off-by: Yang Li <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/vf610-ocotp.c | 3 +--
- 1 file changed, 1 insertion(+), 2 deletions(-)
-
---- a/drivers/nvmem/vf610-ocotp.c
-+++ b/drivers/nvmem/vf610-ocotp.c
-@@ -219,8 +219,7 @@ static int vf610_ocotp_probe(struct plat
-       if (!ocotp_dev)
-               return -ENOMEM;
--      res = platform_get_resource(pdev, IORESOURCE_MEM, 0);
--      ocotp_dev->base = devm_ioremap_resource(dev, res);
-+      ocotp_dev->base = devm_platform_get_and_ioremap_resource(pdev, 0, &res);
-       if (IS_ERR(ocotp_dev->base))
-               return PTR_ERR(ocotp_dev->base);
diff --git a/target/linux/generic/backport-5.15/811-v6.4-0017-nvmem-core-support-specifying-both-cell-raw-data-pos.patch b/target/linux/generic/backport-5.15/811-v6.4-0017-nvmem-core-support-specifying-both-cell-raw-data-pos.patch
deleted file mode 100644 (file)
index eeb407e..0000000
+++ /dev/null
@@ -1,115 +0,0 @@
-From 55d4980ce55b6bb4be66877de4dbec513911b988 Mon Sep 17 00:00:00 2001
-From: =?UTF-8?q?Rafa=C5=82=20Mi=C5=82ecki?= <[email protected]>
-Date: Tue, 4 Apr 2023 18:21:42 +0100
-Subject: [PATCH] nvmem: core: support specifying both: cell raw data & post
- read lengths
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-Callback .read_post_process() is designed to modify raw cell content
-before providing it to the consumer. So far we were dealing with
-modifications that didn't affect cell size (length). In some cases
-however cell content needs to be reformatted and resized.
-
-It's required e.g. to provide properly formatted MAC address in case
-it's stored in a non-binary format (e.g. using ASCII).
-
-There were few discussions how to optimally handle that. Following
-possible solutions were considered:
-1. Allow .read_post_process() to realloc (resize) content buffer
-2. Allow .read_post_process() to adjust (decrease) just buffer length
-3. Register NVMEM cells using post-read sizes
-
-The preferred solution was the last one. The problem is that simply
-adjusting "bytes" in NVMEM providers would result in core code NOT
-passing whole raw data to .read_post_process() callbacks. It means
-callback functions couldn't do their job without somehow manually
-reading original cell content on their own.
-
-This patch deals with that by registering NVMEM cells with both lengths:
-raw content one and post read one. It allows:
-1. Core code to read whole raw cell content
-2. Callbacks to return content they want
-
-Signed-off-by: Rafał Miłecki <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/core.c           | 11 +++++++----
- include/linux/nvmem-provider.h |  2 ++
- 2 files changed, 9 insertions(+), 4 deletions(-)
-
---- a/drivers/nvmem/core.c
-+++ b/drivers/nvmem/core.c
-@@ -50,6 +50,7 @@ struct nvmem_device {
- struct nvmem_cell_entry {
-       const char              *name;
-       int                     offset;
-+      size_t                  raw_len;
-       int                     bytes;
-       int                     bit_offset;
-       int                     nbits;
-@@ -469,6 +470,7 @@ static int nvmem_cell_info_to_nvmem_cell
- {
-       cell->nvmem = nvmem;
-       cell->offset = info->offset;
-+      cell->raw_len = info->raw_len ?: info->bytes;
-       cell->bytes = info->bytes;
-       cell->name = info->name;
-       cell->read_post_process = info->read_post_process;
-@@ -1560,7 +1562,7 @@ static int __nvmem_cell_read(struct nvme
- {
-       int rc;
--      rc = nvmem_reg_read(nvmem, cell->offset, buf, cell->bytes);
-+      rc = nvmem_reg_read(nvmem, cell->offset, buf, cell->raw_len);
-       if (rc)
-               return rc;
-@@ -1571,7 +1573,7 @@ static int __nvmem_cell_read(struct nvme
-       if (cell->read_post_process) {
-               rc = cell->read_post_process(cell->priv, id, index,
--                                           cell->offset, buf, cell->bytes);
-+                                           cell->offset, buf, cell->raw_len);
-               if (rc)
-                       return rc;
-       }
-@@ -1594,14 +1596,15 @@ static int __nvmem_cell_read(struct nvme
-  */
- void *nvmem_cell_read(struct nvmem_cell *cell, size_t *len)
- {
--      struct nvmem_device *nvmem = cell->entry->nvmem;
-+      struct nvmem_cell_entry *entry = cell->entry;
-+      struct nvmem_device *nvmem = entry->nvmem;
-       u8 *buf;
-       int rc;
-       if (!nvmem)
-               return ERR_PTR(-EINVAL);
--      buf = kzalloc(cell->entry->bytes, GFP_KERNEL);
-+      buf = kzalloc(max_t(size_t, entry->raw_len, entry->bytes), GFP_KERNEL);
-       if (!buf)
-               return ERR_PTR(-ENOMEM);
---- a/include/linux/nvmem-provider.h
-+++ b/include/linux/nvmem-provider.h
-@@ -51,6 +51,7 @@ struct nvmem_keepout {
-  * struct nvmem_cell_info - NVMEM cell description
-  * @name:     Name.
-  * @offset:   Offset within the NVMEM device.
-+ * @raw_len:  Length of raw data (without post processing).
-  * @bytes:    Length of the cell.
-  * @bit_offset:       Bit offset if cell is smaller than a byte.
-  * @nbits:    Number of bits.
-@@ -62,6 +63,7 @@ struct nvmem_keepout {
- struct nvmem_cell_info {
-       const char              *name;
-       unsigned int            offset;
-+      size_t                  raw_len;
-       unsigned int            bytes;
-       unsigned int            bit_offset;
-       unsigned int            nbits;
diff --git a/target/linux/generic/backport-5.15/811-v6.4-0018-nvmem-u-boot-env-post-process-ethaddr-env-variable.patch b/target/linux/generic/backport-5.15/811-v6.4-0018-nvmem-u-boot-env-post-process-ethaddr-env-variable.patch
deleted file mode 100644 (file)
index adde0ff..0000000
+++ /dev/null
@@ -1,81 +0,0 @@
-From c49f1a8af6bcf6d18576bca898f8083ca4b129e1 Mon Sep 17 00:00:00 2001
-From: =?UTF-8?q?Rafa=C5=82=20Mi=C5=82ecki?= <[email protected]>
-Date: Tue, 4 Apr 2023 18:21:43 +0100
-Subject: [PATCH] nvmem: u-boot-env: post-process "ethaddr" env variable
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-U-Boot environment variables are stored in ASCII format so "ethaddr"
-requires parsing into binary to make it work with Ethernet interfaces.
-
-This includes support for indexes to support #nvmem-cell-cells = <1>.
-
-Signed-off-by: Rafał Miłecki <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/Kconfig      |  1 +
- drivers/nvmem/u-boot-env.c | 26 ++++++++++++++++++++++++++
- 2 files changed, 27 insertions(+)
-
---- a/drivers/nvmem/Kconfig
-+++ b/drivers/nvmem/Kconfig
-@@ -340,6 +340,7 @@ config NVMEM_U_BOOT_ENV
-       tristate "U-Boot environment variables support"
-       depends on OF && MTD
-       select CRC32
-+      select GENERIC_NET_UTILS
-       help
-         U-Boot stores its setup as environment variables. This driver adds
-         support for verifying & exporting such data. It also exposes variables
---- a/drivers/nvmem/u-boot-env.c
-+++ b/drivers/nvmem/u-boot-env.c
-@@ -4,6 +4,8 @@
-  */
- #include <linux/crc32.h>
-+#include <linux/etherdevice.h>
-+#include <linux/if_ether.h>
- #include <linux/mod_devicetable.h>
- #include <linux/module.h>
- #include <linux/mtd/mtd.h>
-@@ -70,6 +72,25 @@ static int u_boot_env_read(void *context
-       return 0;
- }
-+static int u_boot_env_read_post_process_ethaddr(void *context, const char *id, int index,
-+                                              unsigned int offset, void *buf, size_t bytes)
-+{
-+      u8 mac[ETH_ALEN];
-+
-+      if (bytes != 3 * ETH_ALEN - 1)
-+              return -EINVAL;
-+
-+      if (!mac_pton(buf, mac))
-+              return -EINVAL;
-+
-+      if (index)
-+              eth_addr_add(mac, index);
-+
-+      ether_addr_copy(buf, mac);
-+
-+      return 0;
-+}
-+
- static int u_boot_env_add_cells(struct u_boot_env *priv, uint8_t *buf,
-                               size_t data_offset, size_t data_len)
- {
-@@ -101,6 +122,11 @@ static int u_boot_env_add_cells(struct u
-               priv->cells[idx].offset = data_offset + value - data;
-               priv->cells[idx].bytes = strlen(value);
-               priv->cells[idx].np = of_get_child_by_name(dev->of_node, priv->cells[idx].name);
-+              if (!strcmp(var, "ethaddr")) {
-+                      priv->cells[idx].raw_len = strlen(value);
-+                      priv->cells[idx].bytes = ETH_ALEN;
-+                      priv->cells[idx].read_post_process = u_boot_env_read_post_process_ethaddr;
-+              }
-       }
-       if (WARN_ON(idx != priv->ncells))
diff --git a/target/linux/generic/backport-5.15/811-v6.4-0019-nvmem-Add-macro-to-register-nvmem-layout-drivers.patch b/target/linux/generic/backport-5.15/811-v6.4-0019-nvmem-Add-macro-to-register-nvmem-layout-drivers.patch
deleted file mode 100644 (file)
index 7c6fe22..0000000
+++ /dev/null
@@ -1,42 +0,0 @@
-From 814c978f02db17f16e6aa2efa2a929372f06da09 Mon Sep 17 00:00:00 2001
-From: Miquel Raynal <[email protected]>
-Date: Tue, 4 Apr 2023 18:21:44 +0100
-Subject: [PATCH] nvmem: Add macro to register nvmem layout drivers
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-Provide a module_nvmem_layout_driver() macro at the end of the
-nvmem-provider.h header to reduce the boilerplate when registering nvmem
-layout drivers.
-
-Suggested-by: Srinivas Kandagatla <[email protected]>
-Signed-off-by: Miquel Raynal <[email protected]>
-Acked-by: Rafał Miłecki <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- include/linux/nvmem-provider.h | 6 ++++++
- 1 file changed, 6 insertions(+)
-
---- a/include/linux/nvmem-provider.h
-+++ b/include/linux/nvmem-provider.h
-@@ -9,6 +9,7 @@
- #ifndef _LINUX_NVMEM_PROVIDER_H
- #define _LINUX_NVMEM_PROVIDER_H
-+#include <linux/device/driver.h>
- #include <linux/err.h>
- #include <linux/errno.h>
- #include <linux/gpio/consumer.h>
-@@ -242,4 +243,9 @@ nvmem_layout_get_match_data(struct nvmem
- }
- #endif /* CONFIG_NVMEM */
-+
-+#define module_nvmem_layout_driver(__layout_driver)           \
-+      module_driver(__layout_driver, nvmem_layout_register,   \
-+                    nvmem_layout_unregister)
-+
- #endif  /* ifndef _LINUX_NVMEM_PROVIDER_H */
diff --git a/target/linux/generic/backport-5.15/811-v6.4-0020-nvmem-layouts-sl28vpd-Use-module_nvmem_layout_driver.patch b/target/linux/generic/backport-5.15/811-v6.4-0020-nvmem-layouts-sl28vpd-Use-module_nvmem_layout_driver.patch
deleted file mode 100644 (file)
index 06646dd..0000000
+++ /dev/null
@@ -1,39 +0,0 @@
-From 0abdf99fe0c86252ba274703425f8d543d7e7f0d Mon Sep 17 00:00:00 2001
-From: Miquel Raynal <[email protected]>
-Date: Tue, 4 Apr 2023 18:21:45 +0100
-Subject: [PATCH] nvmem: layouts: sl28vpd: Use module_nvmem_layout_driver()
-
-Stop open-coding the module init/exit functions. Use the
-module_nvmem_layout_driver() instead.
-
-Signed-off-by: Miquel Raynal <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/layouts/sl28vpd.c | 14 +-------------
- 1 file changed, 1 insertion(+), 13 deletions(-)
-
---- a/drivers/nvmem/layouts/sl28vpd.c
-+++ b/drivers/nvmem/layouts/sl28vpd.c
-@@ -146,19 +146,7 @@ struct nvmem_layout sl28vpd_layout = {
-       .of_match_table = sl28vpd_of_match_table,
-       .add_cells = sl28vpd_add_cells,
- };
--
--static int __init sl28vpd_init(void)
--{
--      return nvmem_layout_register(&sl28vpd_layout);
--}
--
--static void __exit sl28vpd_exit(void)
--{
--      nvmem_layout_unregister(&sl28vpd_layout);
--}
--
--module_init(sl28vpd_init);
--module_exit(sl28vpd_exit);
-+module_nvmem_layout_driver(sl28vpd_layout);
- MODULE_LICENSE("GPL");
- MODULE_AUTHOR("Michael Walle <[email protected]>");
diff --git a/target/linux/generic/backport-5.15/811-v6.4-0021-nvmem-layouts-onie-tlv-Use-module_nvmem_layout_drive.patch b/target/linux/generic/backport-5.15/811-v6.4-0021-nvmem-layouts-onie-tlv-Use-module_nvmem_layout_drive.patch
deleted file mode 100644 (file)
index 826f437..0000000
+++ /dev/null
@@ -1,39 +0,0 @@
-From d119eb38faab61125aaa4f63c74eef61585cf34c Mon Sep 17 00:00:00 2001
-From: Miquel Raynal <[email protected]>
-Date: Tue, 4 Apr 2023 18:21:46 +0100
-Subject: [PATCH] nvmem: layouts: onie-tlv: Use module_nvmem_layout_driver()
-
-Stop open-coding the module init/exit functions. Use the
-module_nvmem_layout_driver() instead.
-
-Signed-off-by: Miquel Raynal <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/layouts/onie-tlv.c | 14 +-------------
- 1 file changed, 1 insertion(+), 13 deletions(-)
-
---- a/drivers/nvmem/layouts/onie-tlv.c
-+++ b/drivers/nvmem/layouts/onie-tlv.c
-@@ -237,19 +237,7 @@ static struct nvmem_layout onie_tlv_layo
-       .of_match_table = onie_tlv_of_match_table,
-       .add_cells = onie_tlv_parse_table,
- };
--
--static int __init onie_tlv_init(void)
--{
--      return nvmem_layout_register(&onie_tlv_layout);
--}
--
--static void __exit onie_tlv_exit(void)
--{
--      nvmem_layout_unregister(&onie_tlv_layout);
--}
--
--module_init(onie_tlv_init);
--module_exit(onie_tlv_exit);
-+module_nvmem_layout_driver(onie_tlv_layout);
- MODULE_LICENSE("GPL");
- MODULE_AUTHOR("Miquel Raynal <[email protected]>");
diff --git a/target/linux/generic/backport-5.15/811-v6.4-0022-nvmem-layouts-onie-tlv-Drop-wrong-module-alias.patch b/target/linux/generic/backport-5.15/811-v6.4-0022-nvmem-layouts-onie-tlv-Drop-wrong-module-alias.patch
deleted file mode 100644 (file)
index f20db85..0000000
+++ /dev/null
@@ -1,24 +0,0 @@
-From 6b13e4b6a9a45028ac730e550380077df1845912 Mon Sep 17 00:00:00 2001
-From: Miquel Raynal <[email protected]>
-Date: Tue, 4 Apr 2023 18:21:47 +0100
-Subject: [PATCH] nvmem: layouts: onie-tlv: Drop wrong module alias
-
-The MODULE_ALIAS macro is misused here as it carries the
-description. There is currently no relevant alias to provide so let's
-just drop it.
-
-Signed-off-by: Miquel Raynal <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/layouts/onie-tlv.c | 1 -
- 1 file changed, 1 deletion(-)
-
---- a/drivers/nvmem/layouts/onie-tlv.c
-+++ b/drivers/nvmem/layouts/onie-tlv.c
-@@ -242,4 +242,3 @@ module_nvmem_layout_driver(onie_tlv_layo
- MODULE_LICENSE("GPL");
- MODULE_AUTHOR("Miquel Raynal <[email protected]>");
- MODULE_DESCRIPTION("NVMEM layout driver for Onie TLV table parsing");
--MODULE_ALIAS("NVMEM layout driver for Onie TLV table parsing");
diff --git a/target/linux/generic/backport-5.15/811-v6.4-0023-nvmem-layouts-sl28vpd-set-varaiable-sl28vpd_layout-s.patch b/target/linux/generic/backport-5.15/811-v6.4-0023-nvmem-layouts-sl28vpd-set-varaiable-sl28vpd_layout-s.patch
deleted file mode 100644 (file)
index 5cf847b..0000000
+++ /dev/null
@@ -1,31 +0,0 @@
-From a8642cd11635a35a5f1dc31857887900d6610778 Mon Sep 17 00:00:00 2001
-From: Tom Rix <[email protected]>
-Date: Tue, 4 Apr 2023 18:21:48 +0100
-Subject: [PATCH] nvmem: layouts: sl28vpd: set varaiable sl28vpd_layout
- storage-class-specifier to static
-
-smatch reports
-drivers/nvmem/layouts/sl28vpd.c:144:21: warning: symbol
-  'sl28vpd_layout' was not declared. Should it be static?
-
-This variable is only used in one file so it should be static.
-
-Signed-off-by: Tom Rix <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/layouts/sl28vpd.c | 2 +-
- 1 file changed, 1 insertion(+), 1 deletion(-)
-
---- a/drivers/nvmem/layouts/sl28vpd.c
-+++ b/drivers/nvmem/layouts/sl28vpd.c
-@@ -141,7 +141,7 @@ static const struct of_device_id sl28vpd
- };
- MODULE_DEVICE_TABLE(of, sl28vpd_of_match_table);
--struct nvmem_layout sl28vpd_layout = {
-+static struct nvmem_layout sl28vpd_layout = {
-       .name = "sl28-vpd",
-       .of_match_table = sl28vpd_of_match_table,
-       .add_cells = sl28vpd_add_cells,
diff --git a/target/linux/generic/backport-5.15/812-v6.2-firmware-nvram-bcm47xx-support-init-from-IO-memory.patch b/target/linux/generic/backport-5.15/812-v6.2-firmware-nvram-bcm47xx-support-init-from-IO-memory.patch
deleted file mode 100644 (file)
index 13ee2d4..0000000
+++ /dev/null
@@ -1,100 +0,0 @@
-From a5be5ce0e25439fae3cd42e3d775979547926812 Mon Sep 17 00:00:00 2001
-From: =?UTF-8?q?Rafa=C5=82=20Mi=C5=82ecki?= <[email protected]>
-Date: Thu, 3 Nov 2022 09:25:29 +0100
-Subject: [PATCH] firmware/nvram: bcm47xx: support init from IO memory
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-Provide NVMEM content to the NVRAM driver from a simple
-memory resource. This is necessary to use NVRAM in a memory-
-mapped flash device. Patch taken from OpenWrts development
-tree.
-
-This patch makes it possible to use memory-mapped NVRAM
-on the D-Link DWL-8610AP and the D-Link DIR-890L.
-
-Cc: Hauke Mehrtens <[email protected]>
-Cc: Florian Fainelli <[email protected]>
-Cc: Thomas Bogendoerfer <[email protected]>
-Signed-off-by: Rafał Miłecki <[email protected]>
-[Added an export for modules potentially using the init symbol]
-Signed-off-by: Linus Walleij <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Florian Fainelli <[email protected]>
----
- drivers/firmware/broadcom/bcm47xx_nvram.c | 18 ++++++++++++++++++
- drivers/nvmem/brcm_nvram.c                |  3 +++
- include/linux/bcm47xx_nvram.h             |  6 ++++++
- 3 files changed, 27 insertions(+)
-
---- a/drivers/firmware/broadcom/bcm47xx_nvram.c
-+++ b/drivers/firmware/broadcom/bcm47xx_nvram.c
-@@ -110,6 +110,24 @@ found:
-       return 0;
- }
-+int bcm47xx_nvram_init_from_iomem(void __iomem *nvram_start, size_t res_size)
-+{
-+      if (nvram_len) {
-+              pr_warn("nvram already initialized\n");
-+              return -EEXIST;
-+      }
-+
-+      if (!bcm47xx_nvram_is_valid(nvram_start)) {
-+              pr_err("No valid NVRAM found\n");
-+              return -ENOENT;
-+      }
-+
-+      bcm47xx_nvram_copy(nvram_start, res_size);
-+
-+      return 0;
-+}
-+EXPORT_SYMBOL_GPL(bcm47xx_nvram_init_from_iomem);
-+
- /*
-  * On bcm47xx we need access to the NVRAM very early, so we can't use mtd
-  * subsystem to access flash. We can't even use platform device / driver to
---- a/drivers/nvmem/brcm_nvram.c
-+++ b/drivers/nvmem/brcm_nvram.c
-@@ -3,6 +3,7 @@
-  * Copyright (C) 2021 Rafał Miłecki <[email protected]>
-  */
-+#include <linux/bcm47xx_nvram.h>
- #include <linux/io.h>
- #include <linux/mod_devicetable.h>
- #include <linux/module.h>
-@@ -139,6 +140,8 @@ static int brcm_nvram_probe(struct platf
-       if (err)
-               return err;
-+      bcm47xx_nvram_init_from_iomem(priv->base, resource_size(res));
-+
-       config.dev = dev;
-       config.cells = priv->cells;
-       config.ncells = priv->ncells;
---- a/include/linux/bcm47xx_nvram.h
-+++ b/include/linux/bcm47xx_nvram.h
-@@ -11,6 +11,7 @@
- #include <linux/vmalloc.h>
- #ifdef CONFIG_BCM47XX_NVRAM
-+int bcm47xx_nvram_init_from_iomem(void __iomem *nvram_start, size_t res_size);
- int bcm47xx_nvram_init_from_mem(u32 base, u32 lim);
- int bcm47xx_nvram_getenv(const char *name, char *val, size_t val_len);
- int bcm47xx_nvram_gpio_pin(const char *name);
-@@ -20,6 +21,11 @@ static inline void bcm47xx_nvram_release
-       vfree(nvram);
- };
- #else
-+static inline int bcm47xx_nvram_init_from_iomem(void __iomem *nvram_start,
-+                                              size_t res_size)
-+{
-+      return -ENOTSUPP;
-+}
- static inline int bcm47xx_nvram_init_from_mem(u32 base, u32 lim)
- {
-       return -ENOTSUPP;
diff --git a/target/linux/generic/backport-5.15/813-v6.5-0001-nvmem-imx-ocotp-set-varaiable-imx_ocotp_layout-stora.patch b/target/linux/generic/backport-5.15/813-v6.5-0001-nvmem-imx-ocotp-set-varaiable-imx_ocotp_layout-stora.patch
deleted file mode 100644 (file)
index 38cfccd..0000000
+++ /dev/null
@@ -1,31 +0,0 @@
-From eebc6573ad940b62a87776db3917e912b4f52d78 Mon Sep 17 00:00:00 2001
-From: Tom Rix <[email protected]>
-Date: Sun, 11 Jun 2023 15:03:05 +0100
-Subject: [PATCH] nvmem: imx-ocotp: set varaiable imx_ocotp_layout
- storage-class-specifier to static
-
-smatch reports
-drivers/nvmem/imx-ocotp.c:599:21: warning: symbol
-  'imx_ocotp_layout' was not declared. Should it be static?
-
-This variable is only used in one file so should be static.
-
-Signed-off-by: Tom Rix <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Message-ID: <[email protected]>
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/imx-ocotp.c | 2 +-
- 1 file changed, 1 insertion(+), 1 deletion(-)
-
---- a/drivers/nvmem/imx-ocotp.c
-+++ b/drivers/nvmem/imx-ocotp.c
-@@ -596,7 +596,7 @@ static void imx_ocotp_fixup_cell_info(st
-       cell->read_post_process = imx_ocotp_cell_pp;
- }
--struct nvmem_layout imx_ocotp_layout = {
-+static struct nvmem_layout imx_ocotp_layout = {
-       .fixup_cell_info = imx_ocotp_fixup_cell_info,
- };
diff --git a/target/linux/generic/backport-5.15/813-v6.5-0002-nvmem-imx-ocotp-Reverse-MAC-addresses-on-all-i.MX-de.patch b/target/linux/generic/backport-5.15/813-v6.5-0002-nvmem-imx-ocotp-Reverse-MAC-addresses-on-all-i.MX-de.patch
deleted file mode 100644 (file)
index 7523e5e..0000000
+++ /dev/null
@@ -1,71 +0,0 @@
-From 8a00fc606312c68b98add8fe8e6f7a013ce29e78 Mon Sep 17 00:00:00 2001
-From: Alexander Stein <[email protected]>
-Date: Sun, 11 Jun 2023 15:03:06 +0100
-Subject: [PATCH] nvmem: imx-ocotp: Reverse MAC addresses on all i.MX derivates
-
-Not just i.MX8M, but all i.MX6/7 (and subtypes) need to reverse the
-MAC address read from fuses. Exceptions are i.MX6SLL and i.MX7ULP which
-do not support ethernet at all.
-
-Fixes: d0221a780cbc ("nvmem: imx-ocotp: add support for post processing")
-Signed-off-by: Alexander Stein <[email protected]>
-Tested-by: Richard Leitner <[email protected]> # imx6q
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Message-ID: <[email protected]>
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/imx-ocotp.c | 8 +-------
- 1 file changed, 1 insertion(+), 7 deletions(-)
-
---- a/drivers/nvmem/imx-ocotp.c
-+++ b/drivers/nvmem/imx-ocotp.c
-@@ -97,7 +97,6 @@ struct ocotp_params {
-       unsigned int bank_address_words;
-       void (*set_timing)(struct ocotp_priv *priv);
-       struct ocotp_ctrl_reg ctrl;
--      bool reverse_mac_address;
- };
- static int imx_ocotp_wait_for_busy(struct ocotp_priv *priv, u32 flags)
-@@ -545,7 +544,6 @@ static const struct ocotp_params imx8mq_
-       .bank_address_words = 0,
-       .set_timing = imx_ocotp_set_imx6_timing,
-       .ctrl = IMX_OCOTP_BM_CTRL_DEFAULT,
--      .reverse_mac_address = true,
- };
- static const struct ocotp_params imx8mm_params = {
-@@ -553,7 +551,6 @@ static const struct ocotp_params imx8mm_
-       .bank_address_words = 0,
-       .set_timing = imx_ocotp_set_imx6_timing,
-       .ctrl = IMX_OCOTP_BM_CTRL_DEFAULT,
--      .reverse_mac_address = true,
- };
- static const struct ocotp_params imx8mn_params = {
-@@ -561,7 +558,6 @@ static const struct ocotp_params imx8mn_
-       .bank_address_words = 0,
-       .set_timing = imx_ocotp_set_imx6_timing,
-       .ctrl = IMX_OCOTP_BM_CTRL_DEFAULT,
--      .reverse_mac_address = true,
- };
- static const struct ocotp_params imx8mp_params = {
-@@ -569,7 +565,6 @@ static const struct ocotp_params imx8mp_
-       .bank_address_words = 0,
-       .set_timing = imx_ocotp_set_imx6_timing,
-       .ctrl = IMX_OCOTP_BM_CTRL_8MP,
--      .reverse_mac_address = true,
- };
- static const struct of_device_id imx_ocotp_dt_ids[] = {
-@@ -624,8 +619,7 @@ static int imx_ocotp_probe(struct platfo
-       imx_ocotp_nvmem_config.size = 4 * priv->params->nregs;
-       imx_ocotp_nvmem_config.dev = dev;
-       imx_ocotp_nvmem_config.priv = priv;
--      if (priv->params->reverse_mac_address)
--              imx_ocotp_nvmem_config.layout = &imx_ocotp_layout;
-+      imx_ocotp_nvmem_config.layout = &imx_ocotp_layout;
-       priv->config = &imx_ocotp_nvmem_config;
diff --git a/target/linux/generic/backport-5.15/813-v6.5-0003-nvmem-brcm_nvram-add-.read_post_process-for-MACs.patch b/target/linux/generic/backport-5.15/813-v6.5-0003-nvmem-brcm_nvram-add-.read_post_process-for-MACs.patch
deleted file mode 100644 (file)
index fb4d346..0000000
+++ /dev/null
@@ -1,81 +0,0 @@
-From 73bcd133c910bff3b6d3b3834d0d14be9444e90a Mon Sep 17 00:00:00 2001
-From: =?UTF-8?q?Rafa=C5=82=20Mi=C5=82ecki?= <[email protected]>
-Date: Sun, 11 Jun 2023 15:03:08 +0100
-Subject: [PATCH] nvmem: brcm_nvram: add .read_post_process() for MACs
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-1. Parse ASCII MAC format into byte based
-2. Calculate relative addresses based on index argument
-
-Signed-off-by: Rafał Miłecki <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Message-ID: <[email protected]>
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/Kconfig      |  1 +
- drivers/nvmem/brcm_nvram.c | 28 ++++++++++++++++++++++++++++
- 2 files changed, 29 insertions(+)
-
---- a/drivers/nvmem/Kconfig
-+++ b/drivers/nvmem/Kconfig
-@@ -55,6 +55,7 @@ config NVMEM_BRCM_NVRAM
-       tristate "Broadcom's NVRAM support"
-       depends on ARCH_BCM_5301X || COMPILE_TEST
-       depends on HAS_IOMEM
-+      select GENERIC_NET_UTILS
-       help
-         This driver provides support for Broadcom's NVRAM that can be accessed
-         using I/O mapping.
---- a/drivers/nvmem/brcm_nvram.c
-+++ b/drivers/nvmem/brcm_nvram.c
-@@ -4,6 +4,8 @@
-  */
- #include <linux/bcm47xx_nvram.h>
-+#include <linux/etherdevice.h>
-+#include <linux/if_ether.h>
- #include <linux/io.h>
- #include <linux/mod_devicetable.h>
- #include <linux/module.h>
-@@ -42,6 +44,25 @@ static int brcm_nvram_read(void *context
-       return 0;
- }
-+static int brcm_nvram_read_post_process_macaddr(void *context, const char *id, int index,
-+                                              unsigned int offset, void *buf, size_t bytes)
-+{
-+      u8 mac[ETH_ALEN];
-+
-+      if (bytes != 3 * ETH_ALEN - 1)
-+              return -EINVAL;
-+
-+      if (!mac_pton(buf, mac))
-+              return -EINVAL;
-+
-+      if (index)
-+              eth_addr_add(mac, index);
-+
-+      ether_addr_copy(buf, mac);
-+
-+      return 0;
-+}
-+
- static int brcm_nvram_add_cells(struct brcm_nvram *priv, uint8_t *data,
-                               size_t len)
- {
-@@ -75,6 +96,13 @@ static int brcm_nvram_add_cells(struct b
-               priv->cells[idx].offset = value - (char *)data;
-               priv->cells[idx].bytes = strlen(value);
-               priv->cells[idx].np = of_get_child_by_name(dev->of_node, priv->cells[idx].name);
-+              if (!strcmp(var, "et0macaddr") ||
-+                  !strcmp(var, "et1macaddr") ||
-+                  !strcmp(var, "et2macaddr")) {
-+                      priv->cells[idx].raw_len = strlen(value);
-+                      priv->cells[idx].bytes = ETH_ALEN;
-+                      priv->cells[idx].read_post_process = brcm_nvram_read_post_process_macaddr;
-+              }
-       }
-       return 0;
diff --git a/target/linux/generic/backport-5.15/813-v6.5-0004-nvmem-rockchip-otp-Add-clks-and-reg_read-to-rockchip.patch b/target/linux/generic/backport-5.15/813-v6.5-0004-nvmem-rockchip-otp-Add-clks-and-reg_read-to-rockchip.patch
deleted file mode 100644 (file)
index 3b6e6e5..0000000
+++ /dev/null
@@ -1,166 +0,0 @@
-From 8dc61364164e79e44c07fa2ac0a7b6939f00d5db Mon Sep 17 00:00:00 2001
-From: Cristian Ciocaltea <[email protected]>
-Date: Sun, 11 Jun 2023 15:03:13 +0100
-Subject: [PATCH] nvmem: rockchip-otp: Add clks and reg_read to rockchip_data
-
-In preparation to support new Rockchip OTP memory devices with different
-clock configurations and register layout, extend rockchip_data struct
-with the related members: clks, num_clks, reg_read.
-
-Additionally, to avoid managing redundant driver data, drop num_clks
-member from rockchip_otp struct and update all references to point to
-the equivalent member in rockchip_data.
-
-Signed-off-by: Cristian Ciocaltea <[email protected]>
-Tested-by: Vincent Legoll <[email protected]>
-Reviewed-by: Heiko Stuebner <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Message-ID: <[email protected]>
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/rockchip-otp.c | 79 ++++++++++++++++++++++--------------
- 1 file changed, 49 insertions(+), 30 deletions(-)
-
---- a/drivers/nvmem/rockchip-otp.c
-+++ b/drivers/nvmem/rockchip-otp.c
-@@ -54,21 +54,19 @@
- #define OTPC_TIMEOUT                  10000
-+struct rockchip_data {
-+      int size;
-+      const char * const *clks;
-+      int num_clks;
-+      nvmem_reg_read_t reg_read;
-+};
-+
- struct rockchip_otp {
-       struct device *dev;
-       void __iomem *base;
--      struct clk_bulk_data    *clks;
--      int num_clks;
-+      struct clk_bulk_data *clks;
-       struct reset_control *rst;
--};
--
--/* list of required clocks */
--static const char * const rockchip_otp_clocks[] = {
--      "otp", "apb_pclk", "phy",
--};
--
--struct rockchip_data {
--      int size;
-+      const struct rockchip_data *data;
- };
- static int rockchip_otp_reset(struct rockchip_otp *otp)
-@@ -132,29 +130,23 @@ static int rockchip_otp_ecc_enable(struc
-       return ret;
- }
--static int rockchip_otp_read(void *context, unsigned int offset,
--                           void *val, size_t bytes)
-+static int px30_otp_read(void *context, unsigned int offset,
-+                       void *val, size_t bytes)
- {
-       struct rockchip_otp *otp = context;
-       u8 *buf = val;
--      int ret = 0;
--
--      ret = clk_bulk_prepare_enable(otp->num_clks, otp->clks);
--      if (ret < 0) {
--              dev_err(otp->dev, "failed to prepare/enable clks\n");
--              return ret;
--      }
-+      int ret;
-       ret = rockchip_otp_reset(otp);
-       if (ret) {
-               dev_err(otp->dev, "failed to reset otp phy\n");
--              goto disable_clks;
-+              return ret;
-       }
-       ret = rockchip_otp_ecc_enable(otp, false);
-       if (ret < 0) {
-               dev_err(otp->dev, "rockchip_otp_ecc_enable err\n");
--              goto disable_clks;
-+              return ret;
-       }
-       writel(OTPC_USE_USER | OTPC_USE_USER_MASK, otp->base + OTPC_USER_CTRL);
-@@ -174,8 +166,28 @@ static int rockchip_otp_read(void *conte
- read_end:
-       writel(0x0 | OTPC_USE_USER_MASK, otp->base + OTPC_USER_CTRL);
--disable_clks:
--      clk_bulk_disable_unprepare(otp->num_clks, otp->clks);
-+
-+      return ret;
-+}
-+
-+static int rockchip_otp_read(void *context, unsigned int offset,
-+                           void *val, size_t bytes)
-+{
-+      struct rockchip_otp *otp = context;
-+      int ret;
-+
-+      if (!otp->data || !otp->data->reg_read)
-+              return -EINVAL;
-+
-+      ret = clk_bulk_prepare_enable(otp->data->num_clks, otp->clks);
-+      if (ret < 0) {
-+              dev_err(otp->dev, "failed to prepare/enable clks\n");
-+              return ret;
-+      }
-+
-+      ret = otp->data->reg_read(context, offset, val, bytes);
-+
-+      clk_bulk_disable_unprepare(otp->data->num_clks, otp->clks);
-       return ret;
- }
-@@ -189,8 +201,15 @@ static struct nvmem_config otp_config =
-       .reg_read = rockchip_otp_read,
- };
-+static const char * const px30_otp_clocks[] = {
-+      "otp", "apb_pclk", "phy",
-+};
-+
- static const struct rockchip_data px30_data = {
-       .size = 0x40,
-+      .clks = px30_otp_clocks,
-+      .num_clks = ARRAY_SIZE(px30_otp_clocks),
-+      .reg_read = px30_otp_read,
- };
- static const struct of_device_id rockchip_otp_match[] = {
-@@ -225,21 +244,21 @@ static int rockchip_otp_probe(struct pla
-       if (!otp)
-               return -ENOMEM;
-+      otp->data = data;
-       otp->dev = dev;
-       otp->base = devm_platform_ioremap_resource(pdev, 0);
-       if (IS_ERR(otp->base))
-               return PTR_ERR(otp->base);
--      otp->num_clks = ARRAY_SIZE(rockchip_otp_clocks);
--      otp->clks = devm_kcalloc(dev, otp->num_clks,
--                                   sizeof(*otp->clks), GFP_KERNEL);
-+      otp->clks = devm_kcalloc(dev, data->num_clks, sizeof(*otp->clks),
-+                               GFP_KERNEL);
-       if (!otp->clks)
-               return -ENOMEM;
--      for (i = 0; i < otp->num_clks; ++i)
--              otp->clks[i].id = rockchip_otp_clocks[i];
-+      for (i = 0; i < data->num_clks; ++i)
-+              otp->clks[i].id = data->clks[i];
--      ret = devm_clk_bulk_get(dev, otp->num_clks, otp->clks);
-+      ret = devm_clk_bulk_get(dev, data->num_clks, otp->clks);
-       if (ret)
-               return ret;
diff --git a/target/linux/generic/backport-5.15/813-v6.5-0005-nvmem-rockchip-otp-Generalize-rockchip_otp_wait_stat.patch b/target/linux/generic/backport-5.15/813-v6.5-0005-nvmem-rockchip-otp-Generalize-rockchip_otp_wait_stat.patch
deleted file mode 100644 (file)
index b5b66cf..0000000
+++ /dev/null
@@ -1,62 +0,0 @@
-From 30fd21cfb1e64ef20035559a8246f5fbf682c40e Mon Sep 17 00:00:00 2001
-From: Cristian Ciocaltea <[email protected]>
-Date: Sun, 11 Jun 2023 15:03:14 +0100
-Subject: [PATCH] nvmem: rockchip-otp: Generalize rockchip_otp_wait_status()
-
-In preparation to support additional Rockchip OTP memory devices with
-different register layout, generalize rockchip_otp_wait_status() to
-accept a new parameter for specifying the offset of the status register.
-
-Signed-off-by: Cristian Ciocaltea <[email protected]>
-Tested-by: Vincent Legoll <[email protected]>
-Reviewed-by: Heiko Stuebner <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Message-ID: <[email protected]>
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/rockchip-otp.c | 11 ++++++-----
- 1 file changed, 6 insertions(+), 5 deletions(-)
-
---- a/drivers/nvmem/rockchip-otp.c
-+++ b/drivers/nvmem/rockchip-otp.c
-@@ -90,18 +90,19 @@ static int rockchip_otp_reset(struct roc
-       return 0;
- }
--static int rockchip_otp_wait_status(struct rockchip_otp *otp, u32 flag)
-+static int rockchip_otp_wait_status(struct rockchip_otp *otp,
-+                                  unsigned int reg, u32 flag)
- {
-       u32 status = 0;
-       int ret;
--      ret = readl_poll_timeout_atomic(otp->base + OTPC_INT_STATUS, status,
-+      ret = readl_poll_timeout_atomic(otp->base + reg, status,
-                                       (status & flag), 1, OTPC_TIMEOUT);
-       if (ret)
-               return ret;
-       /* clean int status */
--      writel(flag, otp->base + OTPC_INT_STATUS);
-+      writel(flag, otp->base + reg);
-       return 0;
- }
-@@ -123,7 +124,7 @@ static int rockchip_otp_ecc_enable(struc
-       writel(SBPI_ENABLE_MASK | SBPI_ENABLE, otp->base + OTPC_SBPI_CTRL);
--      ret = rockchip_otp_wait_status(otp, OTPC_SBPI_DONE);
-+      ret = rockchip_otp_wait_status(otp, OTPC_INT_STATUS, OTPC_SBPI_DONE);
-       if (ret < 0)
-               dev_err(otp->dev, "timeout during ecc_enable\n");
-@@ -156,7 +157,7 @@ static int px30_otp_read(void *context,
-                      otp->base + OTPC_USER_ADDR);
-               writel(OTPC_USER_FSM_ENABLE | OTPC_USER_FSM_ENABLE_MASK,
-                      otp->base + OTPC_USER_ENABLE);
--              ret = rockchip_otp_wait_status(otp, OTPC_USER_DONE);
-+              ret = rockchip_otp_wait_status(otp, OTPC_INT_STATUS, OTPC_USER_DONE);
-               if (ret < 0) {
-                       dev_err(otp->dev, "timeout during read setup\n");
-                       goto read_end;
diff --git a/target/linux/generic/backport-5.15/813-v6.5-0006-nvmem-rockchip-otp-Use-devm_reset_control_array_get_.patch b/target/linux/generic/backport-5.15/813-v6.5-0006-nvmem-rockchip-otp-Use-devm_reset_control_array_get_.patch
deleted file mode 100644 (file)
index 3a17479..0000000
+++ /dev/null
@@ -1,31 +0,0 @@
-From d325c9dd2b6e94040ca722ddcadcd6af358dd2be Mon Sep 17 00:00:00 2001
-From: Cristian Ciocaltea <[email protected]>
-Date: Sun, 11 Jun 2023 15:03:15 +0100
-Subject: [PATCH] nvmem: rockchip-otp: Use
- devm_reset_control_array_get_exclusive()
-
-In preparation to support new Rockchip OTP memory devices having
-specific reset configurations, switch devm_reset_control_get() to
-devm_reset_control_array_get_exclusive().
-
-Signed-off-by: Cristian Ciocaltea <[email protected]>
-Tested-by: Vincent Legoll <[email protected]>
-Reviewed-by: Heiko Stuebner <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Message-ID: <[email protected]>
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/rockchip-otp.c | 2 +-
- 1 file changed, 1 insertion(+), 1 deletion(-)
-
---- a/drivers/nvmem/rockchip-otp.c
-+++ b/drivers/nvmem/rockchip-otp.c
-@@ -263,7 +263,7 @@ static int rockchip_otp_probe(struct pla
-       if (ret)
-               return ret;
--      otp->rst = devm_reset_control_get(dev, "phy");
-+      otp->rst = devm_reset_control_array_get_exclusive(dev);
-       if (IS_ERR(otp->rst))
-               return PTR_ERR(otp->rst);
diff --git a/target/linux/generic/backport-5.15/813-v6.5-0007-nvmem-rockchip-otp-Improve-probe-error-handling.patch b/target/linux/generic/backport-5.15/813-v6.5-0007-nvmem-rockchip-otp-Improve-probe-error-handling.patch
deleted file mode 100644 (file)
index 37cb927..0000000
+++ /dev/null
@@ -1,71 +0,0 @@
-From 912517345b867a69542dc9f5c2cc3e9d8beaccf5 Mon Sep 17 00:00:00 2001
-From: Cristian Ciocaltea <[email protected]>
-Date: Sun, 11 Jun 2023 15:03:16 +0100
-Subject: [PATCH] nvmem: rockchip-otp: Improve probe error handling
-
-Enhance error handling in the probe function by making use of
-dev_err_probe(), which ensures the error code is always printed, in
-addition to the specified error message.
-
-Signed-off-by: Cristian Ciocaltea <[email protected]>
-Tested-by: Vincent Legoll <[email protected]>
-Reviewed-by: Heiko Stuebner <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Message-ID: <[email protected]>
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/rockchip-otp.c | 21 ++++++++++++---------
- 1 file changed, 12 insertions(+), 9 deletions(-)
-
---- a/drivers/nvmem/rockchip-otp.c
-+++ b/drivers/nvmem/rockchip-otp.c
-@@ -235,10 +235,8 @@ static int rockchip_otp_probe(struct pla
-       int ret, i;
-       data = of_device_get_match_data(dev);
--      if (!data) {
--              dev_err(dev, "failed to get match data\n");
--              return -EINVAL;
--      }
-+      if (!data)
-+              return dev_err_probe(dev, -EINVAL, "failed to get match data\n");
-       otp = devm_kzalloc(&pdev->dev, sizeof(struct rockchip_otp),
-                          GFP_KERNEL);
-@@ -249,7 +247,8 @@ static int rockchip_otp_probe(struct pla
-       otp->dev = dev;
-       otp->base = devm_platform_ioremap_resource(pdev, 0);
-       if (IS_ERR(otp->base))
--              return PTR_ERR(otp->base);
-+              return dev_err_probe(dev, PTR_ERR(otp->base),
-+                                   "failed to ioremap resource\n");
-       otp->clks = devm_kcalloc(dev, data->num_clks, sizeof(*otp->clks),
-                                GFP_KERNEL);
-@@ -261,18 +260,22 @@ static int rockchip_otp_probe(struct pla
-       ret = devm_clk_bulk_get(dev, data->num_clks, otp->clks);
-       if (ret)
--              return ret;
-+              return dev_err_probe(dev, ret, "failed to get clocks\n");
-       otp->rst = devm_reset_control_array_get_exclusive(dev);
-       if (IS_ERR(otp->rst))
--              return PTR_ERR(otp->rst);
-+              return dev_err_probe(dev, PTR_ERR(otp->rst),
-+                                   "failed to get resets\n");
-       otp_config.size = data->size;
-       otp_config.priv = otp;
-       otp_config.dev = dev;
--      nvmem = devm_nvmem_register(dev, &otp_config);
--      return PTR_ERR_OR_ZERO(nvmem);
-+      nvmem = devm_nvmem_register(dev, &otp_config);
-+      if (IS_ERR(nvmem))
-+              return dev_err_probe(dev, PTR_ERR(nvmem),
-+                                   "failed to register nvmem device\n");
-+      return 0;
- }
- static struct platform_driver rockchip_otp_driver = {
diff --git a/target/linux/generic/backport-5.15/813-v6.5-0008-nvmem-rockchip-otp-Add-support-for-RK3588.patch b/target/linux/generic/backport-5.15/813-v6.5-0008-nvmem-rockchip-otp-Add-support-for-RK3588.patch
deleted file mode 100644 (file)
index c1e2231..0000000
+++ /dev/null
@@ -1,129 +0,0 @@
-From 8ab099fafbbc8c9607c399d21a774784a6cb8b45 Mon Sep 17 00:00:00 2001
-From: Cristian Ciocaltea <[email protected]>
-Date: Sun, 11 Jun 2023 15:03:17 +0100
-Subject: [PATCH] nvmem: rockchip-otp: Add support for RK3588
-
-Add support for the OTP memory device found on the Rockchip RK3588 SoC.
-
-While here, remove the unnecessary 'void *' casts in the OF device ID
-table.
-
-Co-developed-by: Finley Xiao <[email protected]>
-Signed-off-by: Finley Xiao <[email protected]>
-Signed-off-by: Cristian Ciocaltea <[email protected]>
-Tested-by: Vincent Legoll <[email protected]>
-Reviewed-by: Heiko Stuebner <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Message-ID: <[email protected]>
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/rockchip-otp.c | 78 +++++++++++++++++++++++++++++++++++-
- 1 file changed, 76 insertions(+), 2 deletions(-)
-
---- a/drivers/nvmem/rockchip-otp.c
-+++ b/drivers/nvmem/rockchip-otp.c
-@@ -54,6 +54,19 @@
- #define OTPC_TIMEOUT                  10000
-+/* RK3588 Register */
-+#define RK3588_OTPC_AUTO_CTRL         0x04
-+#define RK3588_OTPC_AUTO_EN           0x08
-+#define RK3588_OTPC_INT_ST            0x84
-+#define RK3588_OTPC_DOUT0             0x20
-+#define RK3588_NO_SECURE_OFFSET               0x300
-+#define RK3588_NBYTES                 4
-+#define RK3588_BURST_NUM              1
-+#define RK3588_BURST_SHIFT            8
-+#define RK3588_ADDR_SHIFT             16
-+#define RK3588_AUTO_EN                        BIT(0)
-+#define RK3588_RD_DONE                        BIT(1)
-+
- struct rockchip_data {
-       int size;
-       const char * const *clks;
-@@ -171,6 +184,52 @@ read_end:
-       return ret;
- }
-+static int rk3588_otp_read(void *context, unsigned int offset,
-+                         void *val, size_t bytes)
-+{
-+      struct rockchip_otp *otp = context;
-+      unsigned int addr_start, addr_end, addr_len;
-+      int ret, i = 0;
-+      u32 data;
-+      u8 *buf;
-+
-+      addr_start = round_down(offset, RK3588_NBYTES) / RK3588_NBYTES;
-+      addr_end = round_up(offset + bytes, RK3588_NBYTES) / RK3588_NBYTES;
-+      addr_len = addr_end - addr_start;
-+      addr_start += RK3588_NO_SECURE_OFFSET;
-+
-+      buf = kzalloc(array_size(addr_len, RK3588_NBYTES), GFP_KERNEL);
-+      if (!buf)
-+              return -ENOMEM;
-+
-+      while (addr_len--) {
-+              writel((addr_start << RK3588_ADDR_SHIFT) |
-+                     (RK3588_BURST_NUM << RK3588_BURST_SHIFT),
-+                     otp->base + RK3588_OTPC_AUTO_CTRL);
-+              writel(RK3588_AUTO_EN, otp->base + RK3588_OTPC_AUTO_EN);
-+
-+              ret = rockchip_otp_wait_status(otp, RK3588_OTPC_INT_ST,
-+                                             RK3588_RD_DONE);
-+              if (ret < 0) {
-+                      dev_err(otp->dev, "timeout during read setup\n");
-+                      goto read_end;
-+              }
-+
-+              data = readl(otp->base + RK3588_OTPC_DOUT0);
-+              memcpy(&buf[i], &data, RK3588_NBYTES);
-+
-+              i += RK3588_NBYTES;
-+              addr_start++;
-+      }
-+
-+      memcpy(val, buf + offset % RK3588_NBYTES, bytes);
-+
-+read_end:
-+      kfree(buf);
-+
-+      return ret;
-+}
-+
- static int rockchip_otp_read(void *context, unsigned int offset,
-                            void *val, size_t bytes)
- {
-@@ -213,14 +272,29 @@ static const struct rockchip_data px30_d
-       .reg_read = px30_otp_read,
- };
-+static const char * const rk3588_otp_clocks[] = {
-+      "otp", "apb_pclk", "phy", "arb",
-+};
-+
-+static const struct rockchip_data rk3588_data = {
-+      .size = 0x400,
-+      .clks = rk3588_otp_clocks,
-+      .num_clks = ARRAY_SIZE(rk3588_otp_clocks),
-+      .reg_read = rk3588_otp_read,
-+};
-+
- static const struct of_device_id rockchip_otp_match[] = {
-       {
-               .compatible = "rockchip,px30-otp",
--              .data = (void *)&px30_data,
-+              .data = &px30_data,
-       },
-       {
-               .compatible = "rockchip,rk3308-otp",
--              .data = (void *)&px30_data,
-+              .data = &px30_data,
-+      },
-+      {
-+              .compatible = "rockchip,rk3588-otp",
-+              .data = &rk3588_data,
-       },
-       { /* sentinel */ },
- };
diff --git a/target/linux/generic/backport-5.15/813-v6.5-0009-nvmem-zynqmp-Switch-xilinx.com-emails-to-amd.com.patch b/target/linux/generic/backport-5.15/813-v6.5-0009-nvmem-zynqmp-Switch-xilinx.com-emails-to-amd.com.patch
deleted file mode 100644 (file)
index 220e3e9..0000000
+++ /dev/null
@@ -1,26 +0,0 @@
-From 9734408969e978a1c0d5d752be63dd638288e374 Mon Sep 17 00:00:00 2001
-From: Michal Simek <[email protected]>
-Date: Sun, 11 Jun 2023 15:03:23 +0100
-Subject: [PATCH] nvmem: zynqmp: Switch @xilinx.com emails to @amd.com
-
[email protected] is still working but better to switch to new amd.com after
-AMD/Xilinx acquisition.
-
-Signed-off-by: Michal Simek <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Message-ID: <[email protected]>
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/zynqmp_nvmem.c | 2 +-
- 1 file changed, 1 insertion(+), 1 deletion(-)
-
---- a/drivers/nvmem/zynqmp_nvmem.c
-+++ b/drivers/nvmem/zynqmp_nvmem.c
-@@ -76,6 +76,6 @@ static struct platform_driver zynqmp_nvm
- module_platform_driver(zynqmp_nvmem_driver);
--MODULE_AUTHOR("Michal Simek <[email protected]>, Nava kishore Manne <[email protected]>");
-+MODULE_AUTHOR("Michal Simek <[email protected]>, Nava kishore Manne <[email protected]>");
- MODULE_DESCRIPTION("ZynqMP NVMEM driver");
- MODULE_LICENSE("GPL");
diff --git a/target/linux/generic/backport-5.15/813-v6.5-0010-nvmem-imx-support-i.MX93-OCOTP.patch b/target/linux/generic/backport-5.15/813-v6.5-0010-nvmem-imx-support-i.MX93-OCOTP.patch
deleted file mode 100644 (file)
index f8e6be4..0000000
+++ /dev/null
@@ -1,230 +0,0 @@
-From 22e9e6fcfb5042cb6d6c7874c459b034800092f1 Mon Sep 17 00:00:00 2001
-From: Peng Fan <[email protected]>
-Date: Sun, 11 Jun 2023 15:03:25 +0100
-Subject: [PATCH] nvmem: imx: support i.MX93 OCOTP
-
-Add i.MX93 OCOTP support. i.MX93 OCOTP has two parts: Fuse shadow
-block(fsb) and fuse managed by ELE. The FSB part could be directly
-accessed with MMIO, the ELE could only be accessed with ELE API.
-
-Currently the ELE API is not ready, so NULL function callback is used,
-but it was tested with downstream ELE API.
-
-Signed-off-by: Peng Fan <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Message-ID: <[email protected]>
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/Kconfig         |   9 ++
- drivers/nvmem/Makefile        |   2 +
- drivers/nvmem/imx-ocotp-ele.c | 175 ++++++++++++++++++++++++++++++++++
- 3 files changed, 186 insertions(+)
- create mode 100644 drivers/nvmem/imx-ocotp-ele.c
-
---- a/drivers/nvmem/Kconfig
-+++ b/drivers/nvmem/Kconfig
-@@ -83,6 +83,15 @@ config NVMEM_IMX_OCOTP
-         This driver can also be built as a module. If so, the module
-         will be called nvmem-imx-ocotp.
-+config NVMEM_IMX_OCOTP_ELE
-+      tristate "i.MX On-Chip OTP Controller support"
-+      depends on ARCH_MXC || COMPILE_TEST
-+      depends on HAS_IOMEM
-+      depends on OF
-+      help
-+        This is a driver for the On-Chip OTP Controller (OCOTP)
-+        available on i.MX SoCs which has ELE.
-+
- config NVMEM_IMX_OCOTP_SCU
-       tristate "i.MX8 SCU On-Chip OTP Controller support"
-       depends on IMX_SCU
---- a/drivers/nvmem/Makefile
-+++ b/drivers/nvmem/Makefile
-@@ -18,6 +18,8 @@ obj-$(CONFIG_NVMEM_IMX_IIM)          += nvmem-im
- nvmem-imx-iim-y                               := imx-iim.o
- obj-$(CONFIG_NVMEM_IMX_OCOTP)         += nvmem-imx-ocotp.o
- nvmem-imx-ocotp-y                     := imx-ocotp.o
-+obj-$(CONFIG_NVMEM_IMX_OCOTP_ELE)     += nvmem-imx-ocotp-ele.o
-+nvmem-imx-ocotp-ele-y                 := imx-ocotp-ele.o
- obj-$(CONFIG_NVMEM_IMX_OCOTP_SCU)     += nvmem-imx-ocotp-scu.o
- nvmem-imx-ocotp-scu-y                 := imx-ocotp-scu.o
- obj-$(CONFIG_NVMEM_JZ4780_EFUSE)      += nvmem_jz4780_efuse.o
---- /dev/null
-+++ b/drivers/nvmem/imx-ocotp-ele.c
-@@ -0,0 +1,175 @@
-+// SPDX-License-Identifier: GPL-2.0-only
-+/*
-+ * i.MX9 OCOTP fusebox driver
-+ *
-+ * Copyright 2023 NXP
-+ */
-+
-+#include <linux/device.h>
-+#include <linux/io.h>
-+#include <linux/module.h>
-+#include <linux/nvmem-provider.h>
-+#include <linux/of_device.h>
-+#include <linux/platform_device.h>
-+#include <linux/slab.h>
-+
-+enum fuse_type {
-+      FUSE_FSB = 1,
-+      FUSE_ELE = 2,
-+      FUSE_INVALID = -1
-+};
-+
-+struct ocotp_map_entry {
-+      u32 start; /* start word */
-+      u32 num; /* num words */
-+      enum fuse_type type;
-+};
-+
-+struct ocotp_devtype_data {
-+      u32 reg_off;
-+      char *name;
-+      u32 size;
-+      u32 num_entry;
-+      u32 flag;
-+      nvmem_reg_read_t reg_read;
-+      struct ocotp_map_entry entry[];
-+};
-+
-+struct imx_ocotp_priv {
-+      struct device *dev;
-+      void __iomem *base;
-+      struct nvmem_config config;
-+      struct mutex lock;
-+      const struct ocotp_devtype_data *data;
-+};
-+
-+static enum fuse_type imx_ocotp_fuse_type(void *context, u32 index)
-+{
-+      struct imx_ocotp_priv *priv = context;
-+      const struct ocotp_devtype_data *data = priv->data;
-+      u32 start, end;
-+      int i;
-+
-+      for (i = 0; i < data->num_entry; i++) {
-+              start = data->entry[i].start;
-+              end = data->entry[i].start + data->entry[i].num;
-+
-+              if (index >= start && index < end)
-+                      return data->entry[i].type;
-+      }
-+
-+      return FUSE_INVALID;
-+}
-+
-+static int imx_ocotp_reg_read(void *context, unsigned int offset, void *val, size_t bytes)
-+{
-+      struct imx_ocotp_priv *priv = context;
-+      void __iomem *reg = priv->base + priv->data->reg_off;
-+      u32 count, index, num_bytes;
-+      enum fuse_type type;
-+      u32 *buf;
-+      void *p;
-+      int i;
-+
-+      index = offset;
-+      num_bytes = round_up(bytes, 4);
-+      count = num_bytes >> 2;
-+
-+      if (count > ((priv->data->size >> 2) - index))
-+              count = (priv->data->size >> 2) - index;
-+
-+      p = kzalloc(num_bytes, GFP_KERNEL);
-+      if (!p)
-+              return -ENOMEM;
-+
-+      mutex_lock(&priv->lock);
-+
-+      buf = p;
-+
-+      for (i = index; i < (index + count); i++) {
-+              type = imx_ocotp_fuse_type(context, i);
-+              if (type == FUSE_INVALID || type == FUSE_ELE) {
-+                      *buf++ = 0;
-+                      continue;
-+              }
-+
-+              *buf++ = readl_relaxed(reg + (i << 2));
-+      }
-+
-+      memcpy(val, (u8 *)p, bytes);
-+
-+      mutex_unlock(&priv->lock);
-+
-+      kfree(p);
-+
-+      return 0;
-+};
-+
-+static int imx_ele_ocotp_probe(struct platform_device *pdev)
-+{
-+      struct device *dev = &pdev->dev;
-+      struct imx_ocotp_priv *priv;
-+      struct nvmem_device *nvmem;
-+
-+      priv = devm_kzalloc(dev, sizeof(*priv), GFP_KERNEL);
-+      if (!priv)
-+              return -ENOMEM;
-+
-+      priv->data = of_device_get_match_data(dev);
-+
-+      priv->base = devm_platform_ioremap_resource(pdev, 0);
-+      if (IS_ERR(priv->base))
-+              return PTR_ERR(priv->base);
-+
-+      priv->config.dev = dev;
-+      priv->config.name = "ELE-OCOTP";
-+      priv->config.id = NVMEM_DEVID_AUTO;
-+      priv->config.owner = THIS_MODULE;
-+      priv->config.size = priv->data->size;
-+      priv->config.reg_read = priv->data->reg_read;
-+      priv->config.word_size = 4;
-+      priv->config.stride = 1;
-+      priv->config.priv = priv;
-+      priv->config.read_only = true;
-+      mutex_init(&priv->lock);
-+
-+      nvmem = devm_nvmem_register(dev, &priv->config);
-+      if (IS_ERR(nvmem))
-+              return PTR_ERR(nvmem);
-+
-+      return 0;
-+}
-+
-+static const struct ocotp_devtype_data imx93_ocotp_data = {
-+      .reg_off = 0x8000,
-+      .reg_read = imx_ocotp_reg_read,
-+      .size = 2048,
-+      .num_entry = 6,
-+      .entry = {
-+              { 0, 52, FUSE_FSB },
-+              { 63, 1, FUSE_ELE},
-+              { 128, 16, FUSE_ELE },
-+              { 182, 1, FUSE_ELE },
-+              { 188, 1, FUSE_ELE },
-+              { 312, 200, FUSE_FSB }
-+      },
-+};
-+
-+static const struct of_device_id imx_ele_ocotp_dt_ids[] = {
-+      { .compatible = "fsl,imx93-ocotp", .data = &imx93_ocotp_data, },
-+      {},
-+};
-+MODULE_DEVICE_TABLE(of, imx_ele_ocotp_dt_ids);
-+
-+static struct platform_driver imx_ele_ocotp_driver = {
-+      .driver = {
-+              .name = "imx_ele_ocotp",
-+              .of_match_table = imx_ele_ocotp_dt_ids,
-+      },
-+      .probe = imx_ele_ocotp_probe,
-+};
-+module_platform_driver(imx_ele_ocotp_driver);
-+
-+MODULE_DESCRIPTION("i.MX OCOTP/ELE driver");
-+MODULE_AUTHOR("Peng Fan <[email protected]>");
-+MODULE_LICENSE("GPL");
diff --git a/target/linux/generic/backport-5.15/813-v6.5-0011-nvmem-core-add-support-for-fixed-cells-layout.patch b/target/linux/generic/backport-5.15/813-v6.5-0011-nvmem-core-add-support-for-fixed-cells-layout.patch
deleted file mode 100644 (file)
index 59b2f9f..0000000
+++ /dev/null
@@ -1,96 +0,0 @@
-From 27f699e578b1a72df89dfa3bc42e093a01dc8d10 Mon Sep 17 00:00:00 2001
-From: =?UTF-8?q?Rafa=C5=82=20Mi=C5=82ecki?= <[email protected]>
-Date: Sun, 11 Jun 2023 15:03:29 +0100
-Subject: [PATCH] nvmem: core: add support for fixed cells *layout*
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-This adds support for the "fixed-layout" NVMEM layout binding. It allows
-defining NVMEM cells in a layout DT node named "nvmem-layout".
-
-While NVMEM subsystem supports layout drivers it has been discussed that
-"fixed-layout" may actually be supperted internally. It's because:
-1. It's a very basic layout
-2. It allows sharing code with legacy syntax parsing
-3. It's safer for soc_device_match() due to -EPROBE_DEFER
-4. This will make the syntax transition easier
-
-Signed-off-by: Rafał Miłecki <[email protected]>
-Reviewed-by: Michael Walle <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Message-ID: <[email protected]>
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/core.c | 32 +++++++++++++++++++++++++++++---
- 1 file changed, 29 insertions(+), 3 deletions(-)
-
---- a/drivers/nvmem/core.c
-+++ b/drivers/nvmem/core.c
-@@ -696,7 +696,7 @@ static int nvmem_validate_keepouts(struc
-       return 0;
- }
--static int nvmem_add_cells_from_of(struct nvmem_device *nvmem)
-+static int nvmem_add_cells_from_dt(struct nvmem_device *nvmem, struct device_node *np)
- {
-       struct nvmem_layout *layout = nvmem->layout;
-       struct device *dev = &nvmem->dev;
-@@ -704,7 +704,7 @@ static int nvmem_add_cells_from_of(struc
-       const __be32 *addr;
-       int len, ret;
--      for_each_child_of_node(dev->of_node, child) {
-+      for_each_child_of_node(np, child) {
-               struct nvmem_cell_info info = {0};
-               addr = of_get_property(child, "reg", &len);
-@@ -742,6 +742,28 @@ static int nvmem_add_cells_from_of(struc
-       return 0;
- }
-+static int nvmem_add_cells_from_legacy_of(struct nvmem_device *nvmem)
-+{
-+      return nvmem_add_cells_from_dt(nvmem, nvmem->dev.of_node);
-+}
-+
-+static int nvmem_add_cells_from_fixed_layout(struct nvmem_device *nvmem)
-+{
-+      struct device_node *layout_np;
-+      int err = 0;
-+
-+      layout_np = of_nvmem_layout_get_container(nvmem);
-+      if (!layout_np)
-+              return 0;
-+
-+      if (of_device_is_compatible(layout_np, "fixed-layout"))
-+              err = nvmem_add_cells_from_dt(nvmem, layout_np);
-+
-+      of_node_put(layout_np);
-+
-+      return err;
-+}
-+
- int __nvmem_layout_register(struct nvmem_layout *layout, struct module *owner)
- {
-       layout->owner = owner;
-@@ -972,7 +994,7 @@ struct nvmem_device *nvmem_register(cons
-       if (rval)
-               goto err_remove_cells;
--      rval = nvmem_add_cells_from_of(nvmem);
-+      rval = nvmem_add_cells_from_legacy_of(nvmem);
-       if (rval)
-               goto err_remove_cells;
-@@ -982,6 +1004,10 @@ struct nvmem_device *nvmem_register(cons
-       if (rval)
-               goto err_remove_cells;
-+      rval = nvmem_add_cells_from_fixed_layout(nvmem);
-+      if (rval)
-+              goto err_remove_cells;
-+
-       rval = nvmem_add_cells_from_layout(nvmem);
-       if (rval)
-               goto err_remove_cells;
diff --git a/target/linux/generic/backport-5.15/814-v6.3-leds-Move-led_init_default_state_get-to-the-global-h.patch b/target/linux/generic/backport-5.15/814-v6.3-leds-Move-led_init_default_state_get-to-the-global-h.patch
deleted file mode 100644 (file)
index 592111f..0000000
+++ /dev/null
@@ -1,39 +0,0 @@
-From 156a5bb89ca6f3edd2be0bfd0de15e575442927e Mon Sep 17 00:00:00 2001
-From: Andy Shevchenko <[email protected]>
-Date: Tue, 3 Jan 2023 15:12:47 +0200
-Subject: [PATCH] leds: Move led_init_default_state_get() to the global header
-
-There are users inside and outside LED framework that have implemented
-a local copy of led_init_default_state_get(). In order to deduplicate
-that, as the first step move the declaration from LED header to the
-global one.
-
-Signed-off-by: Andy Shevchenko <[email protected]>
-Signed-off-by: Lee Jones <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
----
- drivers/leds/leds.h  | 1 -
- include/linux/leds.h | 2 ++
- 2 files changed, 2 insertions(+), 1 deletion(-)
-
---- a/drivers/leds/leds.h
-+++ b/drivers/leds/leds.h
-@@ -27,7 +27,6 @@ ssize_t led_trigger_read(struct file *fi
- ssize_t led_trigger_write(struct file *filp, struct kobject *kobj,
-                       struct bin_attribute *bin_attr, char *buf,
-                       loff_t pos, size_t count);
--enum led_default_state led_init_default_state_get(struct fwnode_handle *fwnode);
- extern struct rw_semaphore leds_list_lock;
- extern struct list_head leds_list;
---- a/include/linux/leds.h
-+++ b/include/linux/leds.h
-@@ -63,6 +63,8 @@ struct led_init_data {
-       bool devname_mandatory;
- };
-+enum led_default_state led_init_default_state_get(struct fwnode_handle *fwnode);
-+
- struct led_hw_trigger_type {
-       int dummy;
- };
diff --git a/target/linux/generic/backport-5.15/815-v6.4-01-net-dsa-qca8k-move-qca8k_port_to_phy-to-header.patch b/target/linux/generic/backport-5.15/815-v6.4-01-net-dsa-qca8k-move-qca8k_port_to_phy-to-header.patch
deleted file mode 100644 (file)
index dcdca90..0000000
+++ /dev/null
@@ -1,67 +0,0 @@
-From 3e8b4d6277fd19d98c817576954dd6a4ff3caa2b Mon Sep 17 00:00:00 2001
-From: Christian Marangi <[email protected]>
-Date: Mon, 17 Apr 2023 17:17:23 +0200
-Subject: [PATCH 1/9] net: dsa: qca8k: move qca8k_port_to_phy() to header
-
-Move qca8k_port_to_phy() to qca8k header as it's useful for future
-reference in Switch LEDs module since the same logic is applied to get
-the right index of the switch port.
-Make it inline as it's simple function that just decrease the port.
-
-Signed-off-by: Christian Marangi <[email protected]>
-Reviewed-by: Andrew Lunn <[email protected]>
-Reviewed-by: Michal Kubiak <[email protected]>
-Reviewed-by: Florian Fainelli <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/dsa/qca/qca8k-8xxx.c | 15 ---------------
- drivers/net/dsa/qca/qca8k.h      | 14 ++++++++++++++
- 2 files changed, 14 insertions(+), 15 deletions(-)
-
---- a/drivers/net/dsa/qca/qca8k-8xxx.c
-+++ b/drivers/net/dsa/qca/qca8k-8xxx.c
-@@ -716,21 +716,6 @@ err_clear_skb:
-       return ret;
- }
--static u32
--qca8k_port_to_phy(int port)
--{
--      /* From Andrew Lunn:
--       * Port 0 has no internal phy.
--       * Port 1 has an internal PHY at MDIO address 0.
--       * Port 2 has an internal PHY at MDIO address 1.
--       * ...
--       * Port 5 has an internal PHY at MDIO address 4.
--       * Port 6 has no internal PHY.
--       */
--
--      return port - 1;
--}
--
- static int
- qca8k_mdio_busy_wait(struct mii_bus *bus, u32 reg, u32 mask)
- {
---- a/drivers/net/dsa/qca/qca8k.h
-+++ b/drivers/net/dsa/qca/qca8k.h
-@@ -414,6 +414,20 @@ struct qca8k_fdb {
-       u8 mac[6];
- };
-+static inline u32 qca8k_port_to_phy(int port)
-+{
-+      /* From Andrew Lunn:
-+       * Port 0 has no internal phy.
-+       * Port 1 has an internal PHY at MDIO address 0.
-+       * Port 2 has an internal PHY at MDIO address 1.
-+       * ...
-+       * Port 5 has an internal PHY at MDIO address 4.
-+       * Port 6 has no internal PHY.
-+       */
-+
-+      return port - 1;
-+}
-+
- /* Common setup function */
- extern const struct qca8k_mib_desc ar8327_mib[];
- extern const struct regmap_access_table qca8k_readable_table;
diff --git a/target/linux/generic/backport-5.15/815-v6.4-02-net-dsa-qca8k-add-LEDs-basic-support.patch b/target/linux/generic/backport-5.15/815-v6.4-02-net-dsa-qca8k-add-LEDs-basic-support.patch
deleted file mode 100644 (file)
index baf4c2e..0000000
+++ /dev/null
@@ -1,435 +0,0 @@
-From 1e264f9d2918b5737023c44a23ae04def1095210 Mon Sep 17 00:00:00 2001
-From: Christian Marangi <[email protected]>
-Date: Mon, 17 Apr 2023 17:17:24 +0200
-Subject: [PATCH 2/9] net: dsa: qca8k: add LEDs basic support
-
-Add LEDs basic support for qca8k Switch Family by adding basic
-brightness_set() support.
-
-Since these LEDs refelect port status, the default label is set to
-":port". DT binding should describe the color and function of the
-LEDs using standard LEDs api.
-Each LED always have the device name as prefix. The device name is
-composed from the mii bus id and the PHY addr resulting in example
-names like:
-- qca8k-0.0:00:amber:lan
-- qca8k-0.0:00:white:lan
-- qca8k-0.0:01:amber:lan
-- qca8k-0.0:01:white:lan
-
-These LEDs supports only blocking variant of the brightness_set()
-function since they can sleep during access of the switch leds to set
-the brightness.
-
-While at it add to the qca8k header file each mode defined by the Switch
-Documentation for future use.
-
-Signed-off-by: Christian Marangi <[email protected]>
-Reviewed-by: Florian Fainelli <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/dsa/qca/Kconfig      |   8 ++
- drivers/net/dsa/qca/Makefile     |   3 +
- drivers/net/dsa/qca/qca8k-8xxx.c |   5 +
- drivers/net/dsa/qca/qca8k-leds.c | 239 +++++++++++++++++++++++++++++++
- drivers/net/dsa/qca/qca8k.h      |  60 ++++++++
- drivers/net/dsa/qca/qca8k_leds.h |  16 +++
- 6 files changed, 331 insertions(+)
- create mode 100644 drivers/net/dsa/qca/qca8k-leds.c
- create mode 100644 drivers/net/dsa/qca/qca8k_leds.h
-
---- a/drivers/net/dsa/qca/Kconfig
-+++ b/drivers/net/dsa/qca/Kconfig
-@@ -15,3 +15,11 @@ config NET_DSA_QCA8K
-       help
-         This enables support for the Qualcomm Atheros QCA8K Ethernet
-         switch chips.
-+
-+config NET_DSA_QCA8K_LEDS_SUPPORT
-+      bool "Qualcomm Atheros QCA8K Ethernet switch family LEDs support"
-+      depends on NET_DSA_QCA8K
-+      depends on LEDS_CLASS
-+      help
-+        This enabled support for LEDs present on the Qualcomm Atheros
-+        QCA8K Ethernet switch chips.
---- a/drivers/net/dsa/qca/Makefile
-+++ b/drivers/net/dsa/qca/Makefile
-@@ -2,3 +2,6 @@
- obj-$(CONFIG_NET_DSA_AR9331)  += ar9331.o
- obj-$(CONFIG_NET_DSA_QCA8K)   += qca8k.o
- qca8k-y                       += qca8k-common.o qca8k-8xxx.o
-+ifdef CONFIG_NET_DSA_QCA8K_LEDS_SUPPORT
-+qca8k-y                               += qca8k-leds.o
-+endif
---- a/drivers/net/dsa/qca/qca8k-8xxx.c
-+++ b/drivers/net/dsa/qca/qca8k-8xxx.c
-@@ -22,6 +22,7 @@
- #include <linux/dsa/tag_qca.h>
- #include "qca8k.h"
-+#include "qca8k_leds.h"
- static void
- qca8k_split_addr(u32 regaddr, u16 *r1, u16 *r2, u16 *page)
-@@ -1185,6 +1186,10 @@ qca8k_setup(struct dsa_switch *ds)
-       if (ret)
-               return ret;
-+      ret = qca8k_setup_led_ctrl(priv);
-+      if (ret)
-+              return ret;
-+
-       /* Make sure MAC06 is disabled */
-       ret = regmap_clear_bits(priv->regmap, QCA8K_REG_PORT0_PAD_CTRL,
-                               QCA8K_PORT0_PAD_MAC06_EXCHANGE_EN);
---- /dev/null
-+++ b/drivers/net/dsa/qca/qca8k-leds.c
-@@ -0,0 +1,239 @@
-+// SPDX-License-Identifier: GPL-2.0
-+#include <linux/regmap.h>
-+#include <net/dsa.h>
-+
-+#include "qca8k.h"
-+#include "qca8k_leds.h"
-+
-+static int
-+qca8k_get_enable_led_reg(int port_num, int led_num, struct qca8k_led_pattern_en *reg_info)
-+{
-+      switch (port_num) {
-+      case 0:
-+              reg_info->reg = QCA8K_LED_CTRL_REG(led_num);
-+              reg_info->shift = QCA8K_LED_PHY0123_CONTROL_RULE_SHIFT;
-+              break;
-+      case 1:
-+      case 2:
-+      case 3:
-+              /* Port 123 are controlled on a different reg */
-+              reg_info->reg = QCA8K_LED_CTRL3_REG;
-+              reg_info->shift = QCA8K_LED_PHY123_PATTERN_EN_SHIFT(port_num, led_num);
-+              break;
-+      case 4:
-+              reg_info->reg = QCA8K_LED_CTRL_REG(led_num);
-+              reg_info->shift = QCA8K_LED_PHY4_CONTROL_RULE_SHIFT;
-+              break;
-+      default:
-+              return -EINVAL;
-+      }
-+
-+      return 0;
-+}
-+
-+static int
-+qca8k_led_brightness_set(struct qca8k_led *led,
-+                       enum led_brightness brightness)
-+{
-+      struct qca8k_led_pattern_en reg_info;
-+      struct qca8k_priv *priv = led->priv;
-+      u32 mask, val;
-+
-+      qca8k_get_enable_led_reg(led->port_num, led->led_num, &reg_info);
-+
-+      val = QCA8K_LED_ALWAYS_OFF;
-+      if (brightness)
-+              val = QCA8K_LED_ALWAYS_ON;
-+
-+      /* HW regs to control brightness is special and port 1-2-3
-+       * are placed in a different reg.
-+       *
-+       * To control port 0 brightness:
-+       * - the 2 bit (15, 14) of:
-+       *   - QCA8K_LED_CTRL0_REG for led1
-+       *   - QCA8K_LED_CTRL1_REG for led2
-+       *   - QCA8K_LED_CTRL2_REG for led3
-+       *
-+       * To control port 4:
-+       * - the 2 bit (31, 30) of:
-+       *   - QCA8K_LED_CTRL0_REG for led1
-+       *   - QCA8K_LED_CTRL1_REG for led2
-+       *   - QCA8K_LED_CTRL2_REG for led3
-+       *
-+       * To control port 1:
-+       *   - the 2 bit at (9, 8) of QCA8K_LED_CTRL3_REG are used for led1
-+       *   - the 2 bit at (11, 10) of QCA8K_LED_CTRL3_REG are used for led2
-+       *   - the 2 bit at (13, 12) of QCA8K_LED_CTRL3_REG are used for led3
-+       *
-+       * To control port 2:
-+       *   - the 2 bit at (15, 14) of QCA8K_LED_CTRL3_REG are used for led1
-+       *   - the 2 bit at (17, 16) of QCA8K_LED_CTRL3_REG are used for led2
-+       *   - the 2 bit at (19, 18) of QCA8K_LED_CTRL3_REG are used for led3
-+       *
-+       * To control port 3:
-+       *   - the 2 bit at (21, 20) of QCA8K_LED_CTRL3_REG are used for led1
-+       *   - the 2 bit at (23, 22) of QCA8K_LED_CTRL3_REG are used for led2
-+       *   - the 2 bit at (25, 24) of QCA8K_LED_CTRL3_REG are used for led3
-+       *
-+       * To abstract this and have less code, we use the port and led numm
-+       * to calculate the shift and the correct reg due to this problem of
-+       * not having a 1:1 map of LED with the regs.
-+       */
-+      if (led->port_num == 0 || led->port_num == 4) {
-+              mask = QCA8K_LED_PATTERN_EN_MASK;
-+              val <<= QCA8K_LED_PATTERN_EN_SHIFT;
-+      } else {
-+              mask = QCA8K_LED_PHY123_PATTERN_EN_MASK;
-+      }
-+
-+      return regmap_update_bits(priv->regmap, reg_info.reg,
-+                                mask << reg_info.shift,
-+                                val << reg_info.shift);
-+}
-+
-+static int
-+qca8k_cled_brightness_set_blocking(struct led_classdev *ldev,
-+                                 enum led_brightness brightness)
-+{
-+      struct qca8k_led *led = container_of(ldev, struct qca8k_led, cdev);
-+
-+      return qca8k_led_brightness_set(led, brightness);
-+}
-+
-+static enum led_brightness
-+qca8k_led_brightness_get(struct qca8k_led *led)
-+{
-+      struct qca8k_led_pattern_en reg_info;
-+      struct qca8k_priv *priv = led->priv;
-+      u32 val;
-+      int ret;
-+
-+      qca8k_get_enable_led_reg(led->port_num, led->led_num, &reg_info);
-+
-+      ret = regmap_read(priv->regmap, reg_info.reg, &val);
-+      if (ret)
-+              return 0;
-+
-+      val >>= reg_info.shift;
-+
-+      if (led->port_num == 0 || led->port_num == 4) {
-+              val &= QCA8K_LED_PATTERN_EN_MASK;
-+              val >>= QCA8K_LED_PATTERN_EN_SHIFT;
-+      } else {
-+              val &= QCA8K_LED_PHY123_PATTERN_EN_MASK;
-+      }
-+
-+      /* Assume brightness ON only when the LED is set to always ON */
-+      return val == QCA8K_LED_ALWAYS_ON;
-+}
-+
-+static int
-+qca8k_parse_port_leds(struct qca8k_priv *priv, struct fwnode_handle *port, int port_num)
-+{
-+      struct fwnode_handle *led = NULL, *leds = NULL;
-+      struct led_init_data init_data = { };
-+      struct dsa_switch *ds = priv->ds;
-+      enum led_default_state state;
-+      struct qca8k_led *port_led;
-+      int led_num, led_index;
-+      int ret;
-+
-+      leds = fwnode_get_named_child_node(port, "leds");
-+      if (!leds) {
-+              dev_dbg(priv->dev, "No Leds node specified in device tree for port %d!\n",
-+                      port_num);
-+              return 0;
-+      }
-+
-+      fwnode_for_each_child_node(leds, led) {
-+              /* Reg represent the led number of the port.
-+               * Each port can have at most 3 leds attached
-+               * Commonly:
-+               * 1. is gigabit led
-+               * 2. is mbit led
-+               * 3. additional status led
-+               */
-+              if (fwnode_property_read_u32(led, "reg", &led_num))
-+                      continue;
-+
-+              if (led_num >= QCA8K_LED_PORT_COUNT) {
-+                      dev_warn(priv->dev, "Invalid LED reg %d defined for port %d",
-+                               led_num, port_num);
-+                      continue;
-+              }
-+
-+              led_index = QCA8K_LED_PORT_INDEX(port_num, led_num);
-+
-+              port_led = &priv->ports_led[led_index];
-+              port_led->port_num = port_num;
-+              port_led->led_num = led_num;
-+              port_led->priv = priv;
-+
-+              state = led_init_default_state_get(led);
-+              switch (state) {
-+              case LEDS_DEFSTATE_ON:
-+                      port_led->cdev.brightness = 1;
-+                      qca8k_led_brightness_set(port_led, 1);
-+                      break;
-+              case LEDS_DEFSTATE_KEEP:
-+                      port_led->cdev.brightness =
-+                                      qca8k_led_brightness_get(port_led);
-+                      break;
-+              default:
-+                      port_led->cdev.brightness = 0;
-+                      qca8k_led_brightness_set(port_led, 0);
-+              }
-+
-+              port_led->cdev.max_brightness = 1;
-+              port_led->cdev.brightness_set_blocking = qca8k_cled_brightness_set_blocking;
-+              init_data.default_label = ":port";
-+              init_data.fwnode = led;
-+              init_data.devname_mandatory = true;
-+              init_data.devicename = kasprintf(GFP_KERNEL, "%s:0%d", ds->slave_mii_bus->id,
-+                                               port_num);
-+              if (!init_data.devicename)
-+                      return -ENOMEM;
-+
-+              ret = devm_led_classdev_register_ext(priv->dev, &port_led->cdev, &init_data);
-+              if (ret)
-+                      dev_warn(priv->dev, "Failed to init LED %d for port %d", led_num, port_num);
-+
-+              kfree(init_data.devicename);
-+      }
-+
-+      return 0;
-+}
-+
-+int
-+qca8k_setup_led_ctrl(struct qca8k_priv *priv)
-+{
-+      struct fwnode_handle *ports, *port;
-+      int port_num;
-+      int ret;
-+
-+      ports = device_get_named_child_node(priv->dev, "ports");
-+      if (!ports) {
-+              dev_info(priv->dev, "No ports node specified in device tree!");
-+              return 0;
-+      }
-+
-+      fwnode_for_each_child_node(ports, port) {
-+              if (fwnode_property_read_u32(port, "reg", &port_num))
-+                      continue;
-+
-+              /* Skip checking for CPU port 0 and CPU port 6 as not supported */
-+              if (port_num == 0 || port_num == 6)
-+                      continue;
-+
-+              /* Each port can have at most 3 different leds attached.
-+               * Switch port starts from 0 to 6, but port 0 and 6 are CPU
-+               * port. The port index needs to be decreased by one to identify
-+               * the correct port for LED setup.
-+               */
-+              ret = qca8k_parse_port_leds(priv, port, qca8k_port_to_phy(port_num));
-+              if (ret)
-+                      return ret;
-+      }
-+
-+      return 0;
-+}
---- a/drivers/net/dsa/qca/qca8k.h
-+++ b/drivers/net/dsa/qca/qca8k.h
-@@ -11,6 +11,7 @@
- #include <linux/delay.h>
- #include <linux/regmap.h>
- #include <linux/gpio.h>
-+#include <linux/leds.h>
- #include <linux/dsa/tag_qca.h>
- #define QCA8K_ETHERNET_MDIO_PRIORITY                  7
-@@ -85,6 +86,51 @@
- #define   QCA8K_MDIO_MASTER_DATA(x)                   FIELD_PREP(QCA8K_MDIO_MASTER_DATA_MASK, x)
- #define   QCA8K_MDIO_MASTER_MAX_PORTS                 5
- #define   QCA8K_MDIO_MASTER_MAX_REG                   32
-+
-+/* LED control register */
-+#define QCA8K_LED_PORT_COUNT                          3
-+#define QCA8K_LED_COUNT                                       ((QCA8K_NUM_PORTS - QCA8K_NUM_CPU_PORTS) * QCA8K_LED_PORT_COUNT)
-+#define QCA8K_LED_RULE_COUNT                          6
-+#define QCA8K_LED_RULE_MAX                            11
-+#define QCA8K_LED_PORT_INDEX(_phy, _led)              (((_phy) * QCA8K_LED_PORT_COUNT) + (_led))
-+
-+#define QCA8K_LED_PHY123_PATTERN_EN_SHIFT(_phy, _led) ((((_phy) - 1) * 6) + 8 + (2 * (_led)))
-+#define QCA8K_LED_PHY123_PATTERN_EN_MASK              GENMASK(1, 0)
-+
-+#define QCA8K_LED_PHY0123_CONTROL_RULE_SHIFT          0
-+#define QCA8K_LED_PHY4_CONTROL_RULE_SHIFT             16
-+
-+#define QCA8K_LED_CTRL_REG(_i)                                (0x050 + (_i) * 4)
-+#define QCA8K_LED_CTRL0_REG                           0x50
-+#define QCA8K_LED_CTRL1_REG                           0x54
-+#define QCA8K_LED_CTRL2_REG                           0x58
-+#define QCA8K_LED_CTRL3_REG                           0x5C
-+#define   QCA8K_LED_CTRL_SHIFT(_i)                    (((_i) % 2) * 16)
-+#define   QCA8K_LED_CTRL_MASK                         GENMASK(15, 0)
-+#define QCA8K_LED_RULE_MASK                           GENMASK(13, 0)
-+#define QCA8K_LED_BLINK_FREQ_MASK                     GENMASK(1, 0)
-+#define QCA8K_LED_BLINK_FREQ_SHITF                    0
-+#define   QCA8K_LED_BLINK_2HZ                         0
-+#define   QCA8K_LED_BLINK_4HZ                         1
-+#define   QCA8K_LED_BLINK_8HZ                         2
-+#define   QCA8K_LED_BLINK_AUTO                                3
-+#define QCA8K_LED_LINKUP_OVER_MASK                    BIT(2)
-+#define QCA8K_LED_TX_BLINK_MASK                               BIT(4)
-+#define QCA8K_LED_RX_BLINK_MASK                               BIT(5)
-+#define QCA8K_LED_COL_BLINK_MASK                      BIT(7)
-+#define QCA8K_LED_LINK_10M_EN_MASK                    BIT(8)
-+#define QCA8K_LED_LINK_100M_EN_MASK                   BIT(9)
-+#define QCA8K_LED_LINK_1000M_EN_MASK                  BIT(10)
-+#define QCA8K_LED_POWER_ON_LIGHT_MASK                 BIT(11)
-+#define QCA8K_LED_HALF_DUPLEX_MASK                    BIT(12)
-+#define QCA8K_LED_FULL_DUPLEX_MASK                    BIT(13)
-+#define QCA8K_LED_PATTERN_EN_MASK                     GENMASK(15, 14)
-+#define QCA8K_LED_PATTERN_EN_SHIFT                    14
-+#define   QCA8K_LED_ALWAYS_OFF                                0
-+#define   QCA8K_LED_ALWAYS_BLINK_4HZ                  1
-+#define   QCA8K_LED_ALWAYS_ON                         2
-+#define   QCA8K_LED_RULE_CONTROLLED                   3
-+
- #define QCA8K_GOL_MAC_ADDR0                           0x60
- #define QCA8K_GOL_MAC_ADDR1                           0x64
- #define QCA8K_MAX_FRAME_SIZE                          0x78
-@@ -377,6 +423,19 @@ struct qca8k_mdio_cache {
-       u16 page;
- };
-+struct qca8k_led_pattern_en {
-+      u32 reg;
-+      u8 shift;
-+};
-+
-+struct qca8k_led {
-+      u8 port_num;
-+      u8 led_num;
-+      u16 old_rule;
-+      struct qca8k_priv *priv;
-+      struct led_classdev cdev;
-+};
-+
- struct qca8k_priv {
-       u8 switch_id;
-       u8 switch_revision;
-@@ -399,6 +458,7 @@ struct qca8k_priv {
-       struct qca8k_mib_eth_data mib_eth_data;
-       struct qca8k_mdio_cache mdio_cache;
-       const struct qca8k_match_data *info;
-+      struct qca8k_led ports_led[QCA8K_LED_COUNT];
- };
- struct qca8k_mib_desc {
---- /dev/null
-+++ b/drivers/net/dsa/qca/qca8k_leds.h
-@@ -0,0 +1,16 @@
-+/* SPDX-License-Identifier: GPL-2.0-only */
-+
-+#ifndef __QCA8K_LEDS_H
-+#define __QCA8K_LEDS_H
-+
-+/* Leds Support function */
-+#ifdef CONFIG_NET_DSA_QCA8K_LEDS_SUPPORT
-+int qca8k_setup_led_ctrl(struct qca8k_priv *priv);
-+#else
-+static inline int qca8k_setup_led_ctrl(struct qca8k_priv *priv)
-+{
-+      return 0;
-+}
-+#endif
-+
-+#endif /* __QCA8K_LEDS_H */
diff --git a/target/linux/generic/backport-5.15/815-v6.4-03-net-dsa-qca8k-add-LEDs-blink_set-support.patch b/target/linux/generic/backport-5.15/815-v6.4-03-net-dsa-qca8k-add-LEDs-blink_set-support.patch
deleted file mode 100644 (file)
index 231c415..0000000
+++ /dev/null
@@ -1,74 +0,0 @@
-From 91acadcc6e599dfc62717abcdad58a459cfb1684 Mon Sep 17 00:00:00 2001
-From: Christian Marangi <[email protected]>
-Date: Mon, 17 Apr 2023 17:17:25 +0200
-Subject: [PATCH 3/9] net: dsa: qca8k: add LEDs blink_set() support
-
-Add LEDs blink_set() support to qca8k Switch Family.
-These LEDs support hw accellerated blinking at a fixed rate
-of 4Hz.
-
-Reject any other value since not supported by the LEDs switch.
-
-Signed-off-by: Christian Marangi <[email protected]>
-Reviewed-by: Andrew Lunn <[email protected]>
-Acked-by: Pavel Machek <[email protected]>
-Reviewed-by: Florian Fainelli <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/dsa/qca/qca8k-leds.c | 38 ++++++++++++++++++++++++++++++++
- 1 file changed, 38 insertions(+)
-
---- a/drivers/net/dsa/qca/qca8k-leds.c
-+++ b/drivers/net/dsa/qca/qca8k-leds.c
-@@ -128,6 +128,43 @@ qca8k_led_brightness_get(struct qca8k_le
- }
- static int
-+qca8k_cled_blink_set(struct led_classdev *ldev,
-+                   unsigned long *delay_on,
-+                   unsigned long *delay_off)
-+{
-+      struct qca8k_led *led = container_of(ldev, struct qca8k_led, cdev);
-+      u32 mask, val = QCA8K_LED_ALWAYS_BLINK_4HZ;
-+      struct qca8k_led_pattern_en reg_info;
-+      struct qca8k_priv *priv = led->priv;
-+
-+      if (*delay_on == 0 && *delay_off == 0) {
-+              *delay_on = 125;
-+              *delay_off = 125;
-+      }
-+
-+      if (*delay_on != 125 || *delay_off != 125) {
-+              /* The hardware only supports blinking at 4Hz. Fall back
-+               * to software implementation in other cases.
-+               */
-+              return -EINVAL;
-+      }
-+
-+      qca8k_get_enable_led_reg(led->port_num, led->led_num, &reg_info);
-+
-+      if (led->port_num == 0 || led->port_num == 4) {
-+              mask = QCA8K_LED_PATTERN_EN_MASK;
-+              val <<= QCA8K_LED_PATTERN_EN_SHIFT;
-+      } else {
-+              mask = QCA8K_LED_PHY123_PATTERN_EN_MASK;
-+      }
-+
-+      regmap_update_bits(priv->regmap, reg_info.reg, mask << reg_info.shift,
-+                         val << reg_info.shift);
-+
-+      return 0;
-+}
-+
-+static int
- qca8k_parse_port_leds(struct qca8k_priv *priv, struct fwnode_handle *port, int port_num)
- {
-       struct fwnode_handle *led = NULL, *leds = NULL;
-@@ -186,6 +223,7 @@ qca8k_parse_port_leds(struct qca8k_priv
-               port_led->cdev.max_brightness = 1;
-               port_led->cdev.brightness_set_blocking = qca8k_cled_brightness_set_blocking;
-+              port_led->cdev.blink_set = qca8k_cled_blink_set;
-               init_data.default_label = ":port";
-               init_data.fwnode = led;
-               init_data.devname_mandatory = true;
diff --git a/target/linux/generic/backport-5.15/815-v6.4-04-leds-Provide-stubs-for-when-CLASS_LED-NEW_LEDS-are-d.patch b/target/linux/generic/backport-5.15/815-v6.4-04-leds-Provide-stubs-for-when-CLASS_LED-NEW_LEDS-are-d.patch
deleted file mode 100644 (file)
index bc905b4..0000000
+++ /dev/null
@@ -1,59 +0,0 @@
-From e5029edd53937a29801ef507cee12e657ff31ea9 Mon Sep 17 00:00:00 2001
-From: Andrew Lunn <[email protected]>
-Date: Mon, 17 Apr 2023 17:17:26 +0200
-Subject: [PATCH 4/9] leds: Provide stubs for when CLASS_LED & NEW_LEDS are
- disabled
-
-Provide stubs for devm_led_classdev_register_ext() and
-led_init_default_state_get() so that LED drivers embedded within other
-drivers such as PHYs and Ethernet switches still build when LEDS_CLASS
-or NEW_LEDS are disabled. This also helps with Kconfig dependencies,
-which are somewhat hairy for phylib and mdio and only get worse when
-adding a dependency on LED_CLASS.
-
-Signed-off-by: Andrew Lunn <[email protected]>
-Signed-off-by: Christian Marangi <[email protected]>
-Reviewed-by: Florian Fainelli <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- include/linux/leds.h | 18 ++++++++++++++++++
- 1 file changed, 18 insertions(+)
-
---- a/include/linux/leds.h
-+++ b/include/linux/leds.h
-@@ -63,7 +63,15 @@ struct led_init_data {
-       bool devname_mandatory;
- };
-+#if IS_ENABLED(CONFIG_NEW_LEDS)
- enum led_default_state led_init_default_state_get(struct fwnode_handle *fwnode);
-+#else
-+static inline enum led_default_state
-+led_init_default_state_get(struct fwnode_handle *fwnode)
-+{
-+      return LEDS_DEFSTATE_OFF;
-+}
-+#endif
- struct led_hw_trigger_type {
-       int dummy;
-@@ -198,9 +206,19 @@ static inline int led_classdev_register(
-       return led_classdev_register_ext(parent, led_cdev, NULL);
- }
-+#if IS_ENABLED(CONFIG_LEDS_CLASS)
- int devm_led_classdev_register_ext(struct device *parent,
-                                         struct led_classdev *led_cdev,
-                                         struct led_init_data *init_data);
-+#else
-+static inline int
-+devm_led_classdev_register_ext(struct device *parent,
-+                             struct led_classdev *led_cdev,
-+                             struct led_init_data *init_data)
-+{
-+      return 0;
-+}
-+#endif
- static inline int devm_led_classdev_register(struct device *parent,
-                                            struct led_classdev *led_cdev)
diff --git a/target/linux/generic/backport-5.15/815-v6.4-05-net-phy-Add-a-binding-for-PHY-LEDs.patch b/target/linux/generic/backport-5.15/815-v6.4-05-net-phy-Add-a-binding-for-PHY-LEDs.patch
deleted file mode 100644 (file)
index 6e5ac8b..0000000
+++ /dev/null
@@ -1,191 +0,0 @@
-From 01e5b728e9e43ae444e0369695a5f72209906464 Mon Sep 17 00:00:00 2001
-From: Andrew Lunn <[email protected]>
-Date: Mon, 17 Apr 2023 17:17:27 +0200
-Subject: [PATCH 5/9] net: phy: Add a binding for PHY LEDs
-
-Define common binding parsing for all PHY drivers with LEDs using
-phylib. Parse the DT as part of the phy_probe and add LEDs to the
-linux LED class infrastructure. For the moment, provide a dummy
-brightness function, which will later be replaced with a call into the
-PHY driver. This allows testing since the LED core might otherwise
-reject an LED whose brightness cannot be set.
-
-Add a dependency on LED_CLASS. It either needs to be built in, or not
-enabled, since a modular build can result in linker errors.
-
-Signed-off-by: Andrew Lunn <[email protected]>
-Signed-off-by: Christian Marangi <[email protected]>
-Reviewed-by: Florian Fainelli <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/phy/Kconfig      |  1 +
- drivers/net/phy/phy_device.c | 76 ++++++++++++++++++++++++++++++++++++
- include/linux/phy.h          | 16 ++++++++
- 3 files changed, 93 insertions(+)
-
---- a/drivers/net/phy/Kconfig
-+++ b/drivers/net/phy/Kconfig
-@@ -18,6 +18,7 @@ menuconfig PHYLIB
-       depends on NETDEVICES
-       select MDIO_DEVICE
-       select MDIO_DEVRES
-+      depends on LEDS_CLASS || LEDS_CLASS=n
-       help
-         Ethernet controllers are usually attached to PHY
-         devices.  This option provides infrastructure for
---- a/drivers/net/phy/phy_device.c
-+++ b/drivers/net/phy/phy_device.c
-@@ -19,10 +19,12 @@
- #include <linux/interrupt.h>
- #include <linux/io.h>
- #include <linux/kernel.h>
-+#include <linux/list.h>
- #include <linux/mdio.h>
- #include <linux/mii.h>
- #include <linux/mm.h>
- #include <linux/module.h>
-+#include <linux/of.h>
- #include <linux/netdevice.h>
- #include <linux/phy.h>
- #include <linux/phy_led_triggers.h>
-@@ -641,6 +643,7 @@ struct phy_device *phy_device_create(str
-       device_initialize(&mdiodev->dev);
-       dev->state = PHY_DOWN;
-+      INIT_LIST_HEAD(&dev->leds);
-       mutex_init(&dev->lock);
-       INIT_DELAYED_WORK(&dev->state_queue, phy_state_machine);
-@@ -2942,6 +2945,74 @@ static bool phy_drv_supports_irq(struct
-       return phydrv->config_intr && phydrv->handle_interrupt;
- }
-+/* Dummy implementation until calls into PHY driver are added */
-+static int phy_led_set_brightness(struct led_classdev *led_cdev,
-+                                enum led_brightness value)
-+{
-+      return 0;
-+}
-+
-+static int of_phy_led(struct phy_device *phydev,
-+                    struct device_node *led)
-+{
-+      struct device *dev = &phydev->mdio.dev;
-+      struct led_init_data init_data = {};
-+      struct led_classdev *cdev;
-+      struct phy_led *phyled;
-+      int err;
-+
-+      phyled = devm_kzalloc(dev, sizeof(*phyled), GFP_KERNEL);
-+      if (!phyled)
-+              return -ENOMEM;
-+
-+      cdev = &phyled->led_cdev;
-+
-+      err = of_property_read_u8(led, "reg", &phyled->index);
-+      if (err)
-+              return err;
-+
-+      cdev->brightness_set_blocking = phy_led_set_brightness;
-+      cdev->max_brightness = 1;
-+      init_data.devicename = dev_name(&phydev->mdio.dev);
-+      init_data.fwnode = of_fwnode_handle(led);
-+      init_data.devname_mandatory = true;
-+
-+      err = devm_led_classdev_register_ext(dev, cdev, &init_data);
-+      if (err)
-+              return err;
-+
-+      list_add(&phyled->list, &phydev->leds);
-+
-+      return 0;
-+}
-+
-+static int of_phy_leds(struct phy_device *phydev)
-+{
-+      struct device_node *node = phydev->mdio.dev.of_node;
-+      struct device_node *leds, *led;
-+      int err;
-+
-+      if (!IS_ENABLED(CONFIG_OF_MDIO))
-+              return 0;
-+
-+      if (!node)
-+              return 0;
-+
-+      leds = of_get_child_by_name(node, "leds");
-+      if (!leds)
-+              return 0;
-+
-+      for_each_available_child_of_node(leds, led) {
-+              err = of_phy_led(phydev, led);
-+              if (err) {
-+                      of_node_put(led);
-+                      return err;
-+              }
-+      }
-+
-+      return 0;
-+}
-+
- /**
-  * fwnode_mdio_find_device - Given a fwnode, find the mdio_device
-  * @fwnode: pointer to the mdio_device's fwnode
-@@ -3120,6 +3191,11 @@ static int phy_probe(struct device *dev)
-       /* Set the state to READY by default */
-       phydev->state = PHY_READY;
-+      /* Get the LEDs from the device tree, and instantiate standard
-+       * LEDs for them.
-+       */
-+      err = of_phy_leds(phydev);
-+
- out:
-       /* Re-assert the reset signal on error */
-       if (err)
---- a/include/linux/phy.h
-+++ b/include/linux/phy.h
-@@ -14,6 +14,7 @@
- #include <linux/compiler.h>
- #include <linux/spinlock.h>
- #include <linux/ethtool.h>
-+#include <linux/leds.h>
- #include <linux/linkmode.h>
- #include <linux/netlink.h>
- #include <linux/mdio.h>
-@@ -590,6 +591,7 @@ struct macsec_ops;
-  * @phy_num_led_triggers: Number of triggers in @phy_led_triggers
-  * @led_link_trigger: LED trigger for link up/down
-  * @last_triggered: last LED trigger for link speed
-+ * @leds: list of PHY LED structures
-  * @master_slave_set: User requested master/slave configuration
-  * @master_slave_get: Current master/slave advertisement
-  * @master_slave_state: Current master/slave configuration
-@@ -678,6 +680,7 @@ struct phy_device {
-       struct phy_led_trigger *led_link_trigger;
- #endif
-+      struct list_head leds;
-       /*
-        * Interrupt number for this PHY
-@@ -749,6 +752,19 @@ struct phy_tdr_config {
- #define PHY_PAIR_ALL -1
- /**
-+ * struct phy_led: An LED driven by the PHY
-+ *
-+ * @list: List of LEDs
-+ * @led_cdev: Standard LED class structure
-+ * @index: Number of the LED
-+ */
-+struct phy_led {
-+      struct list_head list;
-+      struct led_classdev led_cdev;
-+      u8 index;
-+};
-+
-+/**
-  * struct phy_driver - Driver structure for a particular PHY type
-  *
-  * @mdiodrv: Data common to all MDIO devices
diff --git a/target/linux/generic/backport-5.15/815-v6.4-06-net-phy-phy_device-Call-into-the-PHY-driver-to-set-L.patch b/target/linux/generic/backport-5.15/815-v6.4-06-net-phy-phy_device-Call-into-the-PHY-driver-to-set-L.patch
deleted file mode 100644 (file)
index 3968a88..0000000
+++ /dev/null
@@ -1,97 +0,0 @@
-From 684818189b04b095b34964ed4a3ea5249a840eab Mon Sep 17 00:00:00 2001
-From: Andrew Lunn <[email protected]>
-Date: Mon, 17 Apr 2023 17:17:28 +0200
-Subject: [PATCH 6/9] net: phy: phy_device: Call into the PHY driver to set LED
- brightness
-
-Linux LEDs can be software controlled via the brightness file in /sys.
-LED drivers need to implement a brightness_set function which the core
-will call. Implement an intermediary in phy_device, which will call
-into the phy driver if it implements the necessary function.
-
-Signed-off-by: Andrew Lunn <[email protected]>
-Signed-off-by: Christian Marangi <[email protected]>
-Reviewed-by: Florian Fainelli <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/phy/phy_device.c | 15 ++++++++++++---
- include/linux/phy.h          | 13 +++++++++++++
- 2 files changed, 25 insertions(+), 3 deletions(-)
-
---- a/drivers/net/phy/phy_device.c
-+++ b/drivers/net/phy/phy_device.c
-@@ -2945,11 +2945,18 @@ static bool phy_drv_supports_irq(struct
-       return phydrv->config_intr && phydrv->handle_interrupt;
- }
--/* Dummy implementation until calls into PHY driver are added */
- static int phy_led_set_brightness(struct led_classdev *led_cdev,
-                                 enum led_brightness value)
- {
--      return 0;
-+      struct phy_led *phyled = to_phy_led(led_cdev);
-+      struct phy_device *phydev = phyled->phydev;
-+      int err;
-+
-+      mutex_lock(&phydev->lock);
-+      err = phydev->drv->led_brightness_set(phydev, phyled->index, value);
-+      mutex_unlock(&phydev->lock);
-+
-+      return err;
- }
- static int of_phy_led(struct phy_device *phydev,
-@@ -2966,12 +2973,14 @@ static int of_phy_led(struct phy_device
-               return -ENOMEM;
-       cdev = &phyled->led_cdev;
-+      phyled->phydev = phydev;
-       err = of_property_read_u8(led, "reg", &phyled->index);
-       if (err)
-               return err;
--      cdev->brightness_set_blocking = phy_led_set_brightness;
-+      if (phydev->drv->led_brightness_set)
-+              cdev->brightness_set_blocking = phy_led_set_brightness;
-       cdev->max_brightness = 1;
-       init_data.devicename = dev_name(&phydev->mdio.dev);
-       init_data.fwnode = of_fwnode_handle(led);
---- a/include/linux/phy.h
-+++ b/include/linux/phy.h
-@@ -755,15 +755,19 @@ struct phy_tdr_config {
-  * struct phy_led: An LED driven by the PHY
-  *
-  * @list: List of LEDs
-+ * @phydev: PHY this LED is attached to
-  * @led_cdev: Standard LED class structure
-  * @index: Number of the LED
-  */
- struct phy_led {
-       struct list_head list;
-+      struct phy_device *phydev;
-       struct led_classdev led_cdev;
-       u8 index;
- };
-+#define to_phy_led(d) container_of(d, struct phy_led, led_cdev)
-+
- /**
-  * struct phy_driver - Driver structure for a particular PHY type
-  *
-@@ -978,6 +982,15 @@ struct phy_driver {
-       int (*get_sqi)(struct phy_device *dev);
-       /** @get_sqi_max: Get the maximum signal quality indication */
-       int (*get_sqi_max)(struct phy_device *dev);
-+
-+      /**
-+       * @led_brightness_set: Set a PHY LED brightness. Index
-+       * indicates which of the PHYs led should be set. Value
-+       * follows the standard LED class meaning, e.g. LED_OFF,
-+       * LED_HALF, LED_FULL.
-+       */
-+      int (*led_brightness_set)(struct phy_device *dev,
-+                                u8 index, enum led_brightness value);
- };
- #define to_phy_driver(d) container_of(to_mdio_common_driver(d),               \
-                                     struct phy_driver, mdiodrv)
diff --git a/target/linux/generic/backport-5.15/815-v6.4-07-net-phy-marvell-Add-software-control-of-the-LEDs.patch b/target/linux/generic/backport-5.15/815-v6.4-07-net-phy-marvell-Add-software-control-of-the-LEDs.patch
deleted file mode 100644 (file)
index 053288c..0000000
+++ /dev/null
@@ -1,112 +0,0 @@
-From 2d3960e58ef7c83fe1dbf952f056b9e906cb6df8 Mon Sep 17 00:00:00 2001
-From: Andrew Lunn <[email protected]>
-Date: Mon, 17 Apr 2023 17:17:29 +0200
-Subject: [PATCH 7/9] net: phy: marvell: Add software control of the LEDs
-
-Add a brightness function, so the LEDs can be controlled from
-software using the standard Linux LED infrastructure.
-
-Signed-off-by: Andrew Lunn <[email protected]>
-Signed-off-by: Christian Marangi <[email protected]>
-Reviewed-by: Florian Fainelli <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/phy/marvell.c | 45 ++++++++++++++++++++++++++++++++++-----
- 1 file changed, 40 insertions(+), 5 deletions(-)
-
---- a/drivers/net/phy/marvell.c
-+++ b/drivers/net/phy/marvell.c
-@@ -144,11 +144,13 @@
- /* WOL Event Interrupt Enable */
- #define MII_88E1318S_PHY_CSIER_WOL_EIE                        BIT(7)
--/* LED Timer Control Register */
--#define MII_88E1318S_PHY_LED_TCR                      0x12
--#define MII_88E1318S_PHY_LED_TCR_FORCE_INT            BIT(15)
--#define MII_88E1318S_PHY_LED_TCR_INTn_ENABLE          BIT(7)
--#define MII_88E1318S_PHY_LED_TCR_INT_ACTIVE_LOW               BIT(11)
-+#define MII_88E1318S_PHY_LED_FUNC             0x10
-+#define MII_88E1318S_PHY_LED_FUNC_OFF         (0x8)
-+#define MII_88E1318S_PHY_LED_FUNC_ON          (0x9)
-+#define MII_88E1318S_PHY_LED_TCR              0x12
-+#define MII_88E1318S_PHY_LED_TCR_FORCE_INT    BIT(15)
-+#define MII_88E1318S_PHY_LED_TCR_INTn_ENABLE  BIT(7)
-+#define MII_88E1318S_PHY_LED_TCR_INT_ACTIVE_LOW       BIT(11)
- /* Magic Packet MAC address registers */
- #define MII_88E1318S_PHY_MAGIC_PACKET_WORD2           0x17
-@@ -2793,6 +2795,34 @@ static int marvell_hwmon_probe(struct ph
- }
- #endif
-+static int m88e1318_led_brightness_set(struct phy_device *phydev,
-+                                     u8 index, enum led_brightness value)
-+{
-+      int reg;
-+
-+      reg = phy_read_paged(phydev, MII_MARVELL_LED_PAGE,
-+                           MII_88E1318S_PHY_LED_FUNC);
-+      if (reg < 0)
-+              return reg;
-+
-+      switch (index) {
-+      case 0:
-+      case 1:
-+      case 2:
-+              reg &= ~(0xf << (4 * index));
-+              if (value == LED_OFF)
-+                      reg |= MII_88E1318S_PHY_LED_FUNC_OFF << (4 * index);
-+              else
-+                      reg |= MII_88E1318S_PHY_LED_FUNC_ON << (4 * index);
-+              break;
-+      default:
-+              return -EINVAL;
-+      }
-+
-+      return phy_write_paged(phydev, MII_MARVELL_LED_PAGE,
-+                             MII_88E1318S_PHY_LED_FUNC, reg);
-+}
-+
- static int marvell_probe(struct phy_device *phydev)
- {
-       struct marvell_priv *priv;
-@@ -3041,6 +3071,7 @@ static struct phy_driver marvell_drivers
-               .get_sset_count = marvell_get_sset_count,
-               .get_strings = marvell_get_strings,
-               .get_stats = marvell_get_stats,
-+              .led_brightness_set = m88e1318_led_brightness_set,
-       },
-       {
-               .phy_id = MARVELL_PHY_ID_88E1145,
-@@ -3147,6 +3178,7 @@ static struct phy_driver marvell_drivers
-               .cable_test_start = marvell_vct7_cable_test_start,
-               .cable_test_tdr_start = marvell_vct5_cable_test_tdr_start,
-               .cable_test_get_status = marvell_vct7_cable_test_get_status,
-+              .led_brightness_set = m88e1318_led_brightness_set,
-       },
-       {
-               .phy_id = MARVELL_PHY_ID_88E1540,
-@@ -3173,6 +3205,7 @@ static struct phy_driver marvell_drivers
-               .cable_test_start = marvell_vct7_cable_test_start,
-               .cable_test_tdr_start = marvell_vct5_cable_test_tdr_start,
-               .cable_test_get_status = marvell_vct7_cable_test_get_status,
-+              .led_brightness_set = m88e1318_led_brightness_set,
-       },
-       {
-               .phy_id = MARVELL_PHY_ID_88E1545,
-@@ -3199,6 +3232,7 @@ static struct phy_driver marvell_drivers
-               .cable_test_start = marvell_vct7_cable_test_start,
-               .cable_test_tdr_start = marvell_vct5_cable_test_tdr_start,
-               .cable_test_get_status = marvell_vct7_cable_test_get_status,
-+              .led_brightness_set = m88e1318_led_brightness_set,
-       },
-       {
-               .phy_id = MARVELL_PHY_ID_88E3016,
-@@ -3340,6 +3374,7 @@ static struct phy_driver marvell_drivers
-               .get_stats = marvell_get_stats,
-               .get_tunable = m88e1540_get_tunable,
-               .set_tunable = m88e1540_set_tunable,
-+              .led_brightness_set = m88e1318_led_brightness_set,
-       },
- };
diff --git a/target/linux/generic/backport-5.15/815-v6.4-08-net-phy-phy_device-Call-into-the-PHY-driver-to-set-L.patch b/target/linux/generic/backport-5.15/815-v6.4-08-net-phy-phy_device-Call-into-the-PHY-driver-to-set-L.patch
deleted file mode 100644 (file)
index 35e1a1c..0000000
+++ /dev/null
@@ -1,73 +0,0 @@
-From 4e901018432e38eab35d2a352661ce4727795be1 Mon Sep 17 00:00:00 2001
-From: Andrew Lunn <[email protected]>
-Date: Mon, 17 Apr 2023 17:17:30 +0200
-Subject: [PATCH 8/9] net: phy: phy_device: Call into the PHY driver to set LED
- blinking
-
-Linux LEDs can be requested to perform hardware accelerated
-blinking. Pass this to the PHY driver, if it implements the op.
-
-Signed-off-by: Andrew Lunn <[email protected]>
-Signed-off-by: Christian Marangi <[email protected]>
-Reviewed-by: Florian Fainelli <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/phy/phy_device.c | 18 ++++++++++++++++++
- include/linux/phy.h          | 12 ++++++++++++
- 2 files changed, 30 insertions(+)
-
---- a/drivers/net/phy/phy_device.c
-+++ b/drivers/net/phy/phy_device.c
-@@ -2959,6 +2959,22 @@ static int phy_led_set_brightness(struct
-       return err;
- }
-+static int phy_led_blink_set(struct led_classdev *led_cdev,
-+                           unsigned long *delay_on,
-+                           unsigned long *delay_off)
-+{
-+      struct phy_led *phyled = to_phy_led(led_cdev);
-+      struct phy_device *phydev = phyled->phydev;
-+      int err;
-+
-+      mutex_lock(&phydev->lock);
-+      err = phydev->drv->led_blink_set(phydev, phyled->index,
-+                                       delay_on, delay_off);
-+      mutex_unlock(&phydev->lock);
-+
-+      return err;
-+}
-+
- static int of_phy_led(struct phy_device *phydev,
-                     struct device_node *led)
- {
-@@ -2981,6 +2997,8 @@ static int of_phy_led(struct phy_device
-       if (phydev->drv->led_brightness_set)
-               cdev->brightness_set_blocking = phy_led_set_brightness;
-+      if (phydev->drv->led_blink_set)
-+              cdev->blink_set = phy_led_blink_set;
-       cdev->max_brightness = 1;
-       init_data.devicename = dev_name(&phydev->mdio.dev);
-       init_data.fwnode = of_fwnode_handle(led);
---- a/include/linux/phy.h
-+++ b/include/linux/phy.h
-@@ -991,6 +991,18 @@ struct phy_driver {
-        */
-       int (*led_brightness_set)(struct phy_device *dev,
-                                 u8 index, enum led_brightness value);
-+
-+      /**
-+       * @led_blink_set: Set a PHY LED brightness.  Index indicates
-+       * which of the PHYs led should be configured to blink. Delays
-+       * are in milliseconds and if both are zero then a sensible
-+       * default should be chosen.  The call should adjust the
-+       * timings in that case and if it can't match the values
-+       * specified exactly.
-+       */
-+      int (*led_blink_set)(struct phy_device *dev, u8 index,
-+                           unsigned long *delay_on,
-+                           unsigned long *delay_off);
- };
- #define to_phy_driver(d) container_of(to_mdio_common_driver(d),               \
-                                     struct phy_driver, mdiodrv)
diff --git a/target/linux/generic/backport-5.15/815-v6.4-09-net-phy-marvell-Implement-led_blink_set.patch b/target/linux/generic/backport-5.15/815-v6.4-09-net-phy-marvell-Implement-led_blink_set.patch
deleted file mode 100644 (file)
index 0f258c6..0000000
+++ /dev/null
@@ -1,104 +0,0 @@
-From ea9e86485decb2ac1750005bd96c166c9b780406 Mon Sep 17 00:00:00 2001
-From: Andrew Lunn <[email protected]>
-Date: Mon, 17 Apr 2023 17:17:31 +0200
-Subject: [PATCH 9/9] net: phy: marvell: Implement led_blink_set()
-
-The Marvell PHY can blink the LEDs, simple on/off. All LEDs blink at
-the same rate, and the reset default is 84ms per blink, which is
-around 12Hz.
-
-Signed-off-by: Andrew Lunn <[email protected]>
-Signed-off-by: Christian Marangi <[email protected]>
-Reviewed-by: Florian Fainelli <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/phy/marvell.c | 36 ++++++++++++++++++++++++++++++++++++
- 1 file changed, 36 insertions(+)
-
---- a/drivers/net/phy/marvell.c
-+++ b/drivers/net/phy/marvell.c
-@@ -147,6 +147,8 @@
- #define MII_88E1318S_PHY_LED_FUNC             0x10
- #define MII_88E1318S_PHY_LED_FUNC_OFF         (0x8)
- #define MII_88E1318S_PHY_LED_FUNC_ON          (0x9)
-+#define MII_88E1318S_PHY_LED_FUNC_HI_Z                (0xa)
-+#define MII_88E1318S_PHY_LED_FUNC_BLINK               (0xb)
- #define MII_88E1318S_PHY_LED_TCR              0x12
- #define MII_88E1318S_PHY_LED_TCR_FORCE_INT    BIT(15)
- #define MII_88E1318S_PHY_LED_TCR_INTn_ENABLE  BIT(7)
-@@ -2823,6 +2825,35 @@ static int m88e1318_led_brightness_set(s
-                              MII_88E1318S_PHY_LED_FUNC, reg);
- }
-+static int m88e1318_led_blink_set(struct phy_device *phydev, u8 index,
-+                                unsigned long *delay_on,
-+                                unsigned long *delay_off)
-+{
-+      int reg;
-+
-+      reg = phy_read_paged(phydev, MII_MARVELL_LED_PAGE,
-+                           MII_88E1318S_PHY_LED_FUNC);
-+      if (reg < 0)
-+              return reg;
-+
-+      switch (index) {
-+      case 0:
-+      case 1:
-+      case 2:
-+              reg &= ~(0xf << (4 * index));
-+                      reg |= MII_88E1318S_PHY_LED_FUNC_BLINK << (4 * index);
-+                      /* Reset default is 84ms */
-+                      *delay_on = 84 / 2;
-+                      *delay_off = 84 / 2;
-+              break;
-+      default:
-+              return -EINVAL;
-+      }
-+
-+      return phy_write_paged(phydev, MII_MARVELL_LED_PAGE,
-+                             MII_88E1318S_PHY_LED_FUNC, reg);
-+}
-+
- static int marvell_probe(struct phy_device *phydev)
- {
-       struct marvell_priv *priv;
-@@ -3072,6 +3103,7 @@ static struct phy_driver marvell_drivers
-               .get_strings = marvell_get_strings,
-               .get_stats = marvell_get_stats,
-               .led_brightness_set = m88e1318_led_brightness_set,
-+              .led_blink_set = m88e1318_led_blink_set,
-       },
-       {
-               .phy_id = MARVELL_PHY_ID_88E1145,
-@@ -3179,6 +3211,7 @@ static struct phy_driver marvell_drivers
-               .cable_test_tdr_start = marvell_vct5_cable_test_tdr_start,
-               .cable_test_get_status = marvell_vct7_cable_test_get_status,
-               .led_brightness_set = m88e1318_led_brightness_set,
-+              .led_blink_set = m88e1318_led_blink_set,
-       },
-       {
-               .phy_id = MARVELL_PHY_ID_88E1540,
-@@ -3206,6 +3239,7 @@ static struct phy_driver marvell_drivers
-               .cable_test_tdr_start = marvell_vct5_cable_test_tdr_start,
-               .cable_test_get_status = marvell_vct7_cable_test_get_status,
-               .led_brightness_set = m88e1318_led_brightness_set,
-+              .led_blink_set = m88e1318_led_blink_set,
-       },
-       {
-               .phy_id = MARVELL_PHY_ID_88E1545,
-@@ -3233,6 +3267,7 @@ static struct phy_driver marvell_drivers
-               .cable_test_tdr_start = marvell_vct5_cable_test_tdr_start,
-               .cable_test_get_status = marvell_vct7_cable_test_get_status,
-               .led_brightness_set = m88e1318_led_brightness_set,
-+              .led_blink_set = m88e1318_led_blink_set,
-       },
-       {
-               .phy_id = MARVELL_PHY_ID_88E3016,
-@@ -3375,6 +3410,7 @@ static struct phy_driver marvell_drivers
-               .get_tunable = m88e1540_get_tunable,
-               .set_tunable = m88e1540_set_tunable,
-               .led_brightness_set = m88e1318_led_brightness_set,
-+              .led_blink_set = m88e1318_led_blink_set,
-       },
- };
diff --git a/target/linux/generic/backport-5.15/816-v6.4-net-phy-marvell-Fix-inconsistent-indenting-in-led_bl.patch b/target/linux/generic/backport-5.15/816-v6.4-net-phy-marvell-Fix-inconsistent-indenting-in-led_bl.patch
deleted file mode 100644 (file)
index c5b611a..0000000
+++ /dev/null
@@ -1,38 +0,0 @@
-From 4774ad841bef97cc51df90195338c5b2573dd4cb Mon Sep 17 00:00:00 2001
-From: Christian Marangi <[email protected]>
-Date: Sun, 23 Apr 2023 19:28:00 +0200
-Subject: [PATCH] net: phy: marvell: Fix inconsistent indenting in
- led_blink_set
-
-Fix inconsistent indeinting in m88e1318_led_blink_set reported by kernel
-test robot, probably done by the presence of an if condition dropped in
-later revision of the same code.
-
-Reported-by: kernel test robot <[email protected]>
-Link: https://lore.kernel.org/oe-kbuild-all/[email protected]/
-Fixes: ea9e86485dec ("net: phy: marvell: Implement led_blink_set()")
-Signed-off-by: Christian Marangi <[email protected]>
-Reviewed-by: Andrew Lunn <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- drivers/net/phy/marvell.c | 8 ++++----
- 1 file changed, 4 insertions(+), 4 deletions(-)
-
---- a/drivers/net/phy/marvell.c
-+++ b/drivers/net/phy/marvell.c
-@@ -2841,10 +2841,10 @@ static int m88e1318_led_blink_set(struct
-       case 1:
-       case 2:
-               reg &= ~(0xf << (4 * index));
--                      reg |= MII_88E1318S_PHY_LED_FUNC_BLINK << (4 * index);
--                      /* Reset default is 84ms */
--                      *delay_on = 84 / 2;
--                      *delay_off = 84 / 2;
-+              reg |= MII_88E1318S_PHY_LED_FUNC_BLINK << (4 * index);
-+              /* Reset default is 84ms */
-+              *delay_on = 84 / 2;
-+              *delay_off = 84 / 2;
-               break;
-       default:
-               return -EINVAL;
diff --git a/target/linux/generic/backport-5.15/817-v6.5-02-leds-trigger-netdev-Drop-NETDEV_LED_MODE_LINKUP-from.patch b/target/linux/generic/backport-5.15/817-v6.5-02-leds-trigger-netdev-Drop-NETDEV_LED_MODE_LINKUP-from.patch
deleted file mode 100644 (file)
index 3170c26..0000000
+++ /dev/null
@@ -1,87 +0,0 @@
-From e2f24cb1b5daf9a4f6f3ba574c1fa74aab9807a4 Mon Sep 17 00:00:00 2001
-From: Christian Marangi <[email protected]>
-Date: Wed, 19 Apr 2023 23:07:40 +0200
-Subject: [PATCH 2/5] leds: trigger: netdev: Drop NETDEV_LED_MODE_LINKUP from
- mode
-
-Putting NETDEV_LED_MODE_LINKUP in the same list of the netdev trigger
-modes is wrong as it's used to set the link state of the device and not
-to set a blink mode as it's done by NETDEV_LED_LINK, NETDEV_LED_TX and
-NETDEV_LED_RX. It's also wrong to put this state in the same bitmap of the
-netdev trigger mode and should be external to it.
-
-Drop NETDEV_LED_MODE_LINKUP from mode list and convert to a simple bool
-that will be true or false based on the carrier link. No functional
-change intended.
-
-Signed-off-by: Christian Marangi <[email protected]>
-Reviewed-by: Andrew Lunn <[email protected]>
-Signed-off-by: Lee Jones <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
----
- drivers/leds/trigger/ledtrig-netdev.c | 19 ++++++++-----------
- 1 file changed, 8 insertions(+), 11 deletions(-)
-
---- a/drivers/leds/trigger/ledtrig-netdev.c
-+++ b/drivers/leds/trigger/ledtrig-netdev.c
-@@ -50,10 +50,10 @@ struct led_netdev_data {
-       unsigned int last_activity;
-       unsigned long mode;
-+      bool carrier_link_up;
- #define NETDEV_LED_LINK       0
- #define NETDEV_LED_TX 1
- #define NETDEV_LED_RX 2
--#define NETDEV_LED_MODE_LINKUP        3
- };
- enum netdev_led_attr {
-@@ -73,9 +73,9 @@ static void set_baseline_state(struct le
-       if (!led_cdev->blink_brightness)
-               led_cdev->blink_brightness = led_cdev->max_brightness;
--      if (!test_bit(NETDEV_LED_MODE_LINKUP, &trigger_data->mode))
-+      if (!trigger_data->carrier_link_up) {
-               led_set_brightness(led_cdev, LED_OFF);
--      else {
-+      } else {
-               if (test_bit(NETDEV_LED_LINK, &trigger_data->mode))
-                       led_set_brightness(led_cdev,
-                                          led_cdev->blink_brightness);
-@@ -131,10 +131,9 @@ static ssize_t device_name_store(struct
-               trigger_data->net_dev =
-                   dev_get_by_name(&init_net, trigger_data->device_name);
--      clear_bit(NETDEV_LED_MODE_LINKUP, &trigger_data->mode);
-+      trigger_data->carrier_link_up = false;
-       if (trigger_data->net_dev != NULL)
--              if (netif_carrier_ok(trigger_data->net_dev))
--                      set_bit(NETDEV_LED_MODE_LINKUP, &trigger_data->mode);
-+              trigger_data->carrier_link_up = netif_carrier_ok(trigger_data->net_dev);
-       trigger_data->last_activity = 0;
-@@ -315,11 +314,10 @@ static int netdev_trig_notify(struct not
-       spin_lock_bh(&trigger_data->lock);
--      clear_bit(NETDEV_LED_MODE_LINKUP, &trigger_data->mode);
-+      trigger_data->carrier_link_up = false;
-       switch (evt) {
-       case NETDEV_CHANGENAME:
--              if (netif_carrier_ok(dev))
--                      set_bit(NETDEV_LED_MODE_LINKUP, &trigger_data->mode);
-+              trigger_data->carrier_link_up = netif_carrier_ok(dev);
-               fallthrough;
-       case NETDEV_REGISTER:
-               if (trigger_data->net_dev)
-@@ -333,8 +331,7 @@ static int netdev_trig_notify(struct not
-               break;
-       case NETDEV_UP:
-       case NETDEV_CHANGE:
--              if (netif_carrier_ok(dev))
--                      set_bit(NETDEV_LED_MODE_LINKUP, &trigger_data->mode);
-+              trigger_data->carrier_link_up = netif_carrier_ok(dev);
-               break;
-       }
diff --git a/target/linux/generic/backport-5.15/817-v6.5-03-leds-trigger-netdev-Rename-add-namespace-to-netdev-t.patch b/target/linux/generic/backport-5.15/817-v6.5-03-leds-trigger-netdev-Rename-add-namespace-to-netdev-t.patch
deleted file mode 100644 (file)
index 19cc1d7..0000000
+++ /dev/null
@@ -1,149 +0,0 @@
-From bdec9cb83936e0ac4cb87fed5b49fad0175f7dec Mon Sep 17 00:00:00 2001
-From: Christian Marangi <[email protected]>
-Date: Wed, 19 Apr 2023 23:07:41 +0200
-Subject: [PATCH 3/5] leds: trigger: netdev: Rename add namespace to netdev
- trigger enum modes
-
-Rename NETDEV trigger enum modes to a more symbolic name and add a
-namespace to them.
-
-Also add __TRIGGER_NETDEV_MAX to identify the max modes of the netdev
-trigger.
-
-This is a cleanup to drop the define and no behaviour change are
-intended.
-
-Signed-off-by: Christian Marangi <[email protected]>
-Reviewed-by: Andrew Lunn <[email protected]>
-Signed-off-by: Lee Jones <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
----
- drivers/leds/trigger/ledtrig-netdev.c | 58 ++++++++++++---------------
- 1 file changed, 25 insertions(+), 33 deletions(-)
-
---- a/drivers/leds/trigger/ledtrig-netdev.c
-+++ b/drivers/leds/trigger/ledtrig-netdev.c
-@@ -51,15 +51,15 @@ struct led_netdev_data {
-       unsigned long mode;
-       bool carrier_link_up;
--#define NETDEV_LED_LINK       0
--#define NETDEV_LED_TX 1
--#define NETDEV_LED_RX 2
- };
--enum netdev_led_attr {
--      NETDEV_ATTR_LINK,
--      NETDEV_ATTR_TX,
--      NETDEV_ATTR_RX
-+enum led_trigger_netdev_modes {
-+      TRIGGER_NETDEV_LINK = 0,
-+      TRIGGER_NETDEV_TX,
-+      TRIGGER_NETDEV_RX,
-+
-+      /* Keep last */
-+      __TRIGGER_NETDEV_MAX,
- };
- static void set_baseline_state(struct led_netdev_data *trigger_data)
-@@ -76,7 +76,7 @@ static void set_baseline_state(struct le
-       if (!trigger_data->carrier_link_up) {
-               led_set_brightness(led_cdev, LED_OFF);
-       } else {
--              if (test_bit(NETDEV_LED_LINK, &trigger_data->mode))
-+              if (test_bit(TRIGGER_NETDEV_LINK, &trigger_data->mode))
-                       led_set_brightness(led_cdev,
-                                          led_cdev->blink_brightness);
-               else
-@@ -85,8 +85,8 @@ static void set_baseline_state(struct le
-               /* If we are looking for RX/TX start periodically
-                * checking stats
-                */
--              if (test_bit(NETDEV_LED_TX, &trigger_data->mode) ||
--                  test_bit(NETDEV_LED_RX, &trigger_data->mode))
-+              if (test_bit(TRIGGER_NETDEV_TX, &trigger_data->mode) ||
-+                  test_bit(TRIGGER_NETDEV_RX, &trigger_data->mode))
-                       schedule_delayed_work(&trigger_data->work, 0);
-       }
- }
-@@ -146,20 +146,16 @@ static ssize_t device_name_store(struct
- static DEVICE_ATTR_RW(device_name);
- static ssize_t netdev_led_attr_show(struct device *dev, char *buf,
--      enum netdev_led_attr attr)
-+                                  enum led_trigger_netdev_modes attr)
- {
-       struct led_netdev_data *trigger_data = led_trigger_get_drvdata(dev);
-       int bit;
-       switch (attr) {
--      case NETDEV_ATTR_LINK:
--              bit = NETDEV_LED_LINK;
--              break;
--      case NETDEV_ATTR_TX:
--              bit = NETDEV_LED_TX;
--              break;
--      case NETDEV_ATTR_RX:
--              bit = NETDEV_LED_RX;
-+      case TRIGGER_NETDEV_LINK:
-+      case TRIGGER_NETDEV_TX:
-+      case TRIGGER_NETDEV_RX:
-+              bit = attr;
-               break;
-       default:
-               return -EINVAL;
-@@ -169,7 +165,7 @@ static ssize_t netdev_led_attr_show(stru
- }
- static ssize_t netdev_led_attr_store(struct device *dev, const char *buf,
--      size_t size, enum netdev_led_attr attr)
-+                                   size_t size, enum led_trigger_netdev_modes attr)
- {
-       struct led_netdev_data *trigger_data = led_trigger_get_drvdata(dev);
-       unsigned long state;
-@@ -181,14 +177,10 @@ static ssize_t netdev_led_attr_store(str
-               return ret;
-       switch (attr) {
--      case NETDEV_ATTR_LINK:
--              bit = NETDEV_LED_LINK;
--              break;
--      case NETDEV_ATTR_TX:
--              bit = NETDEV_LED_TX;
--              break;
--      case NETDEV_ATTR_RX:
--              bit = NETDEV_LED_RX;
-+      case TRIGGER_NETDEV_LINK:
-+      case TRIGGER_NETDEV_TX:
-+      case TRIGGER_NETDEV_RX:
-+              bit = attr;
-               break;
-       default:
-               return -EINVAL;
-@@ -360,21 +352,21 @@ static void netdev_trig_work(struct work
-       }
-       /* If we are not looking for RX/TX then return  */
--      if (!test_bit(NETDEV_LED_TX, &trigger_data->mode) &&
--          !test_bit(NETDEV_LED_RX, &trigger_data->mode))
-+      if (!test_bit(TRIGGER_NETDEV_TX, &trigger_data->mode) &&
-+          !test_bit(TRIGGER_NETDEV_RX, &trigger_data->mode))
-               return;
-       dev_stats = dev_get_stats(trigger_data->net_dev, &temp);
-       new_activity =
--          (test_bit(NETDEV_LED_TX, &trigger_data->mode) ?
-+          (test_bit(TRIGGER_NETDEV_TX, &trigger_data->mode) ?
-               dev_stats->tx_packets : 0) +
--          (test_bit(NETDEV_LED_RX, &trigger_data->mode) ?
-+          (test_bit(TRIGGER_NETDEV_RX, &trigger_data->mode) ?
-               dev_stats->rx_packets : 0);
-       if (trigger_data->last_activity != new_activity) {
-               led_stop_software_blink(trigger_data->led_cdev);
--              invert = test_bit(NETDEV_LED_LINK, &trigger_data->mode);
-+              invert = test_bit(TRIGGER_NETDEV_LINK, &trigger_data->mode);
-               interval = jiffies_to_msecs(
-                               atomic_read(&trigger_data->interval));
-               /* base state is ON (link present) */
diff --git a/target/linux/generic/backport-5.15/817-v6.5-04-leds-trigger-netdev-Convert-device-attr-to-macro.patch b/target/linux/generic/backport-5.15/817-v6.5-04-leds-trigger-netdev-Convert-device-attr-to-macro.patch
deleted file mode 100644 (file)
index 3b45951..0000000
+++ /dev/null
@@ -1,82 +0,0 @@
-From 164b67d53476a9d114be85c885bd31f783835be4 Mon Sep 17 00:00:00 2001
-From: Christian Marangi <[email protected]>
-Date: Wed, 19 Apr 2023 23:07:42 +0200
-Subject: [PATCH 4/5] leds: trigger: netdev: Convert device attr to macro
-
-Convert link tx and rx device attr to a common macro to reduce common
-code and in preparation for additional attr.
-
-Signed-off-by: Christian Marangi <[email protected]>
-Reviewed-by: Andrew Lunn <[email protected]>
-Signed-off-by: Lee Jones <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
----
- drivers/leds/trigger/ledtrig-netdev.c | 57 ++++++++-------------------
- 1 file changed, 16 insertions(+), 41 deletions(-)
-
---- a/drivers/leds/trigger/ledtrig-netdev.c
-+++ b/drivers/leds/trigger/ledtrig-netdev.c
-@@ -198,47 +198,22 @@ static ssize_t netdev_led_attr_store(str
-       return size;
- }
--static ssize_t link_show(struct device *dev,
--      struct device_attribute *attr, char *buf)
--{
--      return netdev_led_attr_show(dev, buf, NETDEV_ATTR_LINK);
--}
--
--static ssize_t link_store(struct device *dev,
--      struct device_attribute *attr, const char *buf, size_t size)
--{
--      return netdev_led_attr_store(dev, buf, size, NETDEV_ATTR_LINK);
--}
--
--static DEVICE_ATTR_RW(link);
--
--static ssize_t tx_show(struct device *dev,
--      struct device_attribute *attr, char *buf)
--{
--      return netdev_led_attr_show(dev, buf, NETDEV_ATTR_TX);
--}
--
--static ssize_t tx_store(struct device *dev,
--      struct device_attribute *attr, const char *buf, size_t size)
--{
--      return netdev_led_attr_store(dev, buf, size, NETDEV_ATTR_TX);
--}
--
--static DEVICE_ATTR_RW(tx);
--
--static ssize_t rx_show(struct device *dev,
--      struct device_attribute *attr, char *buf)
--{
--      return netdev_led_attr_show(dev, buf, NETDEV_ATTR_RX);
--}
--
--static ssize_t rx_store(struct device *dev,
--      struct device_attribute *attr, const char *buf, size_t size)
--{
--      return netdev_led_attr_store(dev, buf, size, NETDEV_ATTR_RX);
--}
--
--static DEVICE_ATTR_RW(rx);
-+#define DEFINE_NETDEV_TRIGGER(trigger_name, trigger) \
-+      static ssize_t trigger_name##_show(struct device *dev, \
-+              struct device_attribute *attr, char *buf) \
-+      { \
-+              return netdev_led_attr_show(dev, buf, trigger); \
-+      } \
-+      static ssize_t trigger_name##_store(struct device *dev, \
-+              struct device_attribute *attr, const char *buf, size_t size) \
-+      { \
-+              return netdev_led_attr_store(dev, buf, size, trigger); \
-+      } \
-+      static DEVICE_ATTR_RW(trigger_name)
-+
-+DEFINE_NETDEV_TRIGGER(link, TRIGGER_NETDEV_LINK);
-+DEFINE_NETDEV_TRIGGER(tx, TRIGGER_NETDEV_TX);
-+DEFINE_NETDEV_TRIGGER(rx, TRIGGER_NETDEV_RX);
- static ssize_t interval_show(struct device *dev,
-                            struct device_attribute *attr, char *buf)
diff --git a/target/linux/generic/backport-5.15/817-v6.5-05-leds-trigger-netdev-Use-mutex-instead-of-spinlocks.patch b/target/linux/generic/backport-5.15/817-v6.5-05-leds-trigger-netdev-Use-mutex-instead-of-spinlocks.patch
deleted file mode 100644 (file)
index 180bee9..0000000
+++ /dev/null
@@ -1,106 +0,0 @@
-From d1b9e1391ab2dc80e9db87fe8b2de015c651e4c9 Mon Sep 17 00:00:00 2001
-From: Christian Marangi <[email protected]>
-Date: Wed, 19 Apr 2023 23:07:43 +0200
-Subject: [PATCH 5/5] leds: trigger: netdev: Use mutex instead of spinlocks
-
-Some LEDs may require to sleep while doing some operation like setting
-brightness and other cleanup.
-
-For this reason, using a spinlock will cause a sleep under spinlock
-warning.
-
-It should be safe to convert this to a sleepable lock since:
-- sysfs read/write can sleep
-- netdev_trig_work is a work queue and can sleep
-- netdev _trig_notify can sleep
-
-The spinlock was used when brightness didn't support sleeping, but this
-changed and now it supported with brightness_set_blocking().
-
-Convert to mutex lock to permit sleeping using brightness_set_blocking().
-
-Signed-off-by: Christian Marangi <[email protected]>
-Reviewed-by: Andrew Lunn <[email protected]>
-Signed-off-by: Lee Jones <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
----
- drivers/leds/trigger/ledtrig-netdev.c | 18 +++++++++---------
- 1 file changed, 9 insertions(+), 9 deletions(-)
-
---- a/drivers/leds/trigger/ledtrig-netdev.c
-+++ b/drivers/leds/trigger/ledtrig-netdev.c
-@@ -20,7 +20,7 @@
- #include <linux/list.h>
- #include <linux/module.h>
- #include <linux/netdevice.h>
--#include <linux/spinlock.h>
-+#include <linux/mutex.h>
- #include <linux/timer.h>
- #include "../leds.h"
-@@ -37,7 +37,7 @@
-  */
- struct led_netdev_data {
--      spinlock_t lock;
-+      struct mutex lock;
-       struct delayed_work work;
-       struct notifier_block notifier;
-@@ -97,9 +97,9 @@ static ssize_t device_name_show(struct d
-       struct led_netdev_data *trigger_data = led_trigger_get_drvdata(dev);
-       ssize_t len;
--      spin_lock_bh(&trigger_data->lock);
-+      mutex_lock(&trigger_data->lock);
-       len = sprintf(buf, "%s\n", trigger_data->device_name);
--      spin_unlock_bh(&trigger_data->lock);
-+      mutex_unlock(&trigger_data->lock);
-       return len;
- }
-@@ -115,7 +115,7 @@ static ssize_t device_name_store(struct
-       cancel_delayed_work_sync(&trigger_data->work);
--      spin_lock_bh(&trigger_data->lock);
-+      mutex_lock(&trigger_data->lock);
-       if (trigger_data->net_dev) {
-               dev_put(trigger_data->net_dev);
-@@ -138,7 +138,7 @@ static ssize_t device_name_store(struct
-       trigger_data->last_activity = 0;
-       set_baseline_state(trigger_data);
--      spin_unlock_bh(&trigger_data->lock);
-+      mutex_unlock(&trigger_data->lock);
-       return size;
- }
-@@ -279,7 +279,7 @@ static int netdev_trig_notify(struct not
-       cancel_delayed_work_sync(&trigger_data->work);
--      spin_lock_bh(&trigger_data->lock);
-+      mutex_lock(&trigger_data->lock);
-       trigger_data->carrier_link_up = false;
-       switch (evt) {
-@@ -304,7 +304,7 @@ static int netdev_trig_notify(struct not
-       set_baseline_state(trigger_data);
--      spin_unlock_bh(&trigger_data->lock);
-+      mutex_unlock(&trigger_data->lock);
-       return NOTIFY_DONE;
- }
-@@ -365,7 +365,7 @@ static int netdev_trig_activate(struct l
-       if (!trigger_data)
-               return -ENOMEM;
--      spin_lock_init(&trigger_data->lock);
-+      mutex_init(&trigger_data->lock);
-       trigger_data->notifier.notifier_call = netdev_trig_notify;
-       trigger_data->notifier.priority = 10;
diff --git a/target/linux/generic/backport-5.15/818-v6.5-01-leds-add-APIs-for-LEDs-hw-control.patch b/target/linux/generic/backport-5.15/818-v6.5-01-leds-add-APIs-for-LEDs-hw-control.patch
deleted file mode 100644 (file)
index ac18611..0000000
+++ /dev/null
@@ -1,74 +0,0 @@
-From ed554d3f945179c5b159bddfad7be34b403fe11a Mon Sep 17 00:00:00 2001
-From: Christian Marangi <[email protected]>
-Date: Mon, 29 May 2023 18:32:31 +0200
-Subject: [PATCH 01/13] leds: add APIs for LEDs hw control
-
-Add an option to permit LED driver to declare support for a specific
-trigger to use hw control and setup the LED to blink based on specific
-provided modes.
-
-Add APIs for LEDs hw control. These functions will be used to activate
-hardware control where a LED will use the provided flags, from an
-unique defined supported trigger, to setup the LED to be driven by
-hardware.
-
-Add hw_control_is_supported() to ask the LED driver if the requested
-mode by the trigger are supported and the LED can be setup to follow
-the requested modes.
-
-Deactivate hardware blink control by setting brightness to LED_OFF via
-the brightness_set() callback.
-
-Signed-off-by: Christian Marangi <[email protected]>
-Reviewed-by: Andrew Lunn <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- include/linux/leds.h | 37 +++++++++++++++++++++++++++++++++++++
- 1 file changed, 37 insertions(+)
-
---- a/include/linux/leds.h
-+++ b/include/linux/leds.h
-@@ -164,6 +164,43 @@ struct led_classdev {
-       /* LEDs that have private triggers have this set */
-       struct led_hw_trigger_type      *trigger_type;
-+
-+      /* Unique trigger name supported by LED set in hw control mode */
-+      const char              *hw_control_trigger;
-+      /*
-+       * Check if the LED driver supports the requested mode provided by the
-+       * defined supported trigger to setup the LED to hw control mode.
-+       *
-+       * Return 0 on success. Return -EOPNOTSUPP when the passed flags are not
-+       * supported and software fallback needs to be used.
-+       * Return a negative error number on any other case  for check fail due
-+       * to various reason like device not ready or timeouts.
-+       */
-+      int                     (*hw_control_is_supported)(struct led_classdev *led_cdev,
-+                                                         unsigned long flags);
-+      /*
-+       * Activate hardware control, LED driver will use the provided flags
-+       * from the supported trigger and setup the LED to be driven by hardware
-+       * following the requested mode from the trigger flags.
-+       * Deactivate hardware blink control by setting brightness to LED_OFF via
-+       * the brightness_set() callback.
-+       *
-+       * Return 0 on success, a negative error number on flags apply fail.
-+       */
-+      int                     (*hw_control_set)(struct led_classdev *led_cdev,
-+                                                unsigned long flags);
-+      /*
-+       * Get from the LED driver the current mode that the LED is set in hw
-+       * control mode and put them in flags.
-+       * Trigger can use this to get the initial state of a LED already set in
-+       * hardware blink control.
-+       *
-+       * Return 0 on success, a negative error number on failing parsing the
-+       * initial mode. Error from this function is NOT FATAL as the device
-+       * may be in a not supported initial state by the attached LED trigger.
-+       */
-+      int                     (*hw_control_get)(struct led_classdev *led_cdev,
-+                                                unsigned long *flags);
- #endif
- #ifdef CONFIG_LEDS_BRIGHTNESS_HW_CHANGED
diff --git a/target/linux/generic/backport-5.15/818-v6.5-02-leds-add-API-to-get-attached-device-for-LED-hw-contr.patch b/target/linux/generic/backport-5.15/818-v6.5-02-leds-add-API-to-get-attached-device-for-LED-hw-contr.patch
deleted file mode 100644 (file)
index 1a22172..0000000
+++ /dev/null
@@ -1,37 +0,0 @@
-From 052c38eb17e866c5b4cd43924e7a5e20167b55c0 Mon Sep 17 00:00:00 2001
-From: Andrew Lunn <[email protected]>
-Date: Mon, 29 May 2023 18:32:32 +0200
-Subject: [PATCH 02/13] leds: add API to get attached device for LED hw control
-
-Some specific LED triggers blink the LED based on events from a device
-or subsystem.
-For example, an LED could be blinked to indicate a network device is
-receiving packets, or a disk is reading blocks. To correctly enable and
-request the hw control of the LED, the trigger has to check if the
-network interface or block device configured via a /sys/class/led file
-match the one the LED driver provide for hw control for.
-
-Provide an API call to get the device which the LED blinks for.
-
-Signed-off-by: Andrew Lunn <[email protected]>
-Signed-off-by: Christian Marangi <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- include/linux/leds.h | 6 ++++++
- 1 file changed, 6 insertions(+)
-
---- a/include/linux/leds.h
-+++ b/include/linux/leds.h
-@@ -201,6 +201,12 @@ struct led_classdev {
-        */
-       int                     (*hw_control_get)(struct led_classdev *led_cdev,
-                                                 unsigned long *flags);
-+      /*
-+       * Get the device this LED blinks in response to.
-+       * e.g. for a PHY LED, it is the network device. If the LED is
-+       * not yet associated to a device, return NULL.
-+       */
-+      struct device           *(*hw_control_get_device)(struct led_classdev *led_cdev);
- #endif
- #ifdef CONFIG_LEDS_BRIGHTNESS_HW_CHANGED
diff --git a/target/linux/generic/backport-5.15/818-v6.5-03-Documentation-leds-leds-class-Document-new-Hardware-.patch b/target/linux/generic/backport-5.15/818-v6.5-03-Documentation-leds-leds-class-Document-new-Hardware-.patch
deleted file mode 100644 (file)
index af9fb7f..0000000
+++ /dev/null
@@ -1,113 +0,0 @@
-From 8aa2fd7b66980ecd2e45e95af61cf7eafede1211 Mon Sep 17 00:00:00 2001
-From: Christian Marangi <[email protected]>
-Date: Mon, 29 May 2023 18:32:33 +0200
-Subject: [PATCH 03/13] Documentation: leds: leds-class: Document new Hardware
- driven LEDs APIs
-
-Document new Hardware driven LEDs APIs.
-
-Some LEDs can be programmed to be driven by hardware. This is not
-limited to blink but also to turn off or on autonomously.
-To support this feature, a LED needs to implement various additional
-ops and needs to declare specific support for the supported triggers.
-
-Add documentation for each required value and API to make hw control
-possible and implementable by both LEDs and triggers.
-
-Signed-off-by: Christian Marangi <[email protected]>
-Reviewed-by: Andrew Lunn <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- Documentation/leds/leds-class.rst | 81 +++++++++++++++++++++++++++++++
- 1 file changed, 81 insertions(+)
-
---- a/Documentation/leds/leds-class.rst
-+++ b/Documentation/leds/leds-class.rst
-@@ -169,6 +169,87 @@ Setting the brightness to zero with brig
- should completely turn off the LED and cancel the previously programmed
- hardware blinking function, if any.
-+Hardware driven LEDs
-+====================
-+
-+Some LEDs can be programmed to be driven by hardware. This is not
-+limited to blink but also to turn off or on autonomously.
-+To support this feature, a LED needs to implement various additional
-+ops and needs to declare specific support for the supported triggers.
-+
-+With hw control we refer to the LED driven by hardware.
-+
-+LED driver must define the following value to support hw control:
-+
-+    - hw_control_trigger:
-+               unique trigger name supported by the LED in hw control
-+               mode.
-+
-+LED driver must implement the following API to support hw control:
-+    - hw_control_is_supported:
-+                check if the flags passed by the supported trigger can
-+                be parsed and activate hw control on the LED.
-+
-+                Return 0 if the passed flags mask is supported and
-+                can be set with hw_control_set().
-+
-+                If the passed flags mask is not supported -EOPNOTSUPP
-+                must be returned, the LED trigger will use software
-+                fallback in this case.
-+
-+                Return a negative error in case of any other error like
-+                device not ready or timeouts.
-+
-+     - hw_control_set:
-+                activate hw control. LED driver will use the provided
-+                flags passed from the supported trigger, parse them to
-+                a set of mode and setup the LED to be driven by hardware
-+                following the requested modes.
-+
-+                Set LED_OFF via the brightness_set to deactivate hw control.
-+
-+                Return 0 on success, a negative error number on failing to
-+                apply flags.
-+
-+    - hw_control_get:
-+                get active modes from a LED already in hw control, parse
-+                them and set in flags the current active flags for the
-+                supported trigger.
-+
-+                Return 0 on success, a negative error number on failing
-+                parsing the initial mode.
-+                Error from this function is NOT FATAL as the device may
-+                be in a not supported initial state by the attached LED
-+                trigger.
-+
-+    - hw_control_get_device:
-+                return the device associated with the LED driver in
-+                hw control. A trigger might use this to match the
-+                returned device from this function with a configured
-+                device for the trigger as the source for blinking
-+                events and correctly enable hw control.
-+                (example a netdev trigger configured to blink for a
-+                particular dev match the returned dev from get_device
-+                to set hw control)
-+
-+                Returns a pointer to a struct device or NULL if nothing
-+                is currently attached.
-+
-+LED driver can activate additional modes by default to workaround the
-+impossibility of supporting each different mode on the supported trigger.
-+Examples are hardcoding the blink speed to a set interval, enable special
-+feature like bypassing blink if some requirements are not met.
-+
-+A trigger should first check if the hw control API are supported by the LED
-+driver and check if the trigger is supported to verify if hw control is possible,
-+use hw_control_is_supported to check if the flags are supported and only at
-+the end use hw_control_set to activate hw control.
-+
-+A trigger can use hw_control_get to check if a LED is already in hw control
-+and init their flags.
-+
-+When the LED is in hw control, no software blink is possible and doing so
-+will effectively disable hw control.
- Known Issues
- ============
diff --git a/target/linux/generic/backport-5.15/818-v6.5-04-leds-trigger-netdev-refactor-code-setting-device-nam.patch b/target/linux/generic/backport-5.15/818-v6.5-04-leds-trigger-netdev-refactor-code-setting-device-nam.patch
deleted file mode 100644 (file)
index 3c804c0..0000000
+++ /dev/null
@@ -1,69 +0,0 @@
-From 28a6a2ef18ad840a390d519840c303b03040961c Mon Sep 17 00:00:00 2001
-From: Andrew Lunn <[email protected]>
-Date: Mon, 29 May 2023 18:32:34 +0200
-Subject: [PATCH 04/13] leds: trigger: netdev: refactor code setting device
- name
-
-Move the code into a helper, ready for it to be called at
-other times. No intended behaviour change.
-
-Signed-off-by: Andrew Lunn <[email protected]>
-Signed-off-by: Christian Marangi <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/leds/trigger/ledtrig-netdev.c | 29 ++++++++++++++++++---------
- 1 file changed, 20 insertions(+), 9 deletions(-)
-
---- a/drivers/leds/trigger/ledtrig-netdev.c
-+++ b/drivers/leds/trigger/ledtrig-netdev.c
-@@ -104,15 +104,9 @@ static ssize_t device_name_show(struct d
-       return len;
- }
--static ssize_t device_name_store(struct device *dev,
--                               struct device_attribute *attr, const char *buf,
--                               size_t size)
-+static int set_device_name(struct led_netdev_data *trigger_data,
-+                         const char *name, size_t size)
- {
--      struct led_netdev_data *trigger_data = led_trigger_get_drvdata(dev);
--
--      if (size >= IFNAMSIZ)
--              return -EINVAL;
--
-       cancel_delayed_work_sync(&trigger_data->work);
-       mutex_lock(&trigger_data->lock);
-@@ -122,7 +116,7 @@ static ssize_t device_name_store(struct
-               trigger_data->net_dev = NULL;
-       }
--      memcpy(trigger_data->device_name, buf, size);
-+      memcpy(trigger_data->device_name, name, size);
-       trigger_data->device_name[size] = 0;
-       if (size > 0 && trigger_data->device_name[size - 1] == '\n')
-               trigger_data->device_name[size - 1] = 0;
-@@ -140,6 +134,23 @@ static ssize_t device_name_store(struct
-       set_baseline_state(trigger_data);
-       mutex_unlock(&trigger_data->lock);
-+      return 0;
-+}
-+
-+static ssize_t device_name_store(struct device *dev,
-+                               struct device_attribute *attr, const char *buf,
-+                               size_t size)
-+{
-+      struct led_netdev_data *trigger_data = led_trigger_get_drvdata(dev);
-+      int ret;
-+
-+      if (size >= IFNAMSIZ)
-+              return -EINVAL;
-+
-+      ret = set_device_name(trigger_data, buf, size);
-+
-+      if (ret < 0)
-+              return ret;
-       return size;
- }
diff --git a/target/linux/generic/backport-5.15/818-v6.5-05-leds-trigger-netdev-introduce-check-for-possible-hw-.patch b/target/linux/generic/backport-5.15/818-v6.5-05-leds-trigger-netdev-introduce-check-for-possible-hw-.patch
deleted file mode 100644 (file)
index 284b519..0000000
+++ /dev/null
@@ -1,54 +0,0 @@
-From 4fd1b6d47a7a38e81fdc6f8be2ccd4216b3f93db Mon Sep 17 00:00:00 2001
-From: Christian Marangi <[email protected]>
-Date: Mon, 29 May 2023 18:32:35 +0200
-Subject: [PATCH 05/13] leds: trigger: netdev: introduce check for possible hw
- control
-
-Introduce function to check if the requested mode can use hw control in
-preparation for hw control support. Currently everything is handled in
-software so can_hw_control will always return false.
-
-Add knob with the new value hw_control in trigger_data struct to
-set hw control possible. Useful for future implementation to implement
-in set_baseline_state() the required function to set the requested mode
-using LEDs hw control ops and in other function to reject set if hw
-control is currently active.
-
-Signed-off-by: Christian Marangi <[email protected]>
-Reviewed-by: Andrew Lunn <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/leds/trigger/ledtrig-netdev.c | 8 ++++++++
- 1 file changed, 8 insertions(+)
-
---- a/drivers/leds/trigger/ledtrig-netdev.c
-+++ b/drivers/leds/trigger/ledtrig-netdev.c
-@@ -51,6 +51,7 @@ struct led_netdev_data {
-       unsigned long mode;
-       bool carrier_link_up;
-+      bool hw_control;
- };
- enum led_trigger_netdev_modes {
-@@ -91,6 +92,11 @@ static void set_baseline_state(struct le
-       }
- }
-+static bool can_hw_control(struct led_netdev_data *trigger_data)
-+{
-+      return false;
-+}
-+
- static ssize_t device_name_show(struct device *dev,
-                               struct device_attribute *attr, char *buf)
- {
-@@ -204,6 +210,8 @@ static ssize_t netdev_led_attr_store(str
-       else
-               clear_bit(bit, &trigger_data->mode);
-+      trigger_data->hw_control = can_hw_control(trigger_data);
-+
-       set_baseline_state(trigger_data);
-       return size;
diff --git a/target/linux/generic/backport-5.15/818-v6.5-06-leds-trigger-netdev-add-basic-check-for-hw-control-s.patch b/target/linux/generic/backport-5.15/818-v6.5-06-leds-trigger-netdev-add-basic-check-for-hw-control-s.patch
deleted file mode 100644 (file)
index 09759bc..0000000
+++ /dev/null
@@ -1,42 +0,0 @@
-From 6352f25f9fadba59d5df2ba7139495759ccc81d5 Mon Sep 17 00:00:00 2001
-From: Christian Marangi <[email protected]>
-Date: Mon, 29 May 2023 18:32:36 +0200
-Subject: [PATCH 06/13] leds: trigger: netdev: add basic check for hw control
- support
-
-Add basic check for hw control support. Check if the required API are
-defined and check if the defined trigger supported in hw control for the
-LED driver match netdev.
-
-Signed-off-by: Christian Marangi <[email protected]>
-Reviewed-by: Andrew Lunn <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/leds/trigger/ledtrig-netdev.c | 14 ++++++++++++++
- 1 file changed, 14 insertions(+)
-
---- a/drivers/leds/trigger/ledtrig-netdev.c
-+++ b/drivers/leds/trigger/ledtrig-netdev.c
-@@ -92,8 +92,22 @@ static void set_baseline_state(struct le
-       }
- }
-+static bool supports_hw_control(struct led_classdev *led_cdev)
-+{
-+      if (!led_cdev->hw_control_get || !led_cdev->hw_control_set ||
-+          !led_cdev->hw_control_is_supported)
-+              return false;
-+
-+      return !strcmp(led_cdev->hw_control_trigger, led_cdev->trigger->name);
-+}
-+
- static bool can_hw_control(struct led_netdev_data *trigger_data)
- {
-+      struct led_classdev *led_cdev = trigger_data->led_cdev;
-+
-+      if (!supports_hw_control(led_cdev))
-+              return false;
-+
-       return false;
- }
diff --git a/target/linux/generic/backport-5.15/818-v6.5-07-leds-trigger-netdev-reject-interval-store-for-hw_con.patch b/target/linux/generic/backport-5.15/818-v6.5-07-leds-trigger-netdev-reject-interval-store-for-hw_con.patch
deleted file mode 100644 (file)
index 6634906..0000000
+++ /dev/null
@@ -1,28 +0,0 @@
-From c84c80c7388f887b10dafd70fc55bc6c5fe9fa5a Mon Sep 17 00:00:00 2001
-From: Christian Marangi <[email protected]>
-Date: Mon, 29 May 2023 18:32:37 +0200
-Subject: [PATCH 07/13] leds: trigger: netdev: reject interval store for
- hw_control
-
-Reject interval store with hw_control enabled. It's are currently not
-supported and MUST be set to the default value with hw control enabled.
-
-Signed-off-by: Christian Marangi <[email protected]>
-Reviewed-by: Andrew Lunn <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/leds/trigger/ledtrig-netdev.c | 3 +++
- 1 file changed, 3 insertions(+)
-
---- a/drivers/leds/trigger/ledtrig-netdev.c
-+++ b/drivers/leds/trigger/ledtrig-netdev.c
-@@ -265,6 +265,9 @@ static ssize_t interval_store(struct dev
-       unsigned long value;
-       int ret;
-+      if (trigger_data->hw_control)
-+              return -EINVAL;
-+
-       ret = kstrtoul(buf, 0, &value);
-       if (ret)
-               return ret;
diff --git a/target/linux/generic/backport-5.15/818-v6.5-08-leds-trigger-netdev-add-support-for-LED-hw-control.patch b/target/linux/generic/backport-5.15/818-v6.5-08-leds-trigger-netdev-add-support-for-LED-hw-control.patch
deleted file mode 100644 (file)
index 52faa48..0000000
+++ /dev/null
@@ -1,107 +0,0 @@
-From 7c145a34ba6e380616af93262fcab9fc7261d851 Mon Sep 17 00:00:00 2001
-From: Christian Marangi <[email protected]>
-Date: Mon, 29 May 2023 18:32:38 +0200
-Subject: [PATCH 08/13] leds: trigger: netdev: add support for LED hw control
-
-Add support for LED hw control for the netdev trigger.
-
-The trigger on calling set_baseline_state to configure a new mode, will
-do various check to verify if hw control can be used for the requested
-mode in can_hw_control() function.
-
-It will first check if the LED driver supports hw control for the netdev
-trigger, then will use hw_control_is_supported() and finally will call
-hw_control_set() to apply the requested mode.
-
-To use such mode, interval MUST be set to the default value and net_dev
-MUST be set. If one of these 2 value are not valid, hw control will
-never be used and normal software fallback is used.
-
-The default interval value is moved to a define to make sure they are
-always synced.
-
-Signed-off-by: Christian Marangi <[email protected]>
-Reviewed-by: Andrew Lunn <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/leds/trigger/ledtrig-netdev.c | 43 +++++++++++++++++++++++++--
- 1 file changed, 41 insertions(+), 2 deletions(-)
-
---- a/drivers/leds/trigger/ledtrig-netdev.c
-+++ b/drivers/leds/trigger/ledtrig-netdev.c
-@@ -24,6 +24,8 @@
- #include <linux/timer.h>
- #include "../leds.h"
-+#define NETDEV_LED_DEFAULT_INTERVAL   50
-+
- /*
-  * Configurable sysfs attributes:
-  *
-@@ -68,6 +70,13 @@ static void set_baseline_state(struct le
-       int current_brightness;
-       struct led_classdev *led_cdev = trigger_data->led_cdev;
-+      /* Already validated, hw control is possible with the requested mode */
-+      if (trigger_data->hw_control) {
-+              led_cdev->hw_control_set(led_cdev, trigger_data->mode);
-+
-+              return;
-+      }
-+
-       current_brightness = led_cdev->brightness;
-       if (current_brightness)
-               led_cdev->blink_brightness = current_brightness;
-@@ -103,12 +112,42 @@ static bool supports_hw_control(struct l
- static bool can_hw_control(struct led_netdev_data *trigger_data)
- {
-+      unsigned long default_interval = msecs_to_jiffies(NETDEV_LED_DEFAULT_INTERVAL);
-+      unsigned int interval = atomic_read(&trigger_data->interval);
-       struct led_classdev *led_cdev = trigger_data->led_cdev;
-+      int ret;
-       if (!supports_hw_control(led_cdev))
-               return false;
--      return false;
-+      /*
-+       * Interval must be set to the default
-+       * value. Any different value is rejected if in hw
-+       * control.
-+       */
-+      if (interval != default_interval)
-+              return false;
-+
-+      /*
-+       * net_dev must be set with hw control, otherwise no
-+       * blinking can be happening and there is nothing to
-+       * offloaded.
-+       */
-+      if (!trigger_data->net_dev)
-+              return false;
-+
-+      /* Check if the requested mode is supported */
-+      ret = led_cdev->hw_control_is_supported(led_cdev, trigger_data->mode);
-+      /* Fall back to software blinking if not supported */
-+      if (ret == -EOPNOTSUPP)
-+              return false;
-+      if (ret) {
-+              dev_warn(led_cdev->dev,
-+                       "Current mode check failed with error %d\n", ret);
-+              return false;
-+      }
-+
-+      return true;
- }
- static ssize_t device_name_show(struct device *dev,
-@@ -413,7 +452,7 @@ static int netdev_trig_activate(struct l
-       trigger_data->device_name[0] = 0;
-       trigger_data->mode = 0;
--      atomic_set(&trigger_data->interval, msecs_to_jiffies(50));
-+      atomic_set(&trigger_data->interval, msecs_to_jiffies(NETDEV_LED_DEFAULT_INTERVAL));
-       trigger_data->last_activity = 0;
-       led_set_trigger_data(led_cdev, trigger_data);
diff --git a/target/linux/generic/backport-5.15/818-v6.5-09-leds-trigger-netdev-validate-configured-netdev.patch b/target/linux/generic/backport-5.15/818-v6.5-09-leds-trigger-netdev-validate-configured-netdev.patch
deleted file mode 100644 (file)
index c129ffa..0000000
+++ /dev/null
@@ -1,58 +0,0 @@
-From 33ec0b53befff2c0a7f3aa19ff08556d60585d6b Mon Sep 17 00:00:00 2001
-From: Andrew Lunn <[email protected]>
-Date: Mon, 29 May 2023 18:32:39 +0200
-Subject: [PATCH 09/13] leds: trigger: netdev: validate configured netdev
-
-The netdev which the LED should blink for is configurable in
-/sys/class/led/foo/device_name. Ensure when offloading that the
-configured netdev is the same as the netdev the LED is associated
-with. If it is not, only perform software blinking.
-
-Signed-off-by: Andrew Lunn <[email protected]>
-Signed-off-by: Christian Marangi <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/leds/trigger/ledtrig-netdev.c | 24 ++++++++++++++++++++++--
- 1 file changed, 22 insertions(+), 2 deletions(-)
-
---- a/drivers/leds/trigger/ledtrig-netdev.c
-+++ b/drivers/leds/trigger/ledtrig-netdev.c
-@@ -110,6 +110,24 @@ static bool supports_hw_control(struct l
-       return !strcmp(led_cdev->hw_control_trigger, led_cdev->trigger->name);
- }
-+/*
-+ * Validate the configured netdev is the same as the one associated with
-+ * the LED driver in hw control.
-+ */
-+static bool validate_net_dev(struct led_classdev *led_cdev,
-+                           struct net_device *net_dev)
-+{
-+      struct device *dev = led_cdev->hw_control_get_device(led_cdev);
-+      struct net_device *ndev;
-+
-+      if (!dev)
-+              return false;
-+
-+      ndev = to_net_dev(dev);
-+
-+      return ndev == net_dev;
-+}
-+
- static bool can_hw_control(struct led_netdev_data *trigger_data)
- {
-       unsigned long default_interval = msecs_to_jiffies(NETDEV_LED_DEFAULT_INTERVAL);
-@@ -131,9 +149,11 @@ static bool can_hw_control(struct led_ne
-       /*
-        * net_dev must be set with hw control, otherwise no
-        * blinking can be happening and there is nothing to
--       * offloaded.
-+       * offloaded. Additionally, for hw control to be
-+       * valid, the configured netdev must be the same as
-+       * netdev associated to the LED.
-        */
--      if (!trigger_data->net_dev)
-+      if (!validate_net_dev(led_cdev, trigger_data->net_dev))
-               return false;
-       /* Check if the requested mode is supported */
diff --git a/target/linux/generic/backport-5.15/818-v6.5-10-leds-trigger-netdev-init-mode-if-hw-control-already-.patch b/target/linux/generic/backport-5.15/818-v6.5-10-leds-trigger-netdev-init-mode-if-hw-control-already-.patch
deleted file mode 100644 (file)
index e20594c..0000000
+++ /dev/null
@@ -1,53 +0,0 @@
-From 0316cc5629d15880dd3f097d221c55ca648bcd61 Mon Sep 17 00:00:00 2001
-From: Christian Marangi <[email protected]>
-Date: Mon, 29 May 2023 18:32:40 +0200
-Subject: [PATCH 10/13] leds: trigger: netdev: init mode if hw control already
- active
-
-On netdev trigger activation, hw control may be already active by
-default. If this is the case and a device is actually provided by
-hw_control_get_device(), init the already active mode and set the
-bool to hw_control bool to true to reflect the already set mode in the
-trigger_data.
-
-Co-developed-by: Andrew Lunn <[email protected]>
-Signed-off-by: Andrew Lunn <[email protected]>
-Signed-off-by: Christian Marangi <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/leds/trigger/ledtrig-netdev.c | 17 +++++++++++++++++
- 1 file changed, 17 insertions(+)
-
---- a/drivers/leds/trigger/ledtrig-netdev.c
-+++ b/drivers/leds/trigger/ledtrig-netdev.c
-@@ -454,6 +454,8 @@ static void netdev_trig_work(struct work
- static int netdev_trig_activate(struct led_classdev *led_cdev)
- {
-       struct led_netdev_data *trigger_data;
-+      unsigned long mode;
-+      struct device *dev;
-       int rc;
-       trigger_data = kzalloc(sizeof(struct led_netdev_data), GFP_KERNEL);
-@@ -475,6 +477,21 @@ static int netdev_trig_activate(struct l
-       atomic_set(&trigger_data->interval, msecs_to_jiffies(NETDEV_LED_DEFAULT_INTERVAL));
-       trigger_data->last_activity = 0;
-+      /* Check if hw control is active by default on the LED.
-+       * Init already enabled mode in hw control.
-+       */
-+      if (supports_hw_control(led_cdev) &&
-+          !led_cdev->hw_control_get(led_cdev, &mode)) {
-+              dev = led_cdev->hw_control_get_device(led_cdev);
-+              if (dev) {
-+                      const char *name = dev_name(dev);
-+
-+                      set_device_name(trigger_data, name, strlen(name));
-+                      trigger_data->hw_control = true;
-+                      trigger_data->mode = mode;
-+              }
-+      }
-+
-       led_set_trigger_data(led_cdev, trigger_data);
-       rc = register_netdevice_notifier(&trigger_data->notifier);
diff --git a/target/linux/generic/backport-5.15/818-v6.5-11-leds-trigger-netdev-expose-netdev-trigger-modes-in-l.patch b/target/linux/generic/backport-5.15/818-v6.5-11-leds-trigger-netdev-expose-netdev-trigger-modes-in-l.patch
deleted file mode 100644 (file)
index 70aed85..0000000
+++ /dev/null
@@ -1,54 +0,0 @@
-From 947acacab5ea151291b861cdfbde16ff5cf1b08c Mon Sep 17 00:00:00 2001
-From: Christian Marangi <[email protected]>
-Date: Mon, 29 May 2023 18:32:41 +0200
-Subject: [PATCH 11/13] leds: trigger: netdev: expose netdev trigger modes in
- linux include
-
-Expose netdev trigger modes to make them accessible by LED driver that
-will support netdev trigger for hw control.
-
-Signed-off-by: Christian Marangi <[email protected]>
-Reviewed-by: Andrew Lunn <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/leds/trigger/ledtrig-netdev.c |  9 ---------
- include/linux/leds.h                  | 10 ++++++++++
- 2 files changed, 10 insertions(+), 9 deletions(-)
-
---- a/drivers/leds/trigger/ledtrig-netdev.c
-+++ b/drivers/leds/trigger/ledtrig-netdev.c
-@@ -56,15 +56,6 @@ struct led_netdev_data {
-       bool hw_control;
- };
--enum led_trigger_netdev_modes {
--      TRIGGER_NETDEV_LINK = 0,
--      TRIGGER_NETDEV_TX,
--      TRIGGER_NETDEV_RX,
--
--      /* Keep last */
--      __TRIGGER_NETDEV_MAX,
--};
--
- static void set_baseline_state(struct led_netdev_data *trigger_data)
- {
-       int current_brightness;
---- a/include/linux/leds.h
-+++ b/include/linux/leds.h
-@@ -527,6 +527,16 @@ static inline void *led_get_trigger_data
- #endif /* CONFIG_LEDS_TRIGGERS */
-+/* Trigger specific enum */
-+enum led_trigger_netdev_modes {
-+      TRIGGER_NETDEV_LINK = 0,
-+      TRIGGER_NETDEV_TX,
-+      TRIGGER_NETDEV_RX,
-+
-+      /* Keep last */
-+      __TRIGGER_NETDEV_MAX,
-+};
-+
- /* Trigger specific functions */
- #ifdef CONFIG_LEDS_TRIGGER_DISK
- void ledtrig_disk_activity(bool write);
diff --git a/target/linux/generic/backport-5.15/818-v6.5-12-net-dsa-qca8k-implement-hw_control-ops.patch b/target/linux/generic/backport-5.15/818-v6.5-12-net-dsa-qca8k-implement-hw_control-ops.patch
deleted file mode 100644 (file)
index ad76d89..0000000
+++ /dev/null
@@ -1,200 +0,0 @@
-From e0256648c831af13cbfe4a1787327fcec01c2807 Mon Sep 17 00:00:00 2001
-From: Christian Marangi <[email protected]>
-Date: Mon, 29 May 2023 18:32:42 +0200
-Subject: [PATCH 12/13] net: dsa: qca8k: implement hw_control ops
-
-Implement hw_control ops to drive Switch LEDs based on hardware events.
-
-Netdev trigger is the declared supported trigger for hw control
-operation and supports the following mode:
-- tx
-- rx
-
-When hw_control_set is called, LEDs are set to follow the requested
-mode.
-Each LEDs will blink at 4Hz by default.
-
-Signed-off-by: Christian Marangi <[email protected]>
-Reviewed-by: Andrew Lunn <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/dsa/qca/qca8k-leds.c | 154 +++++++++++++++++++++++++++++++
- 1 file changed, 154 insertions(+)
-
---- a/drivers/net/dsa/qca/qca8k-leds.c
-+++ b/drivers/net/dsa/qca/qca8k-leds.c
-@@ -32,6 +32,43 @@ qca8k_get_enable_led_reg(int port_num, i
- }
- static int
-+qca8k_get_control_led_reg(int port_num, int led_num, struct qca8k_led_pattern_en *reg_info)
-+{
-+      reg_info->reg = QCA8K_LED_CTRL_REG(led_num);
-+
-+      /* 6 total control rule:
-+       * 3 control rules for phy0-3 that applies to all their leds
-+       * 3 control rules for phy4
-+       */
-+      if (port_num == 4)
-+              reg_info->shift = QCA8K_LED_PHY4_CONTROL_RULE_SHIFT;
-+      else
-+              reg_info->shift = QCA8K_LED_PHY0123_CONTROL_RULE_SHIFT;
-+
-+      return 0;
-+}
-+
-+static int
-+qca8k_parse_netdev(unsigned long rules, u32 *offload_trigger)
-+{
-+      /* Parsing specific to netdev trigger */
-+      if (test_bit(TRIGGER_NETDEV_TX, &rules))
-+              *offload_trigger |= QCA8K_LED_TX_BLINK_MASK;
-+      if (test_bit(TRIGGER_NETDEV_RX, &rules))
-+              *offload_trigger |= QCA8K_LED_RX_BLINK_MASK;
-+
-+      if (rules && !*offload_trigger)
-+              return -EOPNOTSUPP;
-+
-+      /* Enable some default rule by default to the requested mode:
-+       * - Blink at 4Hz by default
-+       */
-+      *offload_trigger |= QCA8K_LED_BLINK_4HZ;
-+
-+      return 0;
-+}
-+
-+static int
- qca8k_led_brightness_set(struct qca8k_led *led,
-                        enum led_brightness brightness)
- {
-@@ -165,6 +202,119 @@ qca8k_cled_blink_set(struct led_classdev
- }
- static int
-+qca8k_cled_trigger_offload(struct led_classdev *ldev, bool enable)
-+{
-+      struct qca8k_led *led = container_of(ldev, struct qca8k_led, cdev);
-+
-+      struct qca8k_led_pattern_en reg_info;
-+      struct qca8k_priv *priv = led->priv;
-+      u32 mask, val = QCA8K_LED_ALWAYS_OFF;
-+
-+      qca8k_get_enable_led_reg(led->port_num, led->led_num, &reg_info);
-+
-+      if (enable)
-+              val = QCA8K_LED_RULE_CONTROLLED;
-+
-+      if (led->port_num == 0 || led->port_num == 4) {
-+              mask = QCA8K_LED_PATTERN_EN_MASK;
-+              val <<= QCA8K_LED_PATTERN_EN_SHIFT;
-+      } else {
-+              mask = QCA8K_LED_PHY123_PATTERN_EN_MASK;
-+      }
-+
-+      return regmap_update_bits(priv->regmap, reg_info.reg, mask << reg_info.shift,
-+                                val << reg_info.shift);
-+}
-+
-+static bool
-+qca8k_cled_hw_control_status(struct led_classdev *ldev)
-+{
-+      struct qca8k_led *led = container_of(ldev, struct qca8k_led, cdev);
-+
-+      struct qca8k_led_pattern_en reg_info;
-+      struct qca8k_priv *priv = led->priv;
-+      u32 val;
-+
-+      qca8k_get_enable_led_reg(led->port_num, led->led_num, &reg_info);
-+
-+      regmap_read(priv->regmap, reg_info.reg, &val);
-+
-+      val >>= reg_info.shift;
-+
-+      if (led->port_num == 0 || led->port_num == 4) {
-+              val &= QCA8K_LED_PATTERN_EN_MASK;
-+              val >>= QCA8K_LED_PATTERN_EN_SHIFT;
-+      } else {
-+              val &= QCA8K_LED_PHY123_PATTERN_EN_MASK;
-+      }
-+
-+      return val == QCA8K_LED_RULE_CONTROLLED;
-+}
-+
-+static int
-+qca8k_cled_hw_control_is_supported(struct led_classdev *ldev, unsigned long rules)
-+{
-+      u32 offload_trigger = 0;
-+
-+      return qca8k_parse_netdev(rules, &offload_trigger);
-+}
-+
-+static int
-+qca8k_cled_hw_control_set(struct led_classdev *ldev, unsigned long rules)
-+{
-+      struct qca8k_led *led = container_of(ldev, struct qca8k_led, cdev);
-+      struct qca8k_led_pattern_en reg_info;
-+      struct qca8k_priv *priv = led->priv;
-+      u32 offload_trigger = 0;
-+      int ret;
-+
-+      ret = qca8k_parse_netdev(rules, &offload_trigger);
-+      if (ret)
-+              return ret;
-+
-+      ret = qca8k_cled_trigger_offload(ldev, true);
-+      if (ret)
-+              return ret;
-+
-+      qca8k_get_control_led_reg(led->port_num, led->led_num, &reg_info);
-+
-+      return regmap_update_bits(priv->regmap, reg_info.reg,
-+                                QCA8K_LED_RULE_MASK << reg_info.shift,
-+                                offload_trigger << reg_info.shift);
-+}
-+
-+static int
-+qca8k_cled_hw_control_get(struct led_classdev *ldev, unsigned long *rules)
-+{
-+      struct qca8k_led *led = container_of(ldev, struct qca8k_led, cdev);
-+      struct qca8k_led_pattern_en reg_info;
-+      struct qca8k_priv *priv = led->priv;
-+      u32 val;
-+      int ret;
-+
-+      /* With hw control not active return err */
-+      if (!qca8k_cled_hw_control_status(ldev))
-+              return -EINVAL;
-+
-+      qca8k_get_control_led_reg(led->port_num, led->led_num, &reg_info);
-+
-+      ret = regmap_read(priv->regmap, reg_info.reg, &val);
-+      if (ret)
-+              return ret;
-+
-+      val >>= reg_info.shift;
-+      val &= QCA8K_LED_RULE_MASK;
-+
-+      /* Parsing specific to netdev trigger */
-+      if (val & QCA8K_LED_TX_BLINK_MASK)
-+              set_bit(TRIGGER_NETDEV_TX, rules);
-+      if (val & QCA8K_LED_RX_BLINK_MASK)
-+              set_bit(TRIGGER_NETDEV_RX, rules);
-+
-+      return 0;
-+}
-+
-+static int
- qca8k_parse_port_leds(struct qca8k_priv *priv, struct fwnode_handle *port, int port_num)
- {
-       struct fwnode_handle *led = NULL, *leds = NULL;
-@@ -224,6 +374,10 @@ qca8k_parse_port_leds(struct qca8k_priv
-               port_led->cdev.max_brightness = 1;
-               port_led->cdev.brightness_set_blocking = qca8k_cled_brightness_set_blocking;
-               port_led->cdev.blink_set = qca8k_cled_blink_set;
-+              port_led->cdev.hw_control_is_supported = qca8k_cled_hw_control_is_supported;
-+              port_led->cdev.hw_control_set = qca8k_cled_hw_control_set;
-+              port_led->cdev.hw_control_get = qca8k_cled_hw_control_get;
-+              port_led->cdev.hw_control_trigger = "netdev";
-               init_data.default_label = ":port";
-               init_data.fwnode = led;
-               init_data.devname_mandatory = true;
diff --git a/target/linux/generic/backport-5.15/818-v6.5-13-net-dsa-qca8k-add-op-to-get-ports-netdev.patch b/target/linux/generic/backport-5.15/818-v6.5-13-net-dsa-qca8k-add-op-to-get-ports-netdev.patch
deleted file mode 100644 (file)
index feb6b9e..0000000
+++ /dev/null
@@ -1,70 +0,0 @@
-From 4f53c27f772e27e4cf4e5507d6f4d5980002cb6a Mon Sep 17 00:00:00 2001
-From: Andrew Lunn <[email protected]>
-Date: Mon, 29 May 2023 18:32:43 +0200
-Subject: [PATCH 13/13] net: dsa: qca8k: add op to get ports netdev
-
-In order that the LED trigger can blink the switch MAC ports LED, it
-needs to know the netdev associated to the port. Add the callback to
-return the struct device of the netdev.
-
-Add an helper function qca8k_phy_to_port() to convert the phy back to
-dsa_port index, as we reference LED port based on the internal PHY
-index and needs to be converted back.
-
-Signed-off-by: Andrew Lunn <[email protected]>
-Signed-off-by: Christian Marangi <[email protected]>
-Signed-off-by: David S. Miller <[email protected]>
----
- drivers/net/dsa/qca/qca8k-leds.c | 27 +++++++++++++++++++++++++++
- 1 file changed, 27 insertions(+)
-
---- a/drivers/net/dsa/qca/qca8k-leds.c
-+++ b/drivers/net/dsa/qca/qca8k-leds.c
-@@ -5,6 +5,18 @@
- #include "qca8k.h"
- #include "qca8k_leds.h"
-+static u32 qca8k_phy_to_port(int phy)
-+{
-+      /* Internal PHY 0 has port at index 1.
-+       * Internal PHY 1 has port at index 2.
-+       * Internal PHY 2 has port at index 3.
-+       * Internal PHY 3 has port at index 4.
-+       * Internal PHY 4 has port at index 5.
-+       */
-+
-+      return phy + 1;
-+}
-+
- static int
- qca8k_get_enable_led_reg(int port_num, int led_num, struct qca8k_led_pattern_en *reg_info)
- {
-@@ -314,6 +326,20 @@ qca8k_cled_hw_control_get(struct led_cla
-       return 0;
- }
-+static struct device *qca8k_cled_hw_control_get_device(struct led_classdev *ldev)
-+{
-+      struct qca8k_led *led = container_of(ldev, struct qca8k_led, cdev);
-+      struct qca8k_priv *priv = led->priv;
-+      struct dsa_port *dp;
-+
-+      dp = dsa_to_port(priv->ds, qca8k_phy_to_port(led->port_num));
-+      if (!dp)
-+              return NULL;
-+      if (dp->slave)
-+              return &dp->slave->dev;
-+      return NULL;
-+}
-+
- static int
- qca8k_parse_port_leds(struct qca8k_priv *priv, struct fwnode_handle *port, int port_num)
- {
-@@ -377,6 +403,7 @@ qca8k_parse_port_leds(struct qca8k_priv
-               port_led->cdev.hw_control_is_supported = qca8k_cled_hw_control_is_supported;
-               port_led->cdev.hw_control_set = qca8k_cled_hw_control_set;
-               port_led->cdev.hw_control_get = qca8k_cled_hw_control_get;
-+              port_led->cdev.hw_control_get_device = qca8k_cled_hw_control_get_device;
-               port_led->cdev.hw_control_trigger = "netdev";
-               init_data.default_label = ":port";
-               init_data.fwnode = led;
diff --git a/target/linux/generic/backport-5.15/819-v6.6-0001-nvmem-sunxi_sid-Convert-to-devm_platform_ioremap_res.patch b/target/linux/generic/backport-5.15/819-v6.6-0001-nvmem-sunxi_sid-Convert-to-devm_platform_ioremap_res.patch
deleted file mode 100644 (file)
index bf7a816..0000000
+++ /dev/null
@@ -1,36 +0,0 @@
-From 9ccfcbeb8f32ff89e99b36cb9cdebaa0d1b44ed1 Mon Sep 17 00:00:00 2001
-From: Yangtao Li <[email protected]>
-Date: Wed, 23 Aug 2023 14:27:24 +0100
-Subject: [PATCH] nvmem: sunxi_sid: Convert to devm_platform_ioremap_resource()
-
-Use devm_platform_ioremap_resource() to simplify code.
-
-Signed-off-by: Yangtao Li <[email protected]>
-Acked-by: Jernej Skrabec <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/sunxi_sid.c | 4 +---
- 1 file changed, 1 insertion(+), 3 deletions(-)
-
---- a/drivers/nvmem/sunxi_sid.c
-+++ b/drivers/nvmem/sunxi_sid.c
-@@ -125,7 +125,6 @@ static int sun8i_sid_read_by_reg(void *c
- static int sunxi_sid_probe(struct platform_device *pdev)
- {
-       struct device *dev = &pdev->dev;
--      struct resource *res;
-       struct nvmem_config *nvmem_cfg;
-       struct nvmem_device *nvmem;
-       struct sunxi_sid *sid;
-@@ -142,8 +141,7 @@ static int sunxi_sid_probe(struct platfo
-               return -EINVAL;
-       sid->value_offset = cfg->value_offset;
--      res = platform_get_resource(pdev, IORESOURCE_MEM, 0);
--      sid->base = devm_ioremap_resource(dev, res);
-+      sid->base = devm_platform_ioremap_resource(pdev, 0);
-       if (IS_ERR(sid->base))
-               return PTR_ERR(sid->base);
diff --git a/target/linux/generic/backport-5.15/819-v6.6-0002-nvmem-brcm_nvram-Use-devm_platform_get_and_ioremap_r.patch b/target/linux/generic/backport-5.15/819-v6.6-0002-nvmem-brcm_nvram-Use-devm_platform_get_and_ioremap_r.patch
deleted file mode 100644 (file)
index f142d73..0000000
+++ /dev/null
@@ -1,30 +0,0 @@
-From cfadd0e7d9225566f320bc4dc716682be910be6c Mon Sep 17 00:00:00 2001
-From: Yangtao Li <[email protected]>
-Date: Wed, 23 Aug 2023 14:27:25 +0100
-Subject: [PATCH] nvmem: brcm_nvram: Use
- devm_platform_get_and_ioremap_resource()
-
-Convert platform_get_resource(), devm_ioremap_resource() to a single
-call to devm_platform_get_and_ioremap_resource(), as this is exactly
-what this function does.
-
-Signed-off-by: Yangtao Li <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/brcm_nvram.c | 3 +--
- 1 file changed, 1 insertion(+), 2 deletions(-)
-
---- a/drivers/nvmem/brcm_nvram.c
-+++ b/drivers/nvmem/brcm_nvram.c
-@@ -159,8 +159,7 @@ static int brcm_nvram_probe(struct platf
-               return -ENOMEM;
-       priv->dev = dev;
--      res = platform_get_resource(pdev, IORESOURCE_MEM, 0);
--      priv->base = devm_ioremap_resource(dev, res);
-+      priv->base = devm_platform_get_and_ioremap_resource(pdev, 0, &res);
-       if (IS_ERR(priv->base))
-               return PTR_ERR(priv->base);
diff --git a/target/linux/generic/backport-5.15/819-v6.6-0003-nvmem-lpc18xx_otp-Convert-to-devm_platform_ioremap_r.patch b/target/linux/generic/backport-5.15/819-v6.6-0003-nvmem-lpc18xx_otp-Convert-to-devm_platform_ioremap_r.patch
deleted file mode 100644 (file)
index 0395bbf..0000000
+++ /dev/null
@@ -1,34 +0,0 @@
-From 0b49178e2b6b4aac3c7fa3ce8d8c02208a13b988 Mon Sep 17 00:00:00 2001
-From: Yangtao Li <[email protected]>
-Date: Wed, 23 Aug 2023 14:27:26 +0100
-Subject: [PATCH] nvmem: lpc18xx_otp: Convert to
- devm_platform_ioremap_resource()
-
-Use devm_platform_ioremap_resource() to simplify code.
-
-Signed-off-by: Yangtao Li <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/lpc18xx_otp.c | 4 +---
- 1 file changed, 1 insertion(+), 3 deletions(-)
-
---- a/drivers/nvmem/lpc18xx_otp.c
-+++ b/drivers/nvmem/lpc18xx_otp.c
-@@ -68,14 +68,12 @@ static int lpc18xx_otp_probe(struct plat
- {
-       struct nvmem_device *nvmem;
-       struct lpc18xx_otp *otp;
--      struct resource *res;
-       otp = devm_kzalloc(&pdev->dev, sizeof(*otp), GFP_KERNEL);
-       if (!otp)
-               return -ENOMEM;
--      res = platform_get_resource(pdev, IORESOURCE_MEM, 0);
--      otp->base = devm_ioremap_resource(&pdev->dev, res);
-+      otp->base = devm_platform_ioremap_resource(pdev, 0);
-       if (IS_ERR(otp->base))
-               return PTR_ERR(otp->base);
diff --git a/target/linux/generic/backport-5.15/819-v6.6-0004-nvmem-meson-mx-efuse-Convert-to-devm_platform_iorema.patch b/target/linux/generic/backport-5.15/819-v6.6-0004-nvmem-meson-mx-efuse-Convert-to-devm_platform_iorema.patch
deleted file mode 100644 (file)
index da077eb..0000000
+++ /dev/null
@@ -1,36 +0,0 @@
-From 0a223a097709b99a0ba738d6be5b4f52c04ffb64 Mon Sep 17 00:00:00 2001
-From: Yangtao Li <[email protected]>
-Date: Wed, 23 Aug 2023 14:27:27 +0100
-Subject: [PATCH] nvmem: meson-mx-efuse: Convert to
- devm_platform_ioremap_resource()
-
-Use devm_platform_ioremap_resource() to simplify code.
-
-Signed-off-by: Yangtao Li <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/meson-mx-efuse.c | 4 +---
- 1 file changed, 1 insertion(+), 3 deletions(-)
-
---- a/drivers/nvmem/meson-mx-efuse.c
-+++ b/drivers/nvmem/meson-mx-efuse.c
-@@ -194,7 +194,6 @@ static int meson_mx_efuse_probe(struct p
- {
-       const struct meson_mx_efuse_platform_data *drvdata;
-       struct meson_mx_efuse *efuse;
--      struct resource *res;
-       drvdata = of_device_get_match_data(&pdev->dev);
-       if (!drvdata)
-@@ -204,8 +203,7 @@ static int meson_mx_efuse_probe(struct p
-       if (!efuse)
-               return -ENOMEM;
--      res = platform_get_resource(pdev, IORESOURCE_MEM, 0);
--      efuse->base = devm_ioremap_resource(&pdev->dev, res);
-+      efuse->base = devm_platform_ioremap_resource(pdev, 0);
-       if (IS_ERR(efuse->base))
-               return PTR_ERR(efuse->base);
diff --git a/target/linux/generic/backport-5.15/819-v6.6-0005-nvmem-rockchip-efuse-Use-devm_platform_get_and_iorem.patch b/target/linux/generic/backport-5.15/819-v6.6-0005-nvmem-rockchip-efuse-Use-devm_platform_get_and_iorem.patch
deleted file mode 100644 (file)
index dc144dd..0000000
+++ /dev/null
@@ -1,31 +0,0 @@
-From 94904db28db49ac8fbb2a273d25156db26a3a985 Mon Sep 17 00:00:00 2001
-From: Yangtao Li <[email protected]>
-Date: Wed, 23 Aug 2023 14:27:28 +0100
-Subject: [PATCH] nvmem: rockchip-efuse: Use
- devm_platform_get_and_ioremap_resource()
-
-Convert platform_get_resource(), devm_ioremap_resource() to a single
-call to devm_platform_get_and_ioremap_resource(), as this is exactly
-what this function does.
-
-Signed-off-by: Yangtao Li <[email protected]>
-Reviewed-by: Heiko Stuebner <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/rockchip-efuse.c | 3 +--
- 1 file changed, 1 insertion(+), 2 deletions(-)
-
---- a/drivers/nvmem/rockchip-efuse.c
-+++ b/drivers/nvmem/rockchip-efuse.c
-@@ -267,8 +267,7 @@ static int rockchip_efuse_probe(struct p
-       if (!efuse)
-               return -ENOMEM;
--      res = platform_get_resource(pdev, IORESOURCE_MEM, 0);
--      efuse->base = devm_ioremap_resource(dev, res);
-+      efuse->base = devm_platform_get_and_ioremap_resource(pdev, 0, &res);
-       if (IS_ERR(efuse->base))
-               return PTR_ERR(efuse->base);
diff --git a/target/linux/generic/backport-5.15/819-v6.6-0006-nvmem-stm32-romem-Use-devm_platform_get_and_ioremap_.patch b/target/linux/generic/backport-5.15/819-v6.6-0006-nvmem-stm32-romem-Use-devm_platform_get_and_ioremap_.patch
deleted file mode 100644 (file)
index 99e2093..0000000
+++ /dev/null
@@ -1,30 +0,0 @@
-From 0a4a8c0d238fec1fa4b85591524ef42ad261cb97 Mon Sep 17 00:00:00 2001
-From: Yangtao Li <[email protected]>
-Date: Wed, 23 Aug 2023 14:27:29 +0100
-Subject: [PATCH] nvmem: stm32-romem: Use
- devm_platform_get_and_ioremap_resource()
-
-Convert platform_get_resource(), devm_ioremap_resource() to a single
-call to devm_platform_get_and_ioremap_resource(), as this is exactly
-what this function does.
-
-Signed-off-by: Yangtao Li <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/stm32-romem.c | 3 +--
- 1 file changed, 1 insertion(+), 2 deletions(-)
-
---- a/drivers/nvmem/stm32-romem.c
-+++ b/drivers/nvmem/stm32-romem.c
-@@ -196,8 +196,7 @@ static int stm32_romem_probe(struct plat
-       if (!priv)
-               return -ENOMEM;
--      res = platform_get_resource(pdev, IORESOURCE_MEM, 0);
--      priv->base = devm_ioremap_resource(dev, res);
-+      priv->base = devm_platform_get_and_ioremap_resource(pdev, 0, &res);
-       if (IS_ERR(priv->base))
-               return PTR_ERR(priv->base);
diff --git a/target/linux/generic/backport-5.15/819-v6.6-0007-nvmem-qfprom-do-some-cleanup.patch b/target/linux/generic/backport-5.15/819-v6.6-0007-nvmem-qfprom-do-some-cleanup.patch
deleted file mode 100644 (file)
index 6d93752..0000000
+++ /dev/null
@@ -1,59 +0,0 @@
-From 0bc0d6dc2a9a05ae6729b4622f09782d9f230815 Mon Sep 17 00:00:00 2001
-From: Yangtao Li <[email protected]>
-Date: Wed, 23 Aug 2023 14:27:30 +0100
-Subject: [PATCH] nvmem: qfprom: do some cleanup
-
-Use devm_platform_ioremap_resource() and
-devm_platform_get_and_ioremap_resource() to simplify code.
-BTW convert to use dev_err_probe() instead of open it.
-
-Signed-off-by: Yangtao Li <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/qfprom.c | 17 +++++------------
- 1 file changed, 5 insertions(+), 12 deletions(-)
-
---- a/drivers/nvmem/qfprom.c
-+++ b/drivers/nvmem/qfprom.c
-@@ -374,8 +374,7 @@ static int qfprom_probe(struct platform_
-               return -ENOMEM;
-       /* The corrected section is always provided */
--      res = platform_get_resource(pdev, IORESOURCE_MEM, 0);
--      priv->qfpcorrected = devm_ioremap_resource(dev, res);
-+      priv->qfpcorrected = devm_platform_get_and_ioremap_resource(pdev, 0, &res);
-       if (IS_ERR(priv->qfpcorrected))
-               return PTR_ERR(priv->qfpcorrected);
-@@ -402,12 +401,10 @@ static int qfprom_probe(struct platform_
-               priv->qfpraw = devm_ioremap_resource(dev, res);
-               if (IS_ERR(priv->qfpraw))
-                       return PTR_ERR(priv->qfpraw);
--              res = platform_get_resource(pdev, IORESOURCE_MEM, 2);
--              priv->qfpconf = devm_ioremap_resource(dev, res);
-+              priv->qfpconf = devm_platform_ioremap_resource(pdev, 2);
-               if (IS_ERR(priv->qfpconf))
-                       return PTR_ERR(priv->qfpconf);
--              res = platform_get_resource(pdev, IORESOURCE_MEM, 3);
--              priv->qfpsecurity = devm_ioremap_resource(dev, res);
-+              priv->qfpsecurity = devm_platform_ioremap_resource(pdev, 3);
-               if (IS_ERR(priv->qfpsecurity))
-                       return PTR_ERR(priv->qfpsecurity);
-@@ -427,12 +424,8 @@ static int qfprom_probe(struct platform_
-                       return PTR_ERR(priv->vcc);
-               priv->secclk = devm_clk_get(dev, "core");
--              if (IS_ERR(priv->secclk)) {
--                      ret = PTR_ERR(priv->secclk);
--                      if (ret != -EPROBE_DEFER)
--                              dev_err(dev, "Error getting clock: %d\n", ret);
--                      return ret;
--              }
-+              if (IS_ERR(priv->secclk))
-+                      return dev_err_probe(dev, PTR_ERR(priv->secclk), "Error getting clock\n");
-               /* Only enable writing if we have SoC data. */
-               if (priv->soc_data)
diff --git a/target/linux/generic/backport-5.15/819-v6.6-0008-nvmem-uniphier-Use-devm_platform_get_and_ioremap_res.patch b/target/linux/generic/backport-5.15/819-v6.6-0008-nvmem-uniphier-Use-devm_platform_get_and_ioremap_res.patch
deleted file mode 100644 (file)
index 3e328a4..0000000
+++ /dev/null
@@ -1,29 +0,0 @@
-From 6ac41c556e22a0d7d267c9b9d48681d73af4b368 Mon Sep 17 00:00:00 2001
-From: Yangtao Li <[email protected]>
-Date: Wed, 23 Aug 2023 14:27:31 +0100
-Subject: [PATCH] nvmem: uniphier: Use devm_platform_get_and_ioremap_resource()
-
-Convert platform_get_resource(), devm_ioremap_resource() to a single
-call to devm_platform_get_and_ioremap_resource(), as this is exactly
-what this function does.
-
-Signed-off-by: Yangtao Li <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/uniphier-efuse.c | 3 +--
- 1 file changed, 1 insertion(+), 2 deletions(-)
-
---- a/drivers/nvmem/uniphier-efuse.c
-+++ b/drivers/nvmem/uniphier-efuse.c
-@@ -41,8 +41,7 @@ static int uniphier_efuse_probe(struct p
-       if (!priv)
-               return -ENOMEM;
--      res = platform_get_resource(pdev, IORESOURCE_MEM, 0);
--      priv->base = devm_ioremap_resource(dev, res);
-+      priv->base = devm_platform_get_and_ioremap_resource(pdev, 0, &res);
-       if (IS_ERR(priv->base))
-               return PTR_ERR(priv->base);
diff --git a/target/linux/generic/backport-5.15/819-v6.6-0009-nvmem-add-new-NXP-QorIQ-eFuse-driver.patch b/target/linux/generic/backport-5.15/819-v6.6-0009-nvmem-add-new-NXP-QorIQ-eFuse-driver.patch
deleted file mode 100644 (file)
index acbe18e..0000000
+++ /dev/null
@@ -1,133 +0,0 @@
-From c8efcf7a86ebf2ff48584d270b3070a7075bc345 Mon Sep 17 00:00:00 2001
-From: Richard Alpe <[email protected]>
-Date: Mon, 10 Apr 2023 10:20:51 +0200
-Subject: [PATCH] nvmem: add new NXP QorIQ eFuse driver
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-Add SFP (Security Fuse Processor) read support for NXP (Freescale)
-QorIQ series SOC's.
-
-This patch adds support for the T1023 SOC using the SFP offset from
-the existing T1023 device tree. In theory this should also work for
-T1024, T1014 and T1013 which uses the same SFP base offset.
-
-Signed-off-by: Richard Alpe <[email protected]>
-Reviewed-by: Niklas Söderlund <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
----
- drivers/nvmem/Kconfig       | 12 ++++++
- drivers/nvmem/Makefile      |  2 +
- drivers/nvmem/qoriq-efuse.c | 78 +++++++++++++++++++++++++++++++++++++
- 3 files changed, 92 insertions(+)
- create mode 100644 drivers/nvmem/qoriq-efuse.c
-
---- a/drivers/nvmem/Kconfig
-+++ b/drivers/nvmem/Kconfig
-@@ -392,4 +392,16 @@ config NVMEM_ZYNQMP
-         If sure, say yes. If unsure, say no.
-+config NVMEM_QORIQ_EFUSE
-+      tristate "NXP QorIQ eFuse support"
-+      depends on PPC_85xx || COMPILE_TEST
-+      depends on HAS_IOMEM
-+      help
-+        This driver provides read support for the eFuses (SFP) on NXP QorIQ
-+        series SoC's. This includes secure boot settings, the globally unique
-+        NXP ID 'FUIDR' and the OEM unique ID 'OUIDR'.
-+
-+        This driver can also be built as a module. If so, the module
-+        will be called nvmem_qoriq_efuse.
-+
- endif
---- a/drivers/nvmem/Makefile
-+++ b/drivers/nvmem/Makefile
-@@ -77,3 +77,5 @@ obj-$(CONFIG_NVMEM_VF610_OCOTP)              += nvme
- nvmem-vf610-ocotp-y                   := vf610-ocotp.o
- obj-$(CONFIG_NVMEM_ZYNQMP)            += nvmem_zynqmp_nvmem.o
- nvmem_zynqmp_nvmem-y                  := zynqmp_nvmem.o
-+obj-$(CONFIG_NVMEM_QORIQ_EFUSE)               += nvmem-qoriq-efuse.o
-+nvmem-qoriq-efuse-y                   := qoriq-efuse.o
---- /dev/null
-+++ b/drivers/nvmem/qoriq-efuse.c
-@@ -0,0 +1,78 @@
-+// SPDX-License-Identifier: GPL-2.0
-+/*
-+ *  Copyright (C) 2023  Westermo Network Technologies AB
-+ */
-+
-+#include <linux/device.h>
-+#include <linux/io.h>
-+#include <linux/module.h>
-+#include <linux/mod_devicetable.h>
-+#include <linux/nvmem-provider.h>
-+#include <linux/platform_device.h>
-+
-+struct qoriq_efuse_priv {
-+      void __iomem *base;
-+};
-+
-+static int qoriq_efuse_read(void *context, unsigned int offset, void *val,
-+                          size_t bytes)
-+{
-+      struct qoriq_efuse_priv *priv = context;
-+
-+      /* .stride = 4 so offset is guaranteed to be aligned */
-+      __ioread32_copy(val, priv->base + offset, bytes / 4);
-+
-+      /* Ignore trailing bytes (there shouldn't be any) */
-+
-+      return 0;
-+}
-+
-+static int qoriq_efuse_probe(struct platform_device *pdev)
-+{
-+      struct nvmem_config config = {
-+              .dev = &pdev->dev,
-+              .read_only = true,
-+              .reg_read = qoriq_efuse_read,
-+              .stride = sizeof(u32),
-+              .word_size = sizeof(u32),
-+              .name = "qoriq_efuse_read",
-+              .id = NVMEM_DEVID_AUTO,
-+              .root_only = true,
-+      };
-+      struct qoriq_efuse_priv *priv;
-+      struct nvmem_device *nvmem;
-+      struct resource *res;
-+
-+      priv = devm_kzalloc(config.dev, sizeof(*priv), GFP_KERNEL);
-+      if (!priv)
-+              return -ENOMEM;
-+
-+      priv->base = devm_platform_get_and_ioremap_resource(pdev, 0, &res);
-+      if (IS_ERR(priv->base))
-+              return PTR_ERR(priv->base);
-+
-+      config.size = resource_size(res);
-+      config.priv = priv;
-+      nvmem = devm_nvmem_register(config.dev, &config);
-+
-+      return PTR_ERR_OR_ZERO(nvmem);
-+}
-+
-+static const struct of_device_id qoriq_efuse_of_match[] = {
-+      { .compatible = "fsl,t1023-sfp", },
-+      {/* sentinel */},
-+};
-+MODULE_DEVICE_TABLE(of, qoriq_efuse_of_match);
-+
-+static struct platform_driver qoriq_efuse_driver = {
-+      .probe = qoriq_efuse_probe,
-+      .driver = {
-+              .name = "qoriq-efuse",
-+              .of_match_table = qoriq_efuse_of_match,
-+      },
-+};
-+module_platform_driver(qoriq_efuse_driver);
-+
-+MODULE_AUTHOR("Richard Alpe <[email protected]>");
-+MODULE_DESCRIPTION("NXP QorIQ Security Fuse Processor (SFP) Reader");
-+MODULE_LICENSE("GPL");
diff --git a/target/linux/generic/backport-5.15/819-v6.6-0011-nvmem-Kconfig-Fix-typo-drive-driver.patch b/target/linux/generic/backport-5.15/819-v6.6-0011-nvmem-Kconfig-Fix-typo-drive-driver.patch
deleted file mode 100644 (file)
index 67f30e3..0000000
+++ /dev/null
@@ -1,37 +0,0 @@
-From 9d53d595f688c9837e88a919229cc61a165c7b9e Mon Sep 17 00:00:00 2001
-From: Diederik de Haas <[email protected]>
-Date: Mon, 24 Jul 2023 13:36:22 +0200
-Subject: [PATCH] nvmem: Kconfig: Fix typo "drive" -> "driver"
-
-Fix typo where "driver" was meant instead of "drive".
-While at it, also capitalize "OTP".
-
-Signed-off-by: Diederik de Haas <[email protected]>
-Reviewed-by: Heiko Stuebner <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
----
- drivers/nvmem/Kconfig | 6 +++---
- 1 file changed, 3 insertions(+), 3 deletions(-)
-
---- a/drivers/nvmem/Kconfig
-+++ b/drivers/nvmem/Kconfig
-@@ -247,7 +247,7 @@ config NVMEM_ROCKCHIP_EFUSE
-       depends on ARCH_ROCKCHIP || COMPILE_TEST
-       depends on HAS_IOMEM
-       help
--        This is a simple drive to dump specified values of Rockchip SoC
-+        This is a simple driver to dump specified values of Rockchip SoC
-         from eFuse, such as cpu-leakage.
-         This driver can also be built as a module. If so, the module
-@@ -258,8 +258,8 @@ config NVMEM_ROCKCHIP_OTP
-       depends on ARCH_ROCKCHIP || COMPILE_TEST
-       depends on HAS_IOMEM
-       help
--        This is a simple drive to dump specified values of Rockchip SoC
--        from otp, such as cpu-leakage.
-+        This is a simple driver to dump specified values of Rockchip SoC
-+        from OTP, such as cpu-leakage.
-         This driver can also be built as a module. If so, the module
-         will be called nvmem_rockchip_otp.
diff --git a/target/linux/generic/backport-5.15/819-v6.6-0012-nvmem-sec-qfprom-Add-Qualcomm-secure-QFPROM-support.patch b/target/linux/generic/backport-5.15/819-v6.6-0012-nvmem-sec-qfprom-Add-Qualcomm-secure-QFPROM-support.patch
deleted file mode 100644 (file)
index d24a624..0000000
+++ /dev/null
@@ -1,152 +0,0 @@
-From 0a9ec38c47c1ca4528aa058e2b9ea61901a7e632 Mon Sep 17 00:00:00 2001
-From: Komal Bajaj <[email protected]>
-Date: Tue, 1 Aug 2023 12:10:25 +0530
-Subject: [PATCH] nvmem: sec-qfprom: Add Qualcomm secure QFPROM support
-
-For some of the Qualcomm SoC's, it is possible that
-some of the fuse regions or entire qfprom region is
-protected from non-secure access. In such situations,
-the OS will have to use secure calls to read the region.
-With that motivation, add secure qfprom driver.
-
-Signed-off-by: Komal Bajaj <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
----
- drivers/nvmem/Kconfig      | 13 ++++++
- drivers/nvmem/Makefile     |  2 +
- drivers/nvmem/sec-qfprom.c | 96 ++++++++++++++++++++++++++++++++++++++
- 3 files changed, 111 insertions(+)
- create mode 100644 drivers/nvmem/sec-qfprom.c
-
---- a/drivers/nvmem/Kconfig
-+++ b/drivers/nvmem/Kconfig
-@@ -226,6 +226,19 @@ config NVMEM_QCOM_QFPROM
-         This driver can also be built as a module. If so, the module
-         will be called nvmem_qfprom.
-+config NVMEM_QCOM_SEC_QFPROM
-+        tristate "QCOM SECURE QFPROM Support"
-+        depends on ARCH_QCOM || COMPILE_TEST
-+        depends on HAS_IOMEM
-+        depends on OF
-+        select QCOM_SCM
-+        help
-+          Say y here to enable secure QFPROM support. The secure QFPROM provides access
-+          functions for QFPROM data to rest of the drivers via nvmem interface.
-+
-+          This driver can also be built as a module. If so, the module will be called
-+          nvmem_sec_qfprom.
-+
- config NVMEM_RAVE_SP_EEPROM
-       tristate "Rave SP EEPROM Support"
-       depends on RAVE_SP_CORE
---- a/drivers/nvmem/Makefile
-+++ b/drivers/nvmem/Makefile
-@@ -46,6 +46,8 @@ obj-$(CONFIG_NVMEM_NINTENDO_OTP)     += nvme
- nvmem-nintendo-otp-y                  := nintendo-otp.o
- obj-$(CONFIG_NVMEM_QCOM_QFPROM)               += nvmem_qfprom.o
- nvmem_qfprom-y                                := qfprom.o
-+obj-$(CONFIG_NVMEM_QCOM_SEC_QFPROM)   += nvmem_sec_qfprom.o
-+nvmem_sec_qfprom-y                    := sec-qfprom.o
- obj-$(CONFIG_NVMEM_RAVE_SP_EEPROM)    += nvmem-rave-sp-eeprom.o
- nvmem-rave-sp-eeprom-y                        := rave-sp-eeprom.o
- obj-$(CONFIG_NVMEM_RMEM)              += nvmem-rmem.o
---- /dev/null
-+++ b/drivers/nvmem/sec-qfprom.c
-@@ -0,0 +1,96 @@
-+// SPDX-License-Identifier: GPL-2.0-only
-+/*
-+ * Copyright (c) 2023, Qualcomm Innovation Center, Inc. All rights reserved.
-+ */
-+
-+#include <linux/firmware/qcom/qcom_scm.h>
-+#include <linux/mod_devicetable.h>
-+#include <linux/nvmem-provider.h>
-+#include <linux/platform_device.h>
-+#include <linux/pm_runtime.h>
-+
-+/**
-+ * struct sec_qfprom - structure holding secure qfprom attributes
-+ *
-+ * @base: starting physical address for secure qfprom corrected address space.
-+ * @dev: qfprom device structure.
-+ */
-+struct sec_qfprom {
-+      phys_addr_t base;
-+      struct device *dev;
-+};
-+
-+static int sec_qfprom_reg_read(void *context, unsigned int reg, void *_val, size_t bytes)
-+{
-+      struct sec_qfprom *priv = context;
-+      unsigned int i;
-+      u8 *val = _val;
-+      u32 read_val;
-+      u8 *tmp;
-+
-+      for (i = 0; i < bytes; i++, reg++) {
-+              if (i == 0 || reg % 4 == 0) {
-+                      if (qcom_scm_io_readl(priv->base + (reg & ~3), &read_val)) {
-+                              dev_err(priv->dev, "Couldn't access fuse register\n");
-+                              return -EINVAL;
-+                      }
-+                      tmp = (u8 *)&read_val;
-+              }
-+
-+              val[i] = tmp[reg & 3];
-+      }
-+
-+      return 0;
-+}
-+
-+static int sec_qfprom_probe(struct platform_device *pdev)
-+{
-+      struct nvmem_config econfig = {
-+              .name = "sec-qfprom",
-+              .stride = 1,
-+              .word_size = 1,
-+              .id = NVMEM_DEVID_AUTO,
-+              .reg_read = sec_qfprom_reg_read,
-+      };
-+      struct device *dev = &pdev->dev;
-+      struct nvmem_device *nvmem;
-+      struct sec_qfprom *priv;
-+      struct resource *res;
-+
-+      priv = devm_kzalloc(dev, sizeof(*priv), GFP_KERNEL);
-+      if (!priv)
-+              return -ENOMEM;
-+
-+      res = platform_get_resource(pdev, IORESOURCE_MEM, 0);
-+      if (!res)
-+              return -EINVAL;
-+
-+      priv->base = res->start;
-+
-+      econfig.size = resource_size(res);
-+      econfig.dev = dev;
-+      econfig.priv = priv;
-+
-+      priv->dev = dev;
-+
-+      nvmem = devm_nvmem_register(dev, &econfig);
-+
-+      return PTR_ERR_OR_ZERO(nvmem);
-+}
-+
-+static const struct of_device_id sec_qfprom_of_match[] = {
-+      { .compatible = "qcom,sec-qfprom" },
-+      {/* sentinel */},
-+};
-+MODULE_DEVICE_TABLE(of, sec_qfprom_of_match);
-+
-+static struct platform_driver qfprom_driver = {
-+      .probe = sec_qfprom_probe,
-+      .driver = {
-+              .name = "qcom_sec_qfprom",
-+              .of_match_table = sec_qfprom_of_match,
-+      },
-+};
-+module_platform_driver(qfprom_driver);
-+MODULE_DESCRIPTION("Qualcomm Secure QFPROM driver");
-+MODULE_LICENSE("GPL");
diff --git a/target/linux/generic/backport-5.15/819-v6.6-0013-nvmem-u-boot-env-Replace-zero-length-array-with-DECL.patch b/target/linux/generic/backport-5.15/819-v6.6-0013-nvmem-u-boot-env-Replace-zero-length-array-with-DECL.patch
deleted file mode 100644 (file)
index dab8ec2..0000000
+++ /dev/null
@@ -1,30 +0,0 @@
-From c32f2186acc9abb4d766361255d7ddf07d15eeb2 Mon Sep 17 00:00:00 2001
-From: Atul Raut <[email protected]>
-Date: Sun, 30 Jul 2023 15:39:15 -0700
-Subject: [PATCH] nvmem: u-boot-env:: Replace zero-length array with
- DECLARE_FLEX_ARRAY() helper
-
-We are moving toward replacing zero-length arrays with C99 flexible-array
-members since they are deprecated. Therefore, the new DECLARE_FLEX_ARRAY()
-helper macro should be used to replace the zero-length array declaration.
-
-This fixes warnings such as:
-./drivers/nvmem/u-boot-env.c:50:9-13: WARNING use flexible-array member instead (https://www.kernel.org/doc/html/latest/process/deprecated.html#zero-length-and-one-element-arrays)
-
-Signed-off-by: Atul Raut <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
----
- drivers/nvmem/u-boot-env.c | 2 +-
- 1 file changed, 1 insertion(+), 1 deletion(-)
-
---- a/drivers/nvmem/u-boot-env.c
-+++ b/drivers/nvmem/u-boot-env.c
-@@ -47,7 +47,7 @@ struct u_boot_env_image_broadcom {
-       __le32 magic;
-       __le32 len;
-       __le32 crc32;
--      uint8_t data[0];
-+      DECLARE_FLEX_ARRAY(uint8_t, data);
- } __packed;
- static int u_boot_env_read(void *context, unsigned int offset, void *val,
diff --git a/target/linux/generic/backport-5.15/819-v6.6-0014-nvmem-core-Create-all-cells-before-adding-the-nvmem-.patch b/target/linux/generic/backport-5.15/819-v6.6-0014-nvmem-core-Create-all-cells-before-adding-the-nvmem-.patch
deleted file mode 100644 (file)
index f9532f3..0000000
+++ /dev/null
@@ -1,40 +0,0 @@
-From 104af6a5b199eb4dc7970d1304aef38ac5a6ed54 Mon Sep 17 00:00:00 2001
-From: Miquel Raynal <[email protected]>
-Date: Tue, 8 Aug 2023 08:29:26 +0200
-Subject: [PATCH] nvmem: core: Create all cells before adding the nvmem device
-
-Let's pack all the cells creation in one place, so they are all created
-before we add the nvmem device.
-
-Signed-off-by: Miquel Raynal <[email protected]>
-Reviewed-by: Michael Walle <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
----
- drivers/nvmem/core.c | 10 +++++-----
- 1 file changed, 5 insertions(+), 5 deletions(-)
-
---- a/drivers/nvmem/core.c
-+++ b/drivers/nvmem/core.c
-@@ -998,17 +998,17 @@ struct nvmem_device *nvmem_register(cons
-       if (rval)
-               goto err_remove_cells;
--      dev_dbg(&nvmem->dev, "Registering nvmem device %s\n", config->name);
--
--      rval = device_add(&nvmem->dev);
-+      rval = nvmem_add_cells_from_fixed_layout(nvmem);
-       if (rval)
-               goto err_remove_cells;
--      rval = nvmem_add_cells_from_fixed_layout(nvmem);
-+      rval = nvmem_add_cells_from_layout(nvmem);
-       if (rval)
-               goto err_remove_cells;
--      rval = nvmem_add_cells_from_layout(nvmem);
-+      dev_dbg(&nvmem->dev, "Registering nvmem device %s\n", config->name);
-+
-+      rval = device_add(&nvmem->dev);
-       if (rval)
-               goto err_remove_cells;
diff --git a/target/linux/generic/backport-5.15/819-v6.6-0015-nvmem-core-Return-NULL-when-no-nvmem-layout-is-found.patch b/target/linux/generic/backport-5.15/819-v6.6-0015-nvmem-core-Return-NULL-when-no-nvmem-layout-is-found.patch
deleted file mode 100644 (file)
index 8f64d0c..0000000
+++ /dev/null
@@ -1,35 +0,0 @@
-From 6c7f48ea2e663b679aa8e60d8d8e1e6306a644f9 Mon Sep 17 00:00:00 2001
-From: Miquel Raynal <[email protected]>
-Date: Tue, 8 Aug 2023 08:29:27 +0200
-Subject: [PATCH] nvmem: core: Return NULL when no nvmem layout is found
-
-Currently, of_nvmem_layout_get_container() returns NULL on error, or an
-error pointer if either CONFIG_NVMEM or CONFIG_OF is turned off. We
-should likely avoid this kind of mix for two reasons: to clarify the
-intend and anyway fix the !CONFIG_OF which will likely always if we use
-this helper somewhere else. Let's just return NULL when no layout is
-found, we don't need an error value here.
-
-Link: https://staticthinking.wordpress.com/2022/08/01/mixing-error-pointers-and-null/
-Fixes: 266570f496b9 ("nvmem: core: introduce NVMEM layouts")
-Reported-by: kernel test robot <[email protected]>
-Reported-by: Dan Carpenter <[email protected]>
-Closes: https://lore.kernel.org/r/[email protected]/
-Signed-off-by: Miquel Raynal <[email protected]>
-Reviewed-by: Michael Walle <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
----
- include/linux/nvmem-consumer.h | 2 +-
- 1 file changed, 1 insertion(+), 1 deletion(-)
-
---- a/include/linux/nvmem-consumer.h
-+++ b/include/linux/nvmem-consumer.h
-@@ -256,7 +256,7 @@ static inline struct nvmem_device *of_nv
- static inline struct device_node *
- of_nvmem_layout_get_container(struct nvmem_device *nvmem)
- {
--      return ERR_PTR(-EOPNOTSUPP);
-+      return NULL;
- }
- #endif /* CONFIG_NVMEM && CONFIG_OF */
diff --git a/target/linux/generic/backport-5.15/819-v6.6-0016-nvmem-core-Do-not-open-code-existing-functions.patch b/target/linux/generic/backport-5.15/819-v6.6-0016-nvmem-core-Do-not-open-code-existing-functions.patch
deleted file mode 100644 (file)
index 28d8bba..0000000
+++ /dev/null
@@ -1,29 +0,0 @@
-From b8257f61b4ddac6d7d0e19a5a4e8b07afb3b4ed3 Mon Sep 17 00:00:00 2001
-From: Miquel Raynal <[email protected]>
-Date: Tue, 8 Aug 2023 08:29:28 +0200
-Subject: [PATCH] nvmem: core: Do not open-code existing functions
-
-Use of_nvmem_layout_get_container() instead of hardcoding it.
-
-Signed-off-by: Miquel Raynal <[email protected]>
-Reviewed-by: Michael Walle <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
----
- drivers/nvmem/core.c | 4 ++--
- 1 file changed, 2 insertions(+), 2 deletions(-)
-
---- a/drivers/nvmem/core.c
-+++ b/drivers/nvmem/core.c
-@@ -786,10 +786,10 @@ EXPORT_SYMBOL_GPL(nvmem_layout_unregiste
- static struct nvmem_layout *nvmem_layout_get(struct nvmem_device *nvmem)
- {
--      struct device_node *layout_np, *np = nvmem->dev.of_node;
-+      struct device_node *layout_np;
-       struct nvmem_layout *l, *layout = ERR_PTR(-EPROBE_DEFER);
--      layout_np = of_get_child_by_name(np, "nvmem-layout");
-+      layout_np = of_nvmem_layout_get_container(nvmem);
-       if (!layout_np)
-               return NULL;
diff --git a/target/linux/generic/backport-5.15/819-v6.6-0017-nvmem-core-Notify-when-a-new-layout-is-registered.patch b/target/linux/generic/backport-5.15/819-v6.6-0017-nvmem-core-Notify-when-a-new-layout-is-registered.patch
deleted file mode 100644 (file)
index b62a0e1..0000000
+++ /dev/null
@@ -1,44 +0,0 @@
-From 0991afbe4b1805e7f0113ef10d7c5f0698a739e4 Mon Sep 17 00:00:00 2001
-From: Miquel Raynal <[email protected]>
-Date: Tue, 8 Aug 2023 08:29:29 +0200
-Subject: [PATCH] nvmem: core: Notify when a new layout is registered
-
-Tell listeners a new layout was introduced and is now available.
-
-Signed-off-by: Miquel Raynal <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
----
- drivers/nvmem/core.c           | 4 ++++
- include/linux/nvmem-consumer.h | 2 ++
- 2 files changed, 6 insertions(+)
-
---- a/drivers/nvmem/core.c
-+++ b/drivers/nvmem/core.c
-@@ -772,12 +772,16 @@ int __nvmem_layout_register(struct nvmem
-       list_add(&layout->node, &nvmem_layouts);
-       spin_unlock(&nvmem_layout_lock);
-+      blocking_notifier_call_chain(&nvmem_notifier, NVMEM_LAYOUT_ADD, layout);
-+
-       return 0;
- }
- EXPORT_SYMBOL_GPL(__nvmem_layout_register);
- void nvmem_layout_unregister(struct nvmem_layout *layout)
- {
-+      blocking_notifier_call_chain(&nvmem_notifier, NVMEM_LAYOUT_REMOVE, layout);
-+
-       spin_lock(&nvmem_layout_lock);
-       list_del(&layout->node);
-       spin_unlock(&nvmem_layout_lock);
---- a/include/linux/nvmem-consumer.h
-+++ b/include/linux/nvmem-consumer.h
-@@ -43,6 +43,8 @@ enum {
-       NVMEM_REMOVE,
-       NVMEM_CELL_ADD,
-       NVMEM_CELL_REMOVE,
-+      NVMEM_LAYOUT_ADD,
-+      NVMEM_LAYOUT_REMOVE,
- };
- #if IS_ENABLED(CONFIG_NVMEM)
diff --git a/target/linux/generic/backport-5.15/820-v6.7-0001-nvmem-qfprom-Mark-core-clk-as-optional.patch b/target/linux/generic/backport-5.15/820-v6.7-0001-nvmem-qfprom-Mark-core-clk-as-optional.patch
deleted file mode 100644 (file)
index 66d4028..0000000
+++ /dev/null
@@ -1,37 +0,0 @@
-From 16724d6ea40a2c9315f5a0d81005dfa4d7a6da24 Mon Sep 17 00:00:00 2001
-From: Luca Weiss <[email protected]>
-Date: Fri, 20 Oct 2023 11:55:40 +0100
-Subject: [PATCH] nvmem: qfprom: Mark core clk as optional
-
-On some platforms like sc7280 on non-ChromeOS devices the core clock
-cannot be touched by Linux so we cannot provide it. Mark it as optional
-as accessing qfprom for reading works without it but we still prohibit
-writing if we cannot provide the clock.
-
-Signed-off-by: Luca Weiss <[email protected]>
-Reviewed-by: Douglas Anderson <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/qfprom.c | 6 +++---
- 1 file changed, 3 insertions(+), 3 deletions(-)
-
---- a/drivers/nvmem/qfprom.c
-+++ b/drivers/nvmem/qfprom.c
-@@ -423,12 +423,12 @@ static int qfprom_probe(struct platform_
-               if (IS_ERR(priv->vcc))
-                       return PTR_ERR(priv->vcc);
--              priv->secclk = devm_clk_get(dev, "core");
-+              priv->secclk = devm_clk_get_optional(dev, "core");
-               if (IS_ERR(priv->secclk))
-                       return dev_err_probe(dev, PTR_ERR(priv->secclk), "Error getting clock\n");
--              /* Only enable writing if we have SoC data. */
--              if (priv->soc_data)
-+              /* Only enable writing if we have SoC data and a valid clock */
-+              if (priv->soc_data && priv->secclk)
-                       econfig.reg_write = qfprom_reg_write;
-       }
diff --git a/target/linux/generic/backport-5.15/820-v6.7-0002-nvmem-add-explicit-config-option-to-read-old-syntax-.patch b/target/linux/generic/backport-5.15/820-v6.7-0002-nvmem-add-explicit-config-option-to-read-old-syntax-.patch
deleted file mode 100644 (file)
index 9ce78e1..0000000
+++ /dev/null
@@ -1,330 +0,0 @@
-From 2cc3b37f5b6df8189d55d0e812d9658ce256dfec Mon Sep 17 00:00:00 2001
-From: =?UTF-8?q?Rafa=C5=82=20Mi=C5=82ecki?= <[email protected]>
-Date: Fri, 20 Oct 2023 11:55:41 +0100
-Subject: [PATCH] nvmem: add explicit config option to read old syntax fixed OF
- cells
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-Binding for fixed NVMEM cells defined directly as NVMEM device subnodes
-has been deprecated. It has been replaced by the "fixed-layout" NVMEM
-layout binding.
-
-New syntax is meant to be clearer and should help avoiding imprecise
-bindings.
-
-NVMEM subsystem already supports the new binding. It should be a good
-idea to limit support for old syntax to existing drivers that actually
-support & use it (we can't break backward compatibility!). That way we
-additionally encourage new bindings & drivers to ignore deprecated
-binding.
-
-It wasn't clear (to me) if rtc and w1 code actually uses old syntax
-fixed cells. I enabled them to don't risk any breakage.
-
-Signed-off-by: Rafał Miłecki <[email protected]>
-[for meson-{efuse,mx-efuse}.c]
-Acked-by: Martin Blumenstingl <[email protected]>
-[for mtk-efuse.c, nvmem/core.c, nvmem-provider.h]
-Reviewed-by: AngeloGioacchino Del Regno <[email protected]>
-[MT8192, MT8195 Chromebooks]
-Tested-by: AngeloGioacchino Del Regno <[email protected]>
-[for microchip-otpc.c]
-Reviewed-by: Claudiu Beznea <[email protected]>
-[SAMA7G5-EK]
-Tested-by: Claudiu Beznea <[email protected]>
-Acked-by: Jernej Skrabec <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/mtd/mtdcore.c          | 2 ++
- drivers/nvmem/apple-efuses.c   | 1 +
- drivers/nvmem/core.c           | 8 +++++---
- drivers/nvmem/imx-ocotp-scu.c  | 1 +
- drivers/nvmem/imx-ocotp.c      | 1 +
- drivers/nvmem/meson-efuse.c    | 1 +
- drivers/nvmem/meson-mx-efuse.c | 1 +
- drivers/nvmem/microchip-otpc.c | 1 +
- drivers/nvmem/mtk-efuse.c      | 1 +
- drivers/nvmem/qcom-spmi-sdam.c | 1 +
- drivers/nvmem/qfprom.c         | 1 +
- drivers/nvmem/rave-sp-eeprom.c | 1 +
- drivers/nvmem/rockchip-efuse.c | 1 +
- drivers/nvmem/sc27xx-efuse.c   | 1 +
- drivers/nvmem/sec-qfprom.c     | 1 +
- drivers/nvmem/sprd-efuse.c     | 1 +
- drivers/nvmem/stm32-romem.c    | 1 +
- drivers/nvmem/sunplus-ocotp.c  | 1 +
- drivers/nvmem/sunxi_sid.c      | 1 +
- drivers/nvmem/uniphier-efuse.c | 1 +
- drivers/nvmem/zynqmp_nvmem.c   | 1 +
- drivers/rtc/nvmem.c            | 1 +
- drivers/w1/slaves/w1_ds250x.c  | 1 +
- include/linux/nvmem-provider.h | 2 ++
- 24 files changed, 30 insertions(+), 3 deletions(-)
-
---- a/drivers/mtd/mtdcore.c
-+++ b/drivers/mtd/mtdcore.c
-@@ -541,6 +541,7 @@ static int mtd_nvmem_add(struct mtd_info
-       config.dev = &mtd->dev;
-       config.name = dev_name(&mtd->dev);
-       config.owner = THIS_MODULE;
-+      config.add_legacy_fixed_of_cells = of_device_is_compatible(node, "nvmem-cells");
-       config.reg_read = mtd_nvmem_reg_read;
-       config.size = mtd->size;
-       config.word_size = 1;
-@@ -898,6 +899,7 @@ static struct nvmem_device *mtd_otp_nvme
-       config.name = compatible;
-       config.id = NVMEM_DEVID_AUTO;
-       config.owner = THIS_MODULE;
-+      config.add_legacy_fixed_of_cells = true;
-       config.type = NVMEM_TYPE_OTP;
-       config.root_only = true;
-       config.ignore_wp = true;
---- a/drivers/nvmem/apple-efuses.c
-+++ b/drivers/nvmem/apple-efuses.c
-@@ -36,6 +36,7 @@ static int apple_efuses_probe(struct pla
-       struct resource *res;
-       struct nvmem_config config = {
-               .dev = &pdev->dev,
-+              .add_legacy_fixed_of_cells = true,
-               .read_only = true,
-               .reg_read = apple_efuses_read,
-               .stride = sizeof(u32),
---- a/drivers/nvmem/core.c
-+++ b/drivers/nvmem/core.c
-@@ -998,9 +998,11 @@ struct nvmem_device *nvmem_register(cons
-       if (rval)
-               goto err_remove_cells;
--      rval = nvmem_add_cells_from_legacy_of(nvmem);
--      if (rval)
--              goto err_remove_cells;
-+      if (config->add_legacy_fixed_of_cells) {
-+              rval = nvmem_add_cells_from_legacy_of(nvmem);
-+              if (rval)
-+                      goto err_remove_cells;
-+      }
-       rval = nvmem_add_cells_from_fixed_layout(nvmem);
-       if (rval)
---- a/drivers/nvmem/imx-ocotp-scu.c
-+++ b/drivers/nvmem/imx-ocotp-scu.c
-@@ -220,6 +220,7 @@ static int imx_scu_ocotp_write(void *con
- static struct nvmem_config imx_scu_ocotp_nvmem_config = {
-       .name = "imx-scu-ocotp",
-+      .add_legacy_fixed_of_cells = true,
-       .read_only = false,
-       .word_size = 4,
-       .stride = 1,
---- a/drivers/nvmem/imx-ocotp.c
-+++ b/drivers/nvmem/imx-ocotp.c
-@@ -616,6 +616,7 @@ static int imx_ocotp_probe(struct platfo
-               return PTR_ERR(priv->clk);
-       priv->params = of_device_get_match_data(&pdev->dev);
-+      imx_ocotp_nvmem_config.add_legacy_fixed_of_cells = true;
-       imx_ocotp_nvmem_config.size = 4 * priv->params->nregs;
-       imx_ocotp_nvmem_config.dev = dev;
-       imx_ocotp_nvmem_config.priv = priv;
---- a/drivers/nvmem/meson-efuse.c
-+++ b/drivers/nvmem/meson-efuse.c
-@@ -74,6 +74,7 @@ static int meson_efuse_probe(struct plat
-       econfig->dev = dev;
-       econfig->name = dev_name(dev);
-+      econfig->add_legacy_fixed_of_cells = true;
-       econfig->stride = 1;
-       econfig->word_size = 1;
-       econfig->reg_read = meson_efuse_read;
---- a/drivers/nvmem/meson-mx-efuse.c
-+++ b/drivers/nvmem/meson-mx-efuse.c
-@@ -211,6 +211,7 @@ static int meson_mx_efuse_probe(struct p
-       efuse->config.owner = THIS_MODULE;
-       efuse->config.dev = &pdev->dev;
-       efuse->config.priv = efuse;
-+      efuse->config.add_legacy_fixed_of_cells = true;
-       efuse->config.stride = drvdata->word_size;
-       efuse->config.word_size = drvdata->word_size;
-       efuse->config.size = SZ_512;
---- a/drivers/nvmem/microchip-otpc.c
-+++ b/drivers/nvmem/microchip-otpc.c
-@@ -261,6 +261,7 @@ static int mchp_otpc_probe(struct platfo
-               return ret;
-       mchp_nvmem_config.dev = otpc->dev;
-+      mchp_nvmem_config.add_legacy_fixed_of_cells = true;
-       mchp_nvmem_config.size = size;
-       mchp_nvmem_config.priv = otpc;
-       nvmem = devm_nvmem_register(&pdev->dev, &mchp_nvmem_config);
---- a/drivers/nvmem/mtk-efuse.c
-+++ b/drivers/nvmem/mtk-efuse.c
-@@ -83,6 +83,7 @@ static int mtk_efuse_probe(struct platfo
-               return PTR_ERR(priv->base);
-       pdata = device_get_match_data(dev);
-+      econfig.add_legacy_fixed_of_cells = true;
-       econfig.stride = 1;
-       econfig.word_size = 1;
-       econfig.reg_read = mtk_reg_read;
---- a/drivers/nvmem/qcom-spmi-sdam.c
-+++ b/drivers/nvmem/qcom-spmi-sdam.c
-@@ -142,6 +142,7 @@ static int sdam_probe(struct platform_de
-       sdam->sdam_config.name = "spmi_sdam";
-       sdam->sdam_config.id = NVMEM_DEVID_AUTO;
-       sdam->sdam_config.owner = THIS_MODULE;
-+      sdam->sdam_config.add_legacy_fixed_of_cells = true;
-       sdam->sdam_config.stride = 1;
-       sdam->sdam_config.word_size = 1;
-       sdam->sdam_config.reg_read = sdam_read;
---- a/drivers/nvmem/qfprom.c
-+++ b/drivers/nvmem/qfprom.c
-@@ -357,6 +357,7 @@ static int qfprom_probe(struct platform_
- {
-       struct nvmem_config econfig = {
-               .name = "qfprom",
-+              .add_legacy_fixed_of_cells = true,
-               .stride = 1,
-               .word_size = 1,
-               .id = NVMEM_DEVID_AUTO,
---- a/drivers/nvmem/rave-sp-eeprom.c
-+++ b/drivers/nvmem/rave-sp-eeprom.c
-@@ -328,6 +328,7 @@ static int rave_sp_eeprom_probe(struct p
-       of_property_read_string(np, "zii,eeprom-name", &config.name);
-       config.priv             = eeprom;
-       config.dev              = dev;
-+      config.add_legacy_fixed_of_cells        = true;
-       config.size             = size;
-       config.reg_read         = rave_sp_eeprom_reg_read;
-       config.reg_write        = rave_sp_eeprom_reg_write;
---- a/drivers/nvmem/rockchip-efuse.c
-+++ b/drivers/nvmem/rockchip-efuse.c
-@@ -205,6 +205,7 @@ static int rockchip_rk3399_efuse_read(vo
- static struct nvmem_config econfig = {
-       .name = "rockchip-efuse",
-+      .add_legacy_fixed_of_cells = true,
-       .stride = 1,
-       .word_size = 1,
-       .read_only = true,
---- a/drivers/nvmem/sc27xx-efuse.c
-+++ b/drivers/nvmem/sc27xx-efuse.c
-@@ -248,6 +248,7 @@ static int sc27xx_efuse_probe(struct pla
-       econfig.reg_read = sc27xx_efuse_read;
-       econfig.priv = efuse;
-       econfig.dev = &pdev->dev;
-+      econfig.add_legacy_fixed_of_cells = true;
-       nvmem = devm_nvmem_register(&pdev->dev, &econfig);
-       if (IS_ERR(nvmem)) {
-               dev_err(&pdev->dev, "failed to register nvmem config\n");
---- a/drivers/nvmem/sec-qfprom.c
-+++ b/drivers/nvmem/sec-qfprom.c
-@@ -47,6 +47,7 @@ static int sec_qfprom_probe(struct platf
- {
-       struct nvmem_config econfig = {
-               .name = "sec-qfprom",
-+              .add_legacy_fixed_of_cells = true,
-               .stride = 1,
-               .word_size = 1,
-               .id = NVMEM_DEVID_AUTO,
---- a/drivers/nvmem/sprd-efuse.c
-+++ b/drivers/nvmem/sprd-efuse.c
-@@ -408,6 +408,7 @@ static int sprd_efuse_probe(struct platf
-       econfig.read_only = false;
-       econfig.name = "sprd-efuse";
-       econfig.size = efuse->data->blk_nums * SPRD_EFUSE_BLOCK_WIDTH;
-+      econfig.add_legacy_fixed_of_cells = true;
-       econfig.reg_read = sprd_efuse_read;
-       econfig.reg_write = sprd_efuse_write;
-       econfig.priv = efuse;
---- a/drivers/nvmem/stm32-romem.c
-+++ b/drivers/nvmem/stm32-romem.c
-@@ -207,6 +207,7 @@ static int stm32_romem_probe(struct plat
-       priv->cfg.priv = priv;
-       priv->cfg.owner = THIS_MODULE;
-       priv->cfg.type = NVMEM_TYPE_OTP;
-+      priv->cfg.add_legacy_fixed_of_cells = true;
-       priv->lower = 0;
---- a/drivers/nvmem/sunplus-ocotp.c
-+++ b/drivers/nvmem/sunplus-ocotp.c
-@@ -145,6 +145,7 @@ disable_clk:
- static struct nvmem_config sp_ocotp_nvmem_config = {
-       .name = "sp-ocotp",
-+      .add_legacy_fixed_of_cells = true,
-       .read_only = true,
-       .word_size = 1,
-       .size = QAC628_OTP_SIZE,
---- a/drivers/nvmem/sunxi_sid.c
-+++ b/drivers/nvmem/sunxi_sid.c
-@@ -154,6 +154,7 @@ static int sunxi_sid_probe(struct platfo
-       nvmem_cfg->dev = dev;
-       nvmem_cfg->name = "sunxi-sid";
-       nvmem_cfg->type = NVMEM_TYPE_OTP;
-+      nvmem_cfg->add_legacy_fixed_of_cells = true;
-       nvmem_cfg->read_only = true;
-       nvmem_cfg->size = cfg->size;
-       nvmem_cfg->word_size = 1;
---- a/drivers/nvmem/uniphier-efuse.c
-+++ b/drivers/nvmem/uniphier-efuse.c
-@@ -52,6 +52,7 @@ static int uniphier_efuse_probe(struct p
-       econfig.size = resource_size(res);
-       econfig.priv = priv;
-       econfig.dev = dev;
-+      econfig.add_legacy_fixed_of_cells = true;
-       nvmem = devm_nvmem_register(dev, &econfig);
-       return PTR_ERR_OR_ZERO(nvmem);
---- a/drivers/nvmem/zynqmp_nvmem.c
-+++ b/drivers/nvmem/zynqmp_nvmem.c
-@@ -58,6 +58,7 @@ static int zynqmp_nvmem_probe(struct pla
-       priv->dev = dev;
-       econfig.dev = dev;
-+      econfig.add_legacy_fixed_of_cells = true;
-       econfig.reg_read = zynqmp_nvmem_read;
-       econfig.priv = priv;
---- a/drivers/rtc/nvmem.c
-+++ b/drivers/rtc/nvmem.c
-@@ -21,6 +21,7 @@ int devm_rtc_nvmem_register(struct rtc_d
-       nvmem_config->dev = dev;
-       nvmem_config->owner = rtc->owner;
-+      nvmem_config->add_legacy_fixed_of_cells = true;
-       nvmem = devm_nvmem_register(dev, nvmem_config);
-       if (IS_ERR(nvmem))
-               dev_err(dev, "failed to register nvmem device for RTC\n");
---- a/drivers/w1/slaves/w1_ds250x.c
-+++ b/drivers/w1/slaves/w1_ds250x.c
-@@ -168,6 +168,7 @@ static int w1_eprom_add_slave(struct w1_
-       struct nvmem_device *nvmem;
-       struct nvmem_config nvmem_cfg = {
-               .dev = &sl->dev,
-+              .add_legacy_fixed_of_cells = true,
-               .reg_read = w1_nvmem_read,
-               .type = NVMEM_TYPE_OTP,
-               .read_only = true,
---- a/include/linux/nvmem-provider.h
-+++ b/include/linux/nvmem-provider.h
-@@ -82,6 +82,7 @@ struct nvmem_cell_info {
-  * @owner:    Pointer to exporter module. Used for refcounting.
-  * @cells:    Optional array of pre-defined NVMEM cells.
-  * @ncells:   Number of elements in cells.
-+ * @add_legacy_fixed_of_cells:        Read fixed NVMEM cells from old OF syntax.
-  * @keepout:  Optional array of keepout ranges (sorted ascending by start).
-  * @nkeepout: Number of elements in the keepout array.
-  * @type:     Type of the nvmem storage
-@@ -112,6 +113,7 @@ struct nvmem_config {
-       struct module           *owner;
-       const struct nvmem_cell_info    *cells;
-       int                     ncells;
-+      bool                    add_legacy_fixed_of_cells;
-       const struct nvmem_keepout *keepout;
-       unsigned int            nkeepout;
-       enum nvmem_type         type;
diff --git a/target/linux/generic/backport-5.15/820-v6.7-0003-nvmem-Use-device_get_match_data.patch b/target/linux/generic/backport-5.15/820-v6.7-0003-nvmem-Use-device_get_match_data.patch
deleted file mode 100644 (file)
index 84c0293..0000000
+++ /dev/null
@@ -1,77 +0,0 @@
-From 0720219f4d34a88a9badb4de70cfad7585687d48 Mon Sep 17 00:00:00 2001
-From: Rob Herring <[email protected]>
-Date: Fri, 20 Oct 2023 11:55:45 +0100
-Subject: [PATCH] nvmem: Use device_get_match_data()
-
-Use preferred device_get_match_data() instead of of_match_device() to
-get the driver match data. With this, adjust the includes to explicitly
-include the correct headers.
-
-Signed-off-by: Rob Herring <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/mxs-ocotp.c   | 10 ++++------
- drivers/nvmem/stm32-romem.c |  7 ++++---
- 2 files changed, 8 insertions(+), 9 deletions(-)
-
---- a/drivers/nvmem/mxs-ocotp.c
-+++ b/drivers/nvmem/mxs-ocotp.c
-@@ -13,8 +13,9 @@
- #include <linux/io.h>
- #include <linux/module.h>
- #include <linux/nvmem-provider.h>
--#include <linux/of_device.h>
-+#include <linux/of.h>
- #include <linux/platform_device.h>
-+#include <linux/property.h>
- #include <linux/slab.h>
- #include <linux/stmp_device.h>
-@@ -140,11 +141,10 @@ static int mxs_ocotp_probe(struct platfo
-       struct device *dev = &pdev->dev;
-       const struct mxs_data *data;
-       struct mxs_ocotp *otp;
--      const struct of_device_id *match;
-       int ret;
--      match = of_match_device(dev->driver->of_match_table, dev);
--      if (!match || !match->data)
-+      data = device_get_match_data(dev);
-+      if (!data)
-               return -EINVAL;
-       otp = devm_kzalloc(dev, sizeof(*otp), GFP_KERNEL);
-@@ -169,8 +169,6 @@ static int mxs_ocotp_probe(struct platfo
-       if (ret)
-               return ret;
--      data = match->data;
--
-       ocotp_config.size = data->size;
-       ocotp_config.priv = otp;
-       ocotp_config.dev = dev;
---- a/drivers/nvmem/stm32-romem.c
-+++ b/drivers/nvmem/stm32-romem.c
-@@ -10,7 +10,9 @@
- #include <linux/io.h>
- #include <linux/module.h>
- #include <linux/nvmem-provider.h>
--#include <linux/of_device.h>
-+#include <linux/of.h>
-+#include <linux/platform_device.h>
-+#include <linux/property.h>
- #include <linux/tee_drv.h>
- #include "stm32-bsec-optee-ta.h"
-@@ -211,8 +213,7 @@ static int stm32_romem_probe(struct plat
-       priv->lower = 0;
--      cfg = (const struct stm32_romem_cfg *)
--              of_match_device(dev->driver->of_match_table, dev)->data;
-+      cfg = device_get_match_data(dev);
-       if (!cfg) {
-               priv->cfg.read_only = true;
-               priv->cfg.size = resource_size(res);
diff --git a/target/linux/generic/backport-5.15/820-v6.7-0004-Revert-nvmem-add-new-config-option.patch b/target/linux/generic/backport-5.15/820-v6.7-0004-Revert-nvmem-add-new-config-option.patch
deleted file mode 100644 (file)
index b23a23e..0000000
+++ /dev/null
@@ -1,77 +0,0 @@
-From f4cf4e5db331a5ce69e3f0b21d322cac0f4e4b5d Mon Sep 17 00:00:00 2001
-From: =?UTF-8?q?Rafa=C5=82=20Mi=C5=82ecki?= <[email protected]>
-Date: Mon, 23 Oct 2023 12:27:59 +0200
-Subject: [PATCH] Revert "nvmem: add new config option"
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-This reverts commit 517f14d9cf3533d5ab4fded195ab6f80a92e378f.
-
-Config option "no_of_node" is no longer needed since adding a more
-explicit and targeted option "add_legacy_fixed_of_cells".
-
-That "no_of_node" config option was needed *earlier* to help mtd's case.
-
-DT nodes of MTD partitions (that are also NVMEM devices) may contain
-subnodes. Those SHOULD NOT be treated as NVMEM fixed cells.
-
-To prevent NVMEM core code from parsing subnodes a "no_of_node" option
-was added (and set to true in mtd) to make for_each_child_of_node() in
-NVMEM a no-op. That was a bit hacky because it was messing with
-"of_node" pointer to achieve some side-effect.
-
-With the introduction of "add_legacy_fixed_of_cells" config option
-things got more explicit. MTD subsystem simply tells NVMEM when to look
-for fixed cells and there is no need to hack "of_node" pointer anymore.
-
-Signed-off-by: Rafał Miłecki <[email protected]>
-Reviewed-by: Miquel Raynal <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/mtd/mtdcore.c          | 1 -
- drivers/nvmem/core.c           | 2 +-
- include/linux/nvmem-provider.h | 2 --
- 3 files changed, 1 insertion(+), 4 deletions(-)
-
---- a/drivers/mtd/mtdcore.c
-+++ b/drivers/mtd/mtdcore.c
-@@ -549,7 +549,6 @@ static int mtd_nvmem_add(struct mtd_info
-       config.read_only = true;
-       config.root_only = true;
-       config.ignore_wp = true;
--      config.no_of_node = !of_device_is_compatible(node, "nvmem-cells");
-       config.priv = mtd;
-       mtd->nvmem = nvmem_register(&config);
---- a/drivers/nvmem/core.c
-+++ b/drivers/nvmem/core.c
-@@ -936,7 +936,7 @@ struct nvmem_device *nvmem_register(cons
-       nvmem->nkeepout = config->nkeepout;
-       if (config->of_node)
-               nvmem->dev.of_node = config->of_node;
--      else if (!config->no_of_node)
-+      else
-               nvmem->dev.of_node = config->dev->of_node;
-       switch (config->id) {
---- a/include/linux/nvmem-provider.h
-+++ b/include/linux/nvmem-provider.h
-@@ -89,7 +89,6 @@ struct nvmem_cell_info {
-  * @read_only:        Device is read-only.
-  * @root_only:        Device is accessibly to root only.
-  * @of_node:  If given, this will be used instead of the parent's of_node.
-- * @no_of_node:       Device should not use the parent's of_node even if it's !NULL.
-  * @reg_read: Callback to read data.
-  * @reg_write:        Callback to write data.
-  * @size:     Device size.
-@@ -122,7 +121,6 @@ struct nvmem_config {
-       bool                    ignore_wp;
-       struct nvmem_layout     *layout;
-       struct device_node      *of_node;
--      bool                    no_of_node;
-       nvmem_reg_read_t        reg_read;
-       nvmem_reg_write_t       reg_write;
-       int     size;
diff --git a/target/linux/generic/backport-5.15/820-v6.7-0005-nvmem-Do-not-expect-fixed-layouts-to-grab-a-layout-d.patch b/target/linux/generic/backport-5.15/820-v6.7-0005-nvmem-Do-not-expect-fixed-layouts-to-grab-a-layout-d.patch
deleted file mode 100644 (file)
index bd5ceaa..0000000
+++ /dev/null
@@ -1,45 +0,0 @@
-From b7c1e53751cb3990153084f31c41f25fde3b629c Mon Sep 17 00:00:00 2001
-From: Miquel Raynal <[email protected]>
-Date: Fri, 24 Nov 2023 20:38:14 +0100
-Subject: [PATCH] nvmem: Do not expect fixed layouts to grab a layout driver
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-Two series lived in parallel for some time, which led to this situation:
-- The nvmem-layout container is used for dynamic layouts
-- We now expect fixed layouts to also use the nvmem-layout container but
-this does not require any additional driver, the support is built-in the
-nvmem core.
-
-Ensure we don't refuse to probe for wrong reasons.
-
-Fixes: 27f699e578b1 ("nvmem: core: add support for fixed cells *layout*")
-Reported-by: Luca Ceresoli <[email protected]>
-Signed-off-by: Miquel Raynal <[email protected]>
-Tested-by: Rafał Miłecki <[email protected]>
-Tested-by: Luca Ceresoli <[email protected]>
-Reviewed-by: Luca Ceresoli <[email protected]>
-
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/core.c | 6 ++++++
- 1 file changed, 6 insertions(+)
-
---- a/drivers/nvmem/core.c
-+++ b/drivers/nvmem/core.c
-@@ -797,6 +797,12 @@ static struct nvmem_layout *nvmem_layout
-       if (!layout_np)
-               return NULL;
-+      /* Fixed layouts don't have a matching driver */
-+      if (of_device_is_compatible(layout_np, "fixed-layout")) {
-+              of_node_put(layout_np);
-+              return NULL;
-+      }
-+
-       /*
-        * In case the nvmem device was built-in while the layout was built as a
-        * module, we shall manually request the layout driver loading otherwise
diff --git a/target/linux/generic/backport-5.15/820-v6.7-0006-nvmem-brcm_nvram-store-a-copy-of-NVRAM-content.patch b/target/linux/generic/backport-5.15/820-v6.7-0006-nvmem-brcm_nvram-store-a-copy-of-NVRAM-content.patch
deleted file mode 100644 (file)
index d49a205..0000000
+++ /dev/null
@@ -1,261 +0,0 @@
-From 1e37bf84afacd5ba17b7a13a18ca2bc78aff05c0 Mon Sep 17 00:00:00 2001
-From: =?UTF-8?q?Rafa=C5=82=20Mi=C5=82ecki?= <[email protected]>
-Date: Fri, 15 Dec 2023 11:13:58 +0000
-Subject: [PATCH] nvmem: brcm_nvram: store a copy of NVRAM content
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-This driver uses MMIO access for reading NVRAM from a flash device.
-Underneath there is a flash controller that reads data and provides
-mapping window.
-
-Using MMIO interface affects controller configuration and may break real
-controller driver. It was reported by multiple users of devices with
-NVRAM stored on NAND.
-
-Modify driver to read & cache NVRAM content during init and use that
-copy to provide NVMEM data when requested. On NAND flashes due to their
-alignment NVRAM partitions can be quite big (1 MiB and more) while
-actual NVRAM content stays quite small (usually 16 to 32 KiB). To avoid
-allocating so much memory check for actual data length.
-
-Link: https://lore.kernel.org/linux-mtd/CACna6rwf3_9QVjYcM+847biTX=K0EoWXuXcSMkJO1Vy_5vmVqA@mail.gmail.com/
-Fixes: 3fef9ed0627a ("nvmem: brcm_nvram: new driver exposing Broadcom's NVRAM")
-Cc: Arınç ÜNAL <[email protected]>
-Cc: Florian Fainelli <[email protected]>
-Cc: Scott Branden <[email protected]>
-Signed-off-by: Rafał Miłecki <[email protected]>
-Acked-by: Arınç ÜNAL <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/brcm_nvram.c | 134 ++++++++++++++++++++++++++-----------
- 1 file changed, 94 insertions(+), 40 deletions(-)
-
---- a/drivers/nvmem/brcm_nvram.c
-+++ b/drivers/nvmem/brcm_nvram.c
-@@ -17,9 +17,23 @@
- #define NVRAM_MAGIC                   "FLSH"
-+/**
-+ * struct brcm_nvram - driver state internal struct
-+ *
-+ * @dev:              NVMEM device pointer
-+ * @nvmem_size:               Size of the whole space available for NVRAM
-+ * @data:             NVRAM data copy stored to avoid poking underlaying flash controller
-+ * @data_len:         NVRAM data size
-+ * @padding_byte:     Padding value used to fill remaining space
-+ * @cells:            Array of discovered NVMEM cells
-+ * @ncells:           Number of elements in cells
-+ */
- struct brcm_nvram {
-       struct device *dev;
--      void __iomem *base;
-+      size_t nvmem_size;
-+      uint8_t *data;
-+      size_t data_len;
-+      uint8_t padding_byte;
-       struct nvmem_cell_info *cells;
-       int ncells;
- };
-@@ -36,10 +50,47 @@ static int brcm_nvram_read(void *context
-                          size_t bytes)
- {
-       struct brcm_nvram *priv = context;
--      u8 *dst = val;
-+      size_t to_copy;
-+
-+      if (offset + bytes > priv->data_len)
-+              to_copy = max_t(ssize_t, (ssize_t)priv->data_len - offset, 0);
-+      else
-+              to_copy = bytes;
-+
-+      memcpy(val, priv->data + offset, to_copy);
-+
-+      memset((uint8_t *)val + to_copy, priv->padding_byte, bytes - to_copy);
-+
-+      return 0;
-+}
-+
-+static int brcm_nvram_copy_data(struct brcm_nvram *priv, struct platform_device *pdev)
-+{
-+      struct resource *res;
-+      void __iomem *base;
-+
-+      base = devm_platform_get_and_ioremap_resource(pdev, 0, &res);
-+      if (IS_ERR(base))
-+              return PTR_ERR(base);
-+
-+      priv->nvmem_size = resource_size(res);
-+
-+      priv->padding_byte = readb(base + priv->nvmem_size - 1);
-+      for (priv->data_len = priv->nvmem_size;
-+           priv->data_len;
-+           priv->data_len--) {
-+              if (readb(base + priv->data_len - 1) != priv->padding_byte)
-+                      break;
-+      }
-+      WARN(priv->data_len > SZ_128K, "Unexpected (big) NVRAM size: %zu B\n", priv->data_len);
--      while (bytes--)
--              *dst++ = readb(priv->base + offset++);
-+      priv->data = devm_kzalloc(priv->dev, priv->data_len, GFP_KERNEL);
-+      if (!priv->data)
-+              return -ENOMEM;
-+
-+      memcpy_fromio(priv->data, base, priv->data_len);
-+
-+      bcm47xx_nvram_init_from_iomem(base, priv->data_len);
-       return 0;
- }
-@@ -67,8 +118,13 @@ static int brcm_nvram_add_cells(struct b
-                               size_t len)
- {
-       struct device *dev = priv->dev;
--      char *var, *value, *eq;
-+      char *var, *value;
-+      uint8_t tmp;
-       int idx;
-+      int err = 0;
-+
-+      tmp = priv->data[len - 1];
-+      priv->data[len - 1] = '\0';
-       priv->ncells = 0;
-       for (var = data + sizeof(struct brcm_nvram_header);
-@@ -78,67 +134,68 @@ static int brcm_nvram_add_cells(struct b
-       }
-       priv->cells = devm_kcalloc(dev, priv->ncells, sizeof(*priv->cells), GFP_KERNEL);
--      if (!priv->cells)
--              return -ENOMEM;
-+      if (!priv->cells) {
-+              err = -ENOMEM;
-+              goto out;
-+      }
-       for (var = data + sizeof(struct brcm_nvram_header), idx = 0;
-            var < (char *)data + len && *var;
-            var = value + strlen(value) + 1, idx++) {
-+              char *eq, *name;
-+
-               eq = strchr(var, '=');
-               if (!eq)
-                       break;
-               *eq = '\0';
-+              name = devm_kstrdup(dev, var, GFP_KERNEL);
-+              *eq = '=';
-+              if (!name) {
-+                      err = -ENOMEM;
-+                      goto out;
-+              }
-               value = eq + 1;
--              priv->cells[idx].name = devm_kstrdup(dev, var, GFP_KERNEL);
--              if (!priv->cells[idx].name)
--                      return -ENOMEM;
-+              priv->cells[idx].name = name;
-               priv->cells[idx].offset = value - (char *)data;
-               priv->cells[idx].bytes = strlen(value);
-               priv->cells[idx].np = of_get_child_by_name(dev->of_node, priv->cells[idx].name);
--              if (!strcmp(var, "et0macaddr") ||
--                  !strcmp(var, "et1macaddr") ||
--                  !strcmp(var, "et2macaddr")) {
-+              if (!strcmp(name, "et0macaddr") ||
-+                  !strcmp(name, "et1macaddr") ||
-+                  !strcmp(name, "et2macaddr")) {
-                       priv->cells[idx].raw_len = strlen(value);
-                       priv->cells[idx].bytes = ETH_ALEN;
-                       priv->cells[idx].read_post_process = brcm_nvram_read_post_process_macaddr;
-               }
-       }
--      return 0;
-+out:
-+      priv->data[len - 1] = tmp;
-+      return err;
- }
- static int brcm_nvram_parse(struct brcm_nvram *priv)
- {
-+      struct brcm_nvram_header *header = (struct brcm_nvram_header *)priv->data;
-       struct device *dev = priv->dev;
--      struct brcm_nvram_header header;
--      uint8_t *data;
-       size_t len;
-       int err;
--      memcpy_fromio(&header, priv->base, sizeof(header));
--
--      if (memcmp(header.magic, NVRAM_MAGIC, 4)) {
-+      if (memcmp(header->magic, NVRAM_MAGIC, 4)) {
-               dev_err(dev, "Invalid NVRAM magic\n");
-               return -EINVAL;
-       }
--      len = le32_to_cpu(header.len);
--
--      data = kzalloc(len, GFP_KERNEL);
--      if (!data)
--              return -ENOMEM;
--
--      memcpy_fromio(data, priv->base, len);
--      data[len - 1] = '\0';
--
--      err = brcm_nvram_add_cells(priv, data, len);
--      if (err) {
--              dev_err(dev, "Failed to add cells: %d\n", err);
--              return err;
-+      len = le32_to_cpu(header->len);
-+      if (len > priv->nvmem_size) {
-+              dev_err(dev, "NVRAM length (%zd) exceeds mapped size (%zd)\n", len,
-+                      priv->nvmem_size);
-+              return -EINVAL;
-       }
--      kfree(data);
-+      err = brcm_nvram_add_cells(priv, priv->data, len);
-+      if (err)
-+              dev_err(dev, "Failed to add cells: %d\n", err);
-       return 0;
- }
-@@ -150,7 +207,6 @@ static int brcm_nvram_probe(struct platf
-               .reg_read = brcm_nvram_read,
-       };
-       struct device *dev = &pdev->dev;
--      struct resource *res;
-       struct brcm_nvram *priv;
-       int err;
-@@ -159,21 +215,19 @@ static int brcm_nvram_probe(struct platf
-               return -ENOMEM;
-       priv->dev = dev;
--      priv->base = devm_platform_get_and_ioremap_resource(pdev, 0, &res);
--      if (IS_ERR(priv->base))
--              return PTR_ERR(priv->base);
-+      err = brcm_nvram_copy_data(priv, pdev);
-+      if (err)
-+              return err;
-       err = brcm_nvram_parse(priv);
-       if (err)
-               return err;
--      bcm47xx_nvram_init_from_iomem(priv->base, resource_size(res));
--
-       config.dev = dev;
-       config.cells = priv->cells;
-       config.ncells = priv->ncells;
-       config.priv = priv;
--      config.size = resource_size(res);
-+      config.size = priv->nvmem_size;
-       return PTR_ERR_OR_ZERO(devm_nvmem_register(dev, &config));
- }
diff --git a/target/linux/generic/backport-5.15/821-v5.16-Bluetooth-btusb-Support-public-address-configuration.patch b/target/linux/generic/backport-5.15/821-v5.16-Bluetooth-btusb-Support-public-address-configuration.patch
deleted file mode 100644 (file)
index 4a63b89..0000000
+++ /dev/null
@@ -1,51 +0,0 @@
-From 5cb03751455c299b1bf10cb48631bf359cfb11b5 Mon Sep 17 00:00:00 2001
-From: "mark-yw.chen" <[email protected]>
-Date: Wed, 1 Sep 2021 11:32:25 +0800
-Subject: [PATCH 1/5] Bluetooth: btusb: Support public address configuration
- for MediaTek Chip.
-
-The MediaTek chip support vendor specific HCI command(0xfc1a) to
-change the public address. Add hdev->set_bdaddr handler for MediaTek
-Chip. After doing a power cycle or MediaTek Bluetooth reset, BD_ADDR
-will bring back the original one.
-
-Signed-off-by: mark-yw.chen <[email protected]>
-Signed-off-by: Marcel Holtmann <[email protected]>
----
- drivers/bluetooth/btusb.c | 18 ++++++++++++++++++
- 1 file changed, 18 insertions(+)
-
---- a/drivers/bluetooth/btusb.c
-+++ b/drivers/bluetooth/btusb.c
-@@ -2289,6 +2289,23 @@ struct btmtk_section_map {
-       };
- } __packed;
-+static int btusb_set_bdaddr_mtk(struct hci_dev *hdev, const bdaddr_t *bdaddr)
-+{
-+      struct sk_buff *skb;
-+      long ret;
-+
-+      skb = __hci_cmd_sync(hdev, 0xfc1a, sizeof(bdaddr), bdaddr, HCI_INIT_TIMEOUT);
-+      if (IS_ERR(skb)) {
-+              ret = PTR_ERR(skb);
-+              bt_dev_err(hdev, "changing Mediatek device address failed (%ld)",
-+                         ret);
-+              return ret;
-+      }
-+      kfree_skb(skb);
-+
-+      return 0;
-+}
-+
- static void btusb_mtk_wmt_recv(struct urb *urb)
- {
-       struct hci_dev *hdev = urb->context;
-@@ -3943,6 +3960,7 @@ static int btusb_probe(struct usb_interf
-               hdev->shutdown = btusb_mtk_shutdown;
-               hdev->manufacturer = 70;
-               hdev->cmd_timeout = btusb_mtk_cmd_timeout;
-+              hdev->set_bdaddr = btusb_set_bdaddr_mtk;
-               set_bit(HCI_QUIRK_NON_PERSISTENT_SETUP, &hdev->quirks);
-               data->recv_acl = btusb_recv_acl_mtk;
-       }
diff --git a/target/linux/generic/backport-5.15/822-v5.17-Bluetooth-btusb-Fix-application-of-sizeof-to-pointer.patch b/target/linux/generic/backport-5.15/822-v5.17-Bluetooth-btusb-Fix-application-of-sizeof-to-pointer.patch
deleted file mode 100644 (file)
index d21adad..0000000
+++ /dev/null
@@ -1,29 +0,0 @@
-From af774a731f7b4c2a90a8476cd44045ba8d1263ba Mon Sep 17 00:00:00 2001
-From: David Yang <[email protected]>
-Date: Wed, 13 Oct 2021 08:56:33 +0800
-Subject: [PATCH 2/5] Bluetooth: btusb: Fix application of sizeof to pointer
-
-The coccinelle check report:
-"./drivers/bluetooth/btusb.c:2239:36-42:
-ERROR: application of sizeof to pointer".
-Using the real size to fix it.
-
-Fixes: 5a87679ffd443 ("Bluetooth: btusb: Support public address configuration for MediaTek Chip.")
-Reported-by: Zeal Robot <[email protected]>
-Signed-off-by: David Yang <[email protected]>
-Signed-off-by: Marcel Holtmann <[email protected]>
----
- drivers/bluetooth/btusb.c | 2 +-
- 1 file changed, 1 insertion(+), 1 deletion(-)
-
---- a/drivers/bluetooth/btusb.c
-+++ b/drivers/bluetooth/btusb.c
-@@ -2294,7 +2294,7 @@ static int btusb_set_bdaddr_mtk(struct h
-       struct sk_buff *skb;
-       long ret;
--      skb = __hci_cmd_sync(hdev, 0xfc1a, sizeof(bdaddr), bdaddr, HCI_INIT_TIMEOUT);
-+      skb = __hci_cmd_sync(hdev, 0xfc1a, 6, bdaddr, HCI_INIT_TIMEOUT);
-       if (IS_ERR(skb)) {
-               ret = PTR_ERR(skb);
-               bt_dev_err(hdev, "changing Mediatek device address failed (%ld)",
diff --git a/target/linux/generic/backport-5.15/823-v5.18-Bluetooth-btusb-Add-a-new-PID-VID-13d3-3567-for-MT79.patch b/target/linux/generic/backport-5.15/823-v5.18-Bluetooth-btusb-Add-a-new-PID-VID-13d3-3567-for-MT79.patch
deleted file mode 100644 (file)
index 30492ac..0000000
+++ /dev/null
@@ -1,70 +0,0 @@
-From e57186fc02cedff191c469a26cce615371e41740 Mon Sep 17 00:00:00 2001
-From: Yake Yang <[email protected]>
-Date: Wed, 23 Feb 2022 07:55:59 +0800
-Subject: [PATCH 3/5] Bluetooth: btusb: Add a new PID/VID 13d3/3567 for MT7921
-
-Add VID 13D3 & PID 3567 for MediaTek MT7921 USB Bluetooth chip.
-
-The information in /sys/kernel/debug/usb/devices about the Bluetooth
-device is listed as the below.
-
-T:  Bus=05 Lev=01 Prnt=01 Port=00 Cnt=01 Dev#=  2 Spd=480  MxCh= 0
-D:  Ver= 2.10 Cls=ef(misc ) Sub=02 Prot=01 MxPS=64 #Cfgs=  1
-P:  Vendor=13d3 ProdID=3567 Rev= 1.00
-S:  Manufacturer=MediaTek Inc.
-S:  Product=Wireless_Device
-S:  SerialNumber=000000000
-C:* #Ifs= 3 Cfg#= 1 Atr=e0 MxPwr=100mA
-A:  FirstIf#= 0 IfCount= 3 Cls=e0(wlcon) Sub=01 Prot=01
-I:* If#= 0 Alt= 0 #EPs= 3 Cls=e0(wlcon) Sub=01 Prot=01 Driver=btusb
-E:  Ad=81(I) Atr=03(Int.) MxPS=  16 Ivl=125us
-E:  Ad=82(I) Atr=02(Bulk) MxPS= 512 Ivl=0ms
-E:  Ad=02(O) Atr=02(Bulk) MxPS= 512 Ivl=0ms
-I:* If#= 1 Alt= 0 #EPs= 2 Cls=e0(wlcon) Sub=01 Prot=01 Driver=btusb
-E:  Ad=83(I) Atr=01(Isoc) MxPS=   0 Ivl=1ms
-E:  Ad=03(O) Atr=01(Isoc) MxPS=   0 Ivl=1ms
-I:  If#= 1 Alt= 1 #EPs= 2 Cls=e0(wlcon) Sub=01 Prot=01 Driver=btusb
-E:  Ad=83(I) Atr=01(Isoc) MxPS=   9 Ivl=1ms
-E:  Ad=03(O) Atr=01(Isoc) MxPS=   9 Ivl=1ms
-I:  If#= 1 Alt= 2 #EPs= 2 Cls=e0(wlcon) Sub=01 Prot=01 Driver=btusb
-E:  Ad=83(I) Atr=01(Isoc) MxPS=  17 Ivl=1ms
-E:  Ad=03(O) Atr=01(Isoc) MxPS=  17 Ivl=1ms
-I:  If#= 1 Alt= 3 #EPs= 2 Cls=e0(wlcon) Sub=01 Prot=01 Driver=btusb
-E:  Ad=83(I) Atr=01(Isoc) MxPS=  25 Ivl=1ms
-E:  Ad=03(O) Atr=01(Isoc) MxPS=  25 Ivl=1ms
-I:  If#= 1 Alt= 4 #EPs= 2 Cls=e0(wlcon) Sub=01 Prot=01 Driver=btusb
-E:  Ad=83(I) Atr=01(Isoc) MxPS=  33 Ivl=1ms
-E:  Ad=03(O) Atr=01(Isoc) MxPS=  33 Ivl=1ms
-I:  If#= 1 Alt= 5 #EPs= 2 Cls=e0(wlcon) Sub=01 Prot=01 Driver=btusb
-E:  Ad=83(I) Atr=01(Isoc) MxPS=  49 Ivl=1ms
-E:  Ad=03(O) Atr=01(Isoc) MxPS=  49 Ivl=1ms
-I:  If#= 1 Alt= 6 #EPs= 2 Cls=e0(wlcon) Sub=01 Prot=01 Driver=btusb
-E:  Ad=83(I) Atr=01(Isoc) MxPS=  63 Ivl=1ms
-E:  Ad=03(O) Atr=01(Isoc) MxPS=  63 Ivl=1ms
-I:* If#= 2 Alt= 0 #EPs= 2 Cls=e0(wlcon) Sub=01 Prot=01 Driver=(none)
-E:  Ad=8a(I) Atr=03(Int.) MxPS=  64 Ivl=125us
-E:  Ad=0a(O) Atr=03(Int.) MxPS=  64 Ivl=125us
-I:  If#= 2 Alt= 1 #EPs= 2 Cls=e0(wlcon) Sub=01 Prot=01 Driver=(none)
-E:  Ad=8a(I) Atr=03(Int.) MxPS=  64 Ivl=125us
-E:  Ad=0a(O) Atr=03(Int.) MxPS=  64 Ivl=125us
-
-Co-developed-by: Sean Wang <[email protected]>
-Signed-off-by: Sean Wang <[email protected]>
-Signed-off-by: Yake Yang <[email protected]>
-Signed-off-by: Marcel Holtmann <[email protected]>
----
- drivers/bluetooth/btusb.c | 3 +++
- 1 file changed, 3 insertions(+)
-
---- a/drivers/bluetooth/btusb.c
-+++ b/drivers/bluetooth/btusb.c
-@@ -478,6 +478,9 @@ static const struct usb_device_id blackl
-       { USB_DEVICE(0x13d3, 0x3564), .driver_info = BTUSB_MEDIATEK |
-                                                    BTUSB_WIDEBAND_SPEECH |
-                                                    BTUSB_VALID_LE_STATES },
-+      { USB_DEVICE(0x13d3, 0x3567), .driver_info = BTUSB_MEDIATEK |
-+                                                   BTUSB_WIDEBAND_SPEECH |
-+                                                   BTUSB_VALID_LE_STATES },
-       { USB_DEVICE(0x0489, 0xe0cd), .driver_info = BTUSB_MEDIATEK |
-                                                    BTUSB_WIDEBAND_SPEECH |
-                                                    BTUSB_VALID_LE_STATES },
diff --git a/target/linux/generic/backport-5.15/824-v5.19-Bluetooth-btusb-Add-a-new-PID-VID-0489-e0c8-for-MT79.patch b/target/linux/generic/backport-5.15/824-v5.19-Bluetooth-btusb-Add-a-new-PID-VID-0489-e0c8-for-MT79.patch
deleted file mode 100644 (file)
index 6bcd81c..0000000
+++ /dev/null
@@ -1,68 +0,0 @@
-From e507366cd1e8e1d4eebe537c08fd142cf0b617fa Mon Sep 17 00:00:00 2001
-From: Sean Wang <[email protected]>
-Date: Thu, 28 Apr 2022 02:38:39 +0800
-Subject: [PATCH 4/5] Bluetooth: btusb: Add a new PID/VID 0489/e0c8 for MT7921
-
-Add VID 0489 & PID e0c8 for MediaTek MT7921 USB Bluetooth chip.
-
-The information in /sys/kernel/debug/usb/devices about the Bluetooth
-device is listed as the below.
-
-T:  Bus=01 Lev=01 Prnt=01 Port=13 Cnt=03 Dev#=  4 Spd=480  MxCh= 0
-D:  Ver= 2.10 Cls=ef(misc ) Sub=02 Prot=01 MxPS=64 #Cfgs=  1
-P:  Vendor=0489 ProdID=e0c8 Rev= 1.00
-S:  Manufacturer=MediaTek Inc.
-S:  Product=Wireless_Device
-S:  SerialNumber=000000000
-C:* #Ifs= 3 Cfg#= 1 Atr=e0 MxPwr=100mA
-A:  FirstIf#= 0 IfCount= 3 Cls=e0(wlcon) Sub=01 Prot=01
-I:* If#= 0 Alt= 0 #EPs= 3 Cls=e0(wlcon) Sub=01 Prot=01 Driver=btusb
-E:  Ad=81(I) Atr=03(Int.) MxPS=  16 Ivl=125us
-E:  Ad=82(I) Atr=02(Bulk) MxPS= 512 Ivl=0ms
-E:  Ad=02(O) Atr=02(Bulk) MxPS= 512 Ivl=0ms
-I:* If#= 1 Alt= 0 #EPs= 2 Cls=e0(wlcon) Sub=01 Prot=01 Driver=btusb
-E:  Ad=83(I) Atr=01(Isoc) MxPS=   0 Ivl=1ms
-E:  Ad=03(O) Atr=01(Isoc) MxPS=   0 Ivl=1ms
-I:  If#= 1 Alt= 1 #EPs= 2 Cls=e0(wlcon) Sub=01 Prot=01 Driver=btusb
-E:  Ad=83(I) Atr=01(Isoc) MxPS=   9 Ivl=1ms
-E:  Ad=03(O) Atr=01(Isoc) MxPS=   9 Ivl=1ms
-I:  If#= 1 Alt= 2 #EPs= 2 Cls=e0(wlcon) Sub=01 Prot=01 Driver=btusb
-E:  Ad=83(I) Atr=01(Isoc) MxPS=  17 Ivl=1ms
-E:  Ad=03(O) Atr=01(Isoc) MxPS=  17 Ivl=1ms
-I:  If#= 1 Alt= 3 #EPs= 2 Cls=e0(wlcon) Sub=01 Prot=01 Driver=btusb
-E:  Ad=83(I) Atr=01(Isoc) MxPS=  25 Ivl=1ms
-E:  Ad=03(O) Atr=01(Isoc) MxPS=  25 Ivl=1ms
-I:  If#= 1 Alt= 4 #EPs= 2 Cls=e0(wlcon) Sub=01 Prot=01 Driver=btusb
-E:  Ad=83(I) Atr=01(Isoc) MxPS=  33 Ivl=1ms
-E:  Ad=03(O) Atr=01(Isoc) MxPS=  33 Ivl=1ms
-I:  If#= 1 Alt= 5 #EPs= 2 Cls=e0(wlcon) Sub=01 Prot=01 Driver=btusb
-E:  Ad=83(I) Atr=01(Isoc) MxPS=  49 Ivl=1ms
-E:  Ad=03(O) Atr=01(Isoc) MxPS=  49 Ivl=1ms
-I:  If#= 1 Alt= 6 #EPs= 2 Cls=e0(wlcon) Sub=01 Prot=01 Driver=btusb
-E:  Ad=83(I) Atr=01(Isoc) MxPS=  63 Ivl=1ms
-E:  Ad=03(O) Atr=01(Isoc) MxPS=  63 Ivl=1ms
-I:* If#= 2 Alt= 0 #EPs= 2 Cls=e0(wlcon) Sub=01 Prot=01 Driver=(none)
-E:  Ad=8a(I) Atr=03(Int.) MxPS=  64 Ivl=125us
-E:  Ad=0a(O) Atr=03(Int.) MxPS=  64 Ivl=125us
-I:  If#= 2 Alt= 1 #EPs= 2 Cls=e0(wlcon) Sub=01 Prot=01 Driver=(none)
-E:  Ad=8a(I) Atr=03(Int.) MxPS= 512 Ivl=125us
-E:  Ad=0a(O) Atr=03(Int.) MxPS= 512 Ivl=125us
-
-Signed-off-by: Sean Wang <[email protected]>
-Signed-off-by: Marcel Holtmann <[email protected]>
----
- drivers/bluetooth/btusb.c | 3 +++
- 1 file changed, 3 insertions(+)
-
---- a/drivers/bluetooth/btusb.c
-+++ b/drivers/bluetooth/btusb.c
-@@ -469,6 +469,9 @@ static const struct usb_device_id blackl
-                                                    BTUSB_VALID_LE_STATES },
-       /* Additional MediaTek MT7921 Bluetooth devices */
-+      { USB_DEVICE(0x0489, 0xe0c8), .driver_info = BTUSB_MEDIATEK |
-+                                                   BTUSB_WIDEBAND_SPEECH |
-+                                                   BTUSB_VALID_LE_STATES },
-       { USB_DEVICE(0x04ca, 0x3802), .driver_info = BTUSB_MEDIATEK |
-                                                    BTUSB_WIDEBAND_SPEECH |
-                                                    BTUSB_VALID_LE_STATES },
diff --git a/target/linux/generic/backport-5.15/825-v6.1-Bluetooth-btusb-Add-a-new-VID-PID-0e8d-0608-for-MT79.patch b/target/linux/generic/backport-5.15/825-v6.1-Bluetooth-btusb-Add-a-new-VID-PID-0e8d-0608-for-MT79.patch
deleted file mode 100644 (file)
index b6b76f6..0000000
+++ /dev/null
@@ -1,66 +0,0 @@
-From be55622ce673f9692cc15d26d77a050cda42a3d3 Mon Sep 17 00:00:00 2001
-From: Daniel Golle <[email protected]>
-Date: Fri, 9 Sep 2022 21:00:30 +0100
-Subject: [PATCH 1/1] Bluetooth: btusb: Add a new VID/PID 0e8d/0608 for MT7921
-
-Add a new PID/VID 0e8d/0608 for MT7921K chip found on AMD RZ608 module.
-
-From /sys/kernel/debug/usb/devices:
-T:  Bus=01 Lev=02 Prnt=02 Port=01 Cnt=01 Dev#=  3 Spd=480  MxCh= 0
-D:  Ver= 2.10 Cls=ef(misc ) Sub=02 Prot=01 MxPS=64 #Cfgs=  1
-P:  Vendor=0e8d ProdID=0608 Rev= 1.00
-S:  Manufacturer=MediaTek Inc.
-S:  Product=Wireless_Device
-S:  SerialNumber=000000000
-C:* #Ifs= 3 Cfg#= 1 Atr=e0 MxPwr=100mA
-A:  FirstIf#= 0 IfCount= 3 Cls=e0(wlcon) Sub=01 Prot=01
-I:* If#= 0 Alt= 0 #EPs= 3 Cls=e0(wlcon) Sub=01 Prot=01 Driver=btusb
-E:  Ad=81(I) Atr=03(Int.) MxPS=  16 Ivl=125us
-E:  Ad=82(I) Atr=02(Bulk) MxPS= 512 Ivl=0ms
-E:  Ad=02(O) Atr=02(Bulk) MxPS= 512 Ivl=0ms
-I:* If#= 1 Alt= 0 #EPs= 2 Cls=e0(wlcon) Sub=01 Prot=01 Driver=btusb
-E:  Ad=83(I) Atr=01(Isoc) MxPS=   0 Ivl=1ms
-E:  Ad=03(O) Atr=01(Isoc) MxPS=   0 Ivl=1ms
-I:  If#= 1 Alt= 1 #EPs= 2 Cls=e0(wlcon) Sub=01 Prot=01 Driver=btusb
-E:  Ad=83(I) Atr=01(Isoc) MxPS=   9 Ivl=1ms
-E:  Ad=03(O) Atr=01(Isoc) MxPS=   9 Ivl=1ms
-I:  If#= 1 Alt= 2 #EPs= 2 Cls=e0(wlcon) Sub=01 Prot=01 Driver=btusb
-E:  Ad=83(I) Atr=01(Isoc) MxPS=  17 Ivl=1ms
-E:  Ad=03(O) Atr=01(Isoc) MxPS=  17 Ivl=1ms
-I:  If#= 1 Alt= 3 #EPs= 2 Cls=e0(wlcon) Sub=01 Prot=01 Driver=btusb
-E:  Ad=83(I) Atr=01(Isoc) MxPS=  25 Ivl=1ms
-E:  Ad=03(O) Atr=01(Isoc) MxPS=  25 Ivl=1ms
-I:  If#= 1 Alt= 4 #EPs= 2 Cls=e0(wlcon) Sub=01 Prot=01 Driver=btusb
-E:  Ad=83(I) Atr=01(Isoc) MxPS=  33 Ivl=1ms
-E:  Ad=03(O) Atr=01(Isoc) MxPS=  33 Ivl=1ms
-I:  If#= 1 Alt= 5 #EPs= 2 Cls=e0(wlcon) Sub=01 Prot=01 Driver=btusb
-E:  Ad=83(I) Atr=01(Isoc) MxPS=  49 Ivl=1ms
-E:  Ad=03(O) Atr=01(Isoc) MxPS=  49 Ivl=1ms
-I:  If#= 1 Alt= 6 #EPs= 2 Cls=e0(wlcon) Sub=01 Prot=01 Driver=btusb
-E:  Ad=83(I) Atr=01(Isoc) MxPS=  63 Ivl=1ms
-E:  Ad=03(O) Atr=01(Isoc) MxPS=  63 Ivl=1ms
-I:* If#= 2 Alt= 0 #EPs= 2 Cls=e0(wlcon) Sub=01 Prot=01 Driver=(none)
-E:  Ad=8a(I) Atr=03(Int.) MxPS=  64 Ivl=125us
-E:  Ad=0a(O) Atr=03(Int.) MxPS=  64 Ivl=125us
-I:  If#= 2 Alt= 1 #EPs= 2 Cls=e0(wlcon) Sub=01 Prot=01 Driver=(none)
-E:  Ad=8a(I) Atr=03(Int.) MxPS=  64 Ivl=125us
-E:  Ad=0a(O) Atr=03(Int.) MxPS=  64 Ivl=125us
-
-Signed-off-by: Daniel Golle <[email protected]>
-Signed-off-by: Luiz Augusto von Dentz <[email protected]>
----
- drivers/bluetooth/btusb.c | 3 +++
- 1 file changed, 3 insertions(+)
-
---- a/drivers/bluetooth/btusb.c
-+++ b/drivers/bluetooth/btusb.c
-@@ -487,6 +487,9 @@ static const struct usb_device_id blackl
-       { USB_DEVICE(0x0489, 0xe0cd), .driver_info = BTUSB_MEDIATEK |
-                                                    BTUSB_WIDEBAND_SPEECH |
-                                                    BTUSB_VALID_LE_STATES },
-+      { USB_DEVICE(0x0e8d, 0x0608), .driver_info = BTUSB_MEDIATEK |
-+                                                   BTUSB_WIDEBAND_SPEECH |
-+                                                   BTUSB_VALID_LE_STATES },
-       /* MediaTek MT7922A Bluetooth devices */
-       { USB_DEVICE(0x0489, 0xe0d8), .driver_info = BTUSB_MEDIATEK |
diff --git a/target/linux/generic/backport-5.15/826-v5.17-of-base-make-small-of_parse_phandle-variants-static-.patch b/target/linux/generic/backport-5.15/826-v5.17-of-base-make-small-of_parse_phandle-variants-static-.patch
deleted file mode 100644 (file)
index 0ad89de..0000000
+++ /dev/null
@@ -1,359 +0,0 @@
-From 66a8f7f04979f4ad739085f01d99c8caf620b4f5 Mon Sep 17 00:00:00 2001
-From: Michael Walle <[email protected]>
-Date: Tue, 18 Jan 2022 18:35:02 +0100
-Subject: [PATCH] of: base: make small of_parse_phandle() variants static
- inline
-
-Make all the smaller variants of the of_parse_phandle() static inline.
-This also let us remove the empty function stubs if CONFIG_OF is not
-defined.
-
-Suggested-by: Rob Herring <[email protected]>
-Signed-off-by: Michael Walle <[email protected]>
-[robh: move index < 0 check into __of_parse_phandle_with_args]
-Signed-off-by: Rob Herring <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
----
- drivers/of/base.c  | 131 +++------------------------------------
- include/linux/of.h | 148 ++++++++++++++++++++++++++++++++++++---------
- 2 files changed, 129 insertions(+), 150 deletions(-)
-
---- a/drivers/of/base.c
-+++ b/drivers/of/base.c
-@@ -1371,15 +1371,18 @@ int of_phandle_iterator_args(struct of_p
-       return count;
- }
--static int __of_parse_phandle_with_args(const struct device_node *np,
--                                      const char *list_name,
--                                      const char *cells_name,
--                                      int cell_count, int index,
--                                      struct of_phandle_args *out_args)
-+int __of_parse_phandle_with_args(const struct device_node *np,
-+                               const char *list_name,
-+                               const char *cells_name,
-+                               int cell_count, int index,
-+                               struct of_phandle_args *out_args)
- {
-       struct of_phandle_iterator it;
-       int rc, cur_index = 0;
-+      if (index < 0)
-+              return -EINVAL;
-+
-       /* Loop over the phandles until all the requested entry is found */
-       of_for_each_phandle(&it, rc, np, list_name, cells_name, cell_count) {
-               /*
-@@ -1422,82 +1425,7 @@ static int __of_parse_phandle_with_args(
-       of_node_put(it.node);
-       return rc;
- }
--
--/**
-- * of_parse_phandle - Resolve a phandle property to a device_node pointer
-- * @np: Pointer to device node holding phandle property
-- * @phandle_name: Name of property holding a phandle value
-- * @index: For properties holding a table of phandles, this is the index into
-- *         the table
-- *
-- * Return: The device_node pointer with refcount incremented.  Use
-- * of_node_put() on it when done.
-- */
--struct device_node *of_parse_phandle(const struct device_node *np,
--                                   const char *phandle_name, int index)
--{
--      struct of_phandle_args args;
--
--      if (index < 0)
--              return NULL;
--
--      if (__of_parse_phandle_with_args(np, phandle_name, NULL, 0,
--                                       index, &args))
--              return NULL;
--
--      return args.np;
--}
--EXPORT_SYMBOL(of_parse_phandle);
--
--/**
-- * of_parse_phandle_with_args() - Find a node pointed by phandle in a list
-- * @np:               pointer to a device tree node containing a list
-- * @list_name:        property name that contains a list
-- * @cells_name:       property name that specifies phandles' arguments count
-- * @index:    index of a phandle to parse out
-- * @out_args: optional pointer to output arguments structure (will be filled)
-- *
-- * This function is useful to parse lists of phandles and their arguments.
-- * Returns 0 on success and fills out_args, on error returns appropriate
-- * errno value.
-- *
-- * Caller is responsible to call of_node_put() on the returned out_args->np
-- * pointer.
-- *
-- * Example::
-- *
-- *  phandle1: node1 {
-- *    #list-cells = <2>;
-- *  };
-- *
-- *  phandle2: node2 {
-- *    #list-cells = <1>;
-- *  };
-- *
-- *  node3 {
-- *    list = <&phandle1 1 2 &phandle2 3>;
-- *  };
-- *
-- * To get a device_node of the ``node2`` node you may call this:
-- * of_parse_phandle_with_args(node3, "list", "#list-cells", 1, &args);
-- */
--int of_parse_phandle_with_args(const struct device_node *np, const char *list_name,
--                              const char *cells_name, int index,
--                              struct of_phandle_args *out_args)
--{
--      int cell_count = -1;
--
--      if (index < 0)
--              return -EINVAL;
--
--      /* If cells_name is NULL we assume a cell count of 0 */
--      if (!cells_name)
--              cell_count = 0;
--
--      return __of_parse_phandle_with_args(np, list_name, cells_name,
--                                          cell_count, index, out_args);
--}
--EXPORT_SYMBOL(of_parse_phandle_with_args);
-+EXPORT_SYMBOL(__of_parse_phandle_with_args);
- /**
-  * of_parse_phandle_with_args_map() - Find a node pointed by phandle in a list and remap it
-@@ -1685,47 +1613,6 @@ free:
- EXPORT_SYMBOL(of_parse_phandle_with_args_map);
- /**
-- * of_parse_phandle_with_fixed_args() - Find a node pointed by phandle in a list
-- * @np:               pointer to a device tree node containing a list
-- * @list_name:        property name that contains a list
-- * @cell_count: number of argument cells following the phandle
-- * @index:    index of a phandle to parse out
-- * @out_args: optional pointer to output arguments structure (will be filled)
-- *
-- * This function is useful to parse lists of phandles and their arguments.
-- * Returns 0 on success and fills out_args, on error returns appropriate
-- * errno value.
-- *
-- * Caller is responsible to call of_node_put() on the returned out_args->np
-- * pointer.
-- *
-- * Example::
-- *
-- *  phandle1: node1 {
-- *  };
-- *
-- *  phandle2: node2 {
-- *  };
-- *
-- *  node3 {
-- *    list = <&phandle1 0 2 &phandle2 2 3>;
-- *  };
-- *
-- * To get a device_node of the ``node2`` node you may call this:
-- * of_parse_phandle_with_fixed_args(node3, "list", 2, 1, &args);
-- */
--int of_parse_phandle_with_fixed_args(const struct device_node *np,
--                              const char *list_name, int cell_count,
--                              int index, struct of_phandle_args *out_args)
--{
--      if (index < 0)
--              return -EINVAL;
--      return __of_parse_phandle_with_args(np, list_name, NULL, cell_count,
--                                         index, out_args);
--}
--EXPORT_SYMBOL(of_parse_phandle_with_fixed_args);
--
--/**
-  * of_count_phandle_with_args() - Find the number of phandles references in a property
-  * @np:               pointer to a device tree node containing a list
-  * @list_name:        property name that contains a list
---- a/include/linux/of.h
-+++ b/include/linux/of.h
-@@ -363,18 +363,12 @@ extern const struct of_device_id *of_mat
-       const struct of_device_id *matches, const struct device_node *node);
- extern int of_modalias_node(struct device_node *node, char *modalias, int len);
- extern void of_print_phandle_args(const char *msg, const struct of_phandle_args *args);
--extern struct device_node *of_parse_phandle(const struct device_node *np,
--                                          const char *phandle_name,
--                                          int index);
--extern int of_parse_phandle_with_args(const struct device_node *np,
--      const char *list_name, const char *cells_name, int index,
--      struct of_phandle_args *out_args);
-+extern int __of_parse_phandle_with_args(const struct device_node *np,
-+      const char *list_name, const char *cells_name, int cell_count,
-+      int index, struct of_phandle_args *out_args);
- extern int of_parse_phandle_with_args_map(const struct device_node *np,
-       const char *list_name, const char *stem_name, int index,
-       struct of_phandle_args *out_args);
--extern int of_parse_phandle_with_fixed_args(const struct device_node *np,
--      const char *list_name, int cells_count, int index,
--      struct of_phandle_args *out_args);
- extern int of_count_phandle_with_args(const struct device_node *np,
-       const char *list_name, const char *cells_name);
-@@ -714,18 +708,12 @@ static inline int of_property_read_strin
-       return -ENOSYS;
- }
--static inline struct device_node *of_parse_phandle(const struct device_node *np,
--                                                 const char *phandle_name,
--                                                 int index)
--{
--      return NULL;
--}
--
--static inline int of_parse_phandle_with_args(const struct device_node *np,
--                                           const char *list_name,
--                                           const char *cells_name,
--                                           int index,
--                                           struct of_phandle_args *out_args)
-+static inline int __of_parse_phandle_with_args(const struct device_node *np,
-+                                             const char *list_name,
-+                                             const char *cells_name,
-+                                             int cell_count,
-+                                             int index,
-+                                             struct of_phandle_args *out_args)
- {
-       return -ENOSYS;
- }
-@@ -739,13 +727,6 @@ static inline int of_parse_phandle_with_
-       return -ENOSYS;
- }
--static inline int of_parse_phandle_with_fixed_args(const struct device_node *np,
--      const char *list_name, int cells_count, int index,
--      struct of_phandle_args *out_args)
--{
--      return -ENOSYS;
--}
--
- static inline int of_count_phandle_with_args(const struct device_node *np,
-                                            const char *list_name,
-                                            const char *cells_name)
-@@ -927,6 +908,117 @@ static inline bool of_node_is_type(const
- }
- /**
-+ * of_parse_phandle - Resolve a phandle property to a device_node pointer
-+ * @np: Pointer to device node holding phandle property
-+ * @phandle_name: Name of property holding a phandle value
-+ * @index: For properties holding a table of phandles, this is the index into
-+ *         the table
-+ *
-+ * Return: The device_node pointer with refcount incremented.  Use
-+ * of_node_put() on it when done.
-+ */
-+static inline struct device_node *of_parse_phandle(const struct device_node *np,
-+                                                 const char *phandle_name,
-+                                                 int index)
-+{
-+      struct of_phandle_args args;
-+
-+      if (__of_parse_phandle_with_args(np, phandle_name, NULL, 0,
-+                                       index, &args))
-+              return NULL;
-+
-+      return args.np;
-+}
-+
-+/**
-+ * of_parse_phandle_with_args() - Find a node pointed by phandle in a list
-+ * @np:               pointer to a device tree node containing a list
-+ * @list_name:        property name that contains a list
-+ * @cells_name:       property name that specifies phandles' arguments count
-+ * @index:    index of a phandle to parse out
-+ * @out_args: optional pointer to output arguments structure (will be filled)
-+ *
-+ * This function is useful to parse lists of phandles and their arguments.
-+ * Returns 0 on success and fills out_args, on error returns appropriate
-+ * errno value.
-+ *
-+ * Caller is responsible to call of_node_put() on the returned out_args->np
-+ * pointer.
-+ *
-+ * Example::
-+ *
-+ *  phandle1: node1 {
-+ *    #list-cells = <2>;
-+ *  };
-+ *
-+ *  phandle2: node2 {
-+ *    #list-cells = <1>;
-+ *  };
-+ *
-+ *  node3 {
-+ *    list = <&phandle1 1 2 &phandle2 3>;
-+ *  };
-+ *
-+ * To get a device_node of the ``node2`` node you may call this:
-+ * of_parse_phandle_with_args(node3, "list", "#list-cells", 1, &args);
-+ */
-+static inline int of_parse_phandle_with_args(const struct device_node *np,
-+                                           const char *list_name,
-+                                           const char *cells_name,
-+                                           int index,
-+                                           struct of_phandle_args *out_args)
-+{
-+      int cell_count = -1;
-+
-+      /* If cells_name is NULL we assume a cell count of 0 */
-+      if (!cells_name)
-+              cell_count = 0;
-+
-+      return __of_parse_phandle_with_args(np, list_name, cells_name,
-+                                          cell_count, index, out_args);
-+}
-+
-+/**
-+ * of_parse_phandle_with_fixed_args() - Find a node pointed by phandle in a list
-+ * @np:               pointer to a device tree node containing a list
-+ * @list_name:        property name that contains a list
-+ * @cell_count: number of argument cells following the phandle
-+ * @index:    index of a phandle to parse out
-+ * @out_args: optional pointer to output arguments structure (will be filled)
-+ *
-+ * This function is useful to parse lists of phandles and their arguments.
-+ * Returns 0 on success and fills out_args, on error returns appropriate
-+ * errno value.
-+ *
-+ * Caller is responsible to call of_node_put() on the returned out_args->np
-+ * pointer.
-+ *
-+ * Example::
-+ *
-+ *  phandle1: node1 {
-+ *  };
-+ *
-+ *  phandle2: node2 {
-+ *  };
-+ *
-+ *  node3 {
-+ *    list = <&phandle1 0 2 &phandle2 2 3>;
-+ *  };
-+ *
-+ * To get a device_node of the ``node2`` node you may call this:
-+ * of_parse_phandle_with_fixed_args(node3, "list", 2, 1, &args);
-+ */
-+static inline int of_parse_phandle_with_fixed_args(const struct device_node *np,
-+                                                 const char *list_name,
-+                                                 int cell_count,
-+                                                 int index,
-+                                                 struct of_phandle_args *out_args)
-+{
-+      return __of_parse_phandle_with_args(np, list_name, NULL, cell_count,
-+                                          index, out_args);
-+}
-+
-+/**
-  * of_property_count_u8_elems - Count the number of u8 elements in a property
-  *
-  * @np:               device node from which the property value is to be read.
diff --git a/target/linux/generic/backport-5.15/827-v6.3-0001-of-base-add-of_parse_phandle_with_optional_args.patch b/target/linux/generic/backport-5.15/827-v6.3-0001-of-base-add-of_parse_phandle_with_optional_args.patch
deleted file mode 100644 (file)
index 97f4c69..0000000
+++ /dev/null
@@ -1,58 +0,0 @@
-From c5d264d4b527c96ae8903376a4b195df47b05203 Mon Sep 17 00:00:00 2001
-From: Michael Walle <[email protected]>
-Date: Mon, 6 Feb 2023 13:43:43 +0000
-Subject: [PATCH] of: base: add of_parse_phandle_with_optional_args()
-
-Add a new variant of the of_parse_phandle_with_args() which treats the
-cells name as optional. If it's missing, it is assumed that the phandle
-has no arguments.
-
-Up until now, a nvmem node didn't have any arguments, so all the device
-trees haven't any '#*-cells' property. But there is a need for an
-additional argument for the phandle, for which we need a '#*-cells'
-property. Therefore, we need to support nvmem nodes with and without
-this property.
-
-Signed-off-by: Michael Walle <[email protected]>
-Reviewed-by: Rob Herring <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- include/linux/of.h | 25 +++++++++++++++++++++++++
- 1 file changed, 25 insertions(+)
-
---- a/include/linux/of.h
-+++ b/include/linux/of.h
-@@ -1019,6 +1019,31 @@ static inline int of_parse_phandle_with_
- }
- /**
-+ * of_parse_phandle_with_optional_args() - Find a node pointed by phandle in a list
-+ * @np:               pointer to a device tree node containing a list
-+ * @list_name:        property name that contains a list
-+ * @cells_name:       property name that specifies phandles' arguments count
-+ * @index:    index of a phandle to parse out
-+ * @out_args: optional pointer to output arguments structure (will be filled)
-+ *
-+ * Same as of_parse_phandle_with_args() except that if the cells_name property
-+ * is not found, cell_count of 0 is assumed.
-+ *
-+ * This is used to useful, if you have a phandle which didn't have arguments
-+ * before and thus doesn't have a '#*-cells' property but is now migrated to
-+ * having arguments while retaining backwards compatibility.
-+ */
-+static inline int of_parse_phandle_with_optional_args(const struct device_node *np,
-+                                                    const char *list_name,
-+                                                    const char *cells_name,
-+                                                    int index,
-+                                                    struct of_phandle_args *out_args)
-+{
-+      return __of_parse_phandle_with_args(np, list_name, cells_name,
-+                                          0, index, out_args);
-+}
-+
-+/**
-  * of_property_count_u8_elems - Count the number of u8 elements in a property
-  *
-  * @np:               device node from which the property value is to be read.
diff --git a/target/linux/generic/backport-5.15/827-v6.3-0002-of-property-make-.-cells-optional-for-simple-props.patch b/target/linux/generic/backport-5.15/827-v6.3-0002-of-property-make-.-cells-optional-for-simple-props.patch
deleted file mode 100644 (file)
index 39d9fae..0000000
+++ /dev/null
@@ -1,34 +0,0 @@
-From ff24fed10ba414d19579e26e60b126fad2f2bb07 Mon Sep 17 00:00:00 2001
-From: Michael Walle <[email protected]>
-Date: Mon, 6 Feb 2023 13:43:44 +0000
-Subject: [PATCH] of: property: make #.*-cells optional for simple props
-
-Sometimes, future bindings for phandles will get additional arguments.
-Thus the target node of the phandle will need a new #.*-cells property.
-To be backwards compatible, this needs to be optional.
-
-Prepare the DEFINE_SIMPLE_PROPS() to handle the cells name as optional.
-
-Signed-off-by: Michael Walle <[email protected]>
-Tested-by: Miquel Raynal <[email protected]>
-Reviewed-by: Rob Herring <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/of/property.c | 4 ++--
- 1 file changed, 2 insertions(+), 2 deletions(-)
-
---- a/drivers/of/property.c
-+++ b/drivers/of/property.c
-@@ -1173,8 +1173,8 @@ static struct device_node *parse_prop_ce
-       if (strcmp(prop_name, list_name))
-               return NULL;
--      if (of_parse_phandle_with_args(np, list_name, cells_name, index,
--                                     &sup_args))
-+      if (__of_parse_phandle_with_args(np, list_name, cells_name, 0, index,
-+                                       &sup_args))
-               return NULL;
-       return sup_args.np;
diff --git a/target/linux/generic/backport-5.15/827-v6.3-0003-of-property-add-nvmem-cell-cells-property.patch b/target/linux/generic/backport-5.15/827-v6.3-0003-of-property-add-nvmem-cell-cells-property.patch
deleted file mode 100644 (file)
index 774e793..0000000
+++ /dev/null
@@ -1,30 +0,0 @@
-From e2d8172043d2e50df19fcd59c11e5593de8188d7 Mon Sep 17 00:00:00 2001
-From: Michael Walle <[email protected]>
-Date: Mon, 6 Feb 2023 13:43:45 +0000
-Subject: [PATCH] of: property: add #nvmem-cell-cells property
-
-Bindings describe the new '#nvmem-cell-cells' property. Now that the
-arguments count property is optional, we just add this property to the
-nvmem-cells.
-
-Signed-off-by: Michael Walle <[email protected]>
-Tested-by: Miquel Raynal <[email protected]>
-Reviewed-by: Rob Herring <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/of/property.c | 2 +-
- 1 file changed, 1 insertion(+), 1 deletion(-)
-
---- a/drivers/of/property.c
-+++ b/drivers/of/property.c
-@@ -1276,7 +1276,7 @@ DEFINE_SIMPLE_PROP(dmas, "dmas", "#dma-c
- DEFINE_SIMPLE_PROP(power_domains, "power-domains", "#power-domain-cells")
- DEFINE_SIMPLE_PROP(hwlocks, "hwlocks", "#hwlock-cells")
- DEFINE_SIMPLE_PROP(extcon, "extcon", NULL)
--DEFINE_SIMPLE_PROP(nvmem_cells, "nvmem-cells", NULL)
-+DEFINE_SIMPLE_PROP(nvmem_cells, "nvmem-cells", "#nvmem-cell-cells")
- DEFINE_SIMPLE_PROP(phys, "phys", "#phy-cells")
- DEFINE_SIMPLE_PROP(wakeup_parent, "wakeup-parent", NULL)
- DEFINE_SIMPLE_PROP(pinctrl0, "pinctrl-0", NULL)
diff --git a/target/linux/generic/backport-5.15/827-v6.3-0004-of-device-Ignore-modalias-of-reused-nodes.patch b/target/linux/generic/backport-5.15/827-v6.3-0004-of-device-Ignore-modalias-of-reused-nodes.patch
deleted file mode 100644 (file)
index 37eefc4..0000000
+++ /dev/null
@@ -1,37 +0,0 @@
-From 553bd29700145e1849698985e9800f14e967da49 Mon Sep 17 00:00:00 2001
-From: Alexander Stein <[email protected]>
-Date: Tue, 7 Feb 2023 12:05:29 +0100
-Subject: [PATCH] of: device: Ignore modalias of reused nodes
-
-If of_node is reused, do not use that node's modalias. This will hide
-the name of the actual device. This is rather prominent in USB glue
-drivers creating a platform device for the host controller.
-
-Signed-off-by: Alexander Stein <[email protected]>
-Reviewed-by: Rob Herring <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/of/device.c | 4 ++--
- 1 file changed, 2 insertions(+), 2 deletions(-)
-
---- a/drivers/of/device.c
-+++ b/drivers/of/device.c
-@@ -249,7 +249,7 @@ static ssize_t of_device_get_modalias(st
-       ssize_t csize;
-       ssize_t tsize;
--      if ((!dev) || (!dev->of_node))
-+      if ((!dev) || (!dev->of_node) || dev->of_node_reused)
-               return -ENODEV;
-       /* Name & Type */
-@@ -372,7 +372,7 @@ int of_device_uevent_modalias(struct dev
- {
-       int sl;
--      if ((!dev) || (!dev->of_node))
-+      if ((!dev) || (!dev->of_node) || dev->of_node_reused)
-               return -ENODEV;
-       /* Devicetree modalias is tricky, we add it in 2 steps */
diff --git a/target/linux/generic/backport-5.15/827-v6.3-0005-of-device-Do-not-ignore-error-code-in-of_device_ueve.patch b/target/linux/generic/backport-5.15/827-v6.3-0005-of-device-Do-not-ignore-error-code-in-of_device_ueve.patch
deleted file mode 100644 (file)
index dd5820e..0000000
+++ /dev/null
@@ -1,29 +0,0 @@
-From 2295bed9bebe8d1eef276194fed5b5fbe89c5363 Mon Sep 17 00:00:00 2001
-From: Alexander Stein <[email protected]>
-Date: Tue, 7 Feb 2023 12:05:30 +0100
-Subject: [PATCH] of: device: Do not ignore error code in
- of_device_uevent_modalias
-
-of_device_get_modalias might return an error code, propagate that one.
-Otherwise the negative, signed integer is propagated to unsigned integer
-for the comparison resulting in a huge 'sl' size.
-
-Signed-off-by: Alexander Stein <[email protected]>
-Reviewed-by: Rob Herring <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/of/device.c | 2 ++
- 1 file changed, 2 insertions(+)
-
---- a/drivers/of/device.c
-+++ b/drivers/of/device.c
-@@ -381,6 +381,8 @@ int of_device_uevent_modalias(struct dev
-       sl = of_device_get_modalias(dev, &env->buf[env->buflen-1],
-                                   sizeof(env->buf) - env->buflen);
-+      if (sl < 0)
-+              return sl;
-       if (sl >= (sizeof(env->buf) - env->buflen))
-               return -ENOMEM;
-       env->buflen += sl;
diff --git a/target/linux/generic/backport-5.15/828-v6.4-0002-of-Update-of_device_get_modalias.patch b/target/linux/generic/backport-5.15/828-v6.4-0002-of-Update-of_device_get_modalias.patch
deleted file mode 100644 (file)
index 4713cc7..0000000
+++ /dev/null
@@ -1,103 +0,0 @@
-From 5c3d15e127ebfc0754cd18def7124633b6d46672 Mon Sep 17 00:00:00 2001
-From: Miquel Raynal <[email protected]>
-Date: Tue, 4 Apr 2023 18:21:15 +0100
-Subject: [PATCH] of: Update of_device_get_modalias()
-
-This function only needs a "struct device_node" to work, but for
-convenience the author (and only user) of this helper did use a "struct
-device" and put it in device.c.
-
-Let's convert this helper to take a "struct device node" instead. This
-change asks for two additional changes: renaming it "of_modalias()"
-to fit the current naming, and moving it outside of device.c which will
-be done in a follow-up commit.
-
-Signed-off-by: Miquel Raynal <[email protected]>
-Reviewed-by: Rob Herring <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/of/device.c | 29 +++++++++++++++++------------
- 1 file changed, 17 insertions(+), 12 deletions(-)
-
---- a/drivers/of/device.c
-+++ b/drivers/of/device.c
-@@ -241,7 +241,7 @@ const void *of_device_get_match_data(con
- }
- EXPORT_SYMBOL(of_device_get_match_data);
--static ssize_t of_device_get_modalias(struct device *dev, char *str, ssize_t len)
-+static ssize_t of_modalias(const struct device_node *np, char *str, ssize_t len)
- {
-       const char *compat;
-       char *c;
-@@ -249,19 +249,16 @@ static ssize_t of_device_get_modalias(st
-       ssize_t csize;
-       ssize_t tsize;
--      if ((!dev) || (!dev->of_node) || dev->of_node_reused)
--              return -ENODEV;
--
-       /* Name & Type */
-       /* %p eats all alphanum characters, so %c must be used here */
--      csize = snprintf(str, len, "of:N%pOFn%c%s", dev->of_node, 'T',
--                       of_node_get_device_type(dev->of_node));
-+      csize = snprintf(str, len, "of:N%pOFn%c%s", np, 'T',
-+                       of_node_get_device_type(np));
-       tsize = csize;
-       len -= csize;
-       if (str)
-               str += csize;
--      of_property_for_each_string(dev->of_node, "compatible", p, compat) {
-+      of_property_for_each_string(np, "compatible", p, compat) {
-               csize = strlen(compat) + 1;
-               tsize += csize;
-               if (csize > len)
-@@ -286,7 +283,10 @@ int of_device_request_module(struct devi
-       ssize_t size;
-       int ret;
--      size = of_device_get_modalias(dev, NULL, 0);
-+      if (!dev || !dev->of_node)
-+              return -ENODEV;
-+
-+      size = of_modalias(dev->of_node, NULL, 0);
-       if (size < 0)
-               return size;
-@@ -297,7 +297,7 @@ int of_device_request_module(struct devi
-       if (!str)
-               return -ENOMEM;
--      of_device_get_modalias(dev, str, size);
-+      of_modalias(dev->of_node, str, size);
-       str[size - 1] = '\0';
-       ret = request_module(str);
-       kfree(str);
-@@ -314,7 +314,12 @@ EXPORT_SYMBOL_GPL(of_device_request_modu
-  */
- ssize_t of_device_modalias(struct device *dev, char *str, ssize_t len)
- {
--      ssize_t sl = of_device_get_modalias(dev, str, len - 2);
-+      ssize_t sl;
-+
-+      if (!dev || !dev->of_node || dev->of_node_reused)
-+              return -ENODEV;
-+
-+      sl = of_modalias(dev->of_node, str, len - 2);
-       if (sl < 0)
-               return sl;
-       if (sl > len - 2)
-@@ -379,8 +384,8 @@ int of_device_uevent_modalias(struct dev
-       if (add_uevent_var(env, "MODALIAS="))
-               return -ENOMEM;
--      sl = of_device_get_modalias(dev, &env->buf[env->buflen-1],
--                                  sizeof(env->buf) - env->buflen);
-+      sl = of_modalias(dev->of_node, &env->buf[env->buflen-1],
-+                       sizeof(env->buf) - env->buflen);
-       if (sl < 0)
-               return sl;
-       if (sl >= (sizeof(env->buf) - env->buflen))
diff --git a/target/linux/generic/backport-5.15/828-v6.4-0003-of-Rename-of_modalias_node.patch b/target/linux/generic/backport-5.15/828-v6.4-0003-of-Rename-of_modalias_node.patch
deleted file mode 100644 (file)
index 7cfdb28..0000000
+++ /dev/null
@@ -1,173 +0,0 @@
-From 673aa1ed1c9b6710bf24e3f0957d85e2f46c77db Mon Sep 17 00:00:00 2001
-From: Miquel Raynal <[email protected]>
-Date: Tue, 4 Apr 2023 18:21:16 +0100
-Subject: [PATCH] of: Rename of_modalias_node()
-
-This helper does not produce a real modalias, but tries to get the
-"product" compatible part of the "vendor,product" compatibles only. It
-is far from creating a purely useful modalias string and does not seem
-to be used like that directly anyway, so let's try to give this helper a
-more meaningful name before moving there a real modalias helper (already
-existing under of/device.c).
-
-Also update the various documentations to refer to the strings as
-"aliases" rather than "modaliases" which has a real meaning in the Linux
-kernel.
-
-There is no functional change.
-
-Cc: Rafael J. Wysocki <[email protected]>
-Cc: Len Brown <[email protected]>
-Cc: Maarten Lankhorst <[email protected]>
-Cc: Maxime Ripard <[email protected]>
-Cc: Thomas Zimmermann <[email protected]>
-Cc: Sebastian Reichel <[email protected]>
-Cc: Wolfram Sang <[email protected]>
-Cc: Mark Brown <[email protected]>
-Signed-off-by: Miquel Raynal <[email protected]>
-Reviewed-by: Rob Herring <[email protected]>
-Acked-by: Mark Brown <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Acked-by: Sebastian Reichel <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/acpi/bus.c                |  7 ++++---
- drivers/gpu/drm/drm_mipi_dsi.c    |  2 +-
- drivers/hsi/hsi_core.c            |  2 +-
- drivers/i2c/busses/i2c-powermac.c |  2 +-
- drivers/i2c/i2c-core-of.c         |  2 +-
- drivers/of/base.c                 | 18 +++++++++++-------
- drivers/spi/spi.c                 |  4 ++--
- include/linux/of.h                |  3 ++-
- 8 files changed, 23 insertions(+), 17 deletions(-)
-
---- a/drivers/acpi/bus.c
-+++ b/drivers/acpi/bus.c
-@@ -785,9 +785,10 @@ static bool acpi_of_modalias(struct acpi
-  * @modalias:   Pointer to buffer that modalias value will be copied into
-  * @len:      Length of modalias buffer
-  *
-- * This is a counterpart of of_modalias_node() for struct acpi_device objects.
-- * If there is a compatible string for @adev, it will be copied to @modalias
-- * with the vendor prefix stripped; otherwise, @default_id will be used.
-+ * This is a counterpart of of_alias_from_compatible() for struct acpi_device
-+ * objects. If there is a compatible string for @adev, it will be copied to
-+ * @modalias with the vendor prefix stripped; otherwise, @default_id will be
-+ * used.
-  */
- void acpi_set_modalias(struct acpi_device *adev, const char *default_id,
-                      char *modalias, size_t len)
---- a/drivers/gpu/drm/drm_mipi_dsi.c
-+++ b/drivers/gpu/drm/drm_mipi_dsi.c
-@@ -160,7 +160,7 @@ of_mipi_dsi_device_add(struct mipi_dsi_h
-       int ret;
-       u32 reg;
--      if (of_modalias_node(node, info.type, sizeof(info.type)) < 0) {
-+      if (of_alias_from_compatible(node, info.type, sizeof(info.type)) < 0) {
-               drm_err(host, "modalias failure on %pOF\n", node);
-               return ERR_PTR(-EINVAL);
-       }
---- a/drivers/hsi/hsi_core.c
-+++ b/drivers/hsi/hsi_core.c
-@@ -207,7 +207,7 @@ static void hsi_add_client_from_dt(struc
-       if (!cl)
-               return;
--      err = of_modalias_node(client, name, sizeof(name));
-+      err = of_alias_from_compatible(client, name, sizeof(name));
-       if (err)
-               goto err;
---- a/drivers/i2c/busses/i2c-powermac.c
-+++ b/drivers/i2c/busses/i2c-powermac.c
-@@ -284,7 +284,7 @@ static bool i2c_powermac_get_type(struct
-        */
-       /* First try proper modalias */
--      if (of_modalias_node(node, tmp, sizeof(tmp)) >= 0) {
-+      if (of_alias_from_compatible(node, tmp, sizeof(tmp)) >= 0) {
-               snprintf(type, type_size, "MAC,%s", tmp);
-               return true;
-       }
---- a/drivers/i2c/i2c-core-of.c
-+++ b/drivers/i2c/i2c-core-of.c
-@@ -27,7 +27,7 @@ int of_i2c_get_board_info(struct device
-       memset(info, 0, sizeof(*info));
--      if (of_modalias_node(node, info->type, sizeof(info->type)) < 0) {
-+      if (of_alias_from_compatible(node, info->type, sizeof(info->type)) < 0) {
-               dev_err(dev, "of_i2c: modalias failure on %pOF\n", node);
-               return -EINVAL;
-       }
---- a/drivers/of/base.c
-+++ b/drivers/of/base.c
-@@ -1159,19 +1159,23 @@ struct device_node *of_find_matching_nod
- EXPORT_SYMBOL(of_find_matching_node_and_match);
- /**
-- * of_modalias_node - Lookup appropriate modalias for a device node
-+ * of_alias_from_compatible - Lookup appropriate alias for a device node
-+ *                          depending on compatible
-  * @node:     pointer to a device tree node
-- * @modalias: Pointer to buffer that modalias value will be copied into
-- * @len:      Length of modalias value
-+ * @alias:    Pointer to buffer that alias value will be copied into
-+ * @len:      Length of alias value
-  *
-  * Based on the value of the compatible property, this routine will attempt
-- * to choose an appropriate modalias value for a particular device tree node.
-+ * to choose an appropriate alias value for a particular device tree node.
-  * It does this by stripping the manufacturer prefix (as delimited by a ',')
-  * from the first entry in the compatible list property.
-  *
-+ * Note: The matching on just the "product" side of the compatible is a relic
-+ * from I2C and SPI. Please do not add any new user.
-+ *
-  * Return: This routine returns 0 on success, <0 on failure.
-  */
--int of_modalias_node(struct device_node *node, char *modalias, int len)
-+int of_alias_from_compatible(const struct device_node *node, char *alias, int len)
- {
-       const char *compatible, *p;
-       int cplen;
-@@ -1180,10 +1184,10 @@ int of_modalias_node(struct device_node
-       if (!compatible || strlen(compatible) > cplen)
-               return -ENODEV;
-       p = strchr(compatible, ',');
--      strlcpy(modalias, p ? p + 1 : compatible, len);
-+      strlcpy(alias, p ? p + 1 : compatible, len);
-       return 0;
- }
--EXPORT_SYMBOL_GPL(of_modalias_node);
-+EXPORT_SYMBOL_GPL(of_alias_from_compatible);
- /**
-  * of_find_node_by_phandle - Find a node given a phandle
---- a/drivers/spi/spi.c
-+++ b/drivers/spi/spi.c
-@@ -2144,8 +2144,8 @@ of_register_spi_device(struct spi_contro
-       }
-       /* Select device driver */
--      rc = of_modalias_node(nc, spi->modalias,
--                              sizeof(spi->modalias));
-+      rc = of_alias_from_compatible(nc, spi->modalias,
-+                                    sizeof(spi->modalias));
-       if (rc < 0) {
-               dev_err(&ctlr->dev, "cannot find modalias for %pOF\n", nc);
-               goto err_out;
---- a/include/linux/of.h
-+++ b/include/linux/of.h
-@@ -361,7 +361,8 @@ extern int of_n_addr_cells(struct device
- extern int of_n_size_cells(struct device_node *np);
- extern const struct of_device_id *of_match_node(
-       const struct of_device_id *matches, const struct device_node *node);
--extern int of_modalias_node(struct device_node *node, char *modalias, int len);
-+extern int of_alias_from_compatible(const struct device_node *node, char *alias,
-+                                  int len);
- extern void of_print_phandle_args(const char *msg, const struct of_phandle_args *args);
- extern int __of_parse_phandle_with_args(const struct device_node *np,
-       const char *list_name, const char *cells_name, int cell_count,
diff --git a/target/linux/generic/backport-5.15/828-v6.4-0004-of-Move-of_modalias-to-module.c.patch b/target/linux/generic/backport-5.15/828-v6.4-0004-of-Move-of_modalias-to-module.c.patch
deleted file mode 100644 (file)
index b4554b2..0000000
+++ /dev/null
@@ -1,160 +0,0 @@
-From bd7a7ed774afd1a4174df34227626c95573be517 Mon Sep 17 00:00:00 2001
-From: Miquel Raynal <[email protected]>
-Date: Tue, 4 Apr 2023 18:21:17 +0100
-Subject: [PATCH] of: Move of_modalias() to module.c
-
-Create a specific .c file for OF related module handling.
-Move of_modalias() inside as a first step.
-
-The helper is exposed through of.h even though it is only used by core
-files because the users from device.c will soon be split into an OF-only
-helper in module.c as well as a device-oriented inline helper in
-of_device.h. Putting this helper in of_private.h would require to
-include of_private.h from of_device.h, which is not acceptable.
-
-Suggested-by: Rob Herring <[email protected]>
-Signed-off-by: Miquel Raynal <[email protected]>
-Reviewed-by: Rob Herring <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/of/Makefile |  2 +-
- drivers/of/device.c | 37 -------------------------------------
- drivers/of/module.c | 44 ++++++++++++++++++++++++++++++++++++++++++++
- include/linux/of.h  |  9 +++++++++
- 4 files changed, 54 insertions(+), 38 deletions(-)
- create mode 100644 drivers/of/module.c
-
---- a/drivers/of/Makefile
-+++ b/drivers/of/Makefile
-@@ -1,5 +1,5 @@
- # SPDX-License-Identifier: GPL-2.0
--obj-y = base.o device.o platform.o property.o
-+obj-y = base.o device.o module.o platform.o property.o
- obj-$(CONFIG_OF_KOBJ) += kobj.o
- obj-$(CONFIG_OF_DYNAMIC) += dynamic.o
- obj-$(CONFIG_OF_FLATTREE) += fdt.o
---- a/drivers/of/device.c
-+++ b/drivers/of/device.c
-@@ -1,5 +1,4 @@
- // SPDX-License-Identifier: GPL-2.0
--#include <linux/string.h>
- #include <linux/kernel.h>
- #include <linux/of.h>
- #include <linux/of_device.h>
-@@ -241,42 +240,6 @@ const void *of_device_get_match_data(con
- }
- EXPORT_SYMBOL(of_device_get_match_data);
--static ssize_t of_modalias(const struct device_node *np, char *str, ssize_t len)
--{
--      const char *compat;
--      char *c;
--      struct property *p;
--      ssize_t csize;
--      ssize_t tsize;
--
--      /* Name & Type */
--      /* %p eats all alphanum characters, so %c must be used here */
--      csize = snprintf(str, len, "of:N%pOFn%c%s", np, 'T',
--                       of_node_get_device_type(np));
--      tsize = csize;
--      len -= csize;
--      if (str)
--              str += csize;
--
--      of_property_for_each_string(np, "compatible", p, compat) {
--              csize = strlen(compat) + 1;
--              tsize += csize;
--              if (csize > len)
--                      continue;
--
--              csize = snprintf(str, len, "C%s", compat);
--              for (c = str; c; ) {
--                      c = strchr(c, ' ');
--                      if (c)
--                              *c++ = '_';
--              }
--              len -= csize;
--              str += csize;
--      }
--
--      return tsize;
--}
--
- int of_device_request_module(struct device *dev)
- {
-       char *str;
---- /dev/null
-+++ b/drivers/of/module.c
-@@ -0,0 +1,44 @@
-+// SPDX-License-Identifier: GPL-2.0
-+/*
-+ * Linux kernel module helpers.
-+ */
-+
-+#include <linux/of.h>
-+#include <linux/slab.h>
-+#include <linux/string.h>
-+
-+ssize_t of_modalias(const struct device_node *np, char *str, ssize_t len)
-+{
-+      const char *compat;
-+      char *c;
-+      struct property *p;
-+      ssize_t csize;
-+      ssize_t tsize;
-+
-+      /* Name & Type */
-+      /* %p eats all alphanum characters, so %c must be used here */
-+      csize = snprintf(str, len, "of:N%pOFn%c%s", np, 'T',
-+                       of_node_get_device_type(np));
-+      tsize = csize;
-+      len -= csize;
-+      if (str)
-+              str += csize;
-+
-+      of_property_for_each_string(np, "compatible", p, compat) {
-+              csize = strlen(compat) + 1;
-+              tsize += csize;
-+              if (csize > len)
-+                      continue;
-+
-+              csize = snprintf(str, len, "C%s", compat);
-+              for (c = str; c; ) {
-+                      c = strchr(c, ' ');
-+                      if (c)
-+                              *c++ = '_';
-+              }
-+              len -= csize;
-+              str += csize;
-+      }
-+
-+      return tsize;
-+}
---- a/include/linux/of.h
-+++ b/include/linux/of.h
-@@ -373,6 +373,9 @@ extern int of_parse_phandle_with_args_ma
- extern int of_count_phandle_with_args(const struct device_node *np,
-       const char *list_name, const char *cells_name);
-+/* module functions */
-+extern ssize_t of_modalias(const struct device_node *np, char *str, ssize_t len);
-+
- /* phandle iterator functions */
- extern int of_phandle_iterator_init(struct of_phandle_iterator *it,
-                                   const struct device_node *np,
-@@ -735,6 +738,12 @@ static inline int of_count_phandle_with_
-       return -ENOSYS;
- }
-+static inline ssize_t of_modalias(const struct device_node *np, char *str,
-+                                ssize_t len)
-+{
-+      return -ENODEV;
-+}
-+
- static inline int of_phandle_iterator_init(struct of_phandle_iterator *it,
-                                          const struct device_node *np,
-                                          const char *list_name,
diff --git a/target/linux/generic/backport-5.15/828-v6.4-0005-of-Move-the-request-module-helper-logic-to-module.c.patch b/target/linux/generic/backport-5.15/828-v6.4-0005-of-Move-the-request-module-helper-logic-to-module.c.patch
deleted file mode 100644 (file)
index ad42039..0000000
+++ /dev/null
@@ -1,131 +0,0 @@
-From e6506f06d5e82765666902ccf9e9162f3e31d518 Mon Sep 17 00:00:00 2001
-From: Miquel Raynal <[email protected]>
-Date: Tue, 4 Apr 2023 18:21:18 +0100
-Subject: [PATCH] of: Move the request module helper logic to module.c
-
-Depending on device.c for pure OF handling is considered
-backwards. Let's extract the content of of_device_request_module() to
-have the real logic under module.c.
-
-The next step will be to convert users of of_device_request_module() to
-use the new helper.
-
-Signed-off-by: Miquel Raynal <[email protected]>
-Reviewed-by: Rob Herring <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/of/device.c | 25 ++-----------------------
- drivers/of/module.c | 30 ++++++++++++++++++++++++++++++
- include/linux/of.h  |  6 ++++++
- 3 files changed, 38 insertions(+), 23 deletions(-)
-
---- a/drivers/of/device.c
-+++ b/drivers/of/device.c
-@@ -8,7 +8,6 @@
- #include <linux/dma-direct.h> /* for bus_dma_region */
- #include <linux/dma-map-ops.h>
- #include <linux/init.h>
--#include <linux/module.h>
- #include <linux/mod_devicetable.h>
- #include <linux/slab.h>
- #include <linux/platform_device.h>
-@@ -242,30 +241,10 @@ EXPORT_SYMBOL(of_device_get_match_data);
- int of_device_request_module(struct device *dev)
- {
--      char *str;
--      ssize_t size;
--      int ret;
--
--      if (!dev || !dev->of_node)
-+      if (!dev)
-               return -ENODEV;
--      size = of_modalias(dev->of_node, NULL, 0);
--      if (size < 0)
--              return size;
--
--      /* Reserve an additional byte for the trailing '\0' */
--      size++;
--
--      str = kmalloc(size, GFP_KERNEL);
--      if (!str)
--              return -ENOMEM;
--
--      of_modalias(dev->of_node, str, size);
--      str[size - 1] = '\0';
--      ret = request_module(str);
--      kfree(str);
--
--      return ret;
-+      return of_request_module(dev->of_node);
- }
- EXPORT_SYMBOL_GPL(of_device_request_module);
---- a/drivers/of/module.c
-+++ b/drivers/of/module.c
-@@ -4,6 +4,7 @@
-  */
- #include <linux/of.h>
-+#include <linux/module.h>
- #include <linux/slab.h>
- #include <linux/string.h>
-@@ -42,3 +43,32 @@ ssize_t of_modalias(const struct device_
-       return tsize;
- }
-+
-+int of_request_module(const struct device_node *np)
-+{
-+      char *str;
-+      ssize_t size;
-+      int ret;
-+
-+      if (!np)
-+              return -ENODEV;
-+
-+      size = of_modalias(np, NULL, 0);
-+      if (size < 0)
-+              return size;
-+
-+      /* Reserve an additional byte for the trailing '\0' */
-+      size++;
-+
-+      str = kmalloc(size, GFP_KERNEL);
-+      if (!str)
-+              return -ENOMEM;
-+
-+      of_modalias(np, str, size);
-+      str[size - 1] = '\0';
-+      ret = request_module(str);
-+      kfree(str);
-+
-+      return ret;
-+}
-+EXPORT_SYMBOL_GPL(of_request_module);
---- a/include/linux/of.h
-+++ b/include/linux/of.h
-@@ -375,6 +375,7 @@ extern int of_count_phandle_with_args(co
- /* module functions */
- extern ssize_t of_modalias(const struct device_node *np, char *str, ssize_t len);
-+extern int of_request_module(const struct device_node *np);
- /* phandle iterator functions */
- extern int of_phandle_iterator_init(struct of_phandle_iterator *it,
-@@ -743,6 +744,11 @@ static inline ssize_t of_modalias(const
- {
-       return -ENODEV;
- }
-+
-+static inline int of_request_module(const struct device_node *np)
-+{
-+      return -ENODEV;
-+}
- static inline int of_phandle_iterator_init(struct of_phandle_iterator *it,
-                                          const struct device_node *np,
diff --git a/target/linux/generic/backport-5.15/829-v6.3-i915-Move-list_count-to-list.h-as-list_count_nodes-f.patch b/target/linux/generic/backport-5.15/829-v6.3-i915-Move-list_count-to-list.h-as-list_count_nodes-f.patch
deleted file mode 100644 (file)
index 1365834..0000000
+++ /dev/null
@@ -1,75 +0,0 @@
-From 4d70c74659d9746502b23d055dba03d1d28ec388 Mon Sep 17 00:00:00 2001
-From: Andy Shevchenko <[email protected]>
-Date: Wed, 30 Nov 2022 15:48:35 +0200
-Subject: [PATCH] i915: Move list_count() to list.h as list_count_nodes() for
- broader use
-
-Some of the existing users, and definitely will be new ones, want to
-count existing nodes in the list. Provide a generic API for that by
-moving code from i915 to list.h.
-
-Reviewed-by: Lucas De Marchi <[email protected]>
-Acked-by: Jani Nikula <[email protected]>
-Signed-off-by: Andy Shevchenko <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/gpu/drm/i915/gt/intel_engine_cs.c | 15 ++-------------
- include/linux/list.h                      | 15 +++++++++++++++
- 2 files changed, 17 insertions(+), 13 deletions(-)
-
---- a/drivers/gpu/drm/i915/gt/intel_engine_cs.c
-+++ b/drivers/gpu/drm/i915/gt/intel_engine_cs.c
-@@ -1639,17 +1639,6 @@ static void print_request_ring(struct dr
-       }
- }
--static unsigned long list_count(struct list_head *list)
--{
--      struct list_head *pos;
--      unsigned long count = 0;
--
--      list_for_each(pos, list)
--              count++;
--
--      return count;
--}
--
- static unsigned long read_ul(void *p, size_t x)
- {
-       return *(unsigned long *)(p + x);
-@@ -1824,8 +1813,8 @@ void intel_engine_dump(struct intel_engi
-       spin_lock_irqsave(&engine->sched_engine->lock, flags);
-       engine_dump_active_requests(engine, m);
--      drm_printf(m, "\tOn hold?: %lu\n",
--                 list_count(&engine->sched_engine->hold));
-+      drm_printf(m, "\tOn hold?: %zu\n",
-+                 list_count_nodes(&engine->sched_engine->hold));
-       spin_unlock_irqrestore(&engine->sched_engine->lock, flags);
-       drm_printf(m, "\tMMIO base:  0x%08x\n", engine->mmio_base);
---- a/include/linux/list.h
-+++ b/include/linux/list.h
-@@ -628,6 +628,21 @@ static inline void list_splice_tail_init
-            pos = n, n = pos->prev)
- /**
-+ * list_count_nodes - count nodes in the list
-+ * @head:     the head for your list.
-+ */
-+static inline size_t list_count_nodes(struct list_head *head)
-+{
-+      struct list_head *pos;
-+      size_t count = 0;
-+
-+      list_for_each(pos, head)
-+              count++;
-+
-+      return count;
-+}
-+
-+/**
-  * list_entry_is_head - test if the entry points to the head of the list
-  * @pos:      the type * to cursor
-  * @head:     the head for your list.
diff --git a/target/linux/generic/backport-5.15/830-v6.0-leds-turris-omnia-convert-to-use-dev_groups.patch b/target/linux/generic/backport-5.15/830-v6.0-leds-turris-omnia-convert-to-use-dev_groups.patch
deleted file mode 100644 (file)
index 99ebe06..0000000
+++ /dev/null
@@ -1,45 +0,0 @@
-From a01633cd867b8ddf2d8321fe575dc3c54e037b09 Mon Sep 17 00:00:00 2001
-From: Greg Kroah-Hartman <[email protected]>
-Date: Fri, 29 Jul 2022 16:03:46 +0200
-Subject: leds: turris-omnia: convert to use dev_groups
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-The driver core supports the ability to handle the creation and removal
-of device-specific sysfs files in a race-free manner.  Take advantage of
-that by converting this driver to use this by moving the sysfs
-attributes into a group and assigning the dev_groups pointer to it.
-
-Cc: Pavel Machek <[email protected]>
-Reviewed-by: Marek Behún <[email protected]>
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
-Signed-off-by: Pavel Machek <[email protected]>
----
- drivers/leds/leds-turris-omnia.c | 4 +---
- 1 file changed, 1 insertion(+), 3 deletions(-)
-
-(limited to 'drivers/leds/leds-turris-omnia.c')
-
---- a/drivers/leds/leds-turris-omnia.c
-+++ b/drivers/leds/leds-turris-omnia.c
-@@ -260,9 +260,6 @@ static int omnia_leds_probe(struct i2c_c
-               led += ret;
-       }
--      if (devm_device_add_groups(dev, omnia_led_controller_groups))
--              dev_warn(dev, "Could not add attribute group!\n");
--
-       return 0;
- }
-@@ -304,6 +301,7 @@ static struct i2c_driver omnia_leds_driv
-       .driver         = {
-               .name   = "leds-turris-omnia",
-               .of_match_table = of_omnia_leds_match,
-+              .dev_groups = omnia_led_controller_groups,
-       },
- };
diff --git a/target/linux/generic/backport-5.15/830-v6.6-1-leds-turris-omnia-Use-sysfs_emit-instead-of-sprintf.patch b/target/linux/generic/backport-5.15/830-v6.6-1-leds-turris-omnia-Use-sysfs_emit-instead-of-sprintf.patch
deleted file mode 100644 (file)
index 835a5e8..0000000
+++ /dev/null
@@ -1,31 +0,0 @@
-From 72a29725b6f2577fa447ca9059cdcd17100043b4 Mon Sep 17 00:00:00 2001
-From: Marek Behún <[email protected]>
-Date: Wed, 2 Aug 2023 18:07:45 +0200
-Subject: leds: turris-omnia: Use sysfs_emit() instead of sprintf()
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-Use the dedicated sysfs_emit() function instead of sprintf() in sysfs
-attribute accessor brightness_show().
-
-Signed-off-by: Marek Behún <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Lee Jones <[email protected]>
----
- drivers/leds/leds-turris-omnia.c | 2 +-
- 1 file changed, 1 insertion(+), 1 deletion(-)
-
-(limited to 'drivers/leds/leds-turris-omnia.c')
-
---- a/drivers/leds/leds-turris-omnia.c
-+++ b/drivers/leds/leds-turris-omnia.c
-@@ -194,7 +194,7 @@ static ssize_t brightness_show(struct de
-       if (ret < 0)
-               return ret;
--      return sprintf(buf, "%d\n", ret);
-+      return sysfs_emit(buf, "%d\n", ret);
- }
- static ssize_t brightness_store(struct device *dev, struct device_attribute *a,
diff --git a/target/linux/generic/backport-5.15/830-v6.7-2-leds-turris-omnia-Make-set_brightness-more-efficient.patch b/target/linux/generic/backport-5.15/830-v6.7-2-leds-turris-omnia-Make-set_brightness-more-efficient.patch
deleted file mode 100644 (file)
index 3f7dd64..0000000
+++ /dev/null
@@ -1,207 +0,0 @@
-From 4d5ed2621c2437d40b8fe92bd0fd34b0b1870753 Mon Sep 17 00:00:00 2001
-From: Marek Behún <[email protected]>
-Date: Mon, 18 Sep 2023 18:11:02 +0200
-Subject: leds: turris-omnia: Make set_brightness() more efficient
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-Implement caching of the LED color and state values that are sent to MCU
-in order to make the set_brightness() operation more efficient by
-avoiding I2C transactions which are not needed.
-
-On Turris Omnia's MCU, which acts as the RGB LED controller, each LED
-has a RGB color, and a ON/OFF state, which are configurable via I2C
-commands CMD_LED_COLOR and CMD_LED_STATE.
-
-The CMD_LED_COLOR command sends 5 bytes and the CMD_LED_STATE command 2
-bytes over the I2C bus, which operates at 100 kHz. With I2C overhead
-this allows ~1670 color changing commands and ~3200 state changing
-commands per second (or around 1000 color + state changes per second).
-This may seem more than enough, but the issue is that the I2C bus is
-shared with another peripheral, the MCU. The MCU exposes an interrupt
-interface, and it can trigger hundreds of interrupts per second. Each
-time, we need to read the interrupt state register over this I2C bus.
-Whenever we are sending a LED color/state changing command, the
-interrupt reading is waiting.
-
-Currently, every time LED brightness or LED multi intensity is changed,
-we send a CMD_LED_STATE command, and if the computed color (brightness
-adjusted multi_intensity) is non-zero, we also send a CMD_LED_COLOR
-command.
-
-Consider for example the situation when we have a netdev trigger enabled
-for a LED. The netdev trigger does not change the LED color, only the
-brightness (either to 0 or to currently configured brightness), and so
-there is no need to send the CMD_LED_COLOR command. But each change of
-brightness to 0 sends one CMD_LED_STATE command, and each change of
-brightness to max_brightness sends one CMD_LED_STATE command and one
-CMD_LED_COLOR command:
-    set_brightness(0)   ->  CMD_LED_STATE
-    set_brightness(255) ->  CMD_LED_STATE + CMD_LED_COLOR
-                                            (unnecessary)
-
-We can avoid the unnecessary I2C transactions if we cache the values of
-state and color that are sent to the controller. If the color does not
-change from the one previously sent, there is no need to do the
-CMD_LED_COLOR I2C transaction, and if the state does not change, there
-is no need to do the CMD_LED_STATE transaction.
-
-Because we need to make sure that our cached values are consistent with
-the controller state, add explicit setting of the LED color to white at
-probe time (this is the default setting when MCU resets, but does not
-necessarily need to be the case, for example if U-Boot played with the
-LED colors).
-
-Signed-off-by: Marek Behún <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Lee Jones <[email protected]>
----
- drivers/leds/leds-turris-omnia.c | 96 ++++++++++++++++++++++++++++++++--------
- 1 file changed, 78 insertions(+), 18 deletions(-)
-
---- a/drivers/leds/leds-turris-omnia.c
-+++ b/drivers/leds/leds-turris-omnia.c
-@@ -30,6 +30,8 @@
- struct omnia_led {
-       struct led_classdev_mc mc_cdev;
-       struct mc_subled subled_info[OMNIA_LED_NUM_CHANNELS];
-+      u8 cached_channels[OMNIA_LED_NUM_CHANNELS];
-+      bool on;
-       int reg;
- };
-@@ -72,36 +74,82 @@ static int omnia_cmd_read_u8(const struc
-               return -EIO;
- }
-+static int omnia_led_send_color_cmd(const struct i2c_client *client,
-+                                  struct omnia_led *led)
-+{
-+      char cmd[5];
-+      int ret;
-+
-+      cmd[0] = CMD_LED_COLOR;
-+      cmd[1] = led->reg;
-+      cmd[2] = led->subled_info[0].brightness;
-+      cmd[3] = led->subled_info[1].brightness;
-+      cmd[4] = led->subled_info[2].brightness;
-+
-+      /* Send the color change command */
-+      ret = i2c_master_send(client, cmd, 5);
-+      if (ret < 0)
-+              return ret;
-+
-+      /* Cache the RGB channel brightnesses */
-+      for (int i = 0; i < OMNIA_LED_NUM_CHANNELS; ++i)
-+              led->cached_channels[i] = led->subled_info[i].brightness;
-+
-+      return 0;
-+}
-+
-+/* Determine if the computed RGB channels are different from the cached ones */
-+static bool omnia_led_channels_changed(struct omnia_led *led)
-+{
-+      for (int i = 0; i < OMNIA_LED_NUM_CHANNELS; ++i)
-+              if (led->subled_info[i].brightness != led->cached_channels[i])
-+                      return true;
-+
-+      return false;
-+}
-+
- static int omnia_led_brightness_set_blocking(struct led_classdev *cdev,
-                                            enum led_brightness brightness)
- {
-       struct led_classdev_mc *mc_cdev = lcdev_to_mccdev(cdev);
-       struct omnia_leds *leds = dev_get_drvdata(cdev->dev->parent);
-       struct omnia_led *led = to_omnia_led(mc_cdev);
--      u8 buf[5], state;
--      int ret;
-+      int err = 0;
-       mutex_lock(&leds->lock);
--      led_mc_calc_color_components(&led->mc_cdev, brightness);
-+      /*
-+       * Only recalculate RGB brightnesses from intensities if brightness is
-+       * non-zero. Otherwise we won't be using them and we can save ourselves
-+       * some software divisions (Omnia's CPU does not implement the division
-+       * instruction).
-+       */
-+      if (brightness) {
-+              led_mc_calc_color_components(mc_cdev, brightness);
-+
-+              /*
-+               * Send color command only if brightness is non-zero and the RGB
-+               * channel brightnesses changed.
-+               */
-+              if (omnia_led_channels_changed(led))
-+                      err = omnia_led_send_color_cmd(leds->client, led);
-+      }
--      buf[0] = CMD_LED_COLOR;
--      buf[1] = led->reg;
--      buf[2] = mc_cdev->subled_info[0].brightness;
--      buf[3] = mc_cdev->subled_info[1].brightness;
--      buf[4] = mc_cdev->subled_info[2].brightness;
--
--      state = CMD_LED_STATE_LED(led->reg);
--      if (buf[2] || buf[3] || buf[4])
--              state |= CMD_LED_STATE_ON;
--
--      ret = omnia_cmd_write_u8(leds->client, CMD_LED_STATE, state);
--      if (ret >= 0 && (state & CMD_LED_STATE_ON))
--              ret = i2c_master_send(leds->client, buf, 5);
-+      /* Send on/off state change only if (bool)brightness changed */
-+      if (!err && !brightness != !led->on) {
-+              u8 state = CMD_LED_STATE_LED(led->reg);
-+
-+              if (brightness)
-+                      state |= CMD_LED_STATE_ON;
-+
-+              err = omnia_cmd_write_u8(leds->client, CMD_LED_STATE, state);
-+              if (!err)
-+                      led->on = !!brightness;
-+      }
-       mutex_unlock(&leds->lock);
--      return ret;
-+      return err;
- }
- static int omnia_led_register(struct i2c_client *client, struct omnia_led *led,
-@@ -129,11 +177,15 @@ static int omnia_led_register(struct i2c
-       }
-       led->subled_info[0].color_index = LED_COLOR_ID_RED;
--      led->subled_info[0].channel = 0;
-       led->subled_info[1].color_index = LED_COLOR_ID_GREEN;
--      led->subled_info[1].channel = 1;
-       led->subled_info[2].color_index = LED_COLOR_ID_BLUE;
--      led->subled_info[2].channel = 2;
-+
-+      /* Initial color is white */
-+      for (int i = 0; i < OMNIA_LED_NUM_CHANNELS; ++i) {
-+              led->subled_info[i].intensity = 255;
-+              led->subled_info[i].brightness = 255;
-+              led->subled_info[i].channel = i;
-+      }
-       led->mc_cdev.subled_info = led->subled_info;
-       led->mc_cdev.num_colors = OMNIA_LED_NUM_CHANNELS;
-@@ -162,6 +214,14 @@ static int omnia_led_register(struct i2c
-               return ret;
-       }
-+      /* Set initial color and cache it */
-+      ret = omnia_led_send_color_cmd(client, led);
-+      if (ret < 0) {
-+              dev_err(dev, "Cannot set LED %pOF initial color: %i\n", np,
-+                      ret);
-+              return ret;
-+      }
-+
-       ret = devm_led_classdev_multicolor_register_ext(dev, &led->mc_cdev,
-                                                       &init_data);
-       if (ret < 0) {
diff --git a/target/linux/generic/backport-5.15/830-v6.7-3-leds-turris-omnia-Support-HW-controlled-mode-via-pri.patch b/target/linux/generic/backport-5.15/830-v6.7-3-leds-turris-omnia-Support-HW-controlled-mode-via-pri.patch
deleted file mode 100644 (file)
index 7f6bac3..0000000
+++ /dev/null
@@ -1,201 +0,0 @@
-From aaf38273cf766d88296f4aa3f2e4e3c0d399a4a2 Mon Sep 17 00:00:00 2001
-From: Marek Behún <[email protected]>
-Date: Mon, 18 Sep 2023 18:11:03 +0200
-Subject: leds: turris-omnia: Support HW controlled mode via private trigger
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-Add support for enabling MCU controlled mode of the Turris Omnia LEDs
-via a LED private trigger called "omnia-mcu". Recall that private LED
-triggers will only be listed in the sysfs trigger file for LEDs that
-support them (currently there is no user of this mechanism).
-
-When in MCU controlled mode, the user can still set LED color, but the
-blinking is done by MCU, which does different things for different LEDs:
-- WAN LED is blinked according to the LED[0] pin of the WAN PHY
-- LAN LEDs are blinked according to the LED[0] output of the
-  corresponding port of the LAN switch
-- PCIe LEDs are blinked according to the logical OR of the MiniPCIe port
-  LED pins
-
-In the future I want to make the netdev trigger to transparently offload
-the blinking to the HW if user sets compatible settings for the netdev
-trigger (for LEDs associated with network devices).
-There was some work on this already, and hopefully we will be able to
-complete it sometime, but for now there are still multiple blockers for
-this, and even if there weren't, we still would not be able to configure
-HW controlled mode for the LEDs associated with MiniPCIe ports.
-
-In the meantime let's support HW controlled mode via the private LED
-trigger mechanism. If, in the future, we manage to complete the netdev
-trigger offloading, we can still keep this private trigger for backwards
-compatibility, if needed.
-
-We also set "omnia-mcu" to cdev->default_trigger, so that the MCU keeps
-control until the user first wants to take over it. If a different
-default trigger is specified in device-tree via the
-'linux,default-trigger' property, LED class will overwrite
-cdev->default_trigger, and so the DT property will be respected.
-
-Signed-off-by: Marek Behún <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Lee Jones <[email protected]>
----
- drivers/leds/Kconfig             |  1 +
- drivers/leds/leds-turris-omnia.c | 98 ++++++++++++++++++++++++++++++++++++----
- 2 files changed, 91 insertions(+), 8 deletions(-)
-
---- a/drivers/leds/Kconfig
-+++ b/drivers/leds/Kconfig
-@@ -164,6 +164,7 @@ config LEDS_TURRIS_OMNIA
-       depends on I2C
-       depends on MACH_ARMADA_38X || COMPILE_TEST
-       depends on OF
-+      select LEDS_TRIGGERS
-       help
-         This option enables basic support for the LEDs found on the front
-         side of CZ.NIC's Turris Omnia router. There are 12 RGB LEDs on the
---- a/drivers/leds/leds-turris-omnia.c
-+++ b/drivers/leds/leds-turris-omnia.c
-@@ -31,7 +31,7 @@ struct omnia_led {
-       struct led_classdev_mc mc_cdev;
-       struct mc_subled subled_info[OMNIA_LED_NUM_CHANNELS];
-       u8 cached_channels[OMNIA_LED_NUM_CHANNELS];
--      bool on;
-+      bool on, hwtrig;
-       int reg;
- };
-@@ -120,12 +120,14 @@ static int omnia_led_brightness_set_bloc
-       /*
-        * Only recalculate RGB brightnesses from intensities if brightness is
--       * non-zero. Otherwise we won't be using them and we can save ourselves
--       * some software divisions (Omnia's CPU does not implement the division
--       * instruction).
-+       * non-zero (if it is zero and the LED is in HW blinking mode, we use
-+       * max_brightness as brightness). Otherwise we won't be using them and
-+       * we can save ourselves some software divisions (Omnia's CPU does not
-+       * implement the division instruction).
-        */
--      if (brightness) {
--              led_mc_calc_color_components(mc_cdev, brightness);
-+      if (brightness || led->hwtrig) {
-+              led_mc_calc_color_components(mc_cdev, brightness ?:
-+                                                    cdev->max_brightness);
-               /*
-                * Send color command only if brightness is non-zero and the RGB
-@@ -135,8 +137,11 @@ static int omnia_led_brightness_set_bloc
-                       err = omnia_led_send_color_cmd(leds->client, led);
-       }
--      /* Send on/off state change only if (bool)brightness changed */
--      if (!err && !brightness != !led->on) {
-+      /*
-+       * Send on/off state change only if (bool)brightness changed and the LED
-+       * is not being blinked by HW.
-+       */
-+      if (!err && !led->hwtrig && !brightness != !led->on) {
-               u8 state = CMD_LED_STATE_LED(led->reg);
-               if (brightness)
-@@ -152,6 +157,71 @@ static int omnia_led_brightness_set_bloc
-       return err;
- }
-+static struct led_hw_trigger_type omnia_hw_trigger_type;
-+
-+static int omnia_hwtrig_activate(struct led_classdev *cdev)
-+{
-+      struct led_classdev_mc *mc_cdev = lcdev_to_mccdev(cdev);
-+      struct omnia_leds *leds = dev_get_drvdata(cdev->dev->parent);
-+      struct omnia_led *led = to_omnia_led(mc_cdev);
-+      int err = 0;
-+
-+      mutex_lock(&leds->lock);
-+
-+      if (!led->on) {
-+              /*
-+               * If the LED is off (brightness was set to 0), the last
-+               * configured color was not necessarily sent to the MCU.
-+               * Recompute with max_brightness and send if needed.
-+               */
-+              led_mc_calc_color_components(mc_cdev, cdev->max_brightness);
-+
-+              if (omnia_led_channels_changed(led))
-+                      err = omnia_led_send_color_cmd(leds->client, led);
-+      }
-+
-+      if (!err) {
-+              /* Put the LED into MCU controlled mode */
-+              err = omnia_cmd_write_u8(leds->client, CMD_LED_MODE,
-+                                       CMD_LED_MODE_LED(led->reg));
-+              if (!err)
-+                      led->hwtrig = true;
-+      }
-+
-+      mutex_unlock(&leds->lock);
-+
-+      return err;
-+}
-+
-+static void omnia_hwtrig_deactivate(struct led_classdev *cdev)
-+{
-+      struct omnia_leds *leds = dev_get_drvdata(cdev->dev->parent);
-+      struct omnia_led *led = to_omnia_led(lcdev_to_mccdev(cdev));
-+      int err;
-+
-+      mutex_lock(&leds->lock);
-+
-+      led->hwtrig = false;
-+
-+      /* Put the LED into software mode */
-+      err = omnia_cmd_write_u8(leds->client, CMD_LED_MODE,
-+                               CMD_LED_MODE_LED(led->reg) |
-+                               CMD_LED_MODE_USER);
-+
-+      mutex_unlock(&leds->lock);
-+
-+      if (err < 0)
-+              dev_err(cdev->dev, "Cannot put LED to software mode: %i\n",
-+                      err);
-+}
-+
-+static struct led_trigger omnia_hw_trigger = {
-+      .name           = "omnia-mcu",
-+      .activate       = omnia_hwtrig_activate,
-+      .deactivate     = omnia_hwtrig_deactivate,
-+      .trigger_type   = &omnia_hw_trigger_type,
-+};
-+
- static int omnia_led_register(struct i2c_client *client, struct omnia_led *led,
-                             struct device_node *np)
- {
-@@ -195,6 +265,12 @@ static int omnia_led_register(struct i2c
-       cdev = &led->mc_cdev.led_cdev;
-       cdev->max_brightness = 255;
-       cdev->brightness_set_blocking = omnia_led_brightness_set_blocking;
-+      cdev->trigger_type = &omnia_hw_trigger_type;
-+      /*
-+       * Use the omnia-mcu trigger as the default trigger. It may be rewritten
-+       * by LED class from the linux,default-trigger property.
-+       */
-+      cdev->default_trigger = omnia_hw_trigger.name;
-       /* put the LED into software mode */
-       ret = omnia_cmd_write_u8(client, CMD_LED_MODE,
-@@ -309,6 +385,12 @@ static int omnia_leds_probe(struct i2c_c
-       mutex_init(&leds->lock);
-+      ret = devm_led_trigger_register(dev, &omnia_hw_trigger);
-+      if (ret < 0) {
-+              dev_err(dev, "Cannot register private LED trigger: %d\n", ret);
-+              return ret;
-+      }
-+
-       led = &leds->leds[0];
-       for_each_available_child_of_node(np, child) {
-               ret = omnia_led_register(client, led, child);
diff --git a/target/linux/generic/backport-5.15/830-v6.7-4-leds-turris-omnia-Add-support-for-enabling-disabling.patch b/target/linux/generic/backport-5.15/830-v6.7-4-leds-turris-omnia-Add-support-for-enabling-disabling.patch
deleted file mode 100644 (file)
index 3bda4a9..0000000
+++ /dev/null
@@ -1,244 +0,0 @@
-From 00125699bb35ef58fffa8425e32a44a7af82cd28 Mon Sep 17 00:00:00 2001
-From: =?UTF-8?q?Marek=20Beh=C3=BAn?= <[email protected]>
-Date: Mon, 18 Sep 2023 18:11:04 +0200
-Subject: [PATCH 07/17] leds: turris-omnia: Add support for enabling/disabling
- HW gamma correction
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-If the MCU on Turris Omnia is running newer firmware versions, the LED
-controller supports RGB gamma correction (and enables it by default for
-newer boards).
-
-Determine whether the gamma correction setting feature is supported and
-add the ability to set it via sysfs attribute file.
-
-Signed-off-by: Marek Behún <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Lee Jones <[email protected]>
----
- .../sysfs-class-led-driver-turris-omnia       |  14 ++
- drivers/leds/leds-turris-omnia.c              | 137 +++++++++++++++---
- 2 files changed, 134 insertions(+), 17 deletions(-)
-
---- a/Documentation/ABI/testing/sysfs-class-led-driver-turris-omnia
-+++ b/Documentation/ABI/testing/sysfs-class-led-driver-turris-omnia
-@@ -12,3 +12,17 @@ Description:        (RW) On the front panel of
-               able to change this setting from software.
-               Format: %i
-+
-+What:         /sys/class/leds/<led>/device/gamma_correction
-+Date:         August 2023
-+KernelVersion:        6.6
-+Contact:      Marek Behún <[email protected]>
-+Description:  (RW) Newer versions of the microcontroller firmware of the
-+              Turris Omnia router support gamma correction for the RGB LEDs.
-+              This feature can be enabled/disabled by writing to this file.
-+
-+              If the feature is not supported because the MCU firmware is too
-+              old, the file always reads as 0, and writing to the file results
-+              in the EOPNOTSUPP error.
-+
-+              Format: %i
---- a/drivers/leds/leds-turris-omnia.c
-+++ b/drivers/leds/leds-turris-omnia.c
-@@ -15,17 +15,30 @@
- #define OMNIA_BOARD_LEDS      12
- #define OMNIA_LED_NUM_CHANNELS        3
--#define CMD_LED_MODE          3
--#define CMD_LED_MODE_LED(l)   ((l) & 0x0f)
--#define CMD_LED_MODE_USER     0x10
--
--#define CMD_LED_STATE         4
--#define CMD_LED_STATE_LED(l)  ((l) & 0x0f)
--#define CMD_LED_STATE_ON      0x10
--
--#define CMD_LED_COLOR         5
--#define CMD_LED_SET_BRIGHTNESS        7
--#define CMD_LED_GET_BRIGHTNESS        8
-+/* MCU controller commands at I2C address 0x2a */
-+#define OMNIA_MCU_I2C_ADDR            0x2a
-+
-+#define CMD_GET_STATUS_WORD           0x01
-+#define STS_FEATURES_SUPPORTED                BIT(2)
-+
-+#define CMD_GET_FEATURES              0x10
-+#define FEAT_LED_GAMMA_CORRECTION     BIT(5)
-+
-+/* LED controller commands at I2C address 0x2b */
-+#define CMD_LED_MODE                  0x03
-+#define CMD_LED_MODE_LED(l)           ((l) & 0x0f)
-+#define CMD_LED_MODE_USER             0x10
-+
-+#define CMD_LED_STATE                 0x04
-+#define CMD_LED_STATE_LED(l)          ((l) & 0x0f)
-+#define CMD_LED_STATE_ON              0x10
-+
-+#define CMD_LED_COLOR                 0x05
-+#define CMD_LED_SET_BRIGHTNESS                0x07
-+#define CMD_LED_GET_BRIGHTNESS                0x08
-+
-+#define CMD_SET_GAMMA_CORRECTION      0x30
-+#define CMD_GET_GAMMA_CORRECTION      0x31
- struct omnia_led {
-       struct led_classdev_mc mc_cdev;
-@@ -40,6 +53,7 @@ struct omnia_led {
- struct omnia_leds {
-       struct i2c_client *client;
-       struct mutex lock;
-+      bool has_gamma_correction;
-       struct omnia_led leds[];
- };
-@@ -50,30 +64,42 @@ static int omnia_cmd_write_u8(const stru
-       return i2c_master_send(client, buf, sizeof(buf));
- }
--static int omnia_cmd_read_u8(const struct i2c_client *client, u8 cmd)
-+static int omnia_cmd_read_raw(struct i2c_adapter *adapter, u8 addr, u8 cmd,
-+                            void *reply, size_t len)
- {
-       struct i2c_msg msgs[2];
--      u8 reply;
-       int ret;
--      msgs[0].addr = client->addr;
-+      msgs[0].addr = addr;
-       msgs[0].flags = 0;
-       msgs[0].len = 1;
-       msgs[0].buf = &cmd;
--      msgs[1].addr = client->addr;
-+      msgs[1].addr = addr;
-       msgs[1].flags = I2C_M_RD;
--      msgs[1].len = 1;
--      msgs[1].buf = &reply;
-+      msgs[1].len = len;
-+      msgs[1].buf = reply;
--      ret = i2c_transfer(client->adapter, msgs, ARRAY_SIZE(msgs));
-+      ret = i2c_transfer(adapter, msgs, ARRAY_SIZE(msgs));
-       if (likely(ret == ARRAY_SIZE(msgs)))
--              return reply;
-+              return len;
-       else if (ret < 0)
-               return ret;
-       else
-               return -EIO;
- }
-+static int omnia_cmd_read_u8(const struct i2c_client *client, u8 cmd)
-+{
-+      u8 reply;
-+      int ret;
-+
-+      ret = omnia_cmd_read_raw(client->adapter, client->addr, cmd, &reply, 1);
-+      if (ret < 0)
-+              return ret;
-+
-+      return reply;
-+}
-+
- static int omnia_led_send_color_cmd(const struct i2c_client *client,
-                                   struct omnia_led *led)
- {
-@@ -352,12 +378,74 @@ static ssize_t brightness_store(struct d
- }
- static DEVICE_ATTR_RW(brightness);
-+static ssize_t gamma_correction_show(struct device *dev,
-+                                   struct device_attribute *a, char *buf)
-+{
-+      struct i2c_client *client = to_i2c_client(dev);
-+      struct omnia_leds *leds = i2c_get_clientdata(client);
-+      int ret;
-+
-+      if (leds->has_gamma_correction) {
-+              ret = omnia_cmd_read_u8(client, CMD_GET_GAMMA_CORRECTION);
-+              if (ret < 0)
-+                      return ret;
-+      } else {
-+              ret = 0;
-+      }
-+
-+      return sysfs_emit(buf, "%d\n", !!ret);
-+}
-+
-+static ssize_t gamma_correction_store(struct device *dev,
-+                                    struct device_attribute *a,
-+                                    const char *buf, size_t count)
-+{
-+      struct i2c_client *client = to_i2c_client(dev);
-+      struct omnia_leds *leds = i2c_get_clientdata(client);
-+      bool val;
-+      int ret;
-+
-+      if (!leds->has_gamma_correction)
-+              return -EOPNOTSUPP;
-+
-+      if (kstrtobool(buf, &val) < 0)
-+              return -EINVAL;
-+
-+      ret = omnia_cmd_write_u8(client, CMD_SET_GAMMA_CORRECTION, val);
-+
-+      return ret < 0 ? ret : count;
-+}
-+static DEVICE_ATTR_RW(gamma_correction);
-+
- static struct attribute *omnia_led_controller_attrs[] = {
-       &dev_attr_brightness.attr,
-+      &dev_attr_gamma_correction.attr,
-       NULL,
- };
- ATTRIBUTE_GROUPS(omnia_led_controller);
-+static int omnia_mcu_get_features(const struct i2c_client *client)
-+{
-+      u16 reply;
-+      int err;
-+
-+      err = omnia_cmd_read_raw(client->adapter, OMNIA_MCU_I2C_ADDR,
-+                               CMD_GET_STATUS_WORD, &reply, sizeof(reply));
-+      if (err < 0)
-+              return err;
-+
-+      /* Check whether MCU firmware supports the CMD_GET_FEAUTRES command */
-+      if (!(le16_to_cpu(reply) & STS_FEATURES_SUPPORTED))
-+              return 0;
-+
-+      err = omnia_cmd_read_raw(client->adapter, OMNIA_MCU_I2C_ADDR,
-+                               CMD_GET_FEATURES, &reply, sizeof(reply));
-+      if (err < 0)
-+              return err;
-+
-+      return le16_to_cpu(reply);
-+}
-+
- static int omnia_leds_probe(struct i2c_client *client,
-                           const struct i2c_device_id *id)
- {
-@@ -383,6 +471,21 @@ static int omnia_leds_probe(struct i2c_c
-       leds->client = client;
-       i2c_set_clientdata(client, leds);
-+      ret = omnia_mcu_get_features(client);
-+      if (ret < 0) {
-+              dev_err(dev, "Cannot determine MCU supported features: %d\n",
-+                      ret);
-+              return ret;
-+      }
-+
-+      leds->has_gamma_correction = ret & FEAT_LED_GAMMA_CORRECTION;
-+      if (!leds->has_gamma_correction) {
-+              dev_info(dev,
-+                       "Your board's MCU firmware does not support the LED gamma correction feature.\n");
-+              dev_info(dev,
-+                       "Consider upgrading MCU firmware with the omnia-mcutool utility.\n");
-+      }
-+
-       mutex_init(&leds->lock);
-       ret = devm_led_trigger_register(dev, &omnia_hw_trigger);
diff --git a/target/linux/generic/backport-5.15/830-v6.7-5-leds-turris-omnia-Fix-brightness-setting-and-trigger.patch b/target/linux/generic/backport-5.15/830-v6.7-5-leds-turris-omnia-Fix-brightness-setting-and-trigger.patch
deleted file mode 100644 (file)
index ec6171e..0000000
+++ /dev/null
@@ -1,167 +0,0 @@
-From 33f339b70f020273ea40fb3c5d7b65697446bd6c Mon Sep 17 00:00:00 2001
-From: =?UTF-8?q?Marek=20Beh=C3=BAn?= <[email protected]>
-Date: Mon, 16 Oct 2023 15:28:06 +0200
-Subject: [PATCH 08/17] leds: turris-omnia: Fix brightness setting and trigger
- activating
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-I have improperly refactored commits
-  4d5ed2621c24 ("leds: turris-omnia: Make set_brightness() more efficient")
-and
-  aaf38273cf76 ("leds: turris-omnia: Support HW controlled mode via private trigger")
-after Lee requested a change in API semantics of the new functions I
-introduced in commit
-  28350bc0ac77 ("leds: turris-omnia: Do not use SMBUS calls").
-
-Before the change, the function omnia_cmd_write_u8() returned 0 on
-success, and afterwards it returned a positive value (number of bytes
-written). The latter version was applied, but the following commits did
-not properly account for this change.
-
-This results in non-functional LED's .brightness_set_blocking() and
-trigger's .activate() methods.
-
-The main reasoning behind the semantics change was that read/write
-methods should return the number of read/written bytes on success.
-It was pointed to me [1] that this is not always true (for example the
-regmap API does not do so), and since the driver never uses this number
-of read/written bytes information, I decided to fix this issue by
-changing the functions to the original semantics (return 0 on success).
-
-[1] https://lore.kernel.org/linux-gpio/[email protected]/
-
-Fixes: 28350bc0ac77 ("leds: turris-omnia: Do not use SMBUS calls")
-Signed-off-by: Marek Behún <[email protected]>
----
- drivers/leds/leds-turris-omnia.c | 37 +++++++++++++++++---------------
- 1 file changed, 20 insertions(+), 17 deletions(-)
-
---- a/drivers/leds/leds-turris-omnia.c
-+++ b/drivers/leds/leds-turris-omnia.c
-@@ -60,8 +60,11 @@ struct omnia_leds {
- static int omnia_cmd_write_u8(const struct i2c_client *client, u8 cmd, u8 val)
- {
-       u8 buf[2] = { cmd, val };
-+      int ret;
-+
-+      ret = i2c_master_send(client, buf, sizeof(buf));
--      return i2c_master_send(client, buf, sizeof(buf));
-+      return ret < 0 ? ret : 0;
- }
- static int omnia_cmd_read_raw(struct i2c_adapter *adapter, u8 addr, u8 cmd,
-@@ -81,7 +84,7 @@ static int omnia_cmd_read_raw(struct i2c
-       ret = i2c_transfer(adapter, msgs, ARRAY_SIZE(msgs));
-       if (likely(ret == ARRAY_SIZE(msgs)))
--              return len;
-+              return 0;
-       else if (ret < 0)
-               return ret;
-       else
-@@ -91,11 +94,11 @@ static int omnia_cmd_read_raw(struct i2c
- static int omnia_cmd_read_u8(const struct i2c_client *client, u8 cmd)
- {
-       u8 reply;
--      int ret;
-+      int err;
--      ret = omnia_cmd_read_raw(client->adapter, client->addr, cmd, &reply, 1);
--      if (ret < 0)
--              return ret;
-+      err = omnia_cmd_read_raw(client->adapter, client->addr, cmd, &reply, 1);
-+      if (err)
-+              return err;
-       return reply;
- }
-@@ -236,7 +239,7 @@ static void omnia_hwtrig_deactivate(stru
-       mutex_unlock(&leds->lock);
--      if (err < 0)
-+      if (err)
-               dev_err(cdev->dev, "Cannot put LED to software mode: %i\n",
-                       err);
- }
-@@ -302,7 +305,7 @@ static int omnia_led_register(struct i2c
-       ret = omnia_cmd_write_u8(client, CMD_LED_MODE,
-                                CMD_LED_MODE_LED(led->reg) |
-                                CMD_LED_MODE_USER);
--      if (ret < 0) {
-+      if (ret) {
-               dev_err(dev, "Cannot set LED %pOF to software mode: %i\n", np,
-                       ret);
-               return ret;
-@@ -311,7 +314,7 @@ static int omnia_led_register(struct i2c
-       /* disable the LED */
-       ret = omnia_cmd_write_u8(client, CMD_LED_STATE,
-                                CMD_LED_STATE_LED(led->reg));
--      if (ret < 0) {
-+      if (ret) {
-               dev_err(dev, "Cannot set LED %pOF brightness: %i\n", np, ret);
-               return ret;
-       }
-@@ -364,7 +367,7 @@ static ssize_t brightness_store(struct d
- {
-       struct i2c_client *client = to_i2c_client(dev);
-       unsigned long brightness;
--      int ret;
-+      int err;
-       if (kstrtoul(buf, 10, &brightness))
-               return -EINVAL;
-@@ -372,9 +375,9 @@ static ssize_t brightness_store(struct d
-       if (brightness > 100)
-               return -EINVAL;
--      ret = omnia_cmd_write_u8(client, CMD_LED_SET_BRIGHTNESS, brightness);
-+      err = omnia_cmd_write_u8(client, CMD_LED_SET_BRIGHTNESS, brightness);
--      return ret < 0 ? ret : count;
-+      return err ?: count;
- }
- static DEVICE_ATTR_RW(brightness);
-@@ -403,7 +406,7 @@ static ssize_t gamma_correction_store(st
-       struct i2c_client *client = to_i2c_client(dev);
-       struct omnia_leds *leds = i2c_get_clientdata(client);
-       bool val;
--      int ret;
-+      int err;
-       if (!leds->has_gamma_correction)
-               return -EOPNOTSUPP;
-@@ -411,9 +414,9 @@ static ssize_t gamma_correction_store(st
-       if (kstrtobool(buf, &val) < 0)
-               return -EINVAL;
--      ret = omnia_cmd_write_u8(client, CMD_SET_GAMMA_CORRECTION, val);
-+      err = omnia_cmd_write_u8(client, CMD_SET_GAMMA_CORRECTION, val);
--      return ret < 0 ? ret : count;
-+      return err ?: count;
- }
- static DEVICE_ATTR_RW(gamma_correction);
-@@ -431,7 +434,7 @@ static int omnia_mcu_get_features(const
-       err = omnia_cmd_read_raw(client->adapter, OMNIA_MCU_I2C_ADDR,
-                                CMD_GET_STATUS_WORD, &reply, sizeof(reply));
--      if (err < 0)
-+      if (err)
-               return err;
-       /* Check whether MCU firmware supports the CMD_GET_FEAUTRES command */
-@@ -440,7 +443,7 @@ static int omnia_mcu_get_features(const
-       err = omnia_cmd_read_raw(client->adapter, OMNIA_MCU_I2C_ADDR,
-                                CMD_GET_FEATURES, &reply, sizeof(reply));
--      if (err < 0)
-+      if (err)
-               return err;
-       return le16_to_cpu(reply);
diff --git a/target/linux/generic/backport-5.15/831-v6.1-dt-bindings-leds-Expand-LED_COLOR_ID-definitions.patch b/target/linux/generic/backport-5.15/831-v6.1-dt-bindings-leds-Expand-LED_COLOR_ID-definitions.patch
deleted file mode 100644 (file)
index c2a938c..0000000
+++ /dev/null
@@ -1,47 +0,0 @@
-From 472d7b9e8141729ec1e3fe6821b88563f6379533 Mon Sep 17 00:00:00 2001
-From: Olliver Schinagl <[email protected]>
-Date: Tue, 30 Aug 2022 15:46:13 +0200
-Subject: [PATCH] dt-bindings: leds: Expand LED_COLOR_ID definitions
-
-In commit 853a78a7d6c7 (dt-bindings: leds: Add LED_COLOR_ID definitions,
-Sun Jun 9 20:19:04 2019 +0200) the most basic color definitions where
-added. However, there's a little more very common LED colors.
-
-While the documentation states 'add what is missing', engineers tend to
-be lazy and will just use what currently exists. So this patch will take
-(a) list from online retailers [0], [1], [2] and use the common LED colors from
-there, this being reasonable as this is what is currently available to purchase.
-
-Note, that LIME seems to be the modern take to 'Yellow-green' or
-'Yellowish-green' from some older datasheets.
-
-[0]: https://www.digikey.com/en/products/filter/led-lighting-color/125
-[1]: https://eu.mouser.com/c/optoelectronics/led-lighting/led-emitters/standard-leds-smd
-[2]: https://nl.farnell.com/en-NL/c/optoelectronics-displays/led-products/standard-single-colour-leds-under-75ma
-
-Signed-off-by: Olliver Schinagl <[email protected]>
-Acked-by: Krzysztof Kozlowski <[email protected]>
-Acked-by: Alexander Dahl <[email protected]>
-Acked-by: Jacek Anaszewski <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Rob Herring <[email protected]>
----
- include/dt-bindings/leds/common.h | 7 ++++++-
- 1 file changed, 6 insertions(+), 1 deletion(-)
-
---- a/include/dt-bindings/leds/common.h
-+++ b/include/dt-bindings/leds/common.h
-@@ -33,7 +33,12 @@
- #define LED_COLOR_ID_MULTI    8       /* For multicolor LEDs */
- #define LED_COLOR_ID_RGB      9       /* For multicolor LEDs that can do arbitrary color,
-                                          so this would include RGBW and similar */
--#define LED_COLOR_ID_MAX      10
-+#define LED_COLOR_ID_PURPLE   10
-+#define LED_COLOR_ID_ORANGE   11
-+#define LED_COLOR_ID_PINK     12
-+#define LED_COLOR_ID_CYAN     13
-+#define LED_COLOR_ID_LIME     14
-+#define LED_COLOR_ID_MAX      15
- /* Standard LED functions */
- /* Keyboard LEDs, usually it would be input4::capslock etc. */
diff --git a/target/linux/generic/backport-5.15/832-v6.8-of-device-Export-of_device_make_bus_id.patch b/target/linux/generic/backport-5.15/832-v6.8-of-device-Export-of_device_make_bus_id.patch
deleted file mode 100644 (file)
index d097c1b..0000000
+++ /dev/null
@@ -1,128 +0,0 @@
-From 7f38b70042fcaa49219045bd1a9a2836e27a58ac Mon Sep 17 00:00:00 2001
-From: Miquel Raynal <[email protected]>
-Date: Fri, 15 Dec 2023 11:15:27 +0000
-Subject: [PATCH] of: device: Export of_device_make_bus_id()
-
-This helper is really handy to create unique device names based on their
-device tree path, we may need it outside of the OF core (in the NVMEM
-subsystem) so let's export it. As this helper has nothing patform
-specific, let's move it to of/device.c instead of of/platform.c so we
-can add its prototype to of_device.h.
-
-Signed-off-by: Miquel Raynal <[email protected]>
-Acked-by: Rob Herring <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/of/device.c       | 41 +++++++++++++++++++++++++++++++++++++++
- drivers/of/platform.c     | 40 --------------------------------------
- include/linux/of_device.h |  6 ++++++
- 3 files changed, 47 insertions(+), 40 deletions(-)
-
---- a/drivers/of/device.c
-+++ b/drivers/of/device.c
-@@ -337,3 +337,38 @@ int of_device_uevent_modalias(struct dev
-       return 0;
- }
- EXPORT_SYMBOL_GPL(of_device_uevent_modalias);
-+
-+/**
-+ * of_device_make_bus_id - Use the device node data to assign a unique name
-+ * @dev: pointer to device structure that is linked to a device tree node
-+ *
-+ * This routine will first try using the translated bus address to
-+ * derive a unique name. If it cannot, then it will prepend names from
-+ * parent nodes until a unique name can be derived.
-+ */
-+void of_device_make_bus_id(struct device *dev)
-+{
-+      struct device_node *node = dev->of_node;
-+      const __be32 *reg;
-+      u64 addr;
-+
-+      /* Construct the name, using parent nodes if necessary to ensure uniqueness */
-+      while (node->parent) {
-+              /*
-+               * If the address can be translated, then that is as much
-+               * uniqueness as we need. Make it the first component and return
-+               */
-+              reg = of_get_property(node, "reg", NULL);
-+              if (reg && (addr = of_translate_address(node, reg)) != OF_BAD_ADDR) {
-+                      dev_set_name(dev, dev_name(dev) ? "%llx.%pOFn:%s" : "%llx.%pOFn",
-+                                   addr, node, dev_name(dev));
-+                      return;
-+              }
-+
-+              /* format arguments only used if dev_name() resolves to NULL */
-+              dev_set_name(dev, dev_name(dev) ? "%s:%s" : "%s",
-+                           kbasename(node->full_name), dev_name(dev));
-+              node = node->parent;
-+      }
-+}
-+EXPORT_SYMBOL_GPL(of_device_make_bus_id);
---- a/drivers/of/platform.c
-+++ b/drivers/of/platform.c
-@@ -64,40 +64,6 @@ EXPORT_SYMBOL(of_find_device_by_node);
-  */
- /**
-- * of_device_make_bus_id - Use the device node data to assign a unique name
-- * @dev: pointer to device structure that is linked to a device tree node
-- *
-- * This routine will first try using the translated bus address to
-- * derive a unique name. If it cannot, then it will prepend names from
-- * parent nodes until a unique name can be derived.
-- */
--static void of_device_make_bus_id(struct device *dev)
--{
--      struct device_node *node = dev->of_node;
--      const __be32 *reg;
--      u64 addr;
--
--      /* Construct the name, using parent nodes if necessary to ensure uniqueness */
--      while (node->parent) {
--              /*
--               * If the address can be translated, then that is as much
--               * uniqueness as we need. Make it the first component and return
--               */
--              reg = of_get_property(node, "reg", NULL);
--              if (reg && (addr = of_translate_address(node, reg)) != OF_BAD_ADDR) {
--                      dev_set_name(dev, dev_name(dev) ? "%llx.%pOFn:%s" : "%llx.%pOFn",
--                                   addr, node, dev_name(dev));
--                      return;
--              }
--
--              /* format arguments only used if dev_name() resolves to NULL */
--              dev_set_name(dev, dev_name(dev) ? "%s:%s" : "%s",
--                           kbasename(node->full_name), dev_name(dev));
--              node = node->parent;
--      }
--}
--
--/**
-  * of_device_alloc - Allocate and initialize an of_device
-  * @np: device node to assign to device
-  * @bus_id: Name to assign to the device.  May be null to use default name.
---- a/include/linux/of_device.h
-+++ b/include/linux/of_device.h
-@@ -56,6 +56,9 @@ static inline int of_dma_configure(struc
- {
-       return of_dma_configure_id(dev, np, force_dma, NULL);
- }
-+
-+void of_device_make_bus_id(struct device *dev);
-+
- #else /* CONFIG_OF */
- static inline int of_driver_match_device(struct device *dev,
-@@ -113,6 +116,9 @@ static inline int of_dma_configure(struc
- {
-       return 0;
- }
-+
-+static inline void of_device_make_bus_id(struct device *dev) {}
-+
- #endif /* CONFIG_OF */
- #endif /* _LINUX_OF_DEVICE_H */
diff --git a/target/linux/generic/backport-5.15/833-v6.8-leds-core-Add-more-colors-from-DT-bindings-to-led_co.patch.patch b/target/linux/generic/backport-5.15/833-v6.8-leds-core-Add-more-colors-from-DT-bindings-to-led_co.patch.patch
deleted file mode 100644 (file)
index b71df6f..0000000
+++ /dev/null
@@ -1,29 +0,0 @@
-From a067943129b4ec6b835e02cfd5fbef01093c1471 Mon Sep 17 00:00:00 2001
-From: Ondrej Jirman <[email protected]>
-Date: Sun, 8 Oct 2023 16:40:13 +0200
-Subject: [PATCH] leds: core: Add more colors from DT bindings to led_colors
-
-The colors are already part of DT bindings. Make sure the kernel is
-able to convert them to strings.
-
-Signed-off-by: Ondrej Jirman <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Lee Jones <[email protected]>
----
- drivers/leds/led-core.c | 5 +++++
- 1 file changed, 5 insertions(+)
-
---- a/drivers/leds/led-core.c
-+++ b/drivers/leds/led-core.c
-@@ -36,6 +36,11 @@ const char * const led_colors[LED_COLOR_
-       [LED_COLOR_ID_IR] = "ir",
-       [LED_COLOR_ID_MULTI] = "multicolor",
-       [LED_COLOR_ID_RGB] = "rgb",
-+      [LED_COLOR_ID_PURPLE] = "purple",
-+      [LED_COLOR_ID_ORANGE] = "orange",
-+      [LED_COLOR_ID_PINK] = "pink",
-+      [LED_COLOR_ID_CYAN] = "cyan",
-+      [LED_COLOR_ID_LIME] = "lime",
- };
- EXPORT_SYMBOL_GPL(led_colors);
diff --git a/target/linux/generic/backport-5.15/834-v6.8-0001-nvmem-Move-of_nvmem_layout_get_container-in-another-.patch b/target/linux/generic/backport-5.15/834-v6.8-0001-nvmem-Move-of_nvmem_layout_get_container-in-another-.patch
deleted file mode 100644 (file)
index 2093fac..0000000
+++ /dev/null
@@ -1,95 +0,0 @@
-From 4a1a40233b4a9fc159a5c7a27dc34c5c7bc5be55 Mon Sep 17 00:00:00 2001
-From: Miquel Raynal <[email protected]>
-Date: Fri, 15 Dec 2023 11:15:28 +0000
-Subject: [PATCH] nvmem: Move of_nvmem_layout_get_container() in another header
-
-nvmem-consumer.h is included by consumer devices, extracting data from
-NVMEM devices whereas nvmem-provider.h is included by devices providing
-NVMEM content.
-
-The only users of of_nvmem_layout_get_container() outside of the core
-are layout drivers, so better move its prototype to nvmem-provider.h.
-
-While we do so, we also move the kdoc associated with the function to
-the header rather than the .c file.
-
-Signed-off-by: Miquel Raynal <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/core.c           |  8 --------
- include/linux/nvmem-consumer.h |  7 -------
- include/linux/nvmem-provider.h | 21 +++++++++++++++++++++
- 3 files changed, 21 insertions(+), 15 deletions(-)
-
---- a/drivers/nvmem/core.c
-+++ b/drivers/nvmem/core.c
-@@ -848,14 +848,6 @@ static int nvmem_add_cells_from_layout(s
- }
- #if IS_ENABLED(CONFIG_OF)
--/**
-- * of_nvmem_layout_get_container() - Get OF node to layout container.
-- *
-- * @nvmem: nvmem device.
-- *
-- * Return: a node pointer with refcount incremented or NULL if no
-- * container exists. Use of_node_put() on it when done.
-- */
- struct device_node *of_nvmem_layout_get_container(struct nvmem_device *nvmem)
- {
-       return of_get_child_by_name(nvmem->dev.of_node, "nvmem-layout");
---- a/include/linux/nvmem-consumer.h
-+++ b/include/linux/nvmem-consumer.h
-@@ -241,7 +241,6 @@ struct nvmem_cell *of_nvmem_cell_get(str
-                                    const char *id);
- struct nvmem_device *of_nvmem_device_get(struct device_node *np,
-                                        const char *name);
--struct device_node *of_nvmem_layout_get_container(struct nvmem_device *nvmem);
- #else
- static inline struct nvmem_cell *of_nvmem_cell_get(struct device_node *np,
-                                                  const char *id)
-@@ -254,12 +253,6 @@ static inline struct nvmem_device *of_nv
- {
-       return ERR_PTR(-EOPNOTSUPP);
- }
--
--static inline struct device_node *
--of_nvmem_layout_get_container(struct nvmem_device *nvmem)
--{
--      return NULL;
--}
- #endif /* CONFIG_NVMEM && CONFIG_OF */
- #endif  /* ifndef _LINUX_NVMEM_CONSUMER_H */
---- a/include/linux/nvmem-provider.h
-+++ b/include/linux/nvmem-provider.h
-@@ -244,6 +244,27 @@ nvmem_layout_get_match_data(struct nvmem
- #endif /* CONFIG_NVMEM */
-+#if IS_ENABLED(CONFIG_NVMEM) && IS_ENABLED(CONFIG_OF)
-+
-+/**
-+ * of_nvmem_layout_get_container() - Get OF node of layout container
-+ *
-+ * @nvmem: nvmem device
-+ *
-+ * Return: a node pointer with refcount incremented or NULL if no
-+ * container exists. Use of_node_put() on it when done.
-+ */
-+struct device_node *of_nvmem_layout_get_container(struct nvmem_device *nvmem);
-+
-+#else  /* CONFIG_NVMEM && CONFIG_OF */
-+
-+static inline struct device_node *of_nvmem_layout_get_container(struct nvmem_device *nvmem)
-+{
-+      return NULL;
-+}
-+
-+#endif /* CONFIG_NVMEM && CONFIG_OF */
-+
- #define module_nvmem_layout_driver(__layout_driver)           \
-       module_driver(__layout_driver, nvmem_layout_register,   \
-                     nvmem_layout_unregister)
diff --git a/target/linux/generic/backport-5.15/834-v6.8-0002-nvmem-Create-a-header-for-internal-sharing.patch b/target/linux/generic/backport-5.15/834-v6.8-0002-nvmem-Create-a-header-for-internal-sharing.patch
deleted file mode 100644 (file)
index e722109..0000000
+++ /dev/null
@@ -1,91 +0,0 @@
-From ec9c08a1cb8dc5e8e003f95f5f62de41dde235bb Mon Sep 17 00:00:00 2001
-From: Miquel Raynal <[email protected]>
-Date: Fri, 15 Dec 2023 11:15:29 +0000
-Subject: [PATCH] nvmem: Create a header for internal sharing
-
-Before adding all the NVMEM layout bus infrastructure to the core, let's
-move the main nvmem_device structure in an internal header, only
-available to the core. This way all the additional code can be added in
-a dedicated file in order to keep the current core file tidy.
-
-Signed-off-by: Miquel Raynal <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/core.c      | 24 +-----------------------
- drivers/nvmem/internals.h | 35 +++++++++++++++++++++++++++++++++++
- 2 files changed, 36 insertions(+), 23 deletions(-)
- create mode 100644 drivers/nvmem/internals.h
-
---- a/drivers/nvmem/core.c
-+++ b/drivers/nvmem/core.c
-@@ -20,29 +20,7 @@
- #include <linux/of_device.h>
- #include <linux/slab.h>
--struct nvmem_device {
--      struct module           *owner;
--      struct device           dev;
--      int                     stride;
--      int                     word_size;
--      int                     id;
--      struct kref             refcnt;
--      size_t                  size;
--      bool                    read_only;
--      bool                    root_only;
--      int                     flags;
--      enum nvmem_type         type;
--      struct bin_attribute    eeprom;
--      struct device           *base_dev;
--      struct list_head        cells;
--      const struct nvmem_keepout *keepout;
--      unsigned int            nkeepout;
--      nvmem_reg_read_t        reg_read;
--      nvmem_reg_write_t       reg_write;
--      struct gpio_desc        *wp_gpio;
--      struct nvmem_layout     *layout;
--      void *priv;
--};
-+#include "internals.h"
- #define to_nvmem_device(d) container_of(d, struct nvmem_device, dev)
---- /dev/null
-+++ b/drivers/nvmem/internals.h
-@@ -0,0 +1,35 @@
-+/* SPDX-License-Identifier: GPL-2.0 */
-+
-+#ifndef _LINUX_NVMEM_INTERNALS_H
-+#define _LINUX_NVMEM_INTERNALS_H
-+
-+#include <linux/device.h>
-+#include <linux/nvmem-consumer.h>
-+#include <linux/nvmem-provider.h>
-+
-+struct nvmem_device {
-+      struct module           *owner;
-+      struct device           dev;
-+      struct list_head        node;
-+      int                     stride;
-+      int                     word_size;
-+      int                     id;
-+      struct kref             refcnt;
-+      size_t                  size;
-+      bool                    read_only;
-+      bool                    root_only;
-+      int                     flags;
-+      enum nvmem_type         type;
-+      struct bin_attribute    eeprom;
-+      struct device           *base_dev;
-+      struct list_head        cells;
-+      const struct nvmem_keepout *keepout;
-+      unsigned int            nkeepout;
-+      nvmem_reg_read_t        reg_read;
-+      nvmem_reg_write_t       reg_write;
-+      struct gpio_desc        *wp_gpio;
-+      struct nvmem_layout     *layout;
-+      void *priv;
-+};
-+
-+#endif  /* ifndef _LINUX_NVMEM_INTERNALS_H */
diff --git a/target/linux/generic/backport-5.15/834-v6.8-0003-nvmem-Simplify-the-add_cells-hook.patch b/target/linux/generic/backport-5.15/834-v6.8-0003-nvmem-Simplify-the-add_cells-hook.patch
deleted file mode 100644 (file)
index db2d8c1..0000000
+++ /dev/null
@@ -1,79 +0,0 @@
-From 1b7c298a4ecbc28cc6ee94005734bff55eb83d22 Mon Sep 17 00:00:00 2001
-From: Miquel Raynal <[email protected]>
-Date: Fri, 15 Dec 2023 11:15:30 +0000
-Subject: [PATCH] nvmem: Simplify the ->add_cells() hook
-
-The layout entry is not used and will anyway be made useless by the new
-layout bus infrastructure coming next, so drop it. While at it, clarify
-the kdoc entry.
-
-Signed-off-by: Miquel Raynal <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/core.c             | 2 +-
- drivers/nvmem/layouts/onie-tlv.c | 3 +--
- drivers/nvmem/layouts/sl28vpd.c  | 3 +--
- include/linux/nvmem-provider.h   | 8 +++-----
- 4 files changed, 6 insertions(+), 10 deletions(-)
-
---- a/drivers/nvmem/core.c
-+++ b/drivers/nvmem/core.c
-@@ -817,7 +817,7 @@ static int nvmem_add_cells_from_layout(s
-       int ret;
-       if (layout && layout->add_cells) {
--              ret = layout->add_cells(&nvmem->dev, nvmem, layout);
-+              ret = layout->add_cells(&nvmem->dev, nvmem);
-               if (ret)
-                       return ret;
-       }
---- a/drivers/nvmem/layouts/onie-tlv.c
-+++ b/drivers/nvmem/layouts/onie-tlv.c
-@@ -182,8 +182,7 @@ static bool onie_tlv_crc_is_valid(struct
-       return true;
- }
--static int onie_tlv_parse_table(struct device *dev, struct nvmem_device *nvmem,
--                              struct nvmem_layout *layout)
-+static int onie_tlv_parse_table(struct device *dev, struct nvmem_device *nvmem)
- {
-       struct onie_tlv_hdr hdr;
-       size_t table_len, data_len, hdr_len;
---- a/drivers/nvmem/layouts/sl28vpd.c
-+++ b/drivers/nvmem/layouts/sl28vpd.c
-@@ -80,8 +80,7 @@ static int sl28vpd_v1_check_crc(struct d
-       return 0;
- }
--static int sl28vpd_add_cells(struct device *dev, struct nvmem_device *nvmem,
--                           struct nvmem_layout *layout)
-+static int sl28vpd_add_cells(struct device *dev, struct nvmem_device *nvmem)
- {
-       const struct nvmem_cell_info *pinfo;
-       struct nvmem_cell_info info = {0};
---- a/include/linux/nvmem-provider.h
-+++ b/include/linux/nvmem-provider.h
-@@ -156,9 +156,8 @@ struct nvmem_cell_table {
-  *
-  * @name:             Layout name.
-  * @of_match_table:   Open firmware match table.
-- * @add_cells:                Will be called if a nvmem device is found which
-- *                    has this layout. The function will add layout
-- *                    specific cells with nvmem_add_one_cell().
-+ * @add_cells:                Called to populate the layout using
-+ *                    nvmem_add_one_cell().
-  * @fixup_cell_info:  Will be called before a cell is added. Can be
-  *                    used to modify the nvmem_cell_info.
-  * @owner:            Pointer to struct module.
-@@ -172,8 +171,7 @@ struct nvmem_cell_table {
- struct nvmem_layout {
-       const char *name;
-       const struct of_device_id *of_match_table;
--      int (*add_cells)(struct device *dev, struct nvmem_device *nvmem,
--                       struct nvmem_layout *layout);
-+      int (*add_cells)(struct device *dev, struct nvmem_device *nvmem);
-       void (*fixup_cell_info)(struct nvmem_device *nvmem,
-                               struct nvmem_layout *layout,
-                               struct nvmem_cell_info *cell);
diff --git a/target/linux/generic/backport-5.15/834-v6.8-0004-nvmem-Move-and-rename-fixup_cell_info.patch b/target/linux/generic/backport-5.15/834-v6.8-0004-nvmem-Move-and-rename-fixup_cell_info.patch
deleted file mode 100644 (file)
index 65aa37f..0000000
+++ /dev/null
@@ -1,169 +0,0 @@
-From 1172460e716784ac7e1049a537bdca8edbf97360 Mon Sep 17 00:00:00 2001
-From: Miquel Raynal <[email protected]>
-Date: Fri, 15 Dec 2023 11:15:31 +0000
-Subject: [PATCH] nvmem: Move and rename ->fixup_cell_info()
-
-This hook is meant to be used by any provider and instantiating a layout
-just for this is useless. Let's instead move this hook to the nvmem
-device and add it to the config structure to be easily shared by the
-providers.
-
-While at moving this hook, rename it ->fixup_dt_cell_info() to clarify
-its main intended purpose.
-
-Signed-off-by: Miquel Raynal <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/core.c           |  6 +++---
- drivers/nvmem/imx-ocotp.c      | 11 +++--------
- drivers/nvmem/internals.h      |  2 ++
- drivers/nvmem/mtk-efuse.c      | 11 +++--------
- include/linux/nvmem-provider.h |  9 ++++-----
- 5 files changed, 15 insertions(+), 24 deletions(-)
-
---- a/drivers/nvmem/core.c
-+++ b/drivers/nvmem/core.c
-@@ -676,7 +676,6 @@ static int nvmem_validate_keepouts(struc
- static int nvmem_add_cells_from_dt(struct nvmem_device *nvmem, struct device_node *np)
- {
--      struct nvmem_layout *layout = nvmem->layout;
-       struct device *dev = &nvmem->dev;
-       struct device_node *child;
-       const __be32 *addr;
-@@ -706,8 +705,8 @@ static int nvmem_add_cells_from_dt(struc
-               info.np = of_node_get(child);
--              if (layout && layout->fixup_cell_info)
--                      layout->fixup_cell_info(nvmem, layout, &info);
-+              if (nvmem->fixup_dt_cell_info)
-+                      nvmem->fixup_dt_cell_info(nvmem, &info);
-               ret = nvmem_add_one_cell(nvmem, &info);
-               kfree(info.name);
-@@ -896,6 +895,7 @@ struct nvmem_device *nvmem_register(cons
-       kref_init(&nvmem->refcnt);
-       INIT_LIST_HEAD(&nvmem->cells);
-+      nvmem->fixup_dt_cell_info = config->fixup_dt_cell_info;
-       nvmem->owner = config->owner;
-       if (!nvmem->owner && config->dev->driver)
---- a/drivers/nvmem/imx-ocotp.c
-+++ b/drivers/nvmem/imx-ocotp.c
-@@ -584,17 +584,12 @@ static const struct of_device_id imx_oco
- };
- MODULE_DEVICE_TABLE(of, imx_ocotp_dt_ids);
--static void imx_ocotp_fixup_cell_info(struct nvmem_device *nvmem,
--                                    struct nvmem_layout *layout,
--                                    struct nvmem_cell_info *cell)
-+static void imx_ocotp_fixup_dt_cell_info(struct nvmem_device *nvmem,
-+                                       struct nvmem_cell_info *cell)
- {
-       cell->read_post_process = imx_ocotp_cell_pp;
- }
--static struct nvmem_layout imx_ocotp_layout = {
--      .fixup_cell_info = imx_ocotp_fixup_cell_info,
--};
--
- static int imx_ocotp_probe(struct platform_device *pdev)
- {
-       struct device *dev = &pdev->dev;
-@@ -620,7 +615,7 @@ static int imx_ocotp_probe(struct platfo
-       imx_ocotp_nvmem_config.size = 4 * priv->params->nregs;
-       imx_ocotp_nvmem_config.dev = dev;
-       imx_ocotp_nvmem_config.priv = priv;
--      imx_ocotp_nvmem_config.layout = &imx_ocotp_layout;
-+      imx_ocotp_nvmem_config.fixup_dt_cell_info = &imx_ocotp_fixup_dt_cell_info;
-       priv->config = &imx_ocotp_nvmem_config;
---- a/drivers/nvmem/internals.h
-+++ b/drivers/nvmem/internals.h
-@@ -23,6 +23,8 @@ struct nvmem_device {
-       struct bin_attribute    eeprom;
-       struct device           *base_dev;
-       struct list_head        cells;
-+      void (*fixup_dt_cell_info)(struct nvmem_device *nvmem,
-+                                 struct nvmem_cell_info *cell);
-       const struct nvmem_keepout *keepout;
-       unsigned int            nkeepout;
-       nvmem_reg_read_t        reg_read;
---- a/drivers/nvmem/mtk-efuse.c
-+++ b/drivers/nvmem/mtk-efuse.c
-@@ -45,9 +45,8 @@ static int mtk_efuse_gpu_speedbin_pp(voi
-       return 0;
- }
--static void mtk_efuse_fixup_cell_info(struct nvmem_device *nvmem,
--                                    struct nvmem_layout *layout,
--                                    struct nvmem_cell_info *cell)
-+static void mtk_efuse_fixup_dt_cell_info(struct nvmem_device *nvmem,
-+                                       struct nvmem_cell_info *cell)
- {
-       size_t sz = strlen(cell->name);
-@@ -61,10 +60,6 @@ static void mtk_efuse_fixup_cell_info(st
-               cell->read_post_process = mtk_efuse_gpu_speedbin_pp;
- }
--static struct nvmem_layout mtk_efuse_layout = {
--      .fixup_cell_info = mtk_efuse_fixup_cell_info,
--};
--
- static int mtk_efuse_probe(struct platform_device *pdev)
- {
-       struct device *dev = &pdev->dev;
-@@ -91,7 +86,7 @@ static int mtk_efuse_probe(struct platfo
-       econfig.priv = priv;
-       econfig.dev = dev;
-       if (pdata->uses_post_processing)
--              econfig.layout = &mtk_efuse_layout;
-+              econfig.fixup_dt_cell_info = &mtk_efuse_fixup_dt_cell_info;
-       nvmem = devm_nvmem_register(dev, &econfig);
-       return PTR_ERR_OR_ZERO(nvmem);
---- a/include/linux/nvmem-provider.h
-+++ b/include/linux/nvmem-provider.h
-@@ -83,6 +83,8 @@ struct nvmem_cell_info {
-  * @cells:    Optional array of pre-defined NVMEM cells.
-  * @ncells:   Number of elements in cells.
-  * @add_legacy_fixed_of_cells:        Read fixed NVMEM cells from old OF syntax.
-+ * @fixup_dt_cell_info: Will be called before a cell is added. Can be
-+ *            used to modify the nvmem_cell_info.
-  * @keepout:  Optional array of keepout ranges (sorted ascending by start).
-  * @nkeepout: Number of elements in the keepout array.
-  * @type:     Type of the nvmem storage
-@@ -113,6 +115,8 @@ struct nvmem_config {
-       const struct nvmem_cell_info    *cells;
-       int                     ncells;
-       bool                    add_legacy_fixed_of_cells;
-+      void (*fixup_dt_cell_info)(struct nvmem_device *nvmem,
-+                                 struct nvmem_cell_info *cell);
-       const struct nvmem_keepout *keepout;
-       unsigned int            nkeepout;
-       enum nvmem_type         type;
-@@ -158,8 +162,6 @@ struct nvmem_cell_table {
-  * @of_match_table:   Open firmware match table.
-  * @add_cells:                Called to populate the layout using
-  *                    nvmem_add_one_cell().
-- * @fixup_cell_info:  Will be called before a cell is added. Can be
-- *                    used to modify the nvmem_cell_info.
-  * @owner:            Pointer to struct module.
-  * @node:             List node.
-  *
-@@ -172,9 +174,6 @@ struct nvmem_layout {
-       const char *name;
-       const struct of_device_id *of_match_table;
-       int (*add_cells)(struct device *dev, struct nvmem_device *nvmem);
--      void (*fixup_cell_info)(struct nvmem_device *nvmem,
--                              struct nvmem_layout *layout,
--                              struct nvmem_cell_info *cell);
-       /* private */
-       struct module *owner;
diff --git a/target/linux/generic/backport-5.15/834-v6.8-0005-nvmem-core-Rework-layouts-to-become-regular-devices.patch b/target/linux/generic/backport-5.15/834-v6.8-0005-nvmem-core-Rework-layouts-to-become-regular-devices.patch
deleted file mode 100644 (file)
index 1881332..0000000
+++ /dev/null
@@ -1,763 +0,0 @@
-From fc29fd821d9ac2ae3d32a722fac39ce874efb883 Mon Sep 17 00:00:00 2001
-From: Miquel Raynal <[email protected]>
-Date: Fri, 15 Dec 2023 11:15:32 +0000
-Subject: [PATCH] nvmem: core: Rework layouts to become regular devices
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-Current layout support was initially written without modules support in
-mind. When the requirement for module support rose, the existing base
-was improved to adopt modularization support, but kind of a design flaw
-was introduced. With the existing implementation, when a storage device
-registers into NVMEM, the core tries to hook a layout (if any) and
-populates its cells immediately. This means, if the hardware description
-expects a layout to be hooked up, but no driver was provided for that,
-the storage medium will fail to probe and try later from
-scratch. Even if we consider that the hardware description shall be
-correct, we could still probe the storage device (especially if it
-contains the rootfs).
-
-One way to overcome this situation is to consider the layouts as
-devices, and leverage the native notifier mechanism. When a new NVMEM
-device is registered, we can populate its nvmem-layout child, if any,
-and wait for the matching to be done in order to get the cells (the
-waiting can be easily done with the NVMEM notifiers). If the layout
-driver is compiled as a module, it should automatically be loaded. This
-way, there is no strong order to enforce, any NVMEM device creation
-or NVMEM layout driver insertion will be observed as a new event which
-may lead to the creation of additional cells, without disturbing the
-probes with costly (and sometimes endless) deferrals.
-
-In order to achieve that goal we create a new bus for the nvmem-layouts
-with minimal logic to match nvmem-layout devices with nvmem-layout
-drivers. All this infrastructure code is created in the layouts.c file.
-
-Signed-off-by: Miquel Raynal <[email protected]>
-Tested-by: Rafał Miłecki <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/Kconfig            |   1 +
- drivers/nvmem/Makefile           |   2 +
- drivers/nvmem/core.c             | 170 ++++++++++----------------
- drivers/nvmem/internals.h        |  21 ++++
- drivers/nvmem/layouts.c          | 201 +++++++++++++++++++++++++++++++
- drivers/nvmem/layouts/Kconfig    |   8 ++
- drivers/nvmem/layouts/onie-tlv.c |  24 +++-
- drivers/nvmem/layouts/sl28vpd.c  |  24 +++-
- include/linux/nvmem-provider.h   |  38 +++---
- 9 files changed, 354 insertions(+), 135 deletions(-)
- create mode 100644 drivers/nvmem/layouts.c
-
---- a/drivers/nvmem/Kconfig
-+++ b/drivers/nvmem/Kconfig
-@@ -1,6 +1,7 @@
- # SPDX-License-Identifier: GPL-2.0-only
- menuconfig NVMEM
-       bool "NVMEM Support"
-+      imply NVMEM_LAYOUTS
-       help
-         Support for NVMEM(Non Volatile Memory) devices like EEPROM, EFUSES...
---- a/drivers/nvmem/Makefile
-+++ b/drivers/nvmem/Makefile
-@@ -5,6 +5,8 @@
- obj-$(CONFIG_NVMEM)           += nvmem_core.o
- nvmem_core-y                  := core.o
-+obj-$(CONFIG_NVMEM_LAYOUTS)   += nvmem_layouts.o
-+nvmem_layouts-y                       := layouts.o
- obj-y                         += layouts/
- # Devices
---- a/drivers/nvmem/core.c
-+++ b/drivers/nvmem/core.c
-@@ -56,9 +56,6 @@ static LIST_HEAD(nvmem_lookup_list);
- static BLOCKING_NOTIFIER_HEAD(nvmem_notifier);
--static DEFINE_SPINLOCK(nvmem_layout_lock);
--static LIST_HEAD(nvmem_layouts);
--
- static int __nvmem_reg_read(struct nvmem_device *nvmem, unsigned int offset,
-                           void *val, size_t bytes)
- {
-@@ -741,97 +738,22 @@ static int nvmem_add_cells_from_fixed_la
-       return err;
- }
--int __nvmem_layout_register(struct nvmem_layout *layout, struct module *owner)
-+int nvmem_layout_register(struct nvmem_layout *layout)
- {
--      layout->owner = owner;
--
--      spin_lock(&nvmem_layout_lock);
--      list_add(&layout->node, &nvmem_layouts);
--      spin_unlock(&nvmem_layout_lock);
--
--      blocking_notifier_call_chain(&nvmem_notifier, NVMEM_LAYOUT_ADD, layout);
-+      if (!layout->add_cells)
-+              return -EINVAL;
--      return 0;
-+      /* Populate the cells */
-+      return layout->add_cells(&layout->nvmem->dev, layout->nvmem);
- }
--EXPORT_SYMBOL_GPL(__nvmem_layout_register);
-+EXPORT_SYMBOL_GPL(nvmem_layout_register);
- void nvmem_layout_unregister(struct nvmem_layout *layout)
- {
--      blocking_notifier_call_chain(&nvmem_notifier, NVMEM_LAYOUT_REMOVE, layout);
--
--      spin_lock(&nvmem_layout_lock);
--      list_del(&layout->node);
--      spin_unlock(&nvmem_layout_lock);
-+      /* Keep the API even with an empty stub in case we need it later */
- }
- EXPORT_SYMBOL_GPL(nvmem_layout_unregister);
--static struct nvmem_layout *nvmem_layout_get(struct nvmem_device *nvmem)
--{
--      struct device_node *layout_np;
--      struct nvmem_layout *l, *layout = ERR_PTR(-EPROBE_DEFER);
--
--      layout_np = of_nvmem_layout_get_container(nvmem);
--      if (!layout_np)
--              return NULL;
--
--      /* Fixed layouts don't have a matching driver */
--      if (of_device_is_compatible(layout_np, "fixed-layout")) {
--              of_node_put(layout_np);
--              return NULL;
--      }
--
--      /*
--       * In case the nvmem device was built-in while the layout was built as a
--       * module, we shall manually request the layout driver loading otherwise
--       * we'll never have any match.
--       */
--      of_request_module(layout_np);
--
--      spin_lock(&nvmem_layout_lock);
--
--      list_for_each_entry(l, &nvmem_layouts, node) {
--              if (of_match_node(l->of_match_table, layout_np)) {
--                      if (try_module_get(l->owner))
--                              layout = l;
--
--                      break;
--              }
--      }
--
--      spin_unlock(&nvmem_layout_lock);
--      of_node_put(layout_np);
--
--      return layout;
--}
--
--static void nvmem_layout_put(struct nvmem_layout *layout)
--{
--      if (layout)
--              module_put(layout->owner);
--}
--
--static int nvmem_add_cells_from_layout(struct nvmem_device *nvmem)
--{
--      struct nvmem_layout *layout = nvmem->layout;
--      int ret;
--
--      if (layout && layout->add_cells) {
--              ret = layout->add_cells(&nvmem->dev, nvmem);
--              if (ret)
--                      return ret;
--      }
--
--      return 0;
--}
--
--#if IS_ENABLED(CONFIG_OF)
--struct device_node *of_nvmem_layout_get_container(struct nvmem_device *nvmem)
--{
--      return of_get_child_by_name(nvmem->dev.of_node, "nvmem-layout");
--}
--EXPORT_SYMBOL_GPL(of_nvmem_layout_get_container);
--#endif
--
- const void *nvmem_layout_get_match_data(struct nvmem_device *nvmem,
-                                       struct nvmem_layout *layout)
- {
-@@ -839,7 +761,7 @@ const void *nvmem_layout_get_match_data(
-       const struct of_device_id *match;
-       layout_np = of_nvmem_layout_get_container(nvmem);
--      match = of_match_node(layout->of_match_table, layout_np);
-+      match = of_match_node(layout->dev.driver->of_match_table, layout_np);
-       return match ? match->data : NULL;
- }
-@@ -951,19 +873,6 @@ struct nvmem_device *nvmem_register(cons
-                       goto err_put_device;
-       }
--      /*
--       * If the driver supplied a layout by config->layout, the module
--       * pointer will be NULL and nvmem_layout_put() will be a noop.
--       */
--      nvmem->layout = config->layout ?: nvmem_layout_get(nvmem);
--      if (IS_ERR(nvmem->layout)) {
--              rval = PTR_ERR(nvmem->layout);
--              nvmem->layout = NULL;
--
--              if (rval == -EPROBE_DEFER)
--                      goto err_teardown_compat;
--      }
--
-       if (config->cells) {
-               rval = nvmem_add_cells(nvmem, config->cells, config->ncells);
-               if (rval)
-@@ -984,24 +893,24 @@ struct nvmem_device *nvmem_register(cons
-       if (rval)
-               goto err_remove_cells;
--      rval = nvmem_add_cells_from_layout(nvmem);
--      if (rval)
--              goto err_remove_cells;
--
-       dev_dbg(&nvmem->dev, "Registering nvmem device %s\n", config->name);
-       rval = device_add(&nvmem->dev);
-       if (rval)
-               goto err_remove_cells;
-+      rval = nvmem_populate_layout(nvmem);
-+      if (rval)
-+              goto err_remove_dev;
-+
-       blocking_notifier_call_chain(&nvmem_notifier, NVMEM_ADD, nvmem);
-       return nvmem;
-+err_remove_dev:
-+      device_del(&nvmem->dev);
- err_remove_cells:
-       nvmem_device_remove_all_cells(nvmem);
--      nvmem_layout_put(nvmem->layout);
--err_teardown_compat:
-       if (config->compat)
-               nvmem_sysfs_remove_compat(nvmem, config);
- err_put_device:
-@@ -1023,7 +932,7 @@ static void nvmem_device_release(struct
-               device_remove_bin_file(nvmem->base_dev, &nvmem->eeprom);
-       nvmem_device_remove_all_cells(nvmem);
--      nvmem_layout_put(nvmem->layout);
-+      nvmem_destroy_layout(nvmem);
-       device_unregister(&nvmem->dev);
- }
-@@ -1325,6 +1234,12 @@ nvmem_cell_get_from_lookup(struct device
-       return cell;
- }
-+static void nvmem_layout_module_put(struct nvmem_device *nvmem)
-+{
-+      if (nvmem->layout && nvmem->layout->dev.driver)
-+              module_put(nvmem->layout->dev.driver->owner);
-+}
-+
- #if IS_ENABLED(CONFIG_OF)
- static struct nvmem_cell_entry *
- nvmem_find_cell_entry_by_node(struct nvmem_device *nvmem, struct device_node *np)
-@@ -1343,6 +1258,18 @@ nvmem_find_cell_entry_by_node(struct nvm
-       return cell;
- }
-+static int nvmem_layout_module_get_optional(struct nvmem_device *nvmem)
-+{
-+      if (!nvmem->layout)
-+              return 0;
-+
-+      if (!nvmem->layout->dev.driver ||
-+          !try_module_get(nvmem->layout->dev.driver->owner))
-+              return -EPROBE_DEFER;
-+
-+      return 0;
-+}
-+
- /**
-  * of_nvmem_cell_get() - Get a nvmem cell from given device node and cell id
-  *
-@@ -1405,16 +1332,29 @@ struct nvmem_cell *of_nvmem_cell_get(str
-               return ERR_CAST(nvmem);
-       }
-+      ret = nvmem_layout_module_get_optional(nvmem);
-+      if (ret) {
-+              of_node_put(cell_np);
-+              __nvmem_device_put(nvmem);
-+              return ERR_PTR(ret);
-+      }
-+
-       cell_entry = nvmem_find_cell_entry_by_node(nvmem, cell_np);
-       of_node_put(cell_np);
-       if (!cell_entry) {
-               __nvmem_device_put(nvmem);
--              return ERR_PTR(-ENOENT);
-+              nvmem_layout_module_put(nvmem);
-+              if (nvmem->layout)
-+                      return ERR_PTR(-EPROBE_DEFER);
-+              else
-+                      return ERR_PTR(-ENOENT);
-       }
-       cell = nvmem_create_cell(cell_entry, id, cell_index);
--      if (IS_ERR(cell))
-+      if (IS_ERR(cell)) {
-               __nvmem_device_put(nvmem);
-+              nvmem_layout_module_put(nvmem);
-+      }
-       return cell;
- }
-@@ -1528,6 +1468,7 @@ void nvmem_cell_put(struct nvmem_cell *c
-       kfree(cell);
-       __nvmem_device_put(nvmem);
-+      nvmem_layout_module_put(nvmem);
- }
- EXPORT_SYMBOL_GPL(nvmem_cell_put);
-@@ -2105,11 +2046,22 @@ EXPORT_SYMBOL_GPL(nvmem_dev_name);
- static int __init nvmem_init(void)
- {
--      return bus_register(&nvmem_bus_type);
-+      int ret;
-+
-+      ret = bus_register(&nvmem_bus_type);
-+      if (ret)
-+              return ret;
-+
-+      ret = nvmem_layout_bus_register();
-+      if (ret)
-+              bus_unregister(&nvmem_bus_type);
-+
-+      return ret;
- }
- static void __exit nvmem_exit(void)
- {
-+      nvmem_layout_bus_unregister();
-       bus_unregister(&nvmem_bus_type);
- }
---- a/drivers/nvmem/internals.h
-+++ b/drivers/nvmem/internals.h
-@@ -34,4 +34,25 @@ struct nvmem_device {
-       void *priv;
- };
-+#if IS_ENABLED(CONFIG_OF)
-+int nvmem_layout_bus_register(void);
-+void nvmem_layout_bus_unregister(void);
-+int nvmem_populate_layout(struct nvmem_device *nvmem);
-+void nvmem_destroy_layout(struct nvmem_device *nvmem);
-+#else /* CONFIG_OF */
-+static inline int nvmem_layout_bus_register(void)
-+{
-+      return 0;
-+}
-+
-+static inline void nvmem_layout_bus_unregister(void) {}
-+
-+static inline int nvmem_populate_layout(struct nvmem_device *nvmem)
-+{
-+      return 0;
-+}
-+
-+static inline void nvmem_destroy_layout(struct nvmem_device *nvmem) { }
-+#endif /* CONFIG_OF */
-+
- #endif  /* ifndef _LINUX_NVMEM_INTERNALS_H */
---- /dev/null
-+++ b/drivers/nvmem/layouts.c
-@@ -0,0 +1,201 @@
-+// SPDX-License-Identifier: GPL-2.0
-+/*
-+ * NVMEM layout bus handling
-+ *
-+ * Copyright (C) 2023 Bootlin
-+ * Author: Miquel Raynal <[email protected]
-+ */
-+
-+#include <linux/device.h>
-+#include <linux/dma-mapping.h>
-+#include <linux/nvmem-consumer.h>
-+#include <linux/nvmem-provider.h>
-+#include <linux/of.h>
-+#include <linux/of_device.h>
-+#include <linux/of_irq.h>
-+
-+#include "internals.h"
-+
-+#define to_nvmem_layout_driver(drv) \
-+      (container_of((drv), struct nvmem_layout_driver, driver))
-+#define to_nvmem_layout_device(_dev) \
-+      container_of((_dev), struct nvmem_layout, dev)
-+
-+static int nvmem_layout_bus_match(struct device *dev, struct device_driver *drv)
-+{
-+      return of_driver_match_device(dev, drv);
-+}
-+
-+static int nvmem_layout_bus_probe(struct device *dev)
-+{
-+      struct nvmem_layout_driver *drv = to_nvmem_layout_driver(dev->driver);
-+      struct nvmem_layout *layout = to_nvmem_layout_device(dev);
-+
-+      if (!drv->probe || !drv->remove)
-+              return -EINVAL;
-+
-+      return drv->probe(layout);
-+}
-+
-+static void nvmem_layout_bus_remove(struct device *dev)
-+{
-+      struct nvmem_layout_driver *drv = to_nvmem_layout_driver(dev->driver);
-+      struct nvmem_layout *layout = to_nvmem_layout_device(dev);
-+
-+      return drv->remove(layout);
-+}
-+
-+static struct bus_type nvmem_layout_bus_type = {
-+      .name           = "nvmem-layout",
-+      .match          = nvmem_layout_bus_match,
-+      .probe          = nvmem_layout_bus_probe,
-+      .remove         = nvmem_layout_bus_remove,
-+};
-+
-+int nvmem_layout_driver_register(struct nvmem_layout_driver *drv)
-+{
-+      drv->driver.bus = &nvmem_layout_bus_type;
-+
-+      return driver_register(&drv->driver);
-+}
-+EXPORT_SYMBOL_GPL(nvmem_layout_driver_register);
-+
-+void nvmem_layout_driver_unregister(struct nvmem_layout_driver *drv)
-+{
-+      driver_unregister(&drv->driver);
-+}
-+EXPORT_SYMBOL_GPL(nvmem_layout_driver_unregister);
-+
-+static void nvmem_layout_release_device(struct device *dev)
-+{
-+      struct nvmem_layout *layout = to_nvmem_layout_device(dev);
-+
-+      of_node_put(layout->dev.of_node);
-+      kfree(layout);
-+}
-+
-+static int nvmem_layout_create_device(struct nvmem_device *nvmem,
-+                                    struct device_node *np)
-+{
-+      struct nvmem_layout *layout;
-+      struct device *dev;
-+      int ret;
-+
-+      layout = kzalloc(sizeof(*layout), GFP_KERNEL);
-+      if (!layout)
-+              return -ENOMEM;
-+
-+      /* Create a bidirectional link */
-+      layout->nvmem = nvmem;
-+      nvmem->layout = layout;
-+
-+      /* Device model registration */
-+      dev = &layout->dev;
-+      device_initialize(dev);
-+      dev->parent = &nvmem->dev;
-+      dev->bus = &nvmem_layout_bus_type;
-+      dev->release = nvmem_layout_release_device;
-+      dev->coherent_dma_mask = DMA_BIT_MASK(32);
-+      dev->dma_mask = &dev->coherent_dma_mask;
-+      device_set_node(dev, of_fwnode_handle(of_node_get(np)));
-+      of_device_make_bus_id(dev);
-+      of_msi_configure(dev, dev->of_node);
-+
-+      ret = device_add(dev);
-+      if (ret) {
-+              put_device(dev);
-+              return ret;
-+      }
-+
-+      return 0;
-+}
-+
-+static const struct of_device_id of_nvmem_layout_skip_table[] = {
-+      { .compatible = "fixed-layout", },
-+      {}
-+};
-+
-+static int nvmem_layout_bus_populate(struct nvmem_device *nvmem,
-+                                   struct device_node *layout_dn)
-+{
-+      int ret;
-+
-+      /* Make sure it has a compatible property */
-+      if (!of_get_property(layout_dn, "compatible", NULL)) {
-+              pr_debug("%s() - skipping %pOF, no compatible prop\n",
-+                       __func__, layout_dn);
-+              return 0;
-+      }
-+
-+      /* Fixed layouts are parsed manually somewhere else for now */
-+      if (of_match_node(of_nvmem_layout_skip_table, layout_dn)) {
-+              pr_debug("%s() - skipping %pOF node\n", __func__, layout_dn);
-+              return 0;
-+      }
-+
-+      if (of_node_check_flag(layout_dn, OF_POPULATED_BUS)) {
-+              pr_debug("%s() - skipping %pOF, already populated\n",
-+                       __func__, layout_dn);
-+
-+              return 0;
-+      }
-+
-+      /* NVMEM layout buses expect only a single device representing the layout */
-+      ret = nvmem_layout_create_device(nvmem, layout_dn);
-+      if (ret)
-+              return ret;
-+
-+      of_node_set_flag(layout_dn, OF_POPULATED_BUS);
-+
-+      return 0;
-+}
-+
-+struct device_node *of_nvmem_layout_get_container(struct nvmem_device *nvmem)
-+{
-+      return of_get_child_by_name(nvmem->dev.of_node, "nvmem-layout");
-+}
-+EXPORT_SYMBOL_GPL(of_nvmem_layout_get_container);
-+
-+/*
-+ * Returns the number of devices populated, 0 if the operation was not relevant
-+ * for this nvmem device, an error code otherwise.
-+ */
-+int nvmem_populate_layout(struct nvmem_device *nvmem)
-+{
-+      struct device_node *layout_dn;
-+      int ret;
-+
-+      layout_dn = of_nvmem_layout_get_container(nvmem);
-+      if (!layout_dn)
-+              return 0;
-+
-+      /* Populate the layout device */
-+      device_links_supplier_sync_state_pause();
-+      ret = nvmem_layout_bus_populate(nvmem, layout_dn);
-+      device_links_supplier_sync_state_resume();
-+
-+      of_node_put(layout_dn);
-+      return ret;
-+}
-+
-+void nvmem_destroy_layout(struct nvmem_device *nvmem)
-+{
-+      struct device *dev;
-+
-+      if (!nvmem->layout)
-+              return;
-+
-+      dev = &nvmem->layout->dev;
-+      of_node_clear_flag(dev->of_node, OF_POPULATED_BUS);
-+      device_unregister(dev);
-+}
-+
-+int nvmem_layout_bus_register(void)
-+{
-+      return bus_register(&nvmem_layout_bus_type);
-+}
-+
-+void nvmem_layout_bus_unregister(void)
-+{
-+      bus_unregister(&nvmem_layout_bus_type);
-+}
---- a/drivers/nvmem/layouts/Kconfig
-+++ b/drivers/nvmem/layouts/Kconfig
-@@ -1,5 +1,11 @@
- # SPDX-License-Identifier: GPL-2.0
-+config NVMEM_LAYOUTS
-+      bool
-+      depends on OF
-+
-+if NVMEM_LAYOUTS
-+
- menu "Layout Types"
- config NVMEM_LAYOUT_SL28_VPD
-@@ -21,3 +27,5 @@ config NVMEM_LAYOUT_ONIE_TLV
-         If unsure, say N.
- endmenu
-+
-+endif
---- a/drivers/nvmem/layouts/onie-tlv.c
-+++ b/drivers/nvmem/layouts/onie-tlv.c
-@@ -225,16 +225,32 @@ static int onie_tlv_parse_table(struct d
-       return 0;
- }
-+static int onie_tlv_probe(struct nvmem_layout *layout)
-+{
-+      layout->add_cells = onie_tlv_parse_table;
-+
-+      return nvmem_layout_register(layout);
-+}
-+
-+static void onie_tlv_remove(struct nvmem_layout *layout)
-+{
-+      nvmem_layout_unregister(layout);
-+}
-+
- static const struct of_device_id onie_tlv_of_match_table[] = {
-       { .compatible = "onie,tlv-layout", },
-       {},
- };
- MODULE_DEVICE_TABLE(of, onie_tlv_of_match_table);
--static struct nvmem_layout onie_tlv_layout = {
--      .name = "ONIE tlv layout",
--      .of_match_table = onie_tlv_of_match_table,
--      .add_cells = onie_tlv_parse_table,
-+static struct nvmem_layout_driver onie_tlv_layout = {
-+      .driver = {
-+              .owner = THIS_MODULE,
-+              .name = "onie-tlv-layout",
-+              .of_match_table = onie_tlv_of_match_table,
-+      },
-+      .probe = onie_tlv_probe,
-+      .remove = onie_tlv_remove,
- };
- module_nvmem_layout_driver(onie_tlv_layout);
---- a/drivers/nvmem/layouts/sl28vpd.c
-+++ b/drivers/nvmem/layouts/sl28vpd.c
-@@ -134,16 +134,32 @@ static int sl28vpd_add_cells(struct devi
-       return 0;
- }
-+static int sl28vpd_probe(struct nvmem_layout *layout)
-+{
-+      layout->add_cells = sl28vpd_add_cells;
-+
-+      return nvmem_layout_register(layout);
-+}
-+
-+static void sl28vpd_remove(struct nvmem_layout *layout)
-+{
-+      nvmem_layout_unregister(layout);
-+}
-+
- static const struct of_device_id sl28vpd_of_match_table[] = {
-       { .compatible = "kontron,sl28-vpd" },
-       {},
- };
- MODULE_DEVICE_TABLE(of, sl28vpd_of_match_table);
--static struct nvmem_layout sl28vpd_layout = {
--      .name = "sl28-vpd",
--      .of_match_table = sl28vpd_of_match_table,
--      .add_cells = sl28vpd_add_cells,
-+static struct nvmem_layout_driver sl28vpd_layout = {
-+      .driver = {
-+              .owner = THIS_MODULE,
-+              .name = "kontron-sl28vpd-layout",
-+              .of_match_table = sl28vpd_of_match_table,
-+      },
-+      .probe = sl28vpd_probe,
-+      .remove = sl28vpd_remove,
- };
- module_nvmem_layout_driver(sl28vpd_layout);
---- a/include/linux/nvmem-provider.h
-+++ b/include/linux/nvmem-provider.h
-@@ -9,6 +9,7 @@
- #ifndef _LINUX_NVMEM_PROVIDER_H
- #define _LINUX_NVMEM_PROVIDER_H
-+#include <linux/device.h>
- #include <linux/device/driver.h>
- #include <linux/err.h>
- #include <linux/errno.h>
-@@ -158,12 +159,11 @@ struct nvmem_cell_table {
- /**
-  * struct nvmem_layout - NVMEM layout definitions
-  *
-- * @name:             Layout name.
-- * @of_match_table:   Open firmware match table.
-- * @add_cells:                Called to populate the layout using
-- *                    nvmem_add_one_cell().
-- * @owner:            Pointer to struct module.
-- * @node:             List node.
-+ * @dev:              Device-model layout device.
-+ * @nvmem:            The underlying NVMEM device
-+ * @add_cells:                Will be called if a nvmem device is found which
-+ *                    has this layout. The function will add layout
-+ *                    specific cells with nvmem_add_one_cell().
-  *
-  * A nvmem device can hold a well defined structure which can just be
-  * evaluated during runtime. For example a TLV list, or a list of "name=val"
-@@ -171,13 +171,15 @@ struct nvmem_cell_table {
-  * cells.
-  */
- struct nvmem_layout {
--      const char *name;
--      const struct of_device_id *of_match_table;
-+      struct device dev;
-+      struct nvmem_device *nvmem;
-       int (*add_cells)(struct device *dev, struct nvmem_device *nvmem);
-+};
--      /* private */
--      struct module *owner;
--      struct list_head node;
-+struct nvmem_layout_driver {
-+      struct device_driver driver;
-+      int (*probe)(struct nvmem_layout *layout);
-+      void (*remove)(struct nvmem_layout *layout);
- };
- #if IS_ENABLED(CONFIG_NVMEM)
-@@ -194,11 +196,15 @@ void nvmem_del_cell_table(struct nvmem_c
- int nvmem_add_one_cell(struct nvmem_device *nvmem,
-                      const struct nvmem_cell_info *info);
--int __nvmem_layout_register(struct nvmem_layout *layout, struct module *owner);
--#define nvmem_layout_register(layout) \
--      __nvmem_layout_register(layout, THIS_MODULE)
-+int nvmem_layout_register(struct nvmem_layout *layout);
- void nvmem_layout_unregister(struct nvmem_layout *layout);
-+int nvmem_layout_driver_register(struct nvmem_layout_driver *drv);
-+void nvmem_layout_driver_unregister(struct nvmem_layout_driver *drv);
-+#define module_nvmem_layout_driver(__nvmem_layout_driver)             \
-+      module_driver(__nvmem_layout_driver, nvmem_layout_driver_register, \
-+                    nvmem_layout_driver_unregister)
-+
- const void *nvmem_layout_get_match_data(struct nvmem_device *nvmem,
-                                       struct nvmem_layout *layout);
-@@ -262,8 +268,4 @@ static inline struct device_node *of_nvm
- #endif /* CONFIG_NVMEM && CONFIG_OF */
--#define module_nvmem_layout_driver(__layout_driver)           \
--      module_driver(__layout_driver, nvmem_layout_register,   \
--                    nvmem_layout_unregister)
--
- #endif  /* ifndef _LINUX_NVMEM_PROVIDER_H */
diff --git a/target/linux/generic/backport-5.15/834-v6.8-0006-nvmem-core-Expose-cells-through-sysfs.patch b/target/linux/generic/backport-5.15/834-v6.8-0006-nvmem-core-Expose-cells-through-sysfs.patch
deleted file mode 100644 (file)
index 89872be..0000000
+++ /dev/null
@@ -1,240 +0,0 @@
-From 0331c611949fffdf486652450901a4dc52bc5cca Mon Sep 17 00:00:00 2001
-From: Miquel Raynal <[email protected]>
-Date: Fri, 15 Dec 2023 11:15:34 +0000
-Subject: [PATCH] nvmem: core: Expose cells through sysfs
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-The binary content of nvmem devices is available to the user so in the
-easiest cases, finding the content of a cell is rather easy as it is
-just a matter of looking at a known and fixed offset. However, nvmem
-layouts have been recently introduced to cope with more advanced
-situations, where the offset and size of the cells is not known in
-advance or is dynamic. When using layouts, more advanced parsers are
-used by the kernel in order to give direct access to the content of each
-cell, regardless of its position/size in the underlying
-device. Unfortunately, these information are not accessible by users,
-unless by fully re-implementing the parser logic in userland.
-
-Let's expose the cells and their content through sysfs to avoid these
-situations. Of course the relevant NVMEM sysfs Kconfig option must be
-enabled for this support to be available.
-
-Not all nvmem devices expose cells. Indeed, the .bin_attrs attribute
-group member will be filled at runtime only when relevant and will
-remain empty otherwise. In this case, as the cells attribute group will
-be empty, it will not lead to any additional folder/file creation.
-
-Exposed cells are read-only. There is, in practice, everything in the
-core to support a write path, but as I don't see any need for that, I
-prefer to keep the interface simple (and probably safer). The interface
-is documented as being in the "testing" state which means we can later
-add a write attribute if though relevant.
-
-Signed-off-by: Miquel Raynal <[email protected]>
-Tested-by: Rafał Miłecki <[email protected]>
-Tested-by: Chen-Yu Tsai <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/core.c      | 135 +++++++++++++++++++++++++++++++++++++-
- drivers/nvmem/internals.h |   1 +
- 2 files changed, 135 insertions(+), 1 deletion(-)
-
---- a/drivers/nvmem/core.c
-+++ b/drivers/nvmem/core.c
-@@ -300,6 +300,43 @@ static umode_t nvmem_bin_attr_is_visible
-       return nvmem_bin_attr_get_umode(nvmem);
- }
-+static struct nvmem_cell *nvmem_create_cell(struct nvmem_cell_entry *entry,
-+                                          const char *id, int index);
-+
-+static ssize_t nvmem_cell_attr_read(struct file *filp, struct kobject *kobj,
-+                                  struct bin_attribute *attr, char *buf,
-+                                  loff_t pos, size_t count)
-+{
-+      struct nvmem_cell_entry *entry;
-+      struct nvmem_cell *cell = NULL;
-+      size_t cell_sz, read_len;
-+      void *content;
-+
-+      entry = attr->private;
-+      cell = nvmem_create_cell(entry, entry->name, 0);
-+      if (IS_ERR(cell))
-+              return PTR_ERR(cell);
-+
-+      if (!cell)
-+              return -EINVAL;
-+
-+      content = nvmem_cell_read(cell, &cell_sz);
-+      if (IS_ERR(content)) {
-+              read_len = PTR_ERR(content);
-+              goto destroy_cell;
-+      }
-+
-+      read_len = min_t(unsigned int, cell_sz - pos, count);
-+      memcpy(buf, content + pos, read_len);
-+      kfree(content);
-+
-+destroy_cell:
-+      kfree_const(cell->id);
-+      kfree(cell);
-+
-+      return read_len;
-+}
-+
- /* default read/write permissions */
- static struct bin_attribute bin_attr_rw_nvmem = {
-       .attr   = {
-@@ -321,11 +358,21 @@ static const struct attribute_group nvme
-       .is_bin_visible = nvmem_bin_attr_is_visible,
- };
-+/* Cell attributes will be dynamically allocated */
-+static struct attribute_group nvmem_cells_group = {
-+      .name           = "cells",
-+};
-+
- static const struct attribute_group *nvmem_dev_groups[] = {
-       &nvmem_bin_group,
-       NULL,
- };
-+static const struct attribute_group *nvmem_cells_groups[] = {
-+      &nvmem_cells_group,
-+      NULL,
-+};
-+
- static struct bin_attribute bin_attr_nvmem_eeprom_compat = {
-       .attr   = {
-               .name   = "eeprom",
-@@ -381,6 +428,68 @@ static void nvmem_sysfs_remove_compat(st
-               device_remove_bin_file(nvmem->base_dev, &nvmem->eeprom);
- }
-+static int nvmem_populate_sysfs_cells(struct nvmem_device *nvmem)
-+{
-+      struct bin_attribute **cells_attrs, *attrs;
-+      struct nvmem_cell_entry *entry;
-+      unsigned int ncells = 0, i = 0;
-+      int ret = 0;
-+
-+      mutex_lock(&nvmem_mutex);
-+
-+      if (list_empty(&nvmem->cells) || nvmem->sysfs_cells_populated) {
-+              nvmem_cells_group.bin_attrs = NULL;
-+              goto unlock_mutex;
-+      }
-+
-+      /* Allocate an array of attributes with a sentinel */
-+      ncells = list_count_nodes(&nvmem->cells);
-+      cells_attrs = devm_kcalloc(&nvmem->dev, ncells + 1,
-+                                 sizeof(struct bin_attribute *), GFP_KERNEL);
-+      if (!cells_attrs) {
-+              ret = -ENOMEM;
-+              goto unlock_mutex;
-+      }
-+
-+      attrs = devm_kcalloc(&nvmem->dev, ncells, sizeof(struct bin_attribute), GFP_KERNEL);
-+      if (!attrs) {
-+              ret = -ENOMEM;
-+              goto unlock_mutex;
-+      }
-+
-+      /* Initialize each attribute to take the name and size of the cell */
-+      list_for_each_entry(entry, &nvmem->cells, node) {
-+              sysfs_bin_attr_init(&attrs[i]);
-+              attrs[i].attr.name = devm_kasprintf(&nvmem->dev, GFP_KERNEL,
-+                                                  "%s@%x", entry->name,
-+                                                  entry->offset);
-+              attrs[i].attr.mode = 0444;
-+              attrs[i].size = entry->bytes;
-+              attrs[i].read = &nvmem_cell_attr_read;
-+              attrs[i].private = entry;
-+              if (!attrs[i].attr.name) {
-+                      ret = -ENOMEM;
-+                      goto unlock_mutex;
-+              }
-+
-+              cells_attrs[i] = &attrs[i];
-+              i++;
-+      }
-+
-+      nvmem_cells_group.bin_attrs = cells_attrs;
-+
-+      ret = devm_device_add_groups(&nvmem->dev, nvmem_cells_groups);
-+      if (ret)
-+              goto unlock_mutex;
-+
-+      nvmem->sysfs_cells_populated = true;
-+
-+unlock_mutex:
-+      mutex_unlock(&nvmem_mutex);
-+
-+      return ret;
-+}
-+
- #else /* CONFIG_NVMEM_SYSFS */
- static int nvmem_sysfs_setup_compat(struct nvmem_device *nvmem,
-@@ -740,11 +849,25 @@ static int nvmem_add_cells_from_fixed_la
- int nvmem_layout_register(struct nvmem_layout *layout)
- {
-+      int ret;
-+
-       if (!layout->add_cells)
-               return -EINVAL;
-       /* Populate the cells */
--      return layout->add_cells(&layout->nvmem->dev, layout->nvmem);
-+      ret = layout->add_cells(&layout->nvmem->dev, layout->nvmem);
-+      if (ret)
-+              return ret;
-+
-+#ifdef CONFIG_NVMEM_SYSFS
-+      ret = nvmem_populate_sysfs_cells(layout->nvmem);
-+      if (ret) {
-+              nvmem_device_remove_all_cells(layout->nvmem);
-+              return ret;
-+      }
-+#endif
-+
-+      return 0;
- }
- EXPORT_SYMBOL_GPL(nvmem_layout_register);
-@@ -903,10 +1026,20 @@ struct nvmem_device *nvmem_register(cons
-       if (rval)
-               goto err_remove_dev;
-+#ifdef CONFIG_NVMEM_SYSFS
-+      rval = nvmem_populate_sysfs_cells(nvmem);
-+      if (rval)
-+              goto err_destroy_layout;
-+#endif
-+
-       blocking_notifier_call_chain(&nvmem_notifier, NVMEM_ADD, nvmem);
-       return nvmem;
-+#ifdef CONFIG_NVMEM_SYSFS
-+err_destroy_layout:
-+      nvmem_destroy_layout(nvmem);
-+#endif
- err_remove_dev:
-       device_del(&nvmem->dev);
- err_remove_cells:
---- a/drivers/nvmem/internals.h
-+++ b/drivers/nvmem/internals.h
-@@ -32,6 +32,7 @@ struct nvmem_device {
-       struct gpio_desc        *wp_gpio;
-       struct nvmem_layout     *layout;
-       void *priv;
-+      bool                    sysfs_cells_populated;
- };
- #if IS_ENABLED(CONFIG_OF)
diff --git a/target/linux/generic/backport-5.15/834-v6.8-0007-nvmem-stm32-add-support-for-STM32MP25-BSEC-to-contro.patch b/target/linux/generic/backport-5.15/834-v6.8-0007-nvmem-stm32-add-support-for-STM32MP25-BSEC-to-contro.patch
deleted file mode 100644 (file)
index f686222..0000000
+++ /dev/null
@@ -1,65 +0,0 @@
-From f0ac5b23039610619ca4a4805528553ecb6bc815 Mon Sep 17 00:00:00 2001
-From: Patrick Delaunay <[email protected]>
-Date: Fri, 15 Dec 2023 11:15:36 +0000
-Subject: [PATCH] nvmem: stm32: add support for STM32MP25 BSEC to control OTP
- data
-
-On STM32MP25, OTP area may be read/written by using BSEC (boot, security
-and OTP control). The BSEC internal peripheral is only managed by the
-secure world.
-
-The 12 Kbits of OTP (effective) are organized into the following regions:
-- lower OTP (OTP0 to OTP127) = 4096 lower OTP bits,
-  bitwise (1-bit) programmable
-- mid OTP (OTP128 to OTP255) = 4096 middle OTP bits,
-  bulk (32-bit) programmable
-- upper OTP (OTP256 to OTP383) = 4096 upper OTP bits,
-  bulk (32-bit) programmable,
-  only accessible when BSEC is in closed state.
-
-As HWKEY and ECIES key are only accessible by ROM code;
-only 368 OTP words are managed in this driver (OTP0 to OTP267).
-
-This patch adds the STM32MP25 configuration for reading and writing
-the OTP data using the OP-TEE BSEC TA services.
-
-Signed-off-by: Patrick Delaunay <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/stm32-romem.c | 16 ++++++++++++++++
- 1 file changed, 16 insertions(+)
-
---- a/drivers/nvmem/stm32-romem.c
-+++ b/drivers/nvmem/stm32-romem.c
-@@ -269,6 +269,19 @@ static const struct stm32_romem_cfg stm3
-       .ta = true,
- };
-+/*
-+ * STM32MP25 BSEC OTP: 3 regions of 32-bits data words
-+ *   lower OTP (OTP0 to OTP127), bitwise (1-bit) programmable
-+ *   mid OTP (OTP128 to OTP255), bulk (32-bit) programmable
-+ *   upper OTP (OTP256 to OTP383), bulk (32-bit) programmable
-+ *              but no access to HWKEY and ECIES key: limited at OTP367
-+ */
-+static const struct stm32_romem_cfg stm32mp25_bsec_cfg = {
-+      .size = 368 * 4,
-+      .lower = 127,
-+      .ta = true,
-+};
-+
- static const struct of_device_id stm32_romem_of_match[] __maybe_unused = {
-       { .compatible = "st,stm32f4-otp", }, {
-               .compatible = "st,stm32mp15-bsec",
-@@ -276,6 +289,9 @@ static const struct of_device_id stm32_r
-       }, {
-               .compatible = "st,stm32mp13-bsec",
-               .data = (void *)&stm32mp13_bsec_cfg,
-+      }, {
-+              .compatible = "st,stm32mp25-bsec",
-+              .data = (void *)&stm32mp25_bsec_cfg,
-       },
-       { /* sentinel */ },
- };
diff --git a/target/linux/generic/backport-5.15/834-v6.8-0008-nvmem-layouts-refactor-.add_cells-callback-arguments.patch b/target/linux/generic/backport-5.15/834-v6.8-0008-nvmem-layouts-refactor-.add_cells-callback-arguments.patch
deleted file mode 100644 (file)
index 1bf3ba3..0000000
+++ /dev/null
@@ -1,94 +0,0 @@
-From 401df0d4f4098ecc9c5278da2f50756d62e5b37d Mon Sep 17 00:00:00 2001
-From: =?UTF-8?q?Rafa=C5=82=20Mi=C5=82ecki?= <[email protected]>
-Date: Tue, 19 Dec 2023 13:01:03 +0100
-Subject: [PATCH] nvmem: layouts: refactor .add_cells() callback arguments
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-Simply pass whole "struct nvmem_layout" instead of single variables.
-There is nothing in "struct nvmem_layout" that we have to hide from
-layout drivers. They also access it during .probe() and .remove().
-
-Thanks to this change:
-
-1. API gets more consistent
-   All layouts drivers callbacks get the same argument
-
-2. Layouts get correct device
-   Before this change NVMEM core code was passing NVMEM device instead
-   of layout device. That resulted in:
-   * Confusing prints
-   * Calling devm_*() helpers on wrong device
-   * Helpers like of_device_get_match_data() dereferencing NULLs
-
-3. It gets possible to get match data
-   First of all nvmem_layout_get_match_data() requires passing "struct
-   nvmem_layout" which .add_cells() callback didn't have before this. It
-   doesn't matter much as it's rather useless now anyway (and will be
-   dropped).
-   What's more important however is that of_device_get_match_data() can
-   be used now thanks to owning a proper device pointer.
-
-Signed-off-by: Rafał Miłecki <[email protected]>
-Reviewed-by: Miquel Raynal <[email protected]>
-Reviewed-by: Michael Walle <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/core.c             | 2 +-
- drivers/nvmem/layouts/onie-tlv.c | 4 +++-
- drivers/nvmem/layouts/sl28vpd.c  | 4 +++-
- include/linux/nvmem-provider.h   | 2 +-
- 4 files changed, 8 insertions(+), 4 deletions(-)
-
---- a/drivers/nvmem/core.c
-+++ b/drivers/nvmem/core.c
-@@ -855,7 +855,7 @@ int nvmem_layout_register(struct nvmem_l
-               return -EINVAL;
-       /* Populate the cells */
--      ret = layout->add_cells(&layout->nvmem->dev, layout->nvmem);
-+      ret = layout->add_cells(layout);
-       if (ret)
-               return ret;
---- a/drivers/nvmem/layouts/onie-tlv.c
-+++ b/drivers/nvmem/layouts/onie-tlv.c
-@@ -182,8 +182,10 @@ static bool onie_tlv_crc_is_valid(struct
-       return true;
- }
--static int onie_tlv_parse_table(struct device *dev, struct nvmem_device *nvmem)
-+static int onie_tlv_parse_table(struct nvmem_layout *layout)
- {
-+      struct nvmem_device *nvmem = layout->nvmem;
-+      struct device *dev = &layout->dev;
-       struct onie_tlv_hdr hdr;
-       size_t table_len, data_len, hdr_len;
-       u8 *table, *data;
---- a/drivers/nvmem/layouts/sl28vpd.c
-+++ b/drivers/nvmem/layouts/sl28vpd.c
-@@ -80,8 +80,10 @@ static int sl28vpd_v1_check_crc(struct d
-       return 0;
- }
--static int sl28vpd_add_cells(struct device *dev, struct nvmem_device *nvmem)
-+static int sl28vpd_add_cells(struct nvmem_layout *layout)
- {
-+      struct nvmem_device *nvmem = layout->nvmem;
-+      struct device *dev = &layout->dev;
-       const struct nvmem_cell_info *pinfo;
-       struct nvmem_cell_info info = {0};
-       struct device_node *layout_np;
---- a/include/linux/nvmem-provider.h
-+++ b/include/linux/nvmem-provider.h
-@@ -173,7 +173,7 @@ struct nvmem_cell_table {
- struct nvmem_layout {
-       struct device dev;
-       struct nvmem_device *nvmem;
--      int (*add_cells)(struct device *dev, struct nvmem_device *nvmem);
-+      int (*add_cells)(struct nvmem_layout *layout);
- };
- struct nvmem_layout_driver {
diff --git a/target/linux/generic/backport-5.15/834-v6.8-0009-nvmem-drop-nvmem_layout_get_match_data.patch b/target/linux/generic/backport-5.15/834-v6.8-0009-nvmem-drop-nvmem_layout_get_match_data.patch
deleted file mode 100644 (file)
index 514b5f2..0000000
+++ /dev/null
@@ -1,72 +0,0 @@
-From 43f60e3fb62edc7bd8891de8779fb422f4ae23ae Mon Sep 17 00:00:00 2001
-From: =?UTF-8?q?Rafa=C5=82=20Mi=C5=82ecki?= <[email protected]>
-Date: Tue, 19 Dec 2023 13:01:04 +0100
-Subject: [PATCH] nvmem: drop nvmem_layout_get_match_data()
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-Thanks for layouts refactoring we now have "struct device" associated
-with layout. Also its OF pointer points directly to the "nvmem-layout"
-DT node.
-
-All it takes to get match data is a generic of_device_get_match_data().
-
-Signed-off-by: Rafał Miłecki <[email protected]>
-Reviewed-by: Miquel Raynal <[email protected]>
-Reviewed-by: Michael Walle <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/core.c           | 13 -------------
- include/linux/nvmem-provider.h | 10 ----------
- 2 files changed, 23 deletions(-)
-
---- a/drivers/nvmem/core.c
-+++ b/drivers/nvmem/core.c
-@@ -877,19 +877,6 @@ void nvmem_layout_unregister(struct nvme
- }
- EXPORT_SYMBOL_GPL(nvmem_layout_unregister);
--const void *nvmem_layout_get_match_data(struct nvmem_device *nvmem,
--                                      struct nvmem_layout *layout)
--{
--      struct device_node __maybe_unused *layout_np;
--      const struct of_device_id *match;
--
--      layout_np = of_nvmem_layout_get_container(nvmem);
--      match = of_match_node(layout->dev.driver->of_match_table, layout_np);
--
--      return match ? match->data : NULL;
--}
--EXPORT_SYMBOL_GPL(nvmem_layout_get_match_data);
--
- /**
-  * nvmem_register() - Register a nvmem device for given nvmem_config.
-  * Also creates a binary entry in /sys/bus/nvmem/devices/dev-name/nvmem
---- a/include/linux/nvmem-provider.h
-+++ b/include/linux/nvmem-provider.h
-@@ -205,9 +205,6 @@ void nvmem_layout_driver_unregister(stru
-       module_driver(__nvmem_layout_driver, nvmem_layout_driver_register, \
-                     nvmem_layout_driver_unregister)
--const void *nvmem_layout_get_match_data(struct nvmem_device *nvmem,
--                                      struct nvmem_layout *layout);
--
- #else
- static inline struct nvmem_device *nvmem_register(const struct nvmem_config *c)
-@@ -238,13 +235,6 @@ static inline int nvmem_layout_register(
- static inline void nvmem_layout_unregister(struct nvmem_layout *layout) {}
--static inline const void *
--nvmem_layout_get_match_data(struct nvmem_device *nvmem,
--                          struct nvmem_layout *layout)
--{
--      return NULL;
--}
--
- #endif /* CONFIG_NVMEM */
- #if IS_ENABLED(CONFIG_NVMEM) && IS_ENABLED(CONFIG_OF)
diff --git a/target/linux/generic/backport-5.15/834-v6.8-0010-nvmem-core-add-nvmem_dev_size-helper.patch b/target/linux/generic/backport-5.15/834-v6.8-0010-nvmem-core-add-nvmem_dev_size-helper.patch
deleted file mode 100644 (file)
index aa0bbaa..0000000
+++ /dev/null
@@ -1,53 +0,0 @@
-From 33cf42e68efc8ff529a7eee08a4f0ba8c8d0a207 Mon Sep 17 00:00:00 2001
-From: =?UTF-8?q?Rafa=C5=82=20Mi=C5=82ecki?= <[email protected]>
-Date: Thu, 21 Dec 2023 18:34:17 +0100
-Subject: [PATCH] nvmem: core: add nvmem_dev_size() helper
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-This is required by layouts that need to read whole NVMEM content. It's
-especially useful for NVMEM devices without hardcoded layout (like
-U-Boot environment data block).
-
-Signed-off-by: Rafał Miłecki <[email protected]>
-Reviewed-by: Miquel Raynal <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/core.c           | 13 +++++++++++++
- include/linux/nvmem-consumer.h |  1 +
- 2 files changed, 14 insertions(+)
-
---- a/drivers/nvmem/core.c
-+++ b/drivers/nvmem/core.c
-@@ -2164,6 +2164,19 @@ const char *nvmem_dev_name(struct nvmem_
- }
- EXPORT_SYMBOL_GPL(nvmem_dev_name);
-+/**
-+ * nvmem_dev_size() - Get the size of a given nvmem device.
-+ *
-+ * @nvmem: nvmem device.
-+ *
-+ * Return: size of the nvmem device.
-+ */
-+size_t nvmem_dev_size(struct nvmem_device *nvmem)
-+{
-+      return nvmem->size;
-+}
-+EXPORT_SYMBOL_GPL(nvmem_dev_size);
-+
- static int __init nvmem_init(void)
- {
-       int ret;
---- a/include/linux/nvmem-consumer.h
-+++ b/include/linux/nvmem-consumer.h
-@@ -81,6 +81,7 @@ int nvmem_device_cell_write(struct nvmem
-                           struct nvmem_cell_info *info, void *buf);
- const char *nvmem_dev_name(struct nvmem_device *nvmem);
-+size_t nvmem_dev_size(struct nvmem_device *nvmem);
- void nvmem_add_cell_lookups(struct nvmem_cell_lookup *entries,
-                           size_t nentries);
diff --git a/target/linux/generic/backport-5.15/834-v6.8-0011-nvmem-u-boot-env-use-nvmem_add_one_cell-nvmem-subsys.patch b/target/linux/generic/backport-5.15/834-v6.8-0011-nvmem-u-boot-env-use-nvmem_add_one_cell-nvmem-subsys.patch
deleted file mode 100644 (file)
index fc826f3..0000000
+++ /dev/null
@@ -1,126 +0,0 @@
-From 7c8979b42b1a9c5604f431ba804928e55919263c Mon Sep 17 00:00:00 2001
-From: =?UTF-8?q?Rafa=C5=82=20Mi=C5=82ecki?= <[email protected]>
-Date: Thu, 21 Dec 2023 18:34:18 +0100
-Subject: [PATCH] nvmem: u-boot-env: use nvmem_add_one_cell() nvmem subsystem
- helper
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-Simplify adding NVMEM cells.
-
-Signed-off-by: Rafał Miłecki <[email protected]>
-Reviewed-by: Miquel Raynal <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/u-boot-env.c | 55 +++++++++++++++-----------------------
- 1 file changed, 21 insertions(+), 34 deletions(-)
-
---- a/drivers/nvmem/u-boot-env.c
-+++ b/drivers/nvmem/u-boot-env.c
-@@ -23,13 +23,10 @@ enum u_boot_env_format {
- struct u_boot_env {
-       struct device *dev;
-+      struct nvmem_device *nvmem;
-       enum u_boot_env_format format;
-       struct mtd_info *mtd;
--
--      /* Cells */
--      struct nvmem_cell_info *cells;
--      int ncells;
- };
- struct u_boot_env_image_single {
-@@ -94,43 +91,36 @@ static int u_boot_env_read_post_process_
- static int u_boot_env_add_cells(struct u_boot_env *priv, uint8_t *buf,
-                               size_t data_offset, size_t data_len)
- {
-+      struct nvmem_device *nvmem = priv->nvmem;
-       struct device *dev = priv->dev;
-       char *data = buf + data_offset;
-       char *var, *value, *eq;
--      int idx;
--
--      priv->ncells = 0;
--      for (var = data; var < data + data_len && *var; var += strlen(var) + 1)
--              priv->ncells++;
--
--      priv->cells = devm_kcalloc(dev, priv->ncells, sizeof(*priv->cells), GFP_KERNEL);
--      if (!priv->cells)
--              return -ENOMEM;
--      for (var = data, idx = 0;
-+      for (var = data;
-            var < data + data_len && *var;
--           var = value + strlen(value) + 1, idx++) {
-+           var = value + strlen(value) + 1) {
-+              struct nvmem_cell_info info = {};
-+
-               eq = strchr(var, '=');
-               if (!eq)
-                       break;
-               *eq = '\0';
-               value = eq + 1;
--              priv->cells[idx].name = devm_kstrdup(dev, var, GFP_KERNEL);
--              if (!priv->cells[idx].name)
-+              info.name = devm_kstrdup(dev, var, GFP_KERNEL);
-+              if (!info.name)
-                       return -ENOMEM;
--              priv->cells[idx].offset = data_offset + value - data;
--              priv->cells[idx].bytes = strlen(value);
--              priv->cells[idx].np = of_get_child_by_name(dev->of_node, priv->cells[idx].name);
-+              info.offset = data_offset + value - data;
-+              info.bytes = strlen(value);
-+              info.np = of_get_child_by_name(dev->of_node, info.name);
-               if (!strcmp(var, "ethaddr")) {
--                      priv->cells[idx].raw_len = strlen(value);
--                      priv->cells[idx].bytes = ETH_ALEN;
--                      priv->cells[idx].read_post_process = u_boot_env_read_post_process_ethaddr;
-+                      info.raw_len = strlen(value);
-+                      info.bytes = ETH_ALEN;
-+                      info.read_post_process = u_boot_env_read_post_process_ethaddr;
-               }
--      }
--      if (WARN_ON(idx != priv->ncells))
--              priv->ncells = idx;
-+              nvmem_add_one_cell(nvmem, &info);
-+      }
-       return 0;
- }
-@@ -209,7 +199,6 @@ static int u_boot_env_probe(struct platf
-       struct device *dev = &pdev->dev;
-       struct device_node *np = dev->of_node;
-       struct u_boot_env *priv;
--      int err;
-       priv = devm_kzalloc(dev, sizeof(*priv), GFP_KERNEL);
-       if (!priv)
-@@ -224,17 +213,15 @@ static int u_boot_env_probe(struct platf
-               return PTR_ERR(priv->mtd);
-       }
--      err = u_boot_env_parse(priv);
--      if (err)
--              return err;
--
-       config.dev = dev;
--      config.cells = priv->cells;
--      config.ncells = priv->ncells;
-       config.priv = priv;
-       config.size = priv->mtd->size;
--      return PTR_ERR_OR_ZERO(devm_nvmem_register(dev, &config));
-+      priv->nvmem = devm_nvmem_register(dev, &config);
-+      if (IS_ERR(priv->nvmem))
-+              return PTR_ERR(priv->nvmem);
-+
-+      return u_boot_env_parse(priv);
- }
- static const struct of_device_id u_boot_env_of_match_table[] = {
diff --git a/target/linux/generic/backport-5.15/834-v6.8-0012-nvmem-u-boot-env-use-nvmem-device-helpers.patch b/target/linux/generic/backport-5.15/834-v6.8-0012-nvmem-u-boot-env-use-nvmem-device-helpers.patch
deleted file mode 100644 (file)
index 70abc7c..0000000
+++ /dev/null
@@ -1,81 +0,0 @@
-From a832556d23c5a11115f300011a5874d6107a0d62 Mon Sep 17 00:00:00 2001
-From: =?UTF-8?q?Rafa=C5=82=20Mi=C5=82ecki?= <[email protected]>
-Date: Thu, 21 Dec 2023 18:34:19 +0100
-Subject: [PATCH] nvmem: u-boot-env: use nvmem device helpers
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-Use nvmem_dev_size() and nvmem_device_read() to make this driver less
-mtd dependent.
-
-Signed-off-by: Rafał Miłecki <[email protected]>
-Reviewed-by: Miquel Raynal <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/u-boot-env.c | 23 +++++++++++++++--------
- 1 file changed, 15 insertions(+), 8 deletions(-)
-
---- a/drivers/nvmem/u-boot-env.c
-+++ b/drivers/nvmem/u-boot-env.c
-@@ -127,27 +127,34 @@ static int u_boot_env_add_cells(struct u
- static int u_boot_env_parse(struct u_boot_env *priv)
- {
-+      struct nvmem_device *nvmem = priv->nvmem;
-       struct device *dev = priv->dev;
-       size_t crc32_data_offset;
-       size_t crc32_data_len;
-       size_t crc32_offset;
-       size_t data_offset;
-       size_t data_len;
-+      size_t dev_size;
-       uint32_t crc32;
-       uint32_t calc;
--      size_t bytes;
-       uint8_t *buf;
-+      int bytes;
-       int err;
--      buf = kcalloc(1, priv->mtd->size, GFP_KERNEL);
-+      dev_size = nvmem_dev_size(nvmem);
-+
-+      buf = kcalloc(1, dev_size, GFP_KERNEL);
-       if (!buf) {
-               err = -ENOMEM;
-               goto err_out;
-       }
--      err = mtd_read(priv->mtd, 0, priv->mtd->size, &bytes, buf);
--      if ((err && !mtd_is_bitflip(err)) || bytes != priv->mtd->size) {
--              dev_err(dev, "Failed to read from mtd: %d\n", err);
-+      bytes = nvmem_device_read(nvmem, 0, dev_size, buf);
-+      if (bytes < 0) {
-+              err = bytes;
-+              goto err_kfree;
-+      } else if (bytes != dev_size) {
-+              err = -EIO;
-               goto err_kfree;
-       }
-@@ -169,8 +176,8 @@ static int u_boot_env_parse(struct u_boo
-               break;
-       }
-       crc32 = le32_to_cpu(*(__le32 *)(buf + crc32_offset));
--      crc32_data_len = priv->mtd->size - crc32_data_offset;
--      data_len = priv->mtd->size - data_offset;
-+      crc32_data_len = dev_size - crc32_data_offset;
-+      data_len = dev_size - data_offset;
-       calc = crc32(~0, buf + crc32_data_offset, crc32_data_len) ^ ~0L;
-       if (calc != crc32) {
-@@ -179,7 +186,7 @@ static int u_boot_env_parse(struct u_boo
-               goto err_kfree;
-       }
--      buf[priv->mtd->size - 1] = '\0';
-+      buf[dev_size - 1] = '\0';
-       err = u_boot_env_add_cells(priv, buf, data_offset, data_len);
-       if (err)
-               dev_err(dev, "Failed to add cells: %d\n", err);
diff --git a/target/linux/generic/backport-5.15/834-v6.8-0013-nvmem-u-boot-env-improve-coding-style.patch b/target/linux/generic/backport-5.15/834-v6.8-0013-nvmem-u-boot-env-improve-coding-style.patch
deleted file mode 100644 (file)
index 273cfed..0000000
+++ /dev/null
@@ -1,62 +0,0 @@
-From 6bafe07c930676d6430be471310958070816a595 Mon Sep 17 00:00:00 2001
-From: =?UTF-8?q?Rafa=C5=82=20Mi=C5=82ecki?= <[email protected]>
-Date: Thu, 21 Dec 2023 18:34:20 +0100
-Subject: [PATCH] nvmem: u-boot-env: improve coding style
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-1. Prefer kzalloc() over kcalloc()
-   See memory-allocation.rst which says: "to be on the safe side it's
-   best to use routines that set memory to zero, like kzalloc()"
-2. Drop dev_err() for u_boot_env_add_cells() fail
-   It can fail only on -ENOMEM. We don't want to print error then.
-3. Add extra "crc32_addr" variable
-   It makes code reading header's crc32 easier to understand / review.
-
-Signed-off-by: Rafał Miłecki <[email protected]>
-Reviewed-by: Miquel Raynal <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/u-boot-env.c | 8 ++++----
- 1 file changed, 4 insertions(+), 4 deletions(-)
-
---- a/drivers/nvmem/u-boot-env.c
-+++ b/drivers/nvmem/u-boot-env.c
-@@ -132,6 +132,7 @@ static int u_boot_env_parse(struct u_boo
-       size_t crc32_data_offset;
-       size_t crc32_data_len;
-       size_t crc32_offset;
-+      __le32 *crc32_addr;
-       size_t data_offset;
-       size_t data_len;
-       size_t dev_size;
-@@ -143,7 +144,7 @@ static int u_boot_env_parse(struct u_boo
-       dev_size = nvmem_dev_size(nvmem);
--      buf = kcalloc(1, dev_size, GFP_KERNEL);
-+      buf = kzalloc(dev_size, GFP_KERNEL);
-       if (!buf) {
-               err = -ENOMEM;
-               goto err_out;
-@@ -175,7 +176,8 @@ static int u_boot_env_parse(struct u_boo
-               data_offset = offsetof(struct u_boot_env_image_broadcom, data);
-               break;
-       }
--      crc32 = le32_to_cpu(*(__le32 *)(buf + crc32_offset));
-+      crc32_addr = (__le32 *)(buf + crc32_offset);
-+      crc32 = le32_to_cpu(*crc32_addr);
-       crc32_data_len = dev_size - crc32_data_offset;
-       data_len = dev_size - data_offset;
-@@ -188,8 +190,6 @@ static int u_boot_env_parse(struct u_boo
-       buf[dev_size - 1] = '\0';
-       err = u_boot_env_add_cells(priv, buf, data_offset, data_len);
--      if (err)
--              dev_err(dev, "Failed to add cells: %d\n", err);
- err_kfree:
-       kfree(buf);
diff --git a/target/linux/generic/backport-5.15/835-v6.9-0001-dt-bindings-leds-Add-FUNCTION-defines-for-per-band-W.patch b/target/linux/generic/backport-5.15/835-v6.9-0001-dt-bindings-leds-Add-FUNCTION-defines-for-per-band-W.patch
deleted file mode 100644 (file)
index 8b6d3e7..0000000
+++ /dev/null
@@ -1,34 +0,0 @@
-From ec18a2a83b8b9f7e39c80105ea148c769c46227b Mon Sep 17 00:00:00 2001
-From: =?UTF-8?q?Rafa=C5=82=20Mi=C5=82ecki?= <[email protected]>
-Date: Wed, 17 Jan 2024 16:17:36 +0100
-Subject: [PATCH] dt-bindings: leds: Add FUNCTION defines for per-band WLANs
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-Most wireless routers and access points can operate in multiple bands
-simultaneously. Vendors often equip their devices with per-band LEDs.
-
-Add defines for those very common functions to allow cleaner & clearer
-bindings.
-
-Signed-off-by: Rafał Miłecki <[email protected]>
-Acked-by: Rob Herring <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Lee Jones <[email protected]>
----
- include/dt-bindings/leds/common.h | 3 +++
- 1 file changed, 3 insertions(+)
-
---- a/include/dt-bindings/leds/common.h
-+++ b/include/dt-bindings/leds/common.h
-@@ -94,6 +94,9 @@
- #define LED_FUNCTION_USB "usb"
- #define LED_FUNCTION_WAN "wan"
- #define LED_FUNCTION_WLAN "wlan"
-+#define LED_FUNCTION_WLAN_2GHZ "wlan-2ghz"
-+#define LED_FUNCTION_WLAN_5GHZ "wlan-5ghz"
-+#define LED_FUNCTION_WLAN_6GHZ "wlan-6ghz"
- #define LED_FUNCTION_WPS "wps"
- #endif /* __DT_BINDINGS_LEDS_H */
diff --git a/target/linux/generic/backport-5.15/835-v6.9-0002-dt-bindings-leds-Add-LED_FUNCTION_WAN_ONLINE-for-Int.patch b/target/linux/generic/backport-5.15/835-v6.9-0002-dt-bindings-leds-Add-LED_FUNCTION_WAN_ONLINE-for-Int.patch
deleted file mode 100644 (file)
index c1399ce..0000000
+++ /dev/null
@@ -1,35 +0,0 @@
-From 64e558500d2d04878b8a6d6578850c475171d6ba Mon Sep 17 00:00:00 2001
-From: =?UTF-8?q?Rafa=C5=82=20Mi=C5=82ecki?= <[email protected]>
-Date: Fri, 23 Feb 2024 12:22:23 +0100
-Subject: [PATCH] dt-bindings: leds: Add LED_FUNCTION_WAN_ONLINE for Internet
- access
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-It's common for routers to have LED indicating link on the WAN port.
-
-Some devices however have an extra LED that's meant to be used if WAN
-connection is actually "online" (there is Internet access available).
-
-It was suggested to add #define for such use case.
-
-Link: https://lore.kernel.org/linux-devicetree/[email protected]/T/#u
-Signed-off-by: Rafał Miłecki <[email protected]>
-Reviewed-by: AngeloGioacchino Del Regno <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Lee Jones <[email protected]>
----
- include/dt-bindings/leds/common.h | 1 +
- 1 file changed, 1 insertion(+)
-
---- a/include/dt-bindings/leds/common.h
-+++ b/include/dt-bindings/leds/common.h
-@@ -93,6 +93,7 @@
- #define LED_FUNCTION_TX "tx"
- #define LED_FUNCTION_USB "usb"
- #define LED_FUNCTION_WAN "wan"
-+#define LED_FUNCTION_WAN_ONLINE "wan-online"
- #define LED_FUNCTION_WLAN "wlan"
- #define LED_FUNCTION_WLAN_2GHZ "wlan-2ghz"
- #define LED_FUNCTION_WLAN_5GHZ "wlan-5ghz"
diff --git a/target/linux/generic/backport-5.15/836-v6.9-0002-nvmem-mtk-efuse-Register-MediaTek-socinfo-driver-fro.patch b/target/linux/generic/backport-5.15/836-v6.9-0002-nvmem-mtk-efuse-Register-MediaTek-socinfo-driver-fro.patch
deleted file mode 100644 (file)
index 8e7c823..0000000
+++ /dev/null
@@ -1,69 +0,0 @@
-From 998f0633773b3432829fe45d2cd2ffb842f3c78e Mon Sep 17 00:00:00 2001
-From: William-tw Lin <[email protected]>
-Date: Sat, 24 Feb 2024 11:45:07 +0000
-Subject: [PATCH] nvmem: mtk-efuse: Register MediaTek socinfo driver from efuse
-
-The socinfo driver reads chip information from eFuses and does not need
-any devicetree node. Register it from mtk-efuse.
-
-While at it, also add the name for this driver's nvmem_config.
-
-Signed-off-by: William-tw Lin <[email protected]>
-Reviewed-by: AngeloGioacchino Del Regno <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/mtk-efuse.c | 21 ++++++++++++++++++++-
- 1 file changed, 20 insertions(+), 1 deletion(-)
-
---- a/drivers/nvmem/mtk-efuse.c
-+++ b/drivers/nvmem/mtk-efuse.c
-@@ -68,6 +68,7 @@ static int mtk_efuse_probe(struct platfo
-       struct nvmem_config econfig = {};
-       struct mtk_efuse_priv *priv;
-       const struct mtk_efuse_pdata *pdata;
-+      struct platform_device *socinfo;
-       priv = devm_kzalloc(dev, sizeof(*priv), GFP_KERNEL);
-       if (!priv)
-@@ -85,11 +86,20 @@ static int mtk_efuse_probe(struct platfo
-       econfig.size = resource_size(res);
-       econfig.priv = priv;
-       econfig.dev = dev;
-+      econfig.name = "mtk-efuse";
-       if (pdata->uses_post_processing)
-               econfig.fixup_dt_cell_info = &mtk_efuse_fixup_dt_cell_info;
-       nvmem = devm_nvmem_register(dev, &econfig);
-+      if (IS_ERR(nvmem))
-+              return PTR_ERR(nvmem);
--      return PTR_ERR_OR_ZERO(nvmem);
-+      socinfo = platform_device_register_data(&pdev->dev, "mtk-socinfo",
-+                                              PLATFORM_DEVID_AUTO, NULL, 0);
-+      if (IS_ERR(socinfo))
-+              dev_info(dev, "MediaTek SoC Information will be unavailable\n");
-+
-+      platform_set_drvdata(pdev, socinfo);
-+      return 0;
- }
- static const struct mtk_efuse_pdata mtk_mt8186_efuse_pdata = {
-@@ -108,8 +118,17 @@ static const struct of_device_id mtk_efu
- };
- MODULE_DEVICE_TABLE(of, mtk_efuse_of_match);
-+static void mtk_efuse_remove(struct platform_device *pdev)
-+{
-+      struct platform_device *socinfo = platform_get_drvdata(pdev);
-+
-+      if (!IS_ERR_OR_NULL(socinfo))
-+              platform_device_unregister(socinfo);
-+}
-+
- static struct platform_driver mtk_efuse_driver = {
-       .probe = mtk_efuse_probe,
-+      .remove_new = mtk_efuse_remove,
-       .driver = {
-               .name = "mediatek,efuse",
-               .of_match_table = mtk_efuse_of_match,
diff --git a/target/linux/generic/backport-5.15/836-v6.9-0003-nvmem-zynqmp_nvmem-zynqmp_nvmem_probe-cleanup.patch b/target/linux/generic/backport-5.15/836-v6.9-0003-nvmem-zynqmp_nvmem-zynqmp_nvmem_probe-cleanup.patch
deleted file mode 100644 (file)
index 0f90e54..0000000
+++ /dev/null
@@ -1,97 +0,0 @@
-From 29be47fcd6a06ea2e79eeeca6e69ad1e23254a69 Mon Sep 17 00:00:00 2001
-From: Praveen Teja Kundanala <[email protected]>
-Date: Sat, 24 Feb 2024 11:45:11 +0000
-Subject: [PATCH] nvmem: zynqmp_nvmem: zynqmp_nvmem_probe cleanup
-
-- Remove static nvmem_config declaration
-- Remove zynqmp_nvmem_data
-
-Signed-off-by: Praveen Teja Kundanala <[email protected]>
-Acked-by: Kalyani Akula <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/zynqmp_nvmem.c | 37 ++++++++++++------------------------
- 1 file changed, 12 insertions(+), 25 deletions(-)
-
---- a/drivers/nvmem/zynqmp_nvmem.c
-+++ b/drivers/nvmem/zynqmp_nvmem.c
-@@ -1,6 +1,7 @@
- // SPDX-License-Identifier: GPL-2.0+
- /*
-  * Copyright (C) 2019 Xilinx, Inc.
-+ * Copyright (C) 2022 - 2023, Advanced Micro Devices, Inc.
-  */
- #include <linux/module.h>
-@@ -11,36 +12,25 @@
- #define SILICON_REVISION_MASK 0xF
--struct zynqmp_nvmem_data {
--      struct device *dev;
--      struct nvmem_device *nvmem;
--};
- static int zynqmp_nvmem_read(void *context, unsigned int offset,
-                            void *val, size_t bytes)
- {
-+      struct device *dev = context;
-       int ret;
--      int idcode, version;
--      struct zynqmp_nvmem_data *priv = context;
-+      int idcode;
-+      int version;
-       ret = zynqmp_pm_get_chipid(&idcode, &version);
-       if (ret < 0)
-               return ret;
--      dev_dbg(priv->dev, "Read chipid val %x %x\n", idcode, version);
-+      dev_dbg(dev, "Read chipid val %x %x\n", idcode, version);
-       *(int *)val = version & SILICON_REVISION_MASK;
-       return 0;
- }
--static struct nvmem_config econfig = {
--      .name = "zynqmp-nvmem",
--      .owner = THIS_MODULE,
--      .word_size = 1,
--      .size = 1,
--      .read_only = true,
--};
--
- static const struct of_device_id zynqmp_nvmem_match[] = {
-       { .compatible = "xlnx,zynqmp-nvmem-fw", },
-       { /* sentinel */ },
-@@ -50,21 +40,18 @@ MODULE_DEVICE_TABLE(of, zynqmp_nvmem_mat
- static int zynqmp_nvmem_probe(struct platform_device *pdev)
- {
-       struct device *dev = &pdev->dev;
--      struct zynqmp_nvmem_data *priv;
-+      struct nvmem_config econfig = {};
--      priv = devm_kzalloc(dev, sizeof(struct zynqmp_nvmem_data), GFP_KERNEL);
--      if (!priv)
--              return -ENOMEM;
--
--      priv->dev = dev;
-+      econfig.name = "zynqmp-nvmem";
-+      econfig.owner = THIS_MODULE;
-+      econfig.word_size = 1;
-+      econfig.size = 1;
-       econfig.dev = dev;
-       econfig.add_legacy_fixed_of_cells = true;
-+      econfig.read_only = true;
-       econfig.reg_read = zynqmp_nvmem_read;
--      econfig.priv = priv;
--
--      priv->nvmem = devm_nvmem_register(dev, &econfig);
--      return PTR_ERR_OR_ZERO(priv->nvmem);
-+      return PTR_ERR_OR_ZERO(devm_nvmem_register(dev, &econfig));
- }
- static struct platform_driver zynqmp_nvmem_driver = {
diff --git a/target/linux/generic/backport-5.15/836-v6.9-0004-nvmem-zynqmp_nvmem-Add-support-to-access-efuse.patch b/target/linux/generic/backport-5.15/836-v6.9-0004-nvmem-zynqmp_nvmem-Add-support-to-access-efuse.patch
deleted file mode 100644 (file)
index 39c2f17..0000000
+++ /dev/null
@@ -1,243 +0,0 @@
-From 737c0c8d07b5f671c0a33cec95965fcb2d2ea893 Mon Sep 17 00:00:00 2001
-From: Praveen Teja Kundanala <[email protected]>
-Date: Sat, 24 Feb 2024 11:45:12 +0000
-Subject: [PATCH] nvmem: zynqmp_nvmem: Add support to access efuse
-
-Add support to read/write efuse memory map of ZynqMP.
-Below are the offsets of ZynqMP efuse memory map
-       0 - SOC version(read only)
-       0xC - 0xFC -ZynqMP specific purpose efuses
-       0x100 - 0x17F - Physical Unclonable Function(PUF)
-                efuses repurposed as user efuses
-
-Signed-off-by: Praveen Teja Kundanala <[email protected]>
-Acked-by: Kalyani Akula <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/zynqmp_nvmem.c | 186 +++++++++++++++++++++++++++++++++--
- 1 file changed, 176 insertions(+), 10 deletions(-)
-
---- a/drivers/nvmem/zynqmp_nvmem.c
-+++ b/drivers/nvmem/zynqmp_nvmem.c
-@@ -4,6 +4,7 @@
-  * Copyright (C) 2022 - 2023, Advanced Micro Devices, Inc.
-  */
-+#include <linux/dma-mapping.h>
- #include <linux/module.h>
- #include <linux/nvmem-provider.h>
- #include <linux/of.h>
-@@ -11,24 +12,189 @@
- #include <linux/firmware/xlnx-zynqmp.h>
- #define SILICON_REVISION_MASK 0xF
-+#define P_USER_0_64_UPPER_MASK        GENMASK(31, 16)
-+#define P_USER_127_LOWER_4_BIT_MASK GENMASK(3, 0)
-+#define WORD_INBYTES          4
-+#define SOC_VER_SIZE          0x4
-+#define EFUSE_MEMORY_SIZE     0x177
-+#define UNUSED_SPACE          0x8
-+#define ZYNQMP_NVMEM_SIZE     (SOC_VER_SIZE + UNUSED_SPACE + \
-+                               EFUSE_MEMORY_SIZE)
-+#define SOC_VERSION_OFFSET    0x0
-+#define EFUSE_START_OFFSET    0xC
-+#define EFUSE_END_OFFSET      0xFC
-+#define EFUSE_PUF_START_OFFSET        0x100
-+#define EFUSE_PUF_MID_OFFSET  0x140
-+#define EFUSE_PUF_END_OFFSET  0x17F
-+#define EFUSE_NOT_ENABLED     29
-+/*
-+ * efuse access type
-+ */
-+enum efuse_access {
-+      EFUSE_READ = 0,
-+      EFUSE_WRITE
-+};
-+
-+/**
-+ * struct xilinx_efuse - the basic structure
-+ * @src:      address of the buffer to store the data to be write/read
-+ * @size:     read/write word count
-+ * @offset:   read/write offset
-+ * @flag:     0 - represents efuse read and 1- represents efuse write
-+ * @pufuserfuse:0 - represents non-puf efuses, offset is used for read/write
-+ *            1 - represents puf user fuse row number.
-+ *
-+ * this structure stores all the required details to
-+ * read/write efuse memory.
-+ */
-+struct xilinx_efuse {
-+      u64 src;
-+      u32 size;
-+      u32 offset;
-+      enum efuse_access flag;
-+      u32 pufuserfuse;
-+};
-+
-+static int zynqmp_efuse_access(void *context, unsigned int offset,
-+                             void *val, size_t bytes, enum efuse_access flag,
-+                             unsigned int pufflag)
-+{
-+      struct device *dev = context;
-+      struct xilinx_efuse *efuse;
-+      dma_addr_t dma_addr;
-+      dma_addr_t dma_buf;
-+      size_t words = bytes / WORD_INBYTES;
-+      int ret;
-+      int value;
-+      char *data;
--static int zynqmp_nvmem_read(void *context, unsigned int offset,
--                           void *val, size_t bytes)
-+      if (bytes % WORD_INBYTES != 0) {
-+              dev_err(dev, "Bytes requested should be word aligned\n");
-+              return -EOPNOTSUPP;
-+      }
-+
-+      if (pufflag == 0 && offset % WORD_INBYTES) {
-+              dev_err(dev, "Offset requested should be word aligned\n");
-+              return -EOPNOTSUPP;
-+      }
-+
-+      if (pufflag == 1 && flag == EFUSE_WRITE) {
-+              memcpy(&value, val, bytes);
-+              if ((offset == EFUSE_PUF_START_OFFSET ||
-+                   offset == EFUSE_PUF_MID_OFFSET) &&
-+                  value & P_USER_0_64_UPPER_MASK) {
-+                      dev_err(dev, "Only lower 4 bytes are allowed to be programmed in P_USER_0 & P_USER_64\n");
-+                      return -EOPNOTSUPP;
-+              }
-+
-+              if (offset == EFUSE_PUF_END_OFFSET &&
-+                  (value & P_USER_127_LOWER_4_BIT_MASK)) {
-+                      dev_err(dev, "Only MSB 28 bits are allowed to be programmed for P_USER_127\n");
-+                      return -EOPNOTSUPP;
-+              }
-+      }
-+
-+      efuse = dma_alloc_coherent(dev, sizeof(struct xilinx_efuse),
-+                                 &dma_addr, GFP_KERNEL);
-+      if (!efuse)
-+              return -ENOMEM;
-+
-+      data = dma_alloc_coherent(dev, sizeof(bytes),
-+                                &dma_buf, GFP_KERNEL);
-+      if (!data) {
-+              ret = -ENOMEM;
-+              goto efuse_data_fail;
-+      }
-+
-+      if (flag == EFUSE_WRITE) {
-+              memcpy(data, val, bytes);
-+              efuse->flag = EFUSE_WRITE;
-+      } else {
-+              efuse->flag = EFUSE_READ;
-+      }
-+
-+      efuse->src = dma_buf;
-+      efuse->size = words;
-+      efuse->offset = offset;
-+      efuse->pufuserfuse = pufflag;
-+
-+      zynqmp_pm_efuse_access(dma_addr, (u32 *)&ret);
-+      if (ret != 0) {
-+              if (ret == EFUSE_NOT_ENABLED) {
-+                      dev_err(dev, "efuse access is not enabled\n");
-+                      ret = -EOPNOTSUPP;
-+              } else {
-+                      dev_err(dev, "Error in efuse read %x\n", ret);
-+                      ret = -EPERM;
-+              }
-+              goto efuse_access_err;
-+      }
-+
-+      if (flag == EFUSE_READ)
-+              memcpy(val, data, bytes);
-+efuse_access_err:
-+      dma_free_coherent(dev, sizeof(bytes),
-+                        data, dma_buf);
-+efuse_data_fail:
-+      dma_free_coherent(dev, sizeof(struct xilinx_efuse),
-+                        efuse, dma_addr);
-+
-+      return ret;
-+}
-+
-+static int zynqmp_nvmem_read(void *context, unsigned int offset, void *val, size_t bytes)
- {
-       struct device *dev = context;
-       int ret;
-+      int pufflag = 0;
-       int idcode;
-       int version;
--      ret = zynqmp_pm_get_chipid(&idcode, &version);
--      if (ret < 0)
--              return ret;
-+      if (offset >= EFUSE_PUF_START_OFFSET && offset <= EFUSE_PUF_END_OFFSET)
-+              pufflag = 1;
-+
-+      switch (offset) {
-+      /* Soc version offset is zero */
-+      case SOC_VERSION_OFFSET:
-+              if (bytes != SOC_VER_SIZE)
-+                      return -EOPNOTSUPP;
-+
-+              ret = zynqmp_pm_get_chipid((u32 *)&idcode, (u32 *)&version);
-+              if (ret < 0)
-+                      return ret;
-+
-+              dev_dbg(dev, "Read chipid val %x %x\n", idcode, version);
-+              *(int *)val = version & SILICON_REVISION_MASK;
-+              break;
-+      /* Efuse offset starts from 0xc */
-+      case EFUSE_START_OFFSET ... EFUSE_END_OFFSET:
-+      case EFUSE_PUF_START_OFFSET ... EFUSE_PUF_END_OFFSET:
-+              ret = zynqmp_efuse_access(context, offset, val,
-+                                        bytes, EFUSE_READ, pufflag);
-+              break;
-+      default:
-+              *(u32 *)val = 0xDEADBEEF;
-+              ret = 0;
-+              break;
-+      }
-+
-+      return ret;
-+}
-+
-+static int zynqmp_nvmem_write(void *context,
-+                            unsigned int offset, void *val, size_t bytes)
-+{
-+      int pufflag = 0;
-+
-+      if (offset < EFUSE_START_OFFSET || offset > EFUSE_PUF_END_OFFSET)
-+              return -EOPNOTSUPP;
--      dev_dbg(dev, "Read chipid val %x %x\n", idcode, version);
--      *(int *)val = version & SILICON_REVISION_MASK;
-+      if (offset >= EFUSE_PUF_START_OFFSET && offset <= EFUSE_PUF_END_OFFSET)
-+              pufflag = 1;
--      return 0;
-+      return zynqmp_efuse_access(context, offset,
-+                                 val, bytes, EFUSE_WRITE, pufflag);
- }
- static const struct of_device_id zynqmp_nvmem_match[] = {
-@@ -45,11 +211,11 @@ static int zynqmp_nvmem_probe(struct pla
-       econfig.name = "zynqmp-nvmem";
-       econfig.owner = THIS_MODULE;
-       econfig.word_size = 1;
--      econfig.size = 1;
-+      econfig.size = ZYNQMP_NVMEM_SIZE;
-       econfig.dev = dev;
-       econfig.add_legacy_fixed_of_cells = true;
--      econfig.read_only = true;
-       econfig.reg_read = zynqmp_nvmem_read;
-+      econfig.reg_write = zynqmp_nvmem_write;
-       return PTR_ERR_OR_ZERO(devm_nvmem_register(dev, &econfig));
- }
diff --git a/target/linux/generic/backport-5.15/836-v6.9-0005-nvmem-mtk-efuse-Drop-NVMEM-device-name.patch b/target/linux/generic/backport-5.15/836-v6.9-0005-nvmem-mtk-efuse-Drop-NVMEM-device-name.patch
deleted file mode 100644 (file)
index c67399c..0000000
+++ /dev/null
@@ -1,35 +0,0 @@
-From 76c345edef754b16cab81ad9452cc49c09e67066 Mon Sep 17 00:00:00 2001
-From: Chen-Yu Tsai <[email protected]>
-Date: Sat, 24 Feb 2024 11:45:14 +0000
-Subject: [PATCH] nvmem: mtk-efuse: Drop NVMEM device name
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-The MT8183 has not one but two efuse devices. The static name and ID
-causes the second efuse device to fail to probe, due to duplicate sysfs
-entries.
-
-With the rework of the mtk-socinfo driver, lookup by name is no longer
-necessary. The custom name can simply be dropped.
-
-Signed-off-by: Chen-Yu Tsai <[email protected]>
-Reviewed-by: AngeloGioacchino Del Regno <[email protected]>
-Tested-by: "Nícolas F. R. A. Prado" <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/mtk-efuse.c | 1 -
- 1 file changed, 1 deletion(-)
-
---- a/drivers/nvmem/mtk-efuse.c
-+++ b/drivers/nvmem/mtk-efuse.c
-@@ -86,7 +86,6 @@ static int mtk_efuse_probe(struct platfo
-       econfig.size = resource_size(res);
-       econfig.priv = priv;
-       econfig.dev = dev;
--      econfig.name = "mtk-efuse";
-       if (pdata->uses_post_processing)
-               econfig.fixup_dt_cell_info = &mtk_efuse_fixup_dt_cell_info;
-       nvmem = devm_nvmem_register(dev, &econfig);
diff --git a/target/linux/generic/backport-5.15/836-v6.9-0007-nvmem-core-Print-error-on-wrong-bits-DT-property.patch b/target/linux/generic/backport-5.15/836-v6.9-0007-nvmem-core-Print-error-on-wrong-bits-DT-property.patch
deleted file mode 100644 (file)
index 47787d9..0000000
+++ /dev/null
@@ -1,32 +0,0 @@
-From def3173d4f17b37cecbd74d7c269a080b0b01598 Mon Sep 17 00:00:00 2001
-From: Markus Schneider-Pargmann <[email protected]>
-Date: Sat, 24 Feb 2024 11:45:16 +0000
-Subject: [PATCH] nvmem: core: Print error on wrong bits DT property
-
-The algorithms in nvmem core are built with the constraint that
-bit_offset < 8. If bit_offset is greater the results are wrong. Print an
-error if the devicetree 'bits' property is outside of the valid range
-and abort parsing.
-
-Signed-off-by: Markus Schneider-Pargmann <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/core.c | 5 +++++
- 1 file changed, 5 insertions(+)
-
---- a/drivers/nvmem/core.c
-+++ b/drivers/nvmem/core.c
-@@ -807,6 +807,11 @@ static int nvmem_add_cells_from_dt(struc
-               if (addr && len == (2 * sizeof(u32))) {
-                       info.bit_offset = be32_to_cpup(addr++);
-                       info.nbits = be32_to_cpup(addr);
-+                      if (info.bit_offset >= BITS_PER_BYTE || info.nbits < 1) {
-+                              dev_err(dev, "nvmem: invalid bits on %pOF\n", child);
-+                              of_node_put(child);
-+                              return -EINVAL;
-+                      }
-               }
-               info.np = of_node_get(child);
diff --git a/target/linux/generic/backport-5.15/837-v6.10-0001-nvmem-layouts-store-owner-from-modules-with-nvmem_la.patch b/target/linux/generic/backport-5.15/837-v6.10-0001-nvmem-layouts-store-owner-from-modules-with-nvmem_la.patch
deleted file mode 100644 (file)
index c15b4b2..0000000
+++ /dev/null
@@ -1,61 +0,0 @@
-From 6d0ca4a2a7e25f9ad07c1f335f20b4d9e048cdd5 Mon Sep 17 00:00:00 2001
-From: Krzysztof Kozlowski <[email protected]>
-Date: Tue, 30 Apr 2024 09:49:11 +0100
-Subject: [PATCH] nvmem: layouts: store owner from modules with
- nvmem_layout_driver_register()
-
-Modules registering driver with nvmem_layout_driver_register() might
-forget to set .owner field.  The field is used by some of other kernel
-parts for reference counting (try_module_get()), so it is expected that
-drivers will set it.
-
-Solve the problem by moving this task away from the drivers to the core
-code, just like we did for platform_driver in
-commit 9447057eaff8 ("platform_device: use a macro instead of
-platform_driver_register").
-
-Signed-off-by: Krzysztof Kozlowski <[email protected]>
-Reviewed-by: Michael Walle <[email protected]>
-Reviewed-by: Miquel Raynal <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/layouts.c        | 6 ++++--
- include/linux/nvmem-provider.h | 5 ++++-
- 2 files changed, 8 insertions(+), 3 deletions(-)
-
---- a/drivers/nvmem/layouts.c
-+++ b/drivers/nvmem/layouts.c
-@@ -52,13 +52,15 @@ static struct bus_type nvmem_layout_bus_
-       .remove         = nvmem_layout_bus_remove,
- };
--int nvmem_layout_driver_register(struct nvmem_layout_driver *drv)
-+int __nvmem_layout_driver_register(struct nvmem_layout_driver *drv,
-+                                 struct module *owner)
- {
-       drv->driver.bus = &nvmem_layout_bus_type;
-+      drv->driver.owner = owner;
-       return driver_register(&drv->driver);
- }
--EXPORT_SYMBOL_GPL(nvmem_layout_driver_register);
-+EXPORT_SYMBOL_GPL(__nvmem_layout_driver_register);
- void nvmem_layout_driver_unregister(struct nvmem_layout_driver *drv)
- {
---- a/include/linux/nvmem-provider.h
-+++ b/include/linux/nvmem-provider.h
-@@ -199,7 +199,10 @@ int nvmem_add_one_cell(struct nvmem_devi
- int nvmem_layout_register(struct nvmem_layout *layout);
- void nvmem_layout_unregister(struct nvmem_layout *layout);
--int nvmem_layout_driver_register(struct nvmem_layout_driver *drv);
-+#define nvmem_layout_driver_register(drv) \
-+      __nvmem_layout_driver_register(drv, THIS_MODULE)
-+int __nvmem_layout_driver_register(struct nvmem_layout_driver *drv,
-+                                 struct module *owner);
- void nvmem_layout_driver_unregister(struct nvmem_layout_driver *drv);
- #define module_nvmem_layout_driver(__nvmem_layout_driver)             \
-       module_driver(__nvmem_layout_driver, nvmem_layout_driver_register, \
diff --git a/target/linux/generic/backport-5.15/837-v6.10-0002-nvmem-layouts-onie-tlv-drop-driver-owner-initializat.patch b/target/linux/generic/backport-5.15/837-v6.10-0002-nvmem-layouts-onie-tlv-drop-driver-owner-initializat.patch
deleted file mode 100644 (file)
index b483dd2..0000000
+++ /dev/null
@@ -1,28 +0,0 @@
-From 21833338eccb91194fec6ba7548d9c454824eca0 Mon Sep 17 00:00:00 2001
-From: Krzysztof Kozlowski <[email protected]>
-Date: Tue, 30 Apr 2024 09:49:12 +0100
-Subject: [PATCH] nvmem: layouts: onie-tlv: drop driver owner initialization
-
-Core in nvmem_layout_driver_register() already sets the .owner, so
-driver does not need to.
-
-Signed-off-by: Krzysztof Kozlowski <[email protected]>
-Reviewed-by: Michael Walle <[email protected]>
-Acked-by: Miquel Raynal <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/layouts/onie-tlv.c | 1 -
- 1 file changed, 1 deletion(-)
-
---- a/drivers/nvmem/layouts/onie-tlv.c
-+++ b/drivers/nvmem/layouts/onie-tlv.c
-@@ -247,7 +247,6 @@ MODULE_DEVICE_TABLE(of, onie_tlv_of_matc
- static struct nvmem_layout_driver onie_tlv_layout = {
-       .driver = {
--              .owner = THIS_MODULE,
-               .name = "onie-tlv-layout",
-               .of_match_table = onie_tlv_of_match_table,
-       },
diff --git a/target/linux/generic/backport-5.15/837-v6.10-0003-nvmem-layouts-sl28vpd-drop-driver-owner-initializati.patch b/target/linux/generic/backport-5.15/837-v6.10-0003-nvmem-layouts-sl28vpd-drop-driver-owner-initializati.patch
deleted file mode 100644 (file)
index 472a65f..0000000
+++ /dev/null
@@ -1,28 +0,0 @@
-From 23fd602f21953c03c0714257d36685cd6b486f04 Mon Sep 17 00:00:00 2001
-From: Krzysztof Kozlowski <[email protected]>
-Date: Tue, 30 Apr 2024 09:49:13 +0100
-Subject: [PATCH] nvmem: layouts: sl28vpd: drop driver owner initialization
-
-Core in nvmem_layout_driver_register() already sets the .owner, so
-driver does not need to.
-
-Signed-off-by: Krzysztof Kozlowski <[email protected]>
-Reviewed-by: Michael Walle <[email protected]>
-Reviewed-by: Miquel Raynal <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/layouts/sl28vpd.c | 1 -
- 1 file changed, 1 deletion(-)
-
---- a/drivers/nvmem/layouts/sl28vpd.c
-+++ b/drivers/nvmem/layouts/sl28vpd.c
-@@ -156,7 +156,6 @@ MODULE_DEVICE_TABLE(of, sl28vpd_of_match
- static struct nvmem_layout_driver sl28vpd_layout = {
-       .driver = {
--              .owner = THIS_MODULE,
-               .name = "kontron-sl28vpd-layout",
-               .of_match_table = sl28vpd_of_match_table,
-       },
diff --git a/target/linux/generic/backport-5.15/837-v6.10-0004-nvmem-sc27xx-fix-module-autoloading.patch b/target/linux/generic/backport-5.15/837-v6.10-0004-nvmem-sc27xx-fix-module-autoloading.patch
deleted file mode 100644 (file)
index 2aa13a5..0000000
+++ /dev/null
@@ -1,26 +0,0 @@
-From dc3d88ade857ba3dca34f008e0b0aed3ef79cb15 Mon Sep 17 00:00:00 2001
-From: Krzysztof Kozlowski <[email protected]>
-Date: Tue, 30 Apr 2024 09:49:14 +0100
-Subject: [PATCH] nvmem: sc27xx: fix module autoloading
-
-Add MODULE_DEVICE_TABLE(), so the module could be properly autoloaded
-based on the alias from of_device_id table.
-
-Signed-off-by: Krzysztof Kozlowski <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/sc27xx-efuse.c | 1 +
- 1 file changed, 1 insertion(+)
-
---- a/drivers/nvmem/sc27xx-efuse.c
-+++ b/drivers/nvmem/sc27xx-efuse.c
-@@ -263,6 +263,7 @@ static const struct of_device_id sc27xx_
-       { .compatible = "sprd,sc2730-efuse", .data = &sc2730_edata},
-       { }
- };
-+MODULE_DEVICE_TABLE(of, sc27xx_efuse_of_match);
- static struct platform_driver sc27xx_efuse_driver = {
-       .probe = sc27xx_efuse_probe,
diff --git a/target/linux/generic/backport-5.15/837-v6.10-0005-nvmem-sprd-fix-module-autoloading.patch b/target/linux/generic/backport-5.15/837-v6.10-0005-nvmem-sprd-fix-module-autoloading.patch
deleted file mode 100644 (file)
index 0953c92..0000000
+++ /dev/null
@@ -1,26 +0,0 @@
-From 154c1ec943e34f3188c9305b0c91d5e7dc1373b8 Mon Sep 17 00:00:00 2001
-From: Krzysztof Kozlowski <[email protected]>
-Date: Tue, 30 Apr 2024 09:49:15 +0100
-Subject: [PATCH] nvmem: sprd: fix module autoloading
-
-Add MODULE_DEVICE_TABLE(), so the module could be properly autoloaded
-based on the alias from of_device_id table.
-
-Signed-off-by: Krzysztof Kozlowski <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/sprd-efuse.c | 1 +
- 1 file changed, 1 insertion(+)
-
---- a/drivers/nvmem/sprd-efuse.c
-+++ b/drivers/nvmem/sprd-efuse.c
-@@ -426,6 +426,7 @@ static const struct of_device_id sprd_ef
-       { .compatible = "sprd,ums312-efuse", .data = &ums312_data },
-       { }
- };
-+MODULE_DEVICE_TABLE(of, sprd_efuse_of_match);
- static struct platform_driver sprd_efuse_driver = {
-       .probe = sprd_efuse_probe,
diff --git a/target/linux/generic/backport-5.15/837-v6.10-0006-nvmem-core-switch-to-use-device_add_groups.patch b/target/linux/generic/backport-5.15/837-v6.10-0006-nvmem-core-switch-to-use-device_add_groups.patch
deleted file mode 100644 (file)
index 07eb082..0000000
+++ /dev/null
@@ -1,32 +0,0 @@
-From 8d8fc146dd7a0d6a6b37695747a524310dfb9d57 Mon Sep 17 00:00:00 2001
-From: Greg Kroah-Hartman <[email protected]>
-Date: Tue, 30 Apr 2024 09:49:16 +0100
-Subject: [PATCH] nvmem: core: switch to use device_add_groups()
-
-devm_device_add_groups() is being removed from the kernel, so move the
-nvmem driver to use device_add_groups() instead.  The logic is
-identical, when the device is removed the driver core will properly
-clean up and remove the groups, and the memory used by the attribute
-groups will be freed because it was created with dev_* calls, so this is
-functionally identical overall.
-
-Cc: Srinivas Kandagatla <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/core.c | 2 +-
- 1 file changed, 1 insertion(+), 1 deletion(-)
-
---- a/drivers/nvmem/core.c
-+++ b/drivers/nvmem/core.c
-@@ -478,7 +478,7 @@ static int nvmem_populate_sysfs_cells(st
-       nvmem_cells_group.bin_attrs = cells_attrs;
--      ret = devm_device_add_groups(&nvmem->dev, nvmem_cells_groups);
-+      ret = device_add_groups(&nvmem->dev, nvmem_cells_groups);
-       if (ret)
-               goto unlock_mutex;
diff --git a/target/linux/generic/backport-5.15/837-v6.10-0007-nvmem-lpc18xx_eeprom-Convert-to-platform-remove-call.patch b/target/linux/generic/backport-5.15/837-v6.10-0007-nvmem-lpc18xx_eeprom-Convert-to-platform-remove-call.patch
deleted file mode 100644 (file)
index 27d9270..0000000
+++ /dev/null
@@ -1,57 +0,0 @@
-From 693d2f629962628ddefc88f4b6b453edda5ac32e Mon Sep 17 00:00:00 2001
-From: =?UTF-8?q?Uwe=20Kleine-K=C3=B6nig?= <[email protected]>
-Date: Tue, 30 Apr 2024 09:49:17 +0100
-Subject: [PATCH] nvmem: lpc18xx_eeprom: Convert to platform remove callback
- returning void
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-The .remove() callback for a platform driver returns an int which makes
-many driver authors wrongly assume it's possible to do error handling by
-returning an error code. However the value returned is ignored (apart
-from emitting a warning) and this typically results in resource leaks.
-
-To improve here there is a quest to make the remove callback return
-void. In the first step of this quest all drivers are converted to
-.remove_new(), which already returns void. Eventually after all drivers
-are converted, .remove_new() will be renamed to .remove().
-
-Trivially convert this driver from always returning zero in the remove
-callback to the void returning variant.
-
-Signed-off-by: Uwe Kleine-König <[email protected]>
-Acked-by: Vladimir Zapolskiy <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/lpc18xx_eeprom.c | 6 ++----
- 1 file changed, 2 insertions(+), 4 deletions(-)
-
---- a/drivers/nvmem/lpc18xx_eeprom.c
-+++ b/drivers/nvmem/lpc18xx_eeprom.c
-@@ -249,13 +249,11 @@ err_clk:
-       return ret;
- }
--static int lpc18xx_eeprom_remove(struct platform_device *pdev)
-+static void lpc18xx_eeprom_remove(struct platform_device *pdev)
- {
-       struct lpc18xx_eeprom_dev *eeprom = platform_get_drvdata(pdev);
-       clk_disable_unprepare(eeprom->clk);
--
--      return 0;
- }
- static const struct of_device_id lpc18xx_eeprom_of_match[] = {
-@@ -266,7 +264,7 @@ MODULE_DEVICE_TABLE(of, lpc18xx_eeprom_o
- static struct platform_driver lpc18xx_eeprom_driver = {
-       .probe = lpc18xx_eeprom_probe,
--      .remove = lpc18xx_eeprom_remove,
-+      .remove_new = lpc18xx_eeprom_remove,
-       .driver = {
-               .name = "lpc18xx-eeprom",
-               .of_match_table = lpc18xx_eeprom_of_match,
diff --git a/target/linux/generic/backport-5.15/837-v6.10-0008-nvmem-meson-mx-efuse-Remove-nvmem_device-from-efuse-.patch b/target/linux/generic/backport-5.15/837-v6.10-0008-nvmem-meson-mx-efuse-Remove-nvmem_device-from-efuse-.patch
deleted file mode 100644 (file)
index 7770052..0000000
+++ /dev/null
@@ -1,50 +0,0 @@
-From 2a1ad6b75292d38aa2f6ded7335979e0632521da Mon Sep 17 00:00:00 2001
-From: Mukesh Ojha <[email protected]>
-Date: Tue, 30 Apr 2024 09:49:21 +0100
-Subject: [PATCH] nvmem: meson-mx-efuse: Remove nvmem_device from efuse struct
-
-nvmem_device is used at one place while registering nvmem
-device and it is not required to be present in efuse struct
-for just this purpose.
-
-Drop nvmem_device and manage with nvmem device stack variable.
-
-Signed-off-by: Mukesh Ojha <[email protected]>
-Reviewed-by: Martin Blumenstingl <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/meson-mx-efuse.c | 6 +++---
- 1 file changed, 3 insertions(+), 3 deletions(-)
-
---- a/drivers/nvmem/meson-mx-efuse.c
-+++ b/drivers/nvmem/meson-mx-efuse.c
-@@ -44,7 +44,6 @@ struct meson_mx_efuse_platform_data {
- struct meson_mx_efuse {
-       void __iomem *base;
-       struct clk *core_clk;
--      struct nvmem_device *nvmem;
-       struct nvmem_config config;
- };
-@@ -194,6 +193,7 @@ static int meson_mx_efuse_probe(struct p
- {
-       const struct meson_mx_efuse_platform_data *drvdata;
-       struct meson_mx_efuse *efuse;
-+      struct nvmem_device *nvmem;
-       drvdata = of_device_get_match_data(&pdev->dev);
-       if (!drvdata)
-@@ -224,9 +224,9 @@ static int meson_mx_efuse_probe(struct p
-               return PTR_ERR(efuse->core_clk);
-       }
--      efuse->nvmem = devm_nvmem_register(&pdev->dev, &efuse->config);
-+      nvmem = devm_nvmem_register(&pdev->dev, &efuse->config);
--      return PTR_ERR_OR_ZERO(efuse->nvmem);
-+      return PTR_ERR_OR_ZERO(nvmem);
- }
- static struct platform_driver meson_mx_efuse_driver = {
diff --git a/target/linux/generic/backport-5.15/837-v6.10-0009-nvmem-rmem-Fix-return-value-of-rmem_read.patch b/target/linux/generic/backport-5.15/837-v6.10-0009-nvmem-rmem-Fix-return-value-of-rmem_read.patch
deleted file mode 100644 (file)
index 0f0f68b..0000000
+++ /dev/null
@@ -1,42 +0,0 @@
-From 28b008751aa295612318a0fbb2f22dd4f6a83139 Mon Sep 17 00:00:00 2001
-From: Joy Chakraborty <[email protected]>
-Date: Fri, 28 Jun 2024 12:37:01 +0100
-Subject: [PATCH] nvmem: rmem: Fix return value of rmem_read()
-
-reg_read() callback registered with nvmem core expects 0 on success and
-a negative value on error but rmem_read() returns the number of bytes
-read which is treated as an error at the nvmem core.
-
-This does not break when rmem is accessed using sysfs via
-bin_attr_nvmem_read()/write() but causes an error when accessed from
-places like nvmem_access_with_keepouts(), etc.
-
-Change to return 0 on success and error in case
-memory_read_from_buffer() returns an error or -EIO if bytes read do not
-match what was requested.
-
-Fixes: 5a3fa75a4d9c ("nvmem: Add driver to expose reserved memory as nvmem")
-Signed-off-by: Joy Chakraborty <[email protected]>
-Reviewed-by: Dan Carpenter <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/rmem.c | 5 ++++-
- 1 file changed, 4 insertions(+), 1 deletion(-)
-
---- a/drivers/nvmem/rmem.c
-+++ b/drivers/nvmem/rmem.c
-@@ -46,7 +46,10 @@ static int rmem_read(void *context, unsi
-       memunmap(addr);
--      return count;
-+      if (count < 0)
-+              return count;
-+
-+      return count == bytes ? 0 : -EIO;
- }
- static int rmem_probe(struct platform_device *pdev)
diff --git a/target/linux/generic/backport-5.15/837-v6.10-0010-nvmem-meson-efuse-Fix-return-value-of-nvmem-callback.patch b/target/linux/generic/backport-5.15/837-v6.10-0010-nvmem-meson-efuse-Fix-return-value-of-nvmem-callback.patch
deleted file mode 100644 (file)
index 9e5d619..0000000
+++ /dev/null
@@ -1,59 +0,0 @@
-From 7a0a6d0a7c805f9380381f4deedffdf87b93f408 Mon Sep 17 00:00:00 2001
-From: Joy Chakraborty <[email protected]>
-Date: Fri, 28 Jun 2024 12:37:02 +0100
-Subject: [PATCH] nvmem: meson-efuse: Fix return value of nvmem callbacks
-
-Read/write callbacks registered with nvmem core expect 0 to be returned
-on success and a negative value to be returned on failure.
-
-meson_efuse_read() and meson_efuse_write() call into
-meson_sm_call_read() and meson_sm_call_write() respectively which return
-the number of bytes read or written on success as per their api
-description.
-
-Fix to return error if meson_sm_call_read()/meson_sm_call_write()
-returns an error else return 0.
-
-Fixes: a29a63bdaf6f ("nvmem: meson-efuse: simplify read callback")
-Signed-off-by: Joy Chakraborty <[email protected]>
-Reviewed-by: Dan Carpenter <[email protected]>
-Reviewed-by: Neil Armstrong <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/meson-efuse.c | 14 ++++++++++----
- 1 file changed, 10 insertions(+), 4 deletions(-)
-
---- a/drivers/nvmem/meson-efuse.c
-+++ b/drivers/nvmem/meson-efuse.c
-@@ -18,18 +18,24 @@ static int meson_efuse_read(void *contex
-                           void *val, size_t bytes)
- {
-       struct meson_sm_firmware *fw = context;
-+      int ret;
--      return meson_sm_call_read(fw, (u8 *)val, bytes, SM_EFUSE_READ, offset,
--                                bytes, 0, 0, 0);
-+      ret = meson_sm_call_read(fw, (u8 *)val, bytes, SM_EFUSE_READ, offset,
-+                               bytes, 0, 0, 0);
-+
-+      return ret < 0 ? ret : 0;
- }
- static int meson_efuse_write(void *context, unsigned int offset,
-                            void *val, size_t bytes)
- {
-       struct meson_sm_firmware *fw = context;
-+      int ret;
-+
-+      ret = meson_sm_call_write(fw, (u8 *)val, bytes, SM_EFUSE_WRITE, offset,
-+                                bytes, 0, 0, 0);
--      return meson_sm_call_write(fw, (u8 *)val, bytes, SM_EFUSE_WRITE, offset,
--                                 bytes, 0, 0, 0);
-+      return ret < 0 ? ret : 0;
- }
- static const struct of_device_id meson_efuse_match[] = {
diff --git a/target/linux/generic/backport-5.15/837-v6.10-0011-nvmem-core-only-change-name-to-fram-for-current-attr.patch b/target/linux/generic/backport-5.15/837-v6.10-0011-nvmem-core-only-change-name-to-fram-for-current-attr.patch
deleted file mode 100644 (file)
index 064a449..0000000
+++ /dev/null
@@ -1,39 +0,0 @@
-From 0ba424c934fd43dccf0d597e1ae8851f07cb2edf Mon Sep 17 00:00:00 2001
-From: =?UTF-8?q?Thomas=20Wei=C3=9Fschuh?= <[email protected]>
-Date: Fri, 28 Jun 2024 12:37:03 +0100
-Subject: [PATCH] nvmem: core: only change name to fram for current attribute
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-bin_attr_nvmem_eeprom_compat is the template from which all future
-compat attributes are created.
-Changing it means to change all subsquent compat attributes, too.
-
-Instead only use the "fram" name for the currently registered attribute.
-
-Fixes: fd307a4ad332 ("nvmem: prepare basics for FRAM support")
-Signed-off-by: Thomas Weißschuh <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/core.c | 5 ++---
- 1 file changed, 2 insertions(+), 3 deletions(-)
-
---- a/drivers/nvmem/core.c
-+++ b/drivers/nvmem/core.c
-@@ -397,10 +397,9 @@ static int nvmem_sysfs_setup_compat(stru
-       if (!config->base_dev)
-               return -EINVAL;
--      if (config->type == NVMEM_TYPE_FRAM)
--              bin_attr_nvmem_eeprom_compat.attr.name = "fram";
--
-       nvmem->eeprom = bin_attr_nvmem_eeprom_compat;
-+      if (config->type == NVMEM_TYPE_FRAM)
-+              nvmem->eeprom.attr.name = "fram";
-       nvmem->eeprom.attr.mode = nvmem_bin_attr_get_umode(nvmem);
-       nvmem->eeprom.size = nvmem->size;
- #ifdef CONFIG_DEBUG_LOCK_ALLOC
diff --git a/target/linux/generic/backport-5.15/837-v6.10-0012-nvmem-core-limit-cell-sysfs-permissions-to-main-attr.patch b/target/linux/generic/backport-5.15/837-v6.10-0012-nvmem-core-limit-cell-sysfs-permissions-to-main-attr.patch
deleted file mode 100644 (file)
index 88453e8..0000000
+++ /dev/null
@@ -1,37 +0,0 @@
-From 6bef98bafd82903a8d461463f9594f19f1fd6a85 Mon Sep 17 00:00:00 2001
-From: =?UTF-8?q?Thomas=20Wei=C3=9Fschuh?= <[email protected]>
-Date: Fri, 28 Jun 2024 12:37:04 +0100
-Subject: [PATCH] nvmem: core: limit cell sysfs permissions to main attribute
- ones
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-The cell sysfs attribute should not provide more access to the nvmem
-data than the main attribute itself.
-For example if nvme_config::root_only was set, the cell attribute
-would still provide read access to everybody.
-
-Mask out permissions not available on the main attribute.
-
-Fixes: 0331c611949f ("nvmem: core: Expose cells through sysfs")
-Signed-off-by: Thomas Weißschuh <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/core.c | 2 +-
- 1 file changed, 1 insertion(+), 1 deletion(-)
-
---- a/drivers/nvmem/core.c
-+++ b/drivers/nvmem/core.c
-@@ -462,7 +462,7 @@ static int nvmem_populate_sysfs_cells(st
-               attrs[i].attr.name = devm_kasprintf(&nvmem->dev, GFP_KERNEL,
-                                                   "%s@%x", entry->name,
-                                                   entry->offset);
--              attrs[i].attr.mode = 0444;
-+              attrs[i].attr.mode = 0444 & nvmem_bin_attr_get_umode(nvmem);
-               attrs[i].size = entry->bytes;
-               attrs[i].read = &nvmem_cell_attr_read;
-               attrs[i].private = entry;
diff --git a/target/linux/generic/backport-5.15/838-v6.11-0001-nvmem-add-missing-MODULE_DESCRIPTION-macros.patch b/target/linux/generic/backport-5.15/838-v6.11-0001-nvmem-add-missing-MODULE_DESCRIPTION-macros.patch
deleted file mode 100644 (file)
index a8ce832..0000000
+++ /dev/null
@@ -1,48 +0,0 @@
-From c553bad4c5fc5ae44bd2fcaa73e1d6bedfb1c35c Mon Sep 17 00:00:00 2001
-From: Jeff Johnson <[email protected]>
-Date: Fri, 5 Jul 2024 08:48:38 +0100
-Subject: [PATCH] nvmem: add missing MODULE_DESCRIPTION() macros
-
-make allmodconfig && make W=1 C=1 reports:
-WARNING: modpost: missing MODULE_DESCRIPTION() in drivers/nvmem/nvmem-apple-efuses.o
-WARNING: modpost: missing MODULE_DESCRIPTION() in drivers/nvmem/nvmem_brcm_nvram.o
-WARNING: modpost: missing MODULE_DESCRIPTION() in drivers/nvmem/nvmem_u-boot-env.o
-
-Add the missing invocations of the MODULE_DESCRIPTION() macro.
-
-Signed-off-by: Jeff Johnson <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/apple-efuses.c | 1 +
- drivers/nvmem/brcm_nvram.c   | 1 +
- drivers/nvmem/u-boot-env.c   | 1 +
- 3 files changed, 3 insertions(+)
-
---- a/drivers/nvmem/apple-efuses.c
-+++ b/drivers/nvmem/apple-efuses.c
-@@ -78,4 +78,5 @@ static struct platform_driver apple_efus
- module_platform_driver(apple_efuses_driver);
- MODULE_AUTHOR("Sven Peter <[email protected]>");
-+MODULE_DESCRIPTION("Apple SoC eFuse driver");
- MODULE_LICENSE("GPL");
---- a/drivers/nvmem/brcm_nvram.c
-+++ b/drivers/nvmem/brcm_nvram.c
-@@ -253,5 +253,6 @@ static int __init brcm_nvram_init(void)
- subsys_initcall_sync(brcm_nvram_init);
- MODULE_AUTHOR("Rafał Miłecki");
-+MODULE_DESCRIPTION("Broadcom I/O-mapped NVRAM support driver");
- MODULE_LICENSE("GPL");
- MODULE_DEVICE_TABLE(of, brcm_nvram_of_match_table);
---- a/drivers/nvmem/u-boot-env.c
-+++ b/drivers/nvmem/u-boot-env.c
-@@ -249,5 +249,6 @@ static struct platform_driver u_boot_env
- module_platform_driver(u_boot_env_driver);
- MODULE_AUTHOR("Rafał Miłecki");
-+MODULE_DESCRIPTION("U-Boot environment variables support module");
- MODULE_LICENSE("GPL");
- MODULE_DEVICE_TABLE(of, u_boot_env_of_match_table);
diff --git a/target/linux/generic/backport-5.15/838-v6.11-0002-nvmem-meson-efuse-Replacing-the-use-of-of_node_put-t.patch b/target/linux/generic/backport-5.15/838-v6.11-0002-nvmem-meson-efuse-Replacing-the-use-of-of_node_put-t.patch
deleted file mode 100644 (file)
index 05c82db..0000000
+++ /dev/null
@@ -1,48 +0,0 @@
-From 5fecb932607d83d37a703c731268e9d9051457f5 Mon Sep 17 00:00:00 2001
-From: MarileneGarcia <[email protected]>
-Date: Fri, 5 Jul 2024 08:48:40 +0100
-Subject: [PATCH] nvmem: meson-efuse: Replacing the use of of_node_put to
- __free
-
-Use __free for device_node values, and thus drop calls to
-of_node_put.
-
-The goal is to reduce memory management issues by using this
-scope-based of_node_put() cleanup to simplify function exit
-handling. When using __free a resource is allocated within a
-block, it is automatically freed at the end of the block.
-
-Suggested-by: Julia Lawall <[email protected]>
-Signed-off-by: MarileneGarcia <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/meson-efuse.c | 5 ++---
- 1 file changed, 2 insertions(+), 3 deletions(-)
-
---- a/drivers/nvmem/meson-efuse.c
-+++ b/drivers/nvmem/meson-efuse.c
-@@ -48,20 +48,19 @@ static int meson_efuse_probe(struct plat
- {
-       struct device *dev = &pdev->dev;
-       struct meson_sm_firmware *fw;
--      struct device_node *sm_np;
-       struct nvmem_device *nvmem;
-       struct nvmem_config *econfig;
-       struct clk *clk;
-       unsigned int size;
-+      struct device_node *sm_np __free(device_node) =
-+                      of_parse_phandle(pdev->dev.of_node, "secure-monitor", 0);
--      sm_np = of_parse_phandle(pdev->dev.of_node, "secure-monitor", 0);
-       if (!sm_np) {
-               dev_err(&pdev->dev, "no secure-monitor node\n");
-               return -ENODEV;
-       }
-       fw = meson_sm_get(sm_np);
--      of_node_put(sm_np);
-       if (!fw)
-               return -EPROBE_DEFER;
diff --git a/target/linux/generic/backport-5.15/838-v6.11-0003-nvmem-rockchip-otp-set-add_legacy_fixed_of_cells-con.patch b/target/linux/generic/backport-5.15/838-v6.11-0003-nvmem-rockchip-otp-set-add_legacy_fixed_of_cells-con.patch
deleted file mode 100644 (file)
index a8a30fc..0000000
+++ /dev/null
@@ -1,28 +0,0 @@
-From 2933e79db3c00a8cdc56f6bb050a857fec1875ad Mon Sep 17 00:00:00 2001
-From: Heiko Stuebner <[email protected]>
-Date: Fri, 5 Jul 2024 08:48:41 +0100
-Subject: [PATCH] nvmem: rockchip-otp: set add_legacy_fixed_of_cells config
- option
-
-The Rockchip OTP describes its layout via devicetree subnodes,
-so set the appropriate property.
-
-Fixes: 2cc3b37f5b6d ("nvmem: add explicit config option to read old syntax fixed OF cells")
-Signed-off-by: Heiko Stuebner <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/rockchip-otp.c | 1 +
- 1 file changed, 1 insertion(+)
-
---- a/drivers/nvmem/rockchip-otp.c
-+++ b/drivers/nvmem/rockchip-otp.c
-@@ -255,6 +255,7 @@ static int rockchip_otp_read(void *conte
- static struct nvmem_config otp_config = {
-       .name = "rockchip-otp",
-       .owner = THIS_MODULE,
-+      .add_legacy_fixed_of_cells = true,
-       .read_only = true,
-       .stride = 1,
-       .word_size = 1,
diff --git a/target/linux/generic/backport-5.15/838-v6.11-0004-nvmem-rockchip-otp-Set-type-to-OTP.patch b/target/linux/generic/backport-5.15/838-v6.11-0004-nvmem-rockchip-otp-Set-type-to-OTP.patch
deleted file mode 100644 (file)
index 8491eb3..0000000
+++ /dev/null
@@ -1,25 +0,0 @@
-From 39f95600d8c53355b212a117e91a6ba15e0cac47 Mon Sep 17 00:00:00 2001
-From: Heiko Stuebner <[email protected]>
-Date: Fri, 5 Jul 2024 08:48:42 +0100
-Subject: [PATCH] nvmem: rockchip-otp: Set type to OTP
-
-The Rockchip OTP is obviously an OTP memory, so document this fact.
-
-Signed-off-by: Heiko Stuebner <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/rockchip-otp.c | 1 +
- 1 file changed, 1 insertion(+)
-
---- a/drivers/nvmem/rockchip-otp.c
-+++ b/drivers/nvmem/rockchip-otp.c
-@@ -256,6 +256,7 @@ static struct nvmem_config otp_config =
-       .name = "rockchip-otp",
-       .owner = THIS_MODULE,
-       .add_legacy_fixed_of_cells = true,
-+      .type = NVMEM_TYPE_OTP,
-       .read_only = true,
-       .stride = 1,
-       .word_size = 1,
diff --git a/target/linux/generic/backport-5.15/838-v6.11-0005-nvmem-rockchip-efuse-set-type-to-OTP.patch b/target/linux/generic/backport-5.15/838-v6.11-0005-nvmem-rockchip-efuse-set-type-to-OTP.patch
deleted file mode 100644 (file)
index 260b03e..0000000
+++ /dev/null
@@ -1,26 +0,0 @@
-From ba64a04474d2989f397982c48e405cfd785e2dd5 Mon Sep 17 00:00:00 2001
-From: Heiko Stuebner <[email protected]>
-Date: Fri, 5 Jul 2024 08:48:43 +0100
-Subject: [PATCH] nvmem: rockchip-efuse: set type to OTP
-
-This device currently reports an "Unknown" type in sysfs.
-Since it is an eFuse hardware device, set its type to OTP.
-
-Signed-off-by: Heiko Stuebner <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/rockchip-efuse.c | 1 +
- 1 file changed, 1 insertion(+)
-
---- a/drivers/nvmem/rockchip-efuse.c
-+++ b/drivers/nvmem/rockchip-efuse.c
-@@ -206,6 +206,7 @@ static int rockchip_rk3399_efuse_read(vo
- static struct nvmem_config econfig = {
-       .name = "rockchip-efuse",
-       .add_legacy_fixed_of_cells = true,
-+      .type = NVMEM_TYPE_OTP,
-       .stride = 1,
-       .word_size = 1,
-       .read_only = true,
diff --git a/target/linux/generic/backport-5.15/838-v6.11-0006-nvmem-core-add-single-sysfs-group.patch b/target/linux/generic/backport-5.15/838-v6.11-0006-nvmem-core-add-single-sysfs-group.patch
deleted file mode 100644 (file)
index 4fb2afd..0000000
+++ /dev/null
@@ -1,42 +0,0 @@
-From 6188f233161c6a5b2d1c396a221dfafc77dc9eec Mon Sep 17 00:00:00 2001
-From: =?UTF-8?q?Thomas=20Wei=C3=9Fschuh?= <[email protected]>
-Date: Fri, 5 Jul 2024 08:48:46 +0100
-Subject: [PATCH] nvmem: core: add single sysfs group
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-The sysfs core provides a function to easily register a single group.
-Use it and remove the now unnecessary nvmem_cells_groups array.
-
-Signed-off-by: Thomas Weißschuh <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/core.c | 7 +------
- 1 file changed, 1 insertion(+), 6 deletions(-)
-
---- a/drivers/nvmem/core.c
-+++ b/drivers/nvmem/core.c
-@@ -368,11 +368,6 @@ static const struct attribute_group *nvm
-       NULL,
- };
--static const struct attribute_group *nvmem_cells_groups[] = {
--      &nvmem_cells_group,
--      NULL,
--};
--
- static struct bin_attribute bin_attr_nvmem_eeprom_compat = {
-       .attr   = {
-               .name   = "eeprom",
-@@ -477,7 +472,7 @@ static int nvmem_populate_sysfs_cells(st
-       nvmem_cells_group.bin_attrs = cells_attrs;
--      ret = device_add_groups(&nvmem->dev, nvmem_cells_groups);
-+      ret = device_add_group(&nvmem->dev, &nvmem_cells_group);
-       if (ret)
-               goto unlock_mutex;
diff --git a/target/linux/generic/backport-5.15/838-v6.11-0007-nvmem-core-remove-global-nvmem_cells_group.patch b/target/linux/generic/backport-5.15/838-v6.11-0007-nvmem-core-remove-global-nvmem_cells_group.patch
deleted file mode 100644 (file)
index ef626d3..0000000
+++ /dev/null
@@ -1,83 +0,0 @@
-From 6839fed062b7898665983368c88269a6fb1fc10f Mon Sep 17 00:00:00 2001
-From: =?UTF-8?q?Thomas=20Wei=C3=9Fschuh?= <[email protected]>
-Date: Fri, 5 Jul 2024 08:48:47 +0100
-Subject: [PATCH] nvmem: core: remove global nvmem_cells_group
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-nvmem_cells_groups is a global variable that is also mutated.
-This is complicated and error-prone.
-
-Instead use a normal stack variable.
-
-Signed-off-by: Thomas Weißschuh <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/core.c | 26 ++++++++++----------------
- 1 file changed, 10 insertions(+), 16 deletions(-)
-
---- a/drivers/nvmem/core.c
-+++ b/drivers/nvmem/core.c
-@@ -358,11 +358,6 @@ static const struct attribute_group nvme
-       .is_bin_visible = nvmem_bin_attr_is_visible,
- };
--/* Cell attributes will be dynamically allocated */
--static struct attribute_group nvmem_cells_group = {
--      .name           = "cells",
--};
--
- static const struct attribute_group *nvmem_dev_groups[] = {
-       &nvmem_bin_group,
-       NULL,
-@@ -424,23 +419,24 @@ static void nvmem_sysfs_remove_compat(st
- static int nvmem_populate_sysfs_cells(struct nvmem_device *nvmem)
- {
--      struct bin_attribute **cells_attrs, *attrs;
-+      struct attribute_group group = {
-+              .name   = "cells",
-+      };
-       struct nvmem_cell_entry *entry;
-+      struct bin_attribute *attrs;
-       unsigned int ncells = 0, i = 0;
-       int ret = 0;
-       mutex_lock(&nvmem_mutex);
--      if (list_empty(&nvmem->cells) || nvmem->sysfs_cells_populated) {
--              nvmem_cells_group.bin_attrs = NULL;
-+      if (list_empty(&nvmem->cells) || nvmem->sysfs_cells_populated)
-               goto unlock_mutex;
--      }
-       /* Allocate an array of attributes with a sentinel */
-       ncells = list_count_nodes(&nvmem->cells);
--      cells_attrs = devm_kcalloc(&nvmem->dev, ncells + 1,
--                                 sizeof(struct bin_attribute *), GFP_KERNEL);
--      if (!cells_attrs) {
-+      group.bin_attrs = devm_kcalloc(&nvmem->dev, ncells + 1,
-+                                     sizeof(struct bin_attribute *), GFP_KERNEL);
-+      if (!group.bin_attrs) {
-               ret = -ENOMEM;
-               goto unlock_mutex;
-       }
-@@ -466,13 +462,11 @@ static int nvmem_populate_sysfs_cells(st
-                       goto unlock_mutex;
-               }
--              cells_attrs[i] = &attrs[i];
-+              group.bin_attrs[i] = &attrs[i];
-               i++;
-       }
--      nvmem_cells_group.bin_attrs = cells_attrs;
--
--      ret = device_add_group(&nvmem->dev, &nvmem_cells_group);
-+      ret = device_add_group(&nvmem->dev, &group);
-       if (ret)
-               goto unlock_mutex;
diff --git a/target/linux/generic/backport-5.15/838-v6.11-0008-nvmem-core-drop-unnecessary-range-checks-in-sysfs-ca.patch b/target/linux/generic/backport-5.15/838-v6.11-0008-nvmem-core-drop-unnecessary-range-checks-in-sysfs-ca.patch
deleted file mode 100644 (file)
index 9b6251b..0000000
+++ /dev/null
@@ -1,61 +0,0 @@
-From 588773802c386d38f9c4e91acd47369e89d95a30 Mon Sep 17 00:00:00 2001
-From: =?UTF-8?q?Thomas=20Wei=C3=9Fschuh?= <[email protected]>
-Date: Fri, 5 Jul 2024 08:48:48 +0100
-Subject: [PATCH] nvmem: core: drop unnecessary range checks in sysfs callbacks
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-The same checks have already been done in sysfs_kf_bin_write() and
-sysfs_kf_bin_read() just before the callbacks are invoked.
-
-Signed-off-by: Thomas Weißschuh <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/core.c | 14 --------------
- 1 file changed, 14 deletions(-)
-
---- a/drivers/nvmem/core.c
-+++ b/drivers/nvmem/core.c
-@@ -204,19 +204,12 @@ static ssize_t bin_attr_nvmem_read(struc
-               dev = kobj_to_dev(kobj);
-       nvmem = to_nvmem_device(dev);
--      /* Stop the user from reading */
--      if (pos >= nvmem->size)
--              return 0;
--
-       if (!IS_ALIGNED(pos, nvmem->stride))
-               return -EINVAL;
-       if (count < nvmem->word_size)
-               return -EINVAL;
--      if (pos + count > nvmem->size)
--              count = nvmem->size - pos;
--
-       count = round_down(count, nvmem->word_size);
-       if (!nvmem->reg_read)
-@@ -244,19 +237,12 @@ static ssize_t bin_attr_nvmem_write(stru
-               dev = kobj_to_dev(kobj);
-       nvmem = to_nvmem_device(dev);
--      /* Stop the user from writing */
--      if (pos >= nvmem->size)
--              return -EFBIG;
--
-       if (!IS_ALIGNED(pos, nvmem->stride))
-               return -EINVAL;
-       if (count < nvmem->word_size)
-               return -EINVAL;
--      if (pos + count > nvmem->size)
--              count = nvmem->size - pos;
--
-       count = round_down(count, nvmem->word_size);
-       if (!nvmem->reg_write)
diff --git a/target/linux/generic/backport-5.15/838-v6.11-0009-nvmem-Use-sysfs_emit-for-type-attribute.patch b/target/linux/generic/backport-5.15/838-v6.11-0009-nvmem-Use-sysfs_emit-for-type-attribute.patch
deleted file mode 100644 (file)
index 3da1feb..0000000
+++ /dev/null
@@ -1,30 +0,0 @@
-From 08c367e45b6d322956878774f0b88bf5e52c6d54 Mon Sep 17 00:00:00 2001
-From: Marek Vasut <[email protected]>
-Date: Fri, 5 Jul 2024 08:48:51 +0100
-Subject: [PATCH] nvmem: Use sysfs_emit() for type attribute
-
-Use sysfs_emit() instead of sprintf() to follow best practice per
-Documentation/filesystems/sysfs.rst
-"
-show() should only use sysfs_emit()...
-"
-
-Signed-off-by: Marek Vasut <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/core.c | 2 +-
- 1 file changed, 1 insertion(+), 1 deletion(-)
-
---- a/drivers/nvmem/core.c
-+++ b/drivers/nvmem/core.c
-@@ -180,7 +180,7 @@ static ssize_t type_show(struct device *
- {
-       struct nvmem_device *nvmem = to_nvmem_device(dev);
--      return sprintf(buf, "%s\n", nvmem_type_str[nvmem->type]);
-+      return sysfs_emit(buf, "%s\n", nvmem_type_str[nvmem->type]);
- }
- static DEVICE_ATTR_RO(type);
diff --git a/target/linux/generic/backport-5.15/838-v6.11-0010-nvmem-core-Implement-force_ro-sysfs-attribute.patch b/target/linux/generic/backport-5.15/838-v6.11-0010-nvmem-core-Implement-force_ro-sysfs-attribute.patch
deleted file mode 100644 (file)
index ac7dda1..0000000
+++ /dev/null
@@ -1,122 +0,0 @@
-From 9d7eb234ac7a56b88aea8a52ed81553a730fe25c Mon Sep 17 00:00:00 2001
-From: Marek Vasut <[email protected]>
-Date: Fri, 5 Jul 2024 08:48:52 +0100
-Subject: [PATCH] nvmem: core: Implement force_ro sysfs attribute
-
-Implement "force_ro" sysfs attribute to allow users to set read-write
-devices as read-only and back to read-write from userspace. The choice
-of the name is based on MMC core 'force_ro' attribute.
-
-This solves a situation where an AT24 I2C EEPROM with GPIO based nWP
-signal may have to be occasionally updated. Such I2C EEPROM device is
-usually set as read-only during most of the regular system operation,
-but in case it has to be updated in a controlled manner, it could be
-unlocked using this new "force_ro" sysfs attribute and then re-locked
-again.
-
-The "read-only" DT property and config->read_only configuration is
-respected and is used to set default state of the device, read-only
-or read-write, for devices which do implement .reg_write function.
-For devices which do not implement .reg_write function, the device
-is unconditionally read-only and the "force_ro" attribute is not
-visible.
-
-Signed-off-by: Marek Vasut <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- Documentation/ABI/stable/sysfs-bus-nvmem | 17 ++++++++++
- drivers/nvmem/core.c                     | 43 ++++++++++++++++++++++++
- 2 files changed, 60 insertions(+)
-
---- a/Documentation/ABI/stable/sysfs-bus-nvmem
-+++ b/Documentation/ABI/stable/sysfs-bus-nvmem
-@@ -1,3 +1,20 @@
-+What:         /sys/bus/nvmem/devices/.../force_ro
-+Date:         June 2024
-+KernelVersion:        6.11
-+Contact:      Marek Vasut <[email protected]>
-+Description:
-+              This read/write attribute allows users to set read-write
-+              devices as read-only and back to read-write from userspace.
-+              This can be used to unlock and relock write-protection of
-+              devices which are generally locked, except during sporadic
-+              programming operation.
-+              Read returns '0' or '1' for read-write or read-only modes
-+              respectively.
-+              Write parses one of 'YyTt1NnFf0', or [oO][NnFf] for "on"
-+              and "off", i.e. what kstrbool() supports.
-+              Note: This file is only present if CONFIG_NVMEM_SYSFS
-+              is enabled.
-+
- What:         /sys/bus/nvmem/devices/.../nvmem
- Date:         July 2015
- KernelVersion:  4.2
---- a/drivers/nvmem/core.c
-+++ b/drivers/nvmem/core.c
-@@ -185,7 +185,30 @@ static ssize_t type_show(struct device *
- static DEVICE_ATTR_RO(type);
-+static ssize_t force_ro_show(struct device *dev, struct device_attribute *attr,
-+                           char *buf)
-+{
-+      struct nvmem_device *nvmem = to_nvmem_device(dev);
-+
-+      return sysfs_emit(buf, "%d\n", nvmem->read_only);
-+}
-+
-+static ssize_t force_ro_store(struct device *dev, struct device_attribute *attr,
-+                            const char *buf, size_t count)
-+{
-+      struct nvmem_device *nvmem = to_nvmem_device(dev);
-+      int ret = kstrtobool(buf, &nvmem->read_only);
-+
-+      if (ret < 0)
-+              return ret;
-+
-+      return count;
-+}
-+
-+static DEVICE_ATTR_RW(force_ro);
-+
- static struct attribute *nvmem_attrs[] = {
-+      &dev_attr_force_ro.attr,
-       &dev_attr_type.attr,
-       NULL,
- };
-@@ -286,6 +309,25 @@ static umode_t nvmem_bin_attr_is_visible
-       return nvmem_bin_attr_get_umode(nvmem);
- }
-+static umode_t nvmem_attr_is_visible(struct kobject *kobj,
-+                                   struct attribute *attr, int i)
-+{
-+      struct device *dev = kobj_to_dev(kobj);
-+      struct nvmem_device *nvmem = to_nvmem_device(dev);
-+
-+      /*
-+       * If the device has no .reg_write operation, do not allow
-+       * configuration as read-write.
-+       * If the device is set as read-only by configuration, it
-+       * can be forced into read-write mode using the 'force_ro'
-+       * attribute.
-+       */
-+      if (attr == &dev_attr_force_ro.attr && !nvmem->reg_write)
-+              return 0;       /* Attribute not visible */
-+
-+      return attr->mode;
-+}
-+
- static struct nvmem_cell *nvmem_create_cell(struct nvmem_cell_entry *entry,
-                                           const char *id, int index);
-@@ -342,6 +384,7 @@ static const struct attribute_group nvme
-       .bin_attrs      = nvmem_bin_attributes,
-       .attrs          = nvmem_attrs,
-       .is_bin_visible = nvmem_bin_attr_is_visible,
-+      .is_visible     = nvmem_attr_is_visible,
- };
- static const struct attribute_group *nvmem_dev_groups[] = {
diff --git a/target/linux/generic/backport-5.15/838-v6.11-0011-nvmem-u-boot-env-error-if-NVMEM-device-is-too-small.patch b/target/linux/generic/backport-5.15/838-v6.11-0011-nvmem-u-boot-env-error-if-NVMEM-device-is-too-small.patch
deleted file mode 100644 (file)
index 70d420f..0000000
+++ /dev/null
@@ -1,40 +0,0 @@
-From 8679e8b4a1ebdb40c4429e49368d29353e07b601 Mon Sep 17 00:00:00 2001
-From: John Thomson <[email protected]>
-Date: Mon, 2 Sep 2024 15:25:08 +0100
-Subject: [PATCH] nvmem: u-boot-env: error if NVMEM device is too small
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-Verify data size before trying to parse it to avoid reading out of
-buffer. This could happen in case of problems at MTD level or invalid DT
-bindings.
-
-Signed-off-by: John Thomson <[email protected]>
-Cc: stable <[email protected]>
-Fixes: d5542923f200 ("nvmem: add driver handling U-Boot environment variables")
-[rmilecki: simplify commit description & rebase]
-Signed-off-by: Rafał Miłecki <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/u-boot-env.c | 7 +++++++
- 1 file changed, 7 insertions(+)
-
---- a/drivers/nvmem/u-boot-env.c
-+++ b/drivers/nvmem/u-boot-env.c
-@@ -176,6 +176,13 @@ static int u_boot_env_parse(struct u_boo
-               data_offset = offsetof(struct u_boot_env_image_broadcom, data);
-               break;
-       }
-+
-+      if (dev_size < data_offset) {
-+              dev_err(dev, "Device too small for u-boot-env\n");
-+              err = -EIO;
-+              goto err_kfree;
-+      }
-+
-       crc32_addr = (__le32 *)(buf + crc32_offset);
-       crc32 = le32_to_cpu(*crc32_addr);
-       crc32_data_len = dev_size - crc32_data_offset;
diff --git a/target/linux/generic/backport-5.15/838-v6.11-0012-nvmem-Fix-return-type-of-devm_nvmem_device_get-in-ke.patch b/target/linux/generic/backport-5.15/838-v6.11-0012-nvmem-Fix-return-type-of-devm_nvmem_device_get-in-ke.patch
deleted file mode 100644 (file)
index 08f6278..0000000
+++ /dev/null
@@ -1,37 +0,0 @@
-From c69f37f6559a8948d70badd2b179db7714dedd62 Mon Sep 17 00:00:00 2001
-From: Geert Uytterhoeven <[email protected]>
-Date: Mon, 2 Sep 2024 15:25:09 +0100
-Subject: [PATCH] nvmem: Fix return type of devm_nvmem_device_get() in
- kerneldoc
-
-devm_nvmem_device_get() returns an nvmem device, not an nvmem cell.
-
-Fixes: e2a5402ec7c6d044 ("nvmem: Add nvmem_device based consumer apis.")
-Cc: stable <[email protected]>
-Signed-off-by: Geert Uytterhoeven <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/core.c | 6 +++---
- 1 file changed, 3 insertions(+), 3 deletions(-)
-
---- a/drivers/nvmem/core.c
-+++ b/drivers/nvmem/core.c
-@@ -1276,13 +1276,13 @@ void nvmem_device_put(struct nvmem_devic
- EXPORT_SYMBOL_GPL(nvmem_device_put);
- /**
-- * devm_nvmem_device_get() - Get nvmem cell of device form a given id
-+ * devm_nvmem_device_get() - Get nvmem device of device form a given id
-  *
-  * @dev: Device that requests the nvmem device.
-  * @id: name id for the requested nvmem device.
-  *
-- * Return: ERR_PTR() on error or a valid pointer to a struct nvmem_cell
-- * on success.  The nvmem_cell will be freed by the automatically once the
-+ * Return: ERR_PTR() on error or a valid pointer to a struct nvmem_device
-+ * on success.  The nvmem_device will be freed by the automatically once the
-  * device is freed.
-  */
- struct nvmem_device *devm_nvmem_device_get(struct device *dev, const char *id)
diff --git a/target/linux/generic/backport-5.15/839-v6.12-0001-nvmem-imx-ocotp-ele-support-i.MX95.patch b/target/linux/generic/backport-5.15/839-v6.12-0001-nvmem-imx-ocotp-ele-support-i.MX95.patch
deleted file mode 100644 (file)
index c19931b..0000000
+++ /dev/null
@@ -1,73 +0,0 @@
-From c3f9b7b4e5f9de319d00784577cda42036ff243a Mon Sep 17 00:00:00 2001
-From: Peng Fan <[email protected]>
-Date: Mon, 2 Sep 2024 15:29:45 +0100
-Subject: [PATCH] nvmem: imx-ocotp-ele: support i.MX95
-
-i.MX95 OCOTP has same accessing method, so add an entry for i.MX95, but
-some fuse has ECC feature, so only read out the lower 16bits for ECC fuses.
-
-Signed-off-by: Peng Fan <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/imx-ocotp-ele.c | 32 +++++++++++++++++++++++++++++---
- 1 file changed, 29 insertions(+), 3 deletions(-)
-
---- a/drivers/nvmem/imx-ocotp-ele.c
-+++ b/drivers/nvmem/imx-ocotp-ele.c
-@@ -14,8 +14,9 @@
- #include <linux/slab.h>
- enum fuse_type {
--      FUSE_FSB = 1,
--      FUSE_ELE = 2,
-+      FUSE_FSB = BIT(0),
-+      FUSE_ELE = BIT(1),
-+      FUSE_ECC = BIT(2),
-       FUSE_INVALID = -1
- };
-@@ -93,7 +94,10 @@ static int imx_ocotp_reg_read(void *cont
-                       continue;
-               }
--              *buf++ = readl_relaxed(reg + (i << 2));
-+              if (type & FUSE_ECC)
-+                      *buf++ = readl_relaxed(reg + (i << 2)) & GENMASK(15, 0);
-+              else
-+                      *buf++ = readl_relaxed(reg + (i << 2));
-       }
-       memcpy(val, (u8 *)p, bytes);
-@@ -155,8 +159,30 @@ static const struct ocotp_devtype_data i
-       },
- };
-+static const struct ocotp_devtype_data imx95_ocotp_data = {
-+      .reg_off = 0x8000,
-+      .reg_read = imx_ocotp_reg_read,
-+      .size = 2048,
-+      .num_entry = 12,
-+      .entry = {
-+              { 0, 1, FUSE_FSB | FUSE_ECC },
-+              { 7, 1, FUSE_FSB | FUSE_ECC },
-+              { 9, 3, FUSE_FSB | FUSE_ECC },
-+              { 12, 24, FUSE_FSB },
-+              { 36, 2, FUSE_FSB  | FUSE_ECC },
-+              { 38, 14, FUSE_FSB },
-+              { 63, 1, FUSE_ELE },
-+              { 128, 16, FUSE_ELE },
-+              { 188, 1, FUSE_ELE },
-+              { 317, 2, FUSE_FSB | FUSE_ECC },
-+              { 320, 7, FUSE_FSB },
-+              { 328, 184, FUSE_FSB }
-+      },
-+};
-+
- static const struct of_device_id imx_ele_ocotp_dt_ids[] = {
-       { .compatible = "fsl,imx93-ocotp", .data = &imx93_ocotp_data, },
-+      { .compatible = "fsl,imx95-ocotp", .data = &imx95_ocotp_data, },
-       {},
- };
- MODULE_DEVICE_TABLE(of, imx_ele_ocotp_dt_ids);
diff --git a/target/linux/generic/backport-5.15/839-v6.12-0002-nvmem-sunplus-ocotp-Use-devm_platform_ioremap_resour.patch b/target/linux/generic/backport-5.15/839-v6.12-0002-nvmem-sunplus-ocotp-Use-devm_platform_ioremap_resour.patch
deleted file mode 100644 (file)
index 13ef50b..0000000
+++ /dev/null
@@ -1,44 +0,0 @@
-From 98ee46391baf35987227236d0c3bb30ab6e758c8 Mon Sep 17 00:00:00 2001
-From: Zhang Zekun <[email protected]>
-Date: Mon, 2 Sep 2024 15:29:50 +0100
-Subject: [PATCH] nvmem: sunplus-ocotp: Use
- devm_platform_ioremap_resource_byname() helper function
-
-platform_get_resource_byname() and devm_ioremap_resource() can be
-replaced by devm_platform_ioremap_resource_byname(), which can
-simplify the code logic a bit, No functional change here.
-
-Signed-off-by: Zhang Zekun <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- drivers/nvmem/sunplus-ocotp.c | 7 ++-----
- 1 file changed, 2 insertions(+), 5 deletions(-)
-
---- a/drivers/nvmem/sunplus-ocotp.c
-+++ b/drivers/nvmem/sunplus-ocotp.c
-@@ -159,7 +159,6 @@ static int sp_ocotp_probe(struct platfor
-       struct device *dev = &pdev->dev;
-       struct nvmem_device *nvmem;
-       struct sp_ocotp_priv *otp;
--      struct resource *res;
-       int ret;
-       otp = devm_kzalloc(dev, sizeof(*otp), GFP_KERNEL);
-@@ -168,13 +167,11 @@ static int sp_ocotp_probe(struct platfor
-       otp->dev = dev;
--      res = platform_get_resource_byname(pdev, IORESOURCE_MEM, "hb_gpio");
--      otp->base[HB_GPIO] = devm_ioremap_resource(dev, res);
-+      otp->base[HB_GPIO] = devm_platform_ioremap_resource_byname(pdev, "hb_gpio");
-       if (IS_ERR(otp->base[HB_GPIO]))
-               return PTR_ERR(otp->base[HB_GPIO]);
--      res = platform_get_resource_byname(pdev, IORESOURCE_MEM, "otprx");
--      otp->base[OTPRX] = devm_ioremap_resource(dev, res);
-+      otp->base[OTPRX] = devm_platform_ioremap_resource_byname(pdev, "otprx");
-       if (IS_ERR(otp->base[OTPRX]))
-               return PTR_ERR(otp->base[OTPRX]);
diff --git a/target/linux/generic/backport-5.15/839-v6.12-0003-nvmem-layouts-add-U-Boot-env-layout.patch b/target/linux/generic/backport-5.15/839-v6.12-0003-nvmem-layouts-add-U-Boot-env-layout.patch
deleted file mode 100644 (file)
index 138e602..0000000
+++ /dev/null
@@ -1,515 +0,0 @@
-From 5f15811286aff4664bf275a7ede64e1b8858151b Mon Sep 17 00:00:00 2001
-From: =?UTF-8?q?Rafa=C5=82=20Mi=C5=82ecki?= <[email protected]>
-Date: Mon, 2 Sep 2024 15:29:47 +0100
-Subject: [PATCH] nvmem: layouts: add U-Boot env layout
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-U-Boot environment variables are stored in a specific format. Actual
-data can be placed in various storage sources (MTD, UBI volume, EEPROM,
-NVRAM, etc.).
-
-Move all generic (NVMEM device independent) code from NVMEM device
-driver to an NVMEM layout driver. Then add a simple NVMEM layout code on
-top of it.
-
-This allows using NVMEM layout for parsing U-Boot env data stored in any
-kind of NVMEM device.
-
-The old NVMEM glue driver stays in place for handling bindings in the
-MTD context. To avoid code duplication it uses exported layout parsing
-function. Please note that handling MTD & NVMEM layout bindings may be
-refactored in the future.
-
-Signed-off-by: Rafał Miłecki <[email protected]>
-Reviewed-by: Miquel Raynal <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
-Link: https://lore.kernel.org/r/[email protected]
-Signed-off-by: Greg Kroah-Hartman <[email protected]>
----
- MAINTAINERS                        |   1 +
- drivers/nvmem/Kconfig              |   3 +-
- drivers/nvmem/layouts/Kconfig      |  11 ++
- drivers/nvmem/layouts/Makefile     |   1 +
- drivers/nvmem/layouts/u-boot-env.c | 211 +++++++++++++++++++++++++++++
- drivers/nvmem/layouts/u-boot-env.h |  15 ++
- drivers/nvmem/u-boot-env.c         | 165 +---------------------
- 7 files changed, 242 insertions(+), 165 deletions(-)
- create mode 100644 drivers/nvmem/layouts/u-boot-env.c
- create mode 100644 drivers/nvmem/layouts/u-boot-env.h
-
---- a/drivers/nvmem/Kconfig
-+++ b/drivers/nvmem/Kconfig
-@@ -363,8 +363,7 @@ config NVMEM_SUNXI_SID
- config NVMEM_U_BOOT_ENV
-       tristate "U-Boot environment variables support"
-       depends on OF && MTD
--      select CRC32
--      select GENERIC_NET_UTILS
-+      select NVMEM_LAYOUT_U_BOOT_ENV
-       help
-         U-Boot stores its setup as environment variables. This driver adds
-         support for verifying & exporting such data. It also exposes variables
---- a/drivers/nvmem/layouts/Kconfig
-+++ b/drivers/nvmem/layouts/Kconfig
-@@ -26,6 +26,17 @@ config NVMEM_LAYOUT_ONIE_TLV
-         If unsure, say N.
-+config NVMEM_LAYOUT_U_BOOT_ENV
-+      tristate "U-Boot environment variables layout"
-+      select CRC32
-+      select GENERIC_NET_UTILS
-+      help
-+        U-Boot stores its setup as environment variables. This driver adds
-+        support for verifying & exporting such data. It also exposes variables
-+        as NVMEM cells so they can be referenced by other drivers.
-+
-+        If unsure, say N.
-+
- endmenu
- endif
---- a/drivers/nvmem/layouts/Makefile
-+++ b/drivers/nvmem/layouts/Makefile
-@@ -5,3 +5,4 @@
- obj-$(CONFIG_NVMEM_LAYOUT_SL28_VPD) += sl28vpd.o
- obj-$(CONFIG_NVMEM_LAYOUT_ONIE_TLV) += onie-tlv.o
-+obj-$(CONFIG_NVMEM_LAYOUT_U_BOOT_ENV) += u-boot-env.o
---- /dev/null
-+++ b/drivers/nvmem/layouts/u-boot-env.c
-@@ -0,0 +1,211 @@
-+// SPDX-License-Identifier: GPL-2.0-only
-+/*
-+ * Copyright (C) 2022 - 2023 Rafał Miłecki <[email protected]>
-+ */
-+
-+#include <linux/crc32.h>
-+#include <linux/etherdevice.h>
-+#include <linux/export.h>
-+#include <linux/if_ether.h>
-+#include <linux/nvmem-consumer.h>
-+#include <linux/nvmem-provider.h>
-+#include <linux/of.h>
-+#include <linux/slab.h>
-+
-+#include "u-boot-env.h"
-+
-+struct u_boot_env_image_single {
-+      __le32 crc32;
-+      uint8_t data[];
-+} __packed;
-+
-+struct u_boot_env_image_redundant {
-+      __le32 crc32;
-+      u8 mark;
-+      uint8_t data[];
-+} __packed;
-+
-+struct u_boot_env_image_broadcom {
-+      __le32 magic;
-+      __le32 len;
-+      __le32 crc32;
-+      DECLARE_FLEX_ARRAY(uint8_t, data);
-+} __packed;
-+
-+static int u_boot_env_read_post_process_ethaddr(void *context, const char *id, int index,
-+                                              unsigned int offset, void *buf, size_t bytes)
-+{
-+      u8 mac[ETH_ALEN];
-+
-+      if (bytes != 3 * ETH_ALEN - 1)
-+              return -EINVAL;
-+
-+      if (!mac_pton(buf, mac))
-+              return -EINVAL;
-+
-+      if (index)
-+              eth_addr_add(mac, index);
-+
-+      ether_addr_copy(buf, mac);
-+
-+      return 0;
-+}
-+
-+static int u_boot_env_parse_cells(struct device *dev, struct nvmem_device *nvmem, uint8_t *buf,
-+                                size_t data_offset, size_t data_len)
-+{
-+      char *data = buf + data_offset;
-+      char *var, *value, *eq;
-+
-+      for (var = data;
-+           var < data + data_len && *var;
-+           var = value + strlen(value) + 1) {
-+              struct nvmem_cell_info info = {};
-+
-+              eq = strchr(var, '=');
-+              if (!eq)
-+                      break;
-+              *eq = '\0';
-+              value = eq + 1;
-+
-+              info.name = devm_kstrdup(dev, var, GFP_KERNEL);
-+              if (!info.name)
-+                      return -ENOMEM;
-+              info.offset = data_offset + value - data;
-+              info.bytes = strlen(value);
-+              info.np = of_get_child_by_name(dev->of_node, info.name);
-+              if (!strcmp(var, "ethaddr")) {
-+                      info.raw_len = strlen(value);
-+                      info.bytes = ETH_ALEN;
-+                      info.read_post_process = u_boot_env_read_post_process_ethaddr;
-+              }
-+
-+              nvmem_add_one_cell(nvmem, &info);
-+      }
-+
-+      return 0;
-+}
-+
-+int u_boot_env_parse(struct device *dev, struct nvmem_device *nvmem,
-+                   enum u_boot_env_format format)
-+{
-+      size_t crc32_data_offset;
-+      size_t crc32_data_len;
-+      size_t crc32_offset;
-+      __le32 *crc32_addr;
-+      size_t data_offset;
-+      size_t data_len;
-+      size_t dev_size;
-+      uint32_t crc32;
-+      uint32_t calc;
-+      uint8_t *buf;
-+      int bytes;
-+      int err;
-+
-+      dev_size = nvmem_dev_size(nvmem);
-+
-+      buf = kzalloc(dev_size, GFP_KERNEL);
-+      if (!buf) {
-+              err = -ENOMEM;
-+              goto err_out;
-+      }
-+
-+      bytes = nvmem_device_read(nvmem, 0, dev_size, buf);
-+      if (bytes < 0) {
-+              err = bytes;
-+              goto err_kfree;
-+      } else if (bytes != dev_size) {
-+              err = -EIO;
-+              goto err_kfree;
-+      }
-+
-+      switch (format) {
-+      case U_BOOT_FORMAT_SINGLE:
-+              crc32_offset = offsetof(struct u_boot_env_image_single, crc32);
-+              crc32_data_offset = offsetof(struct u_boot_env_image_single, data);
-+              data_offset = offsetof(struct u_boot_env_image_single, data);
-+              break;
-+      case U_BOOT_FORMAT_REDUNDANT:
-+              crc32_offset = offsetof(struct u_boot_env_image_redundant, crc32);
-+              crc32_data_offset = offsetof(struct u_boot_env_image_redundant, data);
-+              data_offset = offsetof(struct u_boot_env_image_redundant, data);
-+              break;
-+      case U_BOOT_FORMAT_BROADCOM:
-+              crc32_offset = offsetof(struct u_boot_env_image_broadcom, crc32);
-+              crc32_data_offset = offsetof(struct u_boot_env_image_broadcom, data);
-+              data_offset = offsetof(struct u_boot_env_image_broadcom, data);
-+              break;
-+      }
-+
-+      if (dev_size < data_offset) {
-+              dev_err(dev, "Device too small for u-boot-env\n");
-+              err = -EIO;
-+              goto err_kfree;
-+      }
-+
-+      crc32_addr = (__le32 *)(buf + crc32_offset);
-+      crc32 = le32_to_cpu(*crc32_addr);
-+      crc32_data_len = dev_size - crc32_data_offset;
-+      data_len = dev_size - data_offset;
-+
-+      calc = crc32(~0, buf + crc32_data_offset, crc32_data_len) ^ ~0L;
-+      if (calc != crc32) {
-+              dev_err(dev, "Invalid calculated CRC32: 0x%08x (expected: 0x%08x)\n", calc, crc32);
-+              err = -EINVAL;
-+              goto err_kfree;
-+      }
-+
-+      buf[dev_size - 1] = '\0';
-+      err = u_boot_env_parse_cells(dev, nvmem, buf, data_offset, data_len);
-+
-+err_kfree:
-+      kfree(buf);
-+err_out:
-+      return err;
-+}
-+EXPORT_SYMBOL_GPL(u_boot_env_parse);
-+
-+static int u_boot_env_add_cells(struct nvmem_layout *layout)
-+{
-+      struct device *dev = &layout->dev;
-+      enum u_boot_env_format format;
-+
-+      format = (uintptr_t)device_get_match_data(dev);
-+
-+      return u_boot_env_parse(dev, layout->nvmem, format);
-+}
-+
-+static int u_boot_env_probe(struct nvmem_layout *layout)
-+{
-+      layout->add_cells = u_boot_env_add_cells;
-+
-+      return nvmem_layout_register(layout);
-+}
-+
-+static void u_boot_env_remove(struct nvmem_layout *layout)
-+{
-+      nvmem_layout_unregister(layout);
-+}
-+
-+static const struct of_device_id u_boot_env_of_match_table[] = {
-+      { .compatible = "u-boot,env", .data = (void *)U_BOOT_FORMAT_SINGLE, },
-+      { .compatible = "u-boot,env-redundant-bool", .data = (void *)U_BOOT_FORMAT_REDUNDANT, },
-+      { .compatible = "u-boot,env-redundant-count", .data = (void *)U_BOOT_FORMAT_REDUNDANT, },
-+      { .compatible = "brcm,env", .data = (void *)U_BOOT_FORMAT_BROADCOM, },
-+      {},
-+};
-+
-+static struct nvmem_layout_driver u_boot_env_layout = {
-+      .driver = {
-+              .name = "u-boot-env-layout",
-+              .of_match_table = u_boot_env_of_match_table,
-+      },
-+      .probe = u_boot_env_probe,
-+      .remove = u_boot_env_remove,
-+};
-+module_nvmem_layout_driver(u_boot_env_layout);
-+
-+MODULE_AUTHOR("Rafał Miłecki");
-+MODULE_LICENSE("GPL");
-+MODULE_DEVICE_TABLE(of, u_boot_env_of_match_table);
-+MODULE_DESCRIPTION("NVMEM layout driver for U-Boot environment variables");
---- /dev/null
-+++ b/drivers/nvmem/layouts/u-boot-env.h
-@@ -0,0 +1,15 @@
-+/* SPDX-License-Identifier: GPL-2.0-only */
-+
-+#ifndef _LINUX_NVMEM_LAYOUTS_U_BOOT_ENV_H
-+#define _LINUX_NVMEM_LAYOUTS_U_BOOT_ENV_H
-+
-+enum u_boot_env_format {
-+      U_BOOT_FORMAT_SINGLE,
-+      U_BOOT_FORMAT_REDUNDANT,
-+      U_BOOT_FORMAT_BROADCOM,
-+};
-+
-+int u_boot_env_parse(struct device *dev, struct nvmem_device *nvmem,
-+                   enum u_boot_env_format format);
-+
-+#endif  /* ifndef _LINUX_NVMEM_LAYOUTS_U_BOOT_ENV_H */
---- a/drivers/nvmem/u-boot-env.c
-+++ b/drivers/nvmem/u-boot-env.c
-@@ -3,23 +3,15 @@
-  * Copyright (C) 2022 Rafał Miłecki <[email protected]>
-  */
--#include <linux/crc32.h>
--#include <linux/etherdevice.h>
--#include <linux/if_ether.h>
- #include <linux/mod_devicetable.h>
- #include <linux/module.h>
- #include <linux/mtd/mtd.h>
--#include <linux/nvmem-consumer.h>
- #include <linux/nvmem-provider.h>
- #include <linux/of_device.h>
- #include <linux/platform_device.h>
- #include <linux/slab.h>
--enum u_boot_env_format {
--      U_BOOT_FORMAT_SINGLE,
--      U_BOOT_FORMAT_REDUNDANT,
--      U_BOOT_FORMAT_BROADCOM,
--};
-+#include "layouts/u-boot-env.h"
- struct u_boot_env {
-       struct device *dev;
-@@ -29,24 +21,6 @@ struct u_boot_env {
-       struct mtd_info *mtd;
- };
--struct u_boot_env_image_single {
--      __le32 crc32;
--      uint8_t data[];
--} __packed;
--
--struct u_boot_env_image_redundant {
--      __le32 crc32;
--      u8 mark;
--      uint8_t data[];
--} __packed;
--
--struct u_boot_env_image_broadcom {
--      __le32 magic;
--      __le32 len;
--      __le32 crc32;
--      DECLARE_FLEX_ARRAY(uint8_t, data);
--} __packed;
--
- static int u_boot_env_read(void *context, unsigned int offset, void *val,
-                          size_t bytes)
- {
-@@ -69,141 +43,6 @@ static int u_boot_env_read(void *context
-       return 0;
- }
--static int u_boot_env_read_post_process_ethaddr(void *context, const char *id, int index,
--                                              unsigned int offset, void *buf, size_t bytes)
--{
--      u8 mac[ETH_ALEN];
--
--      if (bytes != 3 * ETH_ALEN - 1)
--              return -EINVAL;
--
--      if (!mac_pton(buf, mac))
--              return -EINVAL;
--
--      if (index)
--              eth_addr_add(mac, index);
--
--      ether_addr_copy(buf, mac);
--
--      return 0;
--}
--
--static int u_boot_env_add_cells(struct u_boot_env *priv, uint8_t *buf,
--                              size_t data_offset, size_t data_len)
--{
--      struct nvmem_device *nvmem = priv->nvmem;
--      struct device *dev = priv->dev;
--      char *data = buf + data_offset;
--      char *var, *value, *eq;
--
--      for (var = data;
--           var < data + data_len && *var;
--           var = value + strlen(value) + 1) {
--              struct nvmem_cell_info info = {};
--
--              eq = strchr(var, '=');
--              if (!eq)
--                      break;
--              *eq = '\0';
--              value = eq + 1;
--
--              info.name = devm_kstrdup(dev, var, GFP_KERNEL);
--              if (!info.name)
--                      return -ENOMEM;
--              info.offset = data_offset + value - data;
--              info.bytes = strlen(value);
--              info.np = of_get_child_by_name(dev->of_node, info.name);
--              if (!strcmp(var, "ethaddr")) {
--                      info.raw_len = strlen(value);
--                      info.bytes = ETH_ALEN;
--                      info.read_post_process = u_boot_env_read_post_process_ethaddr;
--              }
--
--              nvmem_add_one_cell(nvmem, &info);
--      }
--
--      return 0;
--}
--
--static int u_boot_env_parse(struct u_boot_env *priv)
--{
--      struct nvmem_device *nvmem = priv->nvmem;
--      struct device *dev = priv->dev;
--      size_t crc32_data_offset;
--      size_t crc32_data_len;
--      size_t crc32_offset;
--      __le32 *crc32_addr;
--      size_t data_offset;
--      size_t data_len;
--      size_t dev_size;
--      uint32_t crc32;
--      uint32_t calc;
--      uint8_t *buf;
--      int bytes;
--      int err;
--
--      dev_size = nvmem_dev_size(nvmem);
--
--      buf = kzalloc(dev_size, GFP_KERNEL);
--      if (!buf) {
--              err = -ENOMEM;
--              goto err_out;
--      }
--
--      bytes = nvmem_device_read(nvmem, 0, dev_size, buf);
--      if (bytes < 0) {
--              err = bytes;
--              goto err_kfree;
--      } else if (bytes != dev_size) {
--              err = -EIO;
--              goto err_kfree;
--      }
--
--      switch (priv->format) {
--      case U_BOOT_FORMAT_SINGLE:
--              crc32_offset = offsetof(struct u_boot_env_image_single, crc32);
--              crc32_data_offset = offsetof(struct u_boot_env_image_single, data);
--              data_offset = offsetof(struct u_boot_env_image_single, data);
--              break;
--      case U_BOOT_FORMAT_REDUNDANT:
--              crc32_offset = offsetof(struct u_boot_env_image_redundant, crc32);
--              crc32_data_offset = offsetof(struct u_boot_env_image_redundant, data);
--              data_offset = offsetof(struct u_boot_env_image_redundant, data);
--              break;
--      case U_BOOT_FORMAT_BROADCOM:
--              crc32_offset = offsetof(struct u_boot_env_image_broadcom, crc32);
--              crc32_data_offset = offsetof(struct u_boot_env_image_broadcom, data);
--              data_offset = offsetof(struct u_boot_env_image_broadcom, data);
--              break;
--      }
--
--      if (dev_size < data_offset) {
--              dev_err(dev, "Device too small for u-boot-env\n");
--              err = -EIO;
--              goto err_kfree;
--      }
--
--      crc32_addr = (__le32 *)(buf + crc32_offset);
--      crc32 = le32_to_cpu(*crc32_addr);
--      crc32_data_len = dev_size - crc32_data_offset;
--      data_len = dev_size - data_offset;
--
--      calc = crc32(~0, buf + crc32_data_offset, crc32_data_len) ^ ~0L;
--      if (calc != crc32) {
--              dev_err(dev, "Invalid calculated CRC32: 0x%08x (expected: 0x%08x)\n", calc, crc32);
--              err = -EINVAL;
--              goto err_kfree;
--      }
--
--      buf[dev_size - 1] = '\0';
--      err = u_boot_env_add_cells(priv, buf, data_offset, data_len);
--
--err_kfree:
--      kfree(buf);
--err_out:
--      return err;
--}
--
- static int u_boot_env_probe(struct platform_device *pdev)
- {
-       struct nvmem_config config = {
-@@ -235,7 +74,7 @@ static int u_boot_env_probe(struct platf
-       if (IS_ERR(priv->nvmem))
-               return PTR_ERR(priv->nvmem);
--      return u_boot_env_parse(priv);
-+      return u_boot_env_parse(dev, priv->nvmem, priv->format);
- }
- static const struct of_device_id u_boot_env_of_match_table[] = {
diff --git a/target/linux/generic/backport-5.15/860-v5.17-MIPS-ath79-drop-_machine_restart-again.patch b/target/linux/generic/backport-5.15/860-v5.17-MIPS-ath79-drop-_machine_restart-again.patch
deleted file mode 100644 (file)
index e9d692b..0000000
+++ /dev/null
@@ -1,49 +0,0 @@
-From d3115128bdafb62628ab41861a4f06f6d02ac320 Mon Sep 17 00:00:00 2001
-From: Lech Perczak <[email protected]>
-Date: Mon, 10 Jan 2022 23:48:44 +0100
-Subject: MIPS: ath79: drop _machine_restart again
-
-Commit 81424d0ad0d4 ("MIPS: ath79: Use the reset controller to restart
-OF machines") removed setup of _machine_restart on OF machines to use
-reset handler in reset controller driver.
-While removing remnants of non-OF machines in commit 3a77e0d75eed
-("MIPS: ath79: drop machfiles"), this was introduced again, making it
-impossible to use additional restart handlers registered through device
-tree. Drop setting _machine_restart altogether, and ath79_restart
-function, which is no longer used after this.
-
-Fixes: 3a77e0d75eed ("MIPS: ath79: drop machfiles")
-Cc: John Crispin <[email protected]>
-Cc: Florian Fainelli <[email protected]>
-Signed-off-by: Lech Perczak <[email protected]>
-Signed-off-by: Thomas Bogendoerfer <[email protected]>
----
- arch/mips/ath79/setup.c | 10 ----------
- 1 file changed, 10 deletions(-)
-
---- a/arch/mips/ath79/setup.c
-+++ b/arch/mips/ath79/setup.c
-@@ -34,15 +34,6 @@
- static char ath79_sys_type[ATH79_SYS_TYPE_LEN];
--static void ath79_restart(char *command)
--{
--      local_irq_disable();
--      ath79_device_reset_set(AR71XX_RESET_FULL_CHIP);
--      for (;;)
--              if (cpu_wait)
--                      cpu_wait();
--}
--
- static void ath79_halt(void)
- {
-       while (1)
-@@ -234,7 +225,6 @@ void __init plat_mem_setup(void)
-       detect_memory_region(0, ATH79_MEM_SIZE_MIN, ATH79_MEM_SIZE_MAX);
--      _machine_restart = ath79_restart;
-       _machine_halt = ath79_halt;
-       pm_power_off = ath79_halt;
- }
diff --git a/target/linux/generic/backport-5.15/870-v5.18-hwmon-lm70-Add-ti-tmp125-support.patch b/target/linux/generic/backport-5.15/870-v5.18-hwmon-lm70-Add-ti-tmp125-support.patch
deleted file mode 100644 (file)
index fabf177..0000000
+++ /dev/null
@@ -1,71 +0,0 @@
-From 31d8f414e1596ba54a4315418e4c0086fda9e428 Mon Sep 17 00:00:00 2001
-From: Christian Lamparter <[email protected]>
-Date: Fri, 18 Feb 2022 10:06:43 +0100
-Subject: hwmon: (lm70) Add ti,tmp125 support
-
-The TMP125 is a 2 degree Celsius accurate Digital
-Temperature Sensor with a SPI interface.
-
-The temperature register is a 16-bit, read-only register.
-The MSB (Bit 15) is a leading zero and never set. Bits 14
-to 5 are the 1+9 temperature data bits in a two's
-complement format. Bits 4 to 0 are useless copies of
-Bit 5 value and therefore ignored.
-
-Signed-off-by: Christian Lamparter <[email protected]>
-Link: https://lore.kernel.org/r/43b19cbd4e7f51e9509e561b02b5d8d0e7079fac.1645175187.git.chunkeey@gmail.com
-Signed-off-by: Guenter Roeck <[email protected]>
----
---- a/drivers/hwmon/lm70.c
-+++ b/drivers/hwmon/lm70.c
-@@ -34,6 +34,7 @@
- #define LM70_CHIP_LM71                2       /* NS LM71 */
- #define LM70_CHIP_LM74                3       /* NS LM74 */
- #define LM70_CHIP_TMP122      4       /* TI TMP122/TMP124 */
-+#define LM70_CHIP_TMP125      5       /* TI TMP125 */
- struct lm70 {
-       struct spi_device *spi;
-@@ -87,6 +88,12 @@ static ssize_t temp1_input_show(struct d
-        * LM71:
-        * 14 bits of 2's complement data, discard LSB 2 bits,
-        * resolution 0.0312 degrees celsius.
-+       *
-+       * TMP125:
-+       * MSB/D15 is a leading zero. D14 is the sign-bit. This is
-+       * followed by 9 temperature bits (D13..D5) in 2's complement
-+       * data format with a resolution of 0.25 degrees celsius per unit.
-+       * LSB 5 bits (D4..D0) share the same value as D5 and get discarded.
-        */
-       switch (p_lm70->chip) {
-       case LM70_CHIP_LM70:
-@@ -102,6 +109,10 @@ static ssize_t temp1_input_show(struct d
-       case LM70_CHIP_LM71:
-               val = ((int)raw / 4) * 3125 / 100;
-               break;
-+
-+      case LM70_CHIP_TMP125:
-+              val = (sign_extend32(raw, 14) / 32) * 250;
-+              break;
-       }
-       status = sprintf(buf, "%d\n", val); /* millidegrees Celsius */
-@@ -136,6 +147,10 @@ static const struct of_device_id lm70_of
-               .data = (void *) LM70_CHIP_TMP122,
-       },
-       {
-+              .compatible = "ti,tmp125",
-+              .data = (void *) LM70_CHIP_TMP125,
-+      },
-+      {
-               .compatible = "ti,lm71",
-               .data = (void *) LM70_CHIP_LM71,
-       },
-@@ -184,6 +199,7 @@ static const struct spi_device_id lm70_i
-       { "lm70",   LM70_CHIP_LM70 },
-       { "tmp121", LM70_CHIP_TMP121 },
-       { "tmp122", LM70_CHIP_TMP122 },
-+      { "tmp125", LM70_CHIP_TMP125 },
-       { "lm71",   LM70_CHIP_LM71 },
-       { "lm74",   LM70_CHIP_LM74 },
-       { },
diff --git a/target/linux/generic/backport-5.15/880-v5.19-cdc_ether-export-usbnet_cdc_zte_rx_fixup.patch b/target/linux/generic/backport-5.15/880-v5.19-cdc_ether-export-usbnet_cdc_zte_rx_fixup.patch
deleted file mode 100644 (file)
index 39fdb32..0000000
+++ /dev/null
@@ -1,58 +0,0 @@
-From a79a5613e1907e1bf09bb6ba6fd5ff43b66c1afe Mon Sep 17 00:00:00 2001
-From: Lech Perczak <[email protected]>
-Date: Fri, 1 Apr 2022 22:03:55 +0200
-Subject: [PATCH 1/3] cdc_ether: export usbnet_cdc_zte_rx_fixup
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-Commit bfe9b9d2df66 ("cdc_ether: Improve ZTE MF823/831/910 handling")
-introduces a workaround for certain ZTE modems reporting invalid MAC
-addresses over CDC-ECM.
-The same issue was present on their RNDIS interface,which was fixed in
-commit a5a18bdf7453 ("rndis_host: Set valid random MAC on buggy devices").
-
-However, internal modem of ZTE MF286R router, on its RNDIS interface, also
-exhibits a second issue fixed already in CDC-ECM, of the device not
-respecting configured random MAC address. In order to share the fixup for
-this with rndis_host driver, export the workaround function, which will
-be re-used in the following commit in rndis_host.
-
-Cc: Kristian Evensen <[email protected]>
-Cc: Bjørn Mork <[email protected]>
-Cc: Oliver Neukum <[email protected]>
-Signed-off-by: Lech Perczak <[email protected]>
----
- drivers/net/usb/cdc_ether.c | 3 ++-
- include/linux/usb/usbnet.h  | 1 +
- 2 files changed, 3 insertions(+), 1 deletion(-)
-
---- a/drivers/net/usb/cdc_ether.c
-+++ b/drivers/net/usb/cdc_ether.c
-@@ -479,7 +479,7 @@ static int usbnet_cdc_zte_bind(struct us
-  * device MAC address has been updated). Always set MAC address to that of the
-  * device.
-  */
--static int usbnet_cdc_zte_rx_fixup(struct usbnet *dev, struct sk_buff *skb)
-+int usbnet_cdc_zte_rx_fixup(struct usbnet *dev, struct sk_buff *skb)
- {
-       if (skb->len < ETH_HLEN || !(skb->data[0] & 0x02))
-               return 1;
-@@ -489,6 +489,7 @@ static int usbnet_cdc_zte_rx_fixup(struc
-       return 1;
- }
-+EXPORT_SYMBOL_GPL(usbnet_cdc_zte_rx_fixup);
- /* Ensure correct link state
-  *
---- a/include/linux/usb/usbnet.h
-+++ b/include/linux/usb/usbnet.h
-@@ -214,6 +214,7 @@ extern int usbnet_ether_cdc_bind(struct
- extern int usbnet_cdc_bind(struct usbnet *, struct usb_interface *);
- extern void usbnet_cdc_unbind(struct usbnet *, struct usb_interface *);
- extern void usbnet_cdc_status(struct usbnet *, struct urb *);
-+extern int usbnet_cdc_zte_rx_fixup(struct usbnet *dev, struct sk_buff *skb);
- /* CDC and RNDIS support the same host-chosen packet filters for IN transfers */
- #define       DEFAULT_FILTER  (USB_CDC_PACKET_TYPE_BROADCAST \
diff --git a/target/linux/generic/backport-5.15/881-v5.19-rndis_host-enable-the-bogus-MAC-fixup-for-ZTE-device.patch b/target/linux/generic/backport-5.15/881-v5.19-rndis_host-enable-the-bogus-MAC-fixup-for-ZTE-device.patch
deleted file mode 100644 (file)
index 71a6df8..0000000
+++ /dev/null
@@ -1,118 +0,0 @@
-From aa8aff10e969aca0cb64f5e54ff7489355582667 Mon Sep 17 00:00:00 2001
-From: Lech Perczak <[email protected]>
-Date: Fri, 1 Apr 2022 22:04:01 +0200
-Subject: [PATCH 2/3] rndis_host: enable the bogus MAC fixup for ZTE devices
- from cdc_ether
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-Certain ZTE modems, namely: MF823. MF831, MF910, built-in modem from
-MF286R, expose both CDC-ECM and RNDIS network interfaces.
-They have a trait of ignoring the locally-administered MAC address
-configured on the interface both in CDC-ECM and RNDIS part,
-and this leads to dropping of incoming traffic by the host.
-However, the workaround was only present in CDC-ECM, and MF286R
-explicitly requires it in RNDIS mode.
-
-Re-use the workaround in rndis_host as well, to fix operation of MF286R
-module, some versions of which expose only the RNDIS interface. Do so by
-introducing new flag, RNDIS_DRIVER_DATA_DST_MAC_FIXUP, and testing for it
-in rndis_rx_fixup. This is required, as RNDIS uses frame batching, and all
-of the packets inside the batch need the fixup. This might introduce a
-performance penalty, because test is done for every returned Ethernet
-frame.
-
-Apply the workaround to both "flavors" of RNDIS interfaces, as older ZTE
-modems, like MF823 found in the wild, report the USB_CLASS_COMM class
-interfaces, while MF286R reports USB_CLASS_WIRELESS_CONTROLLER.
-
-Suggested-by: Bjørn Mork <[email protected]>
-Cc: Kristian Evensen <[email protected]>
-Cc: Oliver Neukum <[email protected]>
-Signed-off-by: Lech Perczak <[email protected]>
----
- drivers/net/usb/rndis_host.c   | 32 ++++++++++++++++++++++++++++++++
- include/linux/usb/rndis_host.h |  1 +
- 2 files changed, 33 insertions(+)
-
---- a/drivers/net/usb/rndis_host.c
-+++ b/drivers/net/usb/rndis_host.c
-@@ -486,10 +486,14 @@ EXPORT_SYMBOL_GPL(rndis_unbind);
-  */
- int rndis_rx_fixup(struct usbnet *dev, struct sk_buff *skb)
- {
-+      bool dst_mac_fixup;
-+
-       /* This check is no longer done by usbnet */
-       if (skb->len < dev->net->hard_header_len)
-               return 0;
-+      dst_mac_fixup = !!(dev->driver_info->data & RNDIS_DRIVER_DATA_DST_MAC_FIXUP);
-+
-       /* peripheral may have batched packets to us... */
-       while (likely(skb->len)) {
-               struct rndis_data_hdr   *hdr = (void *)skb->data;
-@@ -524,10 +528,17 @@ int rndis_rx_fixup(struct usbnet *dev, s
-                       break;
-               skb_pull(skb, msg_len - sizeof *hdr);
-               skb_trim(skb2, data_len);
-+
-+              if (unlikely(dst_mac_fixup))
-+                      usbnet_cdc_zte_rx_fixup(dev, skb2);
-+
-               usbnet_skb_return(dev, skb2);
-       }
-       /* caller will usbnet_skb_return the remaining packet */
-+      if (unlikely(dst_mac_fixup))
-+              usbnet_cdc_zte_rx_fixup(dev, skb);
-+
-       return 1;
- }
- EXPORT_SYMBOL_GPL(rndis_rx_fixup);
-@@ -601,6 +612,17 @@ static const struct driver_info   rndis_po
-       .tx_fixup =     rndis_tx_fixup,
- };
-+static const struct driver_info       zte_rndis_info = {
-+      .description =  "ZTE RNDIS device",
-+      .flags =        FLAG_ETHER | FLAG_POINTTOPOINT | FLAG_FRAMING_RN | FLAG_NO_SETINT,
-+      .data =         RNDIS_DRIVER_DATA_DST_MAC_FIXUP,
-+      .bind =         rndis_bind,
-+      .unbind =       rndis_unbind,
-+      .status =       rndis_status,
-+      .rx_fixup =     rndis_rx_fixup,
-+      .tx_fixup =     rndis_tx_fixup,
-+};
-+
- /*-------------------------------------------------------------------------*/
- static const struct usb_device_id     products [] = {
-@@ -615,6 +637,16 @@ static const struct usb_device_id produc
-                                     USB_CLASS_COMM, 2 /* ACM */, 0x0ff),
-       .driver_info = (unsigned long)&rndis_info,
- }, {
-+      /* ZTE WWAN modules */
-+      USB_VENDOR_AND_INTERFACE_INFO(0x19d2,
-+                                    USB_CLASS_WIRELESS_CONTROLLER, 1, 3),
-+      .driver_info = (unsigned long)&zte_rndis_info,
-+}, {
-+      /* ZTE WWAN modules, ACM flavour */
-+      USB_VENDOR_AND_INTERFACE_INFO(0x19d2,
-+                                    USB_CLASS_COMM, 2 /* ACM */, 0x0ff),
-+      .driver_info = (unsigned long)&zte_rndis_info,
-+}, {
-       /* RNDIS is MSFT's un-official variant of CDC ACM */
-       USB_INTERFACE_INFO(USB_CLASS_COMM, 2 /* ACM */, 0x0ff),
-       .driver_info = (unsigned long) &rndis_info,
---- a/include/linux/usb/rndis_host.h
-+++ b/include/linux/usb/rndis_host.h
-@@ -197,6 +197,7 @@ struct rndis_keepalive_c { /* IN (option
- /* Flags for driver_info::data */
- #define RNDIS_DRIVER_DATA_POLL_STATUS 1       /* poll status before control */
-+#define RNDIS_DRIVER_DATA_DST_MAC_FIXUP       2       /* device ignores configured MAC address */
- extern void rndis_status(struct usbnet *dev, struct urb *urb);
- extern int
diff --git a/target/linux/generic/backport-5.15/882-v5.19-rndis_host-limit-scope-of-bogus-MAC-address-detectio.patch b/target/linux/generic/backport-5.15/882-v5.19-rndis_host-limit-scope-of-bogus-MAC-address-detectio.patch
deleted file mode 100644 (file)
index bdd812c..0000000
+++ /dev/null
@@ -1,63 +0,0 @@
-From 9bfb4bcda7ba32d73ea322ea56a8ebe32e9247f6 Mon Sep 17 00:00:00 2001
-From: Lech Perczak <[email protected]>
-Date: Sat, 2 Apr 2022 02:19:57 +0200
-Subject: [PATCH 3/3] rndis_host: limit scope of bogus MAC address detection to
- ZTE devices
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-Reporting of bogus MAC addresses and ignoring configuration of new
-destination address wasn't observed outside of a range of ZTE devices,
-among which this seems to be the common bug. Align rndis_host driver
-with implementation found in cdc_ether, which also limits this workaround
-to ZTE devices.
-
-Suggested-by: Bjørn Mork <[email protected]>
-Cc: Kristian Evensen <[email protected]>
-Cc: Oliver Neukum <[email protected]>
-Signed-off-by: Lech Perczak <[email protected]>
----
- drivers/net/usb/rndis_host.c | 17 ++++++++++++-----
- 1 file changed, 12 insertions(+), 5 deletions(-)
-
---- a/drivers/net/usb/rndis_host.c
-+++ b/drivers/net/usb/rndis_host.c
-@@ -419,10 +419,7 @@ generic_rndis_bind(struct usbnet *dev, s
-               goto halt_fail_and_release;
-       }
--      if (bp[0] & 0x02)
--              eth_hw_addr_random(net);
--      else
--              ether_addr_copy(net->dev_addr, bp);
-+      ether_addr_copy(net->dev_addr, bp);
-       /* set a nonzero filter to enable data transfers */
-       memset(u.set, 0, sizeof *u.set);
-@@ -464,6 +461,16 @@ static int rndis_bind(struct usbnet *dev
-       return generic_rndis_bind(dev, intf, FLAG_RNDIS_PHYM_NOT_WIRELESS);
- }
-+static int zte_rndis_bind(struct usbnet *dev, struct usb_interface *intf)
-+{
-+      int status = rndis_bind(dev, intf);
-+
-+      if (!status && (dev->net->dev_addr[0] & 0x02))
-+              eth_hw_addr_random(dev->net);
-+
-+      return status;
-+}
-+
- void rndis_unbind(struct usbnet *dev, struct usb_interface *intf)
- {
-       struct rndis_halt       *halt;
-@@ -616,7 +623,7 @@ static const struct driver_info    zte_rndi
-       .description =  "ZTE RNDIS device",
-       .flags =        FLAG_ETHER | FLAG_POINTTOPOINT | FLAG_FRAMING_RN | FLAG_NO_SETINT,
-       .data =         RNDIS_DRIVER_DATA_DST_MAC_FIXUP,
--      .bind =         rndis_bind,
-+      .bind =         zte_rndis_bind,
-       .unbind =       rndis_unbind,
-       .status =       rndis_status,
-       .rx_fixup =     rndis_rx_fixup,
diff --git a/target/linux/generic/backport-5.15/890-v6.2-mtd-spinand-winbond-fix-flash-detection.patch b/target/linux/generic/backport-5.15/890-v6.2-mtd-spinand-winbond-fix-flash-detection.patch
deleted file mode 100644 (file)
index 38fbc3a..0000000
+++ /dev/null
@@ -1,40 +0,0 @@
-From dbf70fc204d2fbb0d8ad8f42038a60846502efda Mon Sep 17 00:00:00 2001
-From: Mikhail Kshevetskiy <[email protected]>
-Date: Mon, 10 Oct 2022 13:51:09 +0300
-Subject: [PATCH] mtd: spinand: winbond: fix flash identification
-
-Winbond uses 3 bytes to identify flash: vendor_id, dev_id_0, dev_id_1,
-but current driver uses only first 2 bytes of it for devices
-identification. As result Winbond W25N02KV flash (id_bytes: EF, AA, 22)
-is identified as W25N01GV (id_bytes: EF, AA, 21).
-
-Fix this by adding missed identification bytes.
-
-Signed-off-by: Mikhail Kshevetskiy <[email protected]>
-Reviewed-by: Frieder Schrempf <[email protected]>
-Signed-off-by: Miquel Raynal <[email protected]>
-Link: https://lore.kernel.org/linux-mtd/[email protected]
----
- drivers/mtd/nand/spi/winbond.c | 4 ++--
- 1 file changed, 2 insertions(+), 2 deletions(-)
-
---- a/drivers/mtd/nand/spi/winbond.c
-+++ b/drivers/mtd/nand/spi/winbond.c
-@@ -76,7 +76,7 @@ static int w25m02gv_select_target(struct
- static const struct spinand_info winbond_spinand_table[] = {
-       SPINAND_INFO("W25M02GV",
--                   SPINAND_ID(SPINAND_READID_METHOD_OPCODE_DUMMY, 0xab),
-+                   SPINAND_ID(SPINAND_READID_METHOD_OPCODE_DUMMY, 0xab, 0x21),
-                    NAND_MEMORG(1, 2048, 64, 64, 1024, 20, 1, 1, 2),
-                    NAND_ECCREQ(1, 512),
-                    SPINAND_INFO_OP_VARIANTS(&read_cache_variants,
-@@ -86,7 +86,7 @@ static const struct spinand_info winbond
-                    SPINAND_ECCINFO(&w25m02gv_ooblayout, NULL),
-                    SPINAND_SELECT_TARGET(w25m02gv_select_target)),
-       SPINAND_INFO("W25N01GV",
--                   SPINAND_ID(SPINAND_READID_METHOD_OPCODE_DUMMY, 0xaa),
-+                   SPINAND_ID(SPINAND_READID_METHOD_OPCODE_DUMMY, 0xaa, 0x21),
-                    NAND_MEMORG(1, 2048, 64, 64, 1024, 20, 1, 1, 1),
-                    NAND_ECCREQ(1, 512),
-                    SPINAND_INFO_OP_VARIANTS(&read_cache_variants,
diff --git a/target/linux/generic/backport-5.15/891-v6.2-mtd-spinand-winbond-add-W25N02KV.patch b/target/linux/generic/backport-5.15/891-v6.2-mtd-spinand-winbond-add-W25N02KV.patch
deleted file mode 100644 (file)
index d75a1ac..0000000
+++ /dev/null
@@ -1,106 +0,0 @@
-From 6154c7a583483d7b69f53bea868efdc369edd563 Mon Sep 17 00:00:00 2001
-From: Mikhail Kshevetskiy <[email protected]>
-Date: Mon, 10 Oct 2022 13:51:10 +0300
-Subject: [PATCH] mtd: spinand: winbond: add Winbond W25N02KV flash support
-
-Add support of Winbond W25N02KV flash
-
-Signed-off-by: Mikhail Kshevetskiy <[email protected]>
-Reviewed-by: Frieder Schrempf <[email protected]>
-Signed-off-by: Miquel Raynal <[email protected]>
-Link: https://lore.kernel.org/linux-mtd/[email protected]
----
- drivers/mtd/nand/spi/winbond.c | 75 ++++++++++++++++++++++++++++++++++
- 1 file changed, 75 insertions(+)
-
---- a/drivers/mtd/nand/spi/winbond.c
-+++ b/drivers/mtd/nand/spi/winbond.c
-@@ -74,6 +74,72 @@ static int w25m02gv_select_target(struct
-       return spi_mem_exec_op(spinand->spimem, &op);
- }
-+static int w25n02kv_ooblayout_ecc(struct mtd_info *mtd, int section,
-+                                struct mtd_oob_region *region)
-+{
-+      if (section > 3)
-+              return -ERANGE;
-+
-+      region->offset = 64 + (16 * section);
-+      region->length = 13;
-+
-+      return 0;
-+}
-+
-+static int w25n02kv_ooblayout_free(struct mtd_info *mtd, int section,
-+                                 struct mtd_oob_region *region)
-+{
-+      if (section > 3)
-+              return -ERANGE;
-+
-+      region->offset = (16 * section) + 2;
-+      region->length = 14;
-+
-+      return 0;
-+}
-+
-+static const struct mtd_ooblayout_ops w25n02kv_ooblayout = {
-+      .ecc = w25n02kv_ooblayout_ecc,
-+      .free = w25n02kv_ooblayout_free,
-+};
-+
-+static int w25n02kv_ecc_get_status(struct spinand_device *spinand,
-+                                 u8 status)
-+{
-+      struct nand_device *nand = spinand_to_nand(spinand);
-+      u8 mbf = 0;
-+      struct spi_mem_op op = SPINAND_GET_FEATURE_OP(0x30, &mbf);
-+
-+      switch (status & STATUS_ECC_MASK) {
-+      case STATUS_ECC_NO_BITFLIPS:
-+              return 0;
-+
-+      case STATUS_ECC_UNCOR_ERROR:
-+              return -EBADMSG;
-+
-+      case STATUS_ECC_HAS_BITFLIPS:
-+              /*
-+               * Let's try to retrieve the real maximum number of bitflips
-+               * in order to avoid forcing the wear-leveling layer to move
-+               * data around if it's not necessary.
-+               */
-+              if (spi_mem_exec_op(spinand->spimem, &op))
-+                      return nanddev_get_ecc_conf(nand)->strength;
-+
-+              mbf >>= 4;
-+
-+              if (WARN_ON(mbf > nanddev_get_ecc_conf(nand)->strength || !mbf))
-+                      return nanddev_get_ecc_conf(nand)->strength;
-+
-+              return mbf;
-+
-+      default:
-+              break;
-+      }
-+
-+      return -EINVAL;
-+}
-+
- static const struct spinand_info winbond_spinand_table[] = {
-       SPINAND_INFO("W25M02GV",
-                    SPINAND_ID(SPINAND_READID_METHOD_OPCODE_DUMMY, 0xab, 0x21),
-@@ -94,6 +160,15 @@ static const struct spinand_info winbond
-                                             &update_cache_variants),
-                    0,
-                    SPINAND_ECCINFO(&w25m02gv_ooblayout, NULL)),
-+      SPINAND_INFO("W25N02KV",
-+                   SPINAND_ID(SPINAND_READID_METHOD_OPCODE_DUMMY, 0xaa, 0x22),
-+                   NAND_MEMORG(1, 2048, 128, 64, 2048, 40, 1, 1, 1),
-+                   NAND_ECCREQ(8, 512),
-+                   SPINAND_INFO_OP_VARIANTS(&read_cache_variants,
-+                                            &write_cache_variants,
-+                                            &update_cache_variants),
-+                   0,
-+                   SPINAND_ECCINFO(&w25n02kv_ooblayout, w25n02kv_ecc_get_status)),
- };
- static int winbond_spinand_init(struct spinand_device *spinand)
diff --git a/target/linux/generic/backport-5.15/892-v6.5-mtd-spinand-winbond-Fix-ecc_get_status.patch b/target/linux/generic/backport-5.15/892-v6.5-mtd-spinand-winbond-Fix-ecc_get_status.patch
deleted file mode 100644 (file)
index 2f408f5..0000000
+++ /dev/null
@@ -1,49 +0,0 @@
-From f5a05060670a4d8d6523afc7963eb559c2e3615f Mon Sep 17 00:00:00 2001
-From: Olivier Maignial <[email protected]>
-Date: Fri, 23 Jun 2023 17:33:37 +0200
-Subject: [PATCH] mtd: spinand: winbond: Fix ecc_get_status
-
-Reading ECC status is failing.
-
-w25n02kv_ecc_get_status() is using on-stack buffer for
-SPINAND_GET_FEATURE_OP() output. It is not suitable for
-DMA needs of spi-mem.
-
-Fix this by using the spi-mem operations dedicated buffer
-spinand->scratchbuf.
-
-See
-spinand->scratchbuf:
-https://git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git/tree/include/linux/mtd/spinand.h?h=v6.3#n418
-spi_mem_check_op():
-https://git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git/tree/drivers/spi/spi-mem.c?h=v6.3#n199
-
-Fixes: 6154c7a58348 ("mtd: spinand: winbond: add Winbond W25N02KV flash support")
-Signed-off-by: Olivier Maignial <[email protected]>
-Signed-off-by: Miquel Raynal <[email protected]>
-Link: https://lore.kernel.org/linux-mtd/DB4P250MB1032EDB9E36B764A33769039FE23A@DB4P250MB1032.EURP250.PROD.OUTLOOK.COM
----
- drivers/mtd/nand/spi/winbond.c | 4 ++--
- 1 file changed, 2 insertions(+), 2 deletions(-)
-
---- a/drivers/mtd/nand/spi/winbond.c
-+++ b/drivers/mtd/nand/spi/winbond.c
-@@ -108,7 +108,7 @@ static int w25n02kv_ecc_get_status(struc
- {
-       struct nand_device *nand = spinand_to_nand(spinand);
-       u8 mbf = 0;
--      struct spi_mem_op op = SPINAND_GET_FEATURE_OP(0x30, &mbf);
-+      struct spi_mem_op op = SPINAND_GET_FEATURE_OP(0x30, spinand->scratchbuf);
-       switch (status & STATUS_ECC_MASK) {
-       case STATUS_ECC_NO_BITFLIPS:
-@@ -126,7 +126,7 @@ static int w25n02kv_ecc_get_status(struc
-               if (spi_mem_exec_op(spinand->spimem, &op))
-                       return nanddev_get_ecc_conf(nand)->strength;
--              mbf >>= 4;
-+              mbf = *(spinand->scratchbuf) >> 4;
-               if (WARN_ON(mbf > nanddev_get_ecc_conf(nand)->strength || !mbf))
-                       return nanddev_get_ecc_conf(nand)->strength;
diff --git a/target/linux/generic/backport-5.15/893-v6.5-01-net-dsa-mv88e6xxx-pass-directly-chip-structure-to-mv.patch b/target/linux/generic/backport-5.15/893-v6.5-01-net-dsa-mv88e6xxx-pass-directly-chip-structure-to-mv.patch
deleted file mode 100644 (file)
index 177a8ce..0000000
+++ /dev/null
@@ -1,46 +0,0 @@
-From 19f291d8a65cd19e7595006c7872cd95aa6f9e93 Mon Sep 17 00:00:00 2001
-From: =?UTF-8?q?Alexis=20Lothor=C3=A9?= <[email protected]>
-Date: Fri, 4 Aug 2023 19:13:10 +0200
-Subject: [PATCH 893/898] net: dsa: mv88e6xxx: pass directly chip structure to
- mv88e6xxx_phy_is_internal
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-Since this function is a simple helper, we do not need to pass a full
-dsa_switch structure, we can directly pass the mv88e6xxx_chip structure.
-Doing so will allow to share this function with any other function
-not manipulating dsa_switch structure but needing info about number of
-internal phys
-
-Signed-off-by: Alexis Lothoré <[email protected]>
-Reviewed-by: Russell King (Oracle) <[email protected]>
-Reviewed-by: Florian Fainelli <[email protected]>
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- drivers/net/dsa/mv88e6xxx/chip.c | 6 ++----
- 1 file changed, 2 insertions(+), 4 deletions(-)
-
---- a/drivers/net/dsa/mv88e6xxx/chip.c
-+++ b/drivers/net/dsa/mv88e6xxx/chip.c
-@@ -459,10 +459,8 @@ restore_link:
-       return err;
- }
--static int mv88e6xxx_phy_is_internal(struct dsa_switch *ds, int port)
-+static int mv88e6xxx_phy_is_internal(struct mv88e6xxx_chip *chip, int port)
- {
--      struct mv88e6xxx_chip *chip = ds->priv;
--
-       return port < chip->info->num_internal_phys;
- }
-@@ -704,7 +702,7 @@ static void mv88e6xxx_mac_config(struct
-       mv88e6xxx_reg_lock(chip);
--      if (mode != MLO_AN_PHY || !mv88e6xxx_phy_is_internal(ds, port)) {
-+      if (mode != MLO_AN_PHY || !mv88e6xxx_phy_is_internal(chip, port)) {
-               /* In inband mode, the link may come up at any time while the
-                * link is not forced down. Force the link down while we
-                * reconfigure the interface mode.
diff --git a/target/linux/generic/backport-5.15/893-v6.5-02-net-dsa-mv88e6xxx-use-mv88e6xxx_phy_is_internal-in-m.patch b/target/linux/generic/backport-5.15/893-v6.5-02-net-dsa-mv88e6xxx-use-mv88e6xxx_phy_is_internal-in-m.patch
deleted file mode 100644 (file)
index 02cafa3..0000000
+++ /dev/null
@@ -1,31 +0,0 @@
-From 03a50b4f81d9e8bcf86165d6b2ac9376d02e5df9 Mon Sep 17 00:00:00 2001
-From: =?UTF-8?q?Alexis=20Lothor=C3=A9?= <[email protected]>
-Date: Mon, 29 May 2023 10:02:42 +0200
-Subject: [PATCH 894/898] net: dsa: mv88e6xxx: use mv88e6xxx_phy_is_internal in
- mv88e6xxx_port_ppu_updates
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-Make sure to use existing helper to get internal PHYs count instead of
-redoing it manually
-
-Signed-off-by: Alexis Lothoré <[email protected]>
-Reviewed-by: Russell King (Oracle) <[email protected]>
-Reviewed-by: Florian Fainelli <[email protected]>
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- drivers/net/dsa/mv88e6xxx/chip.c | 2 +-
- 1 file changed, 1 insertion(+), 1 deletion(-)
-
---- a/drivers/net/dsa/mv88e6xxx/chip.c
-+++ b/drivers/net/dsa/mv88e6xxx/chip.c
-@@ -473,7 +473,7 @@ static int mv88e6xxx_port_ppu_updates(st
-        * report whether the port is internal.
-        */
-       if (chip->info->family == MV88E6XXX_FAMILY_6250)
--              return port < chip->info->num_internal_phys;
-+              return mv88e6xxx_phy_is_internal(chip, port);
-       err = mv88e6xxx_port_read(chip, port, MV88E6XXX_PORT_STS, &reg);
-       if (err) {
diff --git a/target/linux/generic/backport-5.15/893-v6.5-03-net-dsa-mv88e6xxx-add-field-to-specify-internal-phys.patch b/target/linux/generic/backport-5.15/893-v6.5-03-net-dsa-mv88e6xxx-add-field-to-specify-internal-phys.patch
deleted file mode 100644 (file)
index 239620b..0000000
+++ /dev/null
@@ -1,69 +0,0 @@
-From 07120894b24cc3cf2318925baeaaf0893e3312e4 Mon Sep 17 00:00:00 2001
-From: =?UTF-8?q?Alexis=20Lothor=C3=A9?= <[email protected]>
-Date: Mon, 29 May 2023 10:02:43 +0200
-Subject: [PATCH 895/898] net: dsa: mv88e6xxx: add field to specify internal
- phys layout
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-mv88e6xxx currently assumes that switch equipped with internal phys have
-those phys mapped contiguously starting from port 0 (see
-mv88e6xxx_phy_is_internal). However, some switches have internal PHYs but
-NOT starting from port 0. For example 88e6393X, 88E6193X and 88E6191X have
-integrated PHYs available on ports 1 to 8
-To properly support this offset, add a new field to allow specifying an
-internal PHYs layout. If field is not set, default layout is assumed (start
-at port 0)
-
-Signed-off-by: Alexis Lothoré <[email protected]>
-Reviewed-by: Andrew Lunn <[email protected]>
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- drivers/net/dsa/mv88e6xxx/chip.c    | 4 +++-
- drivers/net/dsa/mv88e6xxx/chip.h    | 5 +++++
- drivers/net/dsa/mv88e6xxx/global2.c | 5 ++++-
- 3 files changed, 12 insertions(+), 2 deletions(-)
-
---- a/drivers/net/dsa/mv88e6xxx/chip.c
-+++ b/drivers/net/dsa/mv88e6xxx/chip.c
-@@ -461,7 +461,9 @@ restore_link:
- static int mv88e6xxx_phy_is_internal(struct mv88e6xxx_chip *chip, int port)
- {
--      return port < chip->info->num_internal_phys;
-+      return port >= chip->info->internal_phys_offset &&
-+              port < chip->info->num_internal_phys +
-+                      chip->info->internal_phys_offset;
- }
- static int mv88e6xxx_port_ppu_updates(struct mv88e6xxx_chip *chip, int port)
---- a/drivers/net/dsa/mv88e6xxx/chip.h
-+++ b/drivers/net/dsa/mv88e6xxx/chip.h
-@@ -165,6 +165,11 @@ struct mv88e6xxx_info {
-       /* Supports PTP */
-       bool ptp_support;
-+
-+      /* Internal PHY start index. 0 means that internal PHYs range starts at
-+       * port 0, 1 means internal PHYs range starts at port 1, etc
-+       */
-+      unsigned int internal_phys_offset;
- };
- struct mv88e6xxx_atu_entry {
---- a/drivers/net/dsa/mv88e6xxx/global2.c
-+++ b/drivers/net/dsa/mv88e6xxx/global2.c
-@@ -1185,8 +1185,11 @@ int mv88e6xxx_g2_irq_mdio_setup(struct m
-                               struct mii_bus *bus)
- {
-       int phy, irq, err, err_phy;
-+      int phy_start = chip->info->internal_phys_offset;
-+      int phy_end = chip->info->internal_phys_offset +
-+                    chip->info->num_internal_phys;
--      for (phy = 0; phy < chip->info->num_internal_phys; phy++) {
-+      for (phy = phy_start; phy < phy_end; phy++) {
-               irq = irq_find_mapping(chip->g2_irq.domain, phy);
-               if (irq < 0) {
-                       err = irq;
diff --git a/target/linux/generic/backport-5.15/893-v6.5-04-net-dsa-mv88e6xxx-fix-88E6393X-family-internal-phys-.patch b/target/linux/generic/backport-5.15/893-v6.5-04-net-dsa-mv88e6xxx-fix-88E6393X-family-internal-phys-.patch
deleted file mode 100644 (file)
index d0a2a98..0000000
+++ /dev/null
@@ -1,52 +0,0 @@
-From 492b06747f544c19b5ffe531a24b67858764c50e Mon Sep 17 00:00:00 2001
-From: =?UTF-8?q?Alexis=20Lothor=C3=A9?= <[email protected]>
-Date: Mon, 29 May 2023 10:02:44 +0200
-Subject: [PATCH 896/898] net: dsa: mv88e6xxx: fix 88E6393X family internal
- phys layout
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-88E6393X/88E6193X/88E6191X switches have in fact 8 internal PHYs, but those
-are not present starting at port 0: supported ports go from 1 to 8
-
-Signed-off-by: Alexis Lothoré <[email protected]>
-Reviewed-by: Andrew Lunn <[email protected]>
-Reviewed-by: Florian Fainelli <[email protected]>
-Signed-off-by: Jakub Kicinski <[email protected]>
----
- drivers/net/dsa/mv88e6xxx/chip.c | 9 ++++++---
- 1 file changed, 6 insertions(+), 3 deletions(-)
-
---- a/drivers/net/dsa/mv88e6xxx/chip.c
-+++ b/drivers/net/dsa/mv88e6xxx/chip.c
-@@ -5414,7 +5414,8 @@ static const struct mv88e6xxx_info mv88e
-               .name = "Marvell 88E6191X",
-               .num_databases = 4096,
-               .num_ports = 11,        /* 10 + Z80 */
--              .num_internal_phys = 9,
-+              .num_internal_phys = 8,
-+              .internal_phys_offset = 1,
-               .max_vid = 8191,
-               .port_base_addr = 0x0,
-               .phy_base_addr = 0x0,
-@@ -5436,7 +5437,8 @@ static const struct mv88e6xxx_info mv88e
-               .name = "Marvell 88E6193X",
-               .num_databases = 4096,
-               .num_ports = 11,        /* 10 + Z80 */
--              .num_internal_phys = 9,
-+              .num_internal_phys = 8,
-+              .internal_phys_offset = 1,
-               .max_vid = 8191,
-               .port_base_addr = 0x0,
-               .phy_base_addr = 0x0,
-@@ -5746,7 +5748,8 @@ static const struct mv88e6xxx_info mv88e
-               .name = "Marvell 88E6393X",
-               .num_databases = 4096,
-               .num_ports = 11,        /* 10 + Z80 */
--              .num_internal_phys = 9,
-+              .num_internal_phys = 8,
-+              .internal_phys_offset = 1,
-               .max_vid = 8191,
-               .port_base_addr = 0x0,
-               .phy_base_addr = 0x0,
diff --git a/target/linux/generic/backport-5.15/893-v6.5-05-net-dsa-mv88e6xxx-pass-mv88e6xxx_chip-structure-to-p.patch b/target/linux/generic/backport-5.15/893-v6.5-05-net-dsa-mv88e6xxx-pass-mv88e6xxx_chip-structure-to-p.patch
deleted file mode 100644 (file)
index 9122960..0000000
+++ /dev/null
@@ -1,113 +0,0 @@
-From 68690045f8e220826517c0d6f9388ffc1faa57ea Mon Sep 17 00:00:00 2001
-From: =?UTF-8?q?Alexis=20Lothor=C3=A9?= <[email protected]>
-Date: Mon, 29 May 2023 10:02:45 +0200
-Subject: [PATCH 897/898] net: dsa: mv88e6xxx: pass mv88e6xxx_chip structure to
- port_max_speed_mode
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-Some switches families have minor differences on supported link speed for
-ports. Instead of redefining a new port_max_speed_mode for each different
-configuration, allow to pass mv88e6xxx_chip structure to allow
-differentiating those chips by known chip id
-
-Signed-off-by: Alexis Lothoré <[email protected]>
-Reviewed-by: Florian Fainelli <[email protected]>
-Signed-off-by: Jakub Kicinski <[email protected]>
-Update one more instance of port_max_speed_mode that 5.15 has.
-[Robert Marko]
-Signed-off-by: Robert Marko <[email protected]>
----
- drivers/net/dsa/mv88e6xxx/chip.c |  2 +-
- drivers/net/dsa/mv88e6xxx/chip.h |  3 ++-
- drivers/net/dsa/mv88e6xxx/port.c | 12 ++++++++----
- drivers/net/dsa/mv88e6xxx/port.h | 12 ++++++++----
- 4 files changed, 19 insertions(+), 10 deletions(-)
-
---- a/drivers/net/dsa/mv88e6xxx/chip.c
-+++ b/drivers/net/dsa/mv88e6xxx/chip.c
-@@ -443,7 +443,7 @@ static int mv88e6xxx_port_setup_mac(stru
-       }
-       if (speed == SPEED_MAX && chip->info->ops->port_max_speed_mode)
--              mode = chip->info->ops->port_max_speed_mode(port);
-+              mode = chip->info->ops->port_max_speed_mode(chip, port);
-       if (chip->info->ops->port_set_pause) {
-               err = chip->info->ops->port_set_pause(chip, port, pause);
---- a/drivers/net/dsa/mv88e6xxx/chip.h
-+++ b/drivers/net/dsa/mv88e6xxx/chip.h
-@@ -491,7 +491,8 @@ struct mv88e6xxx_ops {
-                                    int speed, int duplex);
-       /* What interface mode should be used for maximum speed? */
--      phy_interface_t (*port_max_speed_mode)(int port);
-+      phy_interface_t (*port_max_speed_mode)(struct mv88e6xxx_chip *chip,
-+                                             int port);
-       int (*port_tag_remap)(struct mv88e6xxx_chip *chip, int port);
---- a/drivers/net/dsa/mv88e6xxx/port.c
-+++ b/drivers/net/dsa/mv88e6xxx/port.c
-@@ -357,7 +357,8 @@ int mv88e6341_port_set_speed_duplex(stru
-                                              duplex);
- }
--phy_interface_t mv88e6341_port_max_speed_mode(int port)
-+phy_interface_t mv88e6341_port_max_speed_mode(struct mv88e6xxx_chip *chip,
-+                                            int port)
- {
-       if (port == 5)
-               return PHY_INTERFACE_MODE_2500BASEX;
-@@ -402,7 +403,8 @@ int mv88e6390_port_set_speed_duplex(stru
-                                              duplex);
- }
--phy_interface_t mv88e6390_port_max_speed_mode(int port)
-+phy_interface_t mv88e6390_port_max_speed_mode(struct mv88e6xxx_chip *chip,
-+                                            int port)
- {
-       if (port == 9 || port == 10)
-               return PHY_INTERFACE_MODE_2500BASEX;
-@@ -427,7 +429,8 @@ int mv88e6390x_port_set_speed_duplex(str
-                                              duplex);
- }
--phy_interface_t mv88e6390x_port_max_speed_mode(int port)
-+phy_interface_t mv88e6390x_port_max_speed_mode(struct mv88e6xxx_chip *chip,
-+                                             int port)
- {
-       if (port == 9 || port == 10)
-               return PHY_INTERFACE_MODE_XAUI;
-@@ -527,7 +530,8 @@ int mv88e6393x_port_set_speed_duplex(str
-       return 0;
- }
--phy_interface_t mv88e6393x_port_max_speed_mode(int port)
-+phy_interface_t mv88e6393x_port_max_speed_mode(struct mv88e6xxx_chip *chip,
-+                                             int port)
- {
-       if (port == 0 || port == 9 || port == 10)
-               return PHY_INTERFACE_MODE_10GBASER;
---- a/drivers/net/dsa/mv88e6xxx/port.h
-+++ b/drivers/net/dsa/mv88e6xxx/port.h
-@@ -350,10 +350,14 @@ int mv88e6390x_port_set_speed_duplex(str
- int mv88e6393x_port_set_speed_duplex(struct mv88e6xxx_chip *chip, int port,
-                                    int speed, int duplex);
--phy_interface_t mv88e6341_port_max_speed_mode(int port);
--phy_interface_t mv88e6390_port_max_speed_mode(int port);
--phy_interface_t mv88e6390x_port_max_speed_mode(int port);
--phy_interface_t mv88e6393x_port_max_speed_mode(int port);
-+phy_interface_t mv88e6341_port_max_speed_mode(struct mv88e6xxx_chip *chip,
-+                                            int port);
-+phy_interface_t mv88e6390_port_max_speed_mode(struct mv88e6xxx_chip *chip,
-+                                            int port);
-+phy_interface_t mv88e6390x_port_max_speed_mode(struct mv88e6xxx_chip *chip,
-+                                             int port);
-+phy_interface_t mv88e6393x_port_max_speed_mode(struct mv88e6xxx_chip *chip,
-+                                             int port);
- int mv88e6xxx_port_set_state(struct mv88e6xxx_chip *chip, int port, u8 state);
diff --git a/target/linux/generic/backport-5.15/893-v6.5-06-net-dsa-mv88e6xxx-enable-support-for-88E6361-switch.patch b/target/linux/generic/backport-5.15/893-v6.5-06-net-dsa-mv88e6xxx-enable-support-for-88E6361-switch.patch
deleted file mode 100644 (file)
index acb8d26..0000000
+++ /dev/null
@@ -1,165 +0,0 @@
-From f318a015330a11befd8c69336efc6284e240f535 Mon Sep 17 00:00:00 2001
-From: =?UTF-8?q?Alexis=20Lothor=C3=A9?= <[email protected]>
-Date: Mon, 29 May 2023 10:02:46 +0200
-Subject: [PATCH 898/898] net: dsa: mv88e6xxx: enable support for 88E6361
- switch
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-Marvell 88E6361 is an 8-port switch derived from the
-88E6393X/88E9193X/88E6191X switches family. It can benefit from the
-existing mv88e6xxx driver by simply adding the proper switch description in
-the driver. Main differences with other switches from this
-family are:
-- 8 ports exposed (instead of 11): ports 1, 2 and 8 not available
-- No 5GBase-x nor SFI/USXGMII support
-
-Signed-off-by: Alexis Lothoré <[email protected]>
-Reviewed-by: Andrew Lunn <[email protected]>
-Signed-off-by: Jakub Kicinski <[email protected]>
-Adapt to 5.15 since we dont have phylink_get_caps yet.
-So, update the old mv88e6393x_phylink_validate instead.
-Remove max_sid since 5.15 driver does not support it yet.
-[Robert Marko]
-Signed-off-by: Robert Marko <[email protected]>
----
- drivers/net/dsa/mv88e6xxx/chip.c | 49 +++++++++++++++++++++++++++++++-
- drivers/net/dsa/mv88e6xxx/chip.h |  3 +-
- drivers/net/dsa/mv88e6xxx/port.c | 14 +++++++--
- drivers/net/dsa/mv88e6xxx/port.h |  1 +
- 4 files changed, 62 insertions(+), 5 deletions(-)
-
---- a/drivers/net/dsa/mv88e6xxx/chip.c
-+++ b/drivers/net/dsa/mv88e6xxx/chip.c
-@@ -648,6 +648,8 @@ static void mv88e6393x_phylink_validate(
- {
-       bool is_6191x =
-               chip->info->prod_num == MV88E6XXX_PORT_SWITCH_ID_PROD_6191X;
-+      bool is_6361 =
-+              chip->info->prod_num == MV88E6XXX_PORT_SWITCH_ID_PROD_6361;
-       if (((port == 0 || port == 9) && !is_6191x) || port == 10) {
-               phylink_set(mask, 10000baseT_Full);
-@@ -662,8 +664,28 @@ static void mv88e6393x_phylink_validate(
-               phylink_set(mask, 2500baseT_Full);
-       }
-+      if (port == 0 || port == 9 || port == 10) {
-+              phylink_set(mask, 1000baseX_Full);
-+
-+              /* 6191X supports >1G modes only on port 10 */
-+              if (!is_6191x || port == 10) {
-+                      phylink_set(mask, 2500baseX_Full);
-+                      phylink_set(mask, 2500baseT_Full);
-+
-+                      if (!is_6361) {
-+                              phylink_set(mask, 10000baseT_Full);
-+                              phylink_set(mask, 10000baseKR_Full);
-+                              phylink_set(mask, 10000baseCR_Full);
-+                              phylink_set(mask, 10000baseSR_Full);
-+                              phylink_set(mask, 10000baseLR_Full);
-+                              phylink_set(mask, 10000baseLRM_Full);
-+                              phylink_set(mask, 10000baseER_Full);
-+                              phylink_set(mask, 5000baseT_Full);
-+                      }
-+              }
-+      }
-+
-       phylink_set(mask, 1000baseT_Full);
--      phylink_set(mask, 1000baseX_Full);
-       mv88e6065_phylink_validate(chip, port, mask, state);
- }
-@@ -5693,6 +5715,31 @@ static const struct mv88e6xxx_info mv88e
-               .ptp_support = true,
-               .ops = &mv88e6352_ops,
-       },
-+      [MV88E6361] = {
-+              .prod_num = MV88E6XXX_PORT_SWITCH_ID_PROD_6361,
-+              .family = MV88E6XXX_FAMILY_6393,
-+              .name = "Marvell 88E6361",
-+              .num_databases = 4096,
-+              .num_macs = 16384,
-+              .num_ports = 11,
-+              /* Ports 1, 2 and 8 are not routed */
-+              .invalid_port_mask = BIT(1) | BIT(2) | BIT(8),
-+              .num_internal_phys = 5,
-+              .internal_phys_offset = 3,
-+              .max_vid = 4095,
-+              .port_base_addr = 0x0,
-+              .phy_base_addr = 0x0,
-+              .global1_addr = 0x1b,
-+              .global2_addr = 0x1c,
-+              .age_time_coeff = 3750,
-+              .g1_irqs = 10,
-+              .g2_irqs = 14,
-+              .atu_move_port_mask = 0x1f,
-+              .pvt = true,
-+              .multi_chip = true,
-+              .ptp_support = true,
-+              .ops = &mv88e6393x_ops,
-+      },
-       [MV88E6390] = {
-               .prod_num = MV88E6XXX_PORT_SWITCH_ID_PROD_6390,
-               .family = MV88E6XXX_FAMILY_6390,
---- a/drivers/net/dsa/mv88e6xxx/chip.h
-+++ b/drivers/net/dsa/mv88e6xxx/chip.h
-@@ -81,6 +81,7 @@ enum mv88e6xxx_model {
-       MV88E6350,
-       MV88E6351,
-       MV88E6352,
-+      MV88E6361,
-       MV88E6390,
-       MV88E6390X,
-       MV88E6393X,
-@@ -99,7 +100,7 @@ enum mv88e6xxx_family {
-       MV88E6XXX_FAMILY_6351,  /* 6171 6175 6350 6351 */
-       MV88E6XXX_FAMILY_6352,  /* 6172 6176 6240 6352 */
-       MV88E6XXX_FAMILY_6390,  /* 6190 6190X 6191 6290 6390 6390X */
--      MV88E6XXX_FAMILY_6393,  /* 6191X 6193X 6393X */
-+      MV88E6XXX_FAMILY_6393,  /* 6191X 6193X 6361 6393X */
- };
- /**
---- a/drivers/net/dsa/mv88e6xxx/port.c
-+++ b/drivers/net/dsa/mv88e6xxx/port.c
-@@ -451,6 +451,10 @@ int mv88e6393x_port_set_speed_duplex(str
-       if (speed == SPEED_MAX)
-               speed = (port > 0 && port < 9) ? 1000 : 10000;
-+      if (chip->info->prod_num == MV88E6XXX_PORT_SWITCH_ID_PROD_6361 &&
-+          speed > 2500)
-+              return -EOPNOTSUPP;
-+
-       if (speed == 200 && port != 0)
-               return -EOPNOTSUPP;
-@@ -533,10 +537,14 @@ int mv88e6393x_port_set_speed_duplex(str
- phy_interface_t mv88e6393x_port_max_speed_mode(struct mv88e6xxx_chip *chip,
-                                              int port)
- {
--      if (port == 0 || port == 9 || port == 10)
--              return PHY_INTERFACE_MODE_10GBASER;
--      return PHY_INTERFACE_MODE_NA;
-+      if (port != 0 && port != 9 && port != 10)
-+              return PHY_INTERFACE_MODE_NA;
-+
-+      if (chip->info->prod_num == MV88E6XXX_PORT_SWITCH_ID_PROD_6361)
-+              return PHY_INTERFACE_MODE_2500BASEX;
-+
-+      return PHY_INTERFACE_MODE_10GBASER;
- }
- static int mv88e6xxx_port_set_cmode(struct mv88e6xxx_chip *chip, int port,
---- a/drivers/net/dsa/mv88e6xxx/port.h
-+++ b/drivers/net/dsa/mv88e6xxx/port.h
-@@ -128,6 +128,7 @@
- #define MV88E6XXX_PORT_SWITCH_ID_PROD_6220    0x2200
- #define MV88E6XXX_PORT_SWITCH_ID_PROD_6240    0x2400
- #define MV88E6XXX_PORT_SWITCH_ID_PROD_6250    0x2500
-+#define MV88E6XXX_PORT_SWITCH_ID_PROD_6361    0x2610
- #define MV88E6XXX_PORT_SWITCH_ID_PROD_6290    0x2900
- #define MV88E6XXX_PORT_SWITCH_ID_PROD_6321    0x3100
- #define MV88E6XXX_PORT_SWITCH_ID_PROD_6141    0x3400
diff --git a/target/linux/generic/backport-5.15/894-v6.8-net-ethtool-implement-ethtool_puts.patch b/target/linux/generic/backport-5.15/894-v6.8-net-ethtool-implement-ethtool_puts.patch
deleted file mode 100644 (file)
index 283e226..0000000
+++ /dev/null
@@ -1,139 +0,0 @@
-From mboxrd@z Thu Jan  1 00:00:00 1970
-Authentication-Results: smtp.subspace.kernel.org;
-       dkim=pass (2048-bit key) header.d=google.com [email protected] header.b="sMUeie/T"
-Received: from mail-yb1-xb49.google.com (mail-yb1-xb49.google.com [IPv6:2607:f8b0:4864:20::b49])
-       by lindbergh.monkeyblade.net (Postfix) with ESMTPS id 84BB8D6D
-       for <[email protected]>; Wed,  6 Dec 2023 15:16:16 -0800 (PST)
-Received: by mail-yb1-xb49.google.com with SMTP id 3f1490d57ef6-db5416d0fccso403298276.1
-        for <[email protected]>; Wed, 06 Dec 2023 15:16:16 -0800 (PST)
-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed;
-        d=google.com; s=20230601; t=1701904575; x=1702509375; darn=vger.kernel.org;
-        h=cc:to:from:subject:message-id:references:mime-version:in-reply-to
-         :date:from:to:cc:subject:date:message-id:reply-to;
-        bh=/7eYcPC4ZNNyPcPPs0B5tDplF0arxw3r0vINNNou0rY=;
-        b=sMUeie/TxdytzC0EyT11QWi1TqTtiv7KCTs1F2vLmUUvPKNA3+1MHFo8ECW+0gQuDE
-         FGrgdZKGK5mXQgkF0N3JiSLvKO8tpQOIB57JLCG5IVy5dr2vVv0ExU3Dag2Cc4oBIBIO
-         w/cH95O1oPlvluIpATmAsxenVr7mFomU63BqYiRGLaEhWeb2hJ636GO8lubtsDfdFFoi
-         GPOL2tQwV93VnqmywBBpFaNAULN0UoCFhfkKv5prvpkXq19sWI7zyorVZ+rdTYem5m4T
-         dXsDaLXPtC3Dh2JOad1duSQIah/wCHYYUcV3IoFhwj2y0Uk/TTCrnZPORweSADcEy6Ho
-         vDrA==
-X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed;
-        d=1e100.net; s=20230601; t=1701904575; x=1702509375;
-        h=cc:to:from:subject:message-id:references:mime-version:in-reply-to
-         :date:x-gm-message-state:from:to:cc:subject:date:message-id:reply-to;
-        bh=/7eYcPC4ZNNyPcPPs0B5tDplF0arxw3r0vINNNou0rY=;
-        b=Dmc6aSntxPlxAk72zVO1G9WoZnFtLolxENlLscYYAHG3VE+PQ8gGN2rPzcGoKb2Btb
-         4b0PvjOzSlPQyghahdhdlz04RtAeeGG/MkfNiYjFql5OifIoovb51kroiPYrVsa7Ps7Y
-         +Pxug0+NPdTm5s9TNz940ZKl3GRME8UTmVxpWJRX03XMOqb6Wgsh2SK9ahXKc4yRsi62
-         3a3J72WmmSgvimxwM/99fXwvoUQpiv2J1xCoqc1Ng4q4qSuZvzmHN7ZTGaUhLxOqLeLK
-         3W4RKHW6rZ7UjppuB6I3NXW+D344By2rdKp1sRXpjdQ0GS3YUcvlRETcJBXJudHfQP5Y
-         CLOw==
-X-Gm-Message-State: AOJu0YzdCTLdwny+N99zeMgyKqFsEZhfIhL2cbgKA6zC1U/OLkxxRLoM
-       XrYVBC9DmxCGmP4o+M/Z/kHUew/9faHlCiLGxw==
-X-Google-Smtp-Source: AGHT+IFRXxBV6JuX5Cl/k2o1+WKkCwkR8j20MJSkmoGCedPAtqFttH8OVh1/6vdfnq8MPN++A2h89peZQhyG8OsJ8A==
-X-Received: from jstitt-linux1.c.googlers.com ([fda3:e722:ac3:cc00:2b:ff92:c0a8:23b5])
- (user=justinstitt job=sendgmr) by 2002:a25:dac7:0:b0:da0:3117:f35 with SMTP
- id n190-20020a25dac7000000b00da031170f35mr28652ybf.3.1701904575576; Wed, 06
- Dec 2023 15:16:15 -0800 (PST)
-Date: Wed, 06 Dec 2023 23:16:10 +0000
-In-Reply-To: <[email protected]>
-Precedence: bulk
-X-Mailing-List: [email protected]
-List-Id: <bpf.vger.kernel.org>
-List-Subscribe: <mailto:[email protected]>
-List-Unsubscribe: <mailto:[email protected]>
-Mime-Version: 1.0
-References: <[email protected]>
-X-Developer-Key: [email protected]; a=ed25519; pk=tC3hNkJQTpNX/gLKxTNQKDmiQl6QjBNCGKJINqAdJsE=
-X-Developer-Signature: v=1; a=ed25519-sha256; t=1701904573; l=1840;
[email protected]; s=20230717; h=from:subject:message-id;
- bh=UMdetIL2ZsPIkSodqhw2fM21NHJVjCu0lRImFuNhVoM=; b=a8rMnXfVVQ5gsxHWG4WRMwOLxZgflqXZtNuKx26vv4DwYvvCtCiYjl3f1frOjV/Ul2kaxq5g/
- b/UOv678JKCDASVokxG5GJifAnU7/kqRxdhcwfRkrD8RUfcsmiZOfyF
-X-Mailer: b4 0.12.3
-Message-ID: <[email protected]>
-Subject: [PATCH net-next v5 1/3] ethtool: Implement ethtool_puts()
-To: "David S. Miller" <[email protected]>, Eric Dumazet <[email protected]>, 
-       Jakub Kicinski <[email protected]>, Paolo Abeni <[email protected]>, Shay Agroskin <[email protected]>, 
-       Arthur Kiyanovski <[email protected]>, David Arinzon <[email protected]>, Noam Dagan <[email protected]>, 
-       Saeed Bishara <[email protected]>, Rasesh Mody <[email protected]>, 
-       Sudarsana Kalluru <[email protected]>, [email protected]
-       Dimitris Michailidis <[email protected]>, Yisen Zhuang <[email protected]>, 
-       Salil Mehta <[email protected]>, Jesse Brandeburg <[email protected]>, 
-       Tony Nguyen <[email protected]>, Louis Peens <[email protected]>, 
-       Shannon Nelson <[email protected]>, Brett Creeley <[email protected]>, [email protected]
-       "K. Y. Srinivasan" <[email protected]>, Haiyang Zhang <[email protected]>, Wei Liu <[email protected]>, 
-       Dexuan Cui <[email protected]>, Ronak Doshi <[email protected]>, 
-       VMware PV-Drivers Reviewers <[email protected]>, Andy Whitcroft <[email protected]>, Joe Perches <[email protected]>, 
-       Dwaipayan Ray <[email protected]>, Lukas Bulwahn <[email protected]>, 
-       Hauke Mehrtens <[email protected]>, Andrew Lunn <[email protected]>, 
-       Florian Fainelli <[email protected]>, Vladimir Oltean <[email protected]>, 
-       "=?utf-8?q?Ar=C4=B1n=C3=A7_=C3=9CNAL?=" <[email protected]>, Daniel Golle <[email protected]>, 
-       Landen Chao <[email protected]>, DENG Qingfang <[email protected]>, 
-       Sean Wang <[email protected]>, Matthias Brugger <[email protected]>, 
-       AngeloGioacchino Del Regno <[email protected]>, 
-       Linus Walleij <[email protected]>, 
-       "=?utf-8?q?Alvin_=C5=A0ipraga?=" <[email protected]>, Wei Fang <[email protected]>, 
-       Shenwei Wang <[email protected]>, Clark Wang <[email protected]>, 
-       NXP Linux Team <[email protected]>, Lars Povlsen <[email protected]>, 
-       Steen Hegelund <[email protected]>, Daniel Machon <[email protected]>, 
-       [email protected], Jiawen Wu <[email protected]>, 
-       Mengyuan Lou <[email protected]>, Heiner Kallweit <[email protected]>, 
-       Russell King <[email protected]>, Alexei Starovoitov <[email protected]>, 
-       Daniel Borkmann <[email protected]>, Jesper Dangaard Brouer <[email protected]>, 
-       John Fastabend <[email protected]>
-       Nick Desaulniers <[email protected]>, Nathan Chancellor <[email protected]>, 
-       Kees Cook <[email protected]>, [email protected]
-       [email protected], Justin Stitt <[email protected]>
-Content-Type: text/plain; charset="utf-8"
-
-Use strscpy() to implement ethtool_puts().
-
-Functionally the same as ethtool_sprintf() when it's used with two
-arguments or with just "%s" format specifier.
-
-Signed-off-by: Justin Stitt <[email protected]>
----
- include/linux/ethtool.h | 13 +++++++++++++
- net/ethtool/ioctl.c     |  7 +++++++
- 2 files changed, 20 insertions(+)
-
---- a/include/linux/ethtool.h
-+++ b/include/linux/ethtool.h
-@@ -788,4 +788,17 @@ int ethtool_get_phc_vclocks(struct net_d
-  * next string.
-  */
- extern __printf(2, 3) void ethtool_sprintf(u8 **data, const char *fmt, ...);
-+
-+/**
-+ * ethtool_puts - Write string to ethtool string data
-+ * @data: Pointer to a pointer to the start of string to update
-+ * @str: String to write
-+ *
-+ * Write string to *data without a trailing newline. Update *data
-+ * to point at start of next string.
-+ *
-+ * Prefer this function to ethtool_sprintf() when given only
-+ * two arguments or if @fmt is just "%s".
-+ */
-+extern void ethtool_puts(u8 **data, const char *str);
- #endif /* _LINUX_ETHTOOL_H */
---- a/net/ethtool/ioctl.c
-+++ b/net/ethtool/ioctl.c
-@@ -1954,6 +1954,13 @@ __printf(2, 3) void ethtool_sprintf(u8 *
- }
- EXPORT_SYMBOL(ethtool_sprintf);
-+void ethtool_puts(u8 **data, const char *str)
-+{
-+      strscpy(*data, str, ETH_GSTRING_LEN);
-+      *data += ETH_GSTRING_LEN;
-+}
-+EXPORT_SYMBOL(ethtool_puts);
-+
- static int ethtool_phys_id(struct net_device *dev, void __user *useraddr)
- {
-       struct ethtool_value id;
diff --git a/target/linux/generic/config-5.15 b/target/linux/generic/config-5.15
deleted file mode 100644 (file)
index 4c5b808..0000000
+++ /dev/null
@@ -1,7622 +0,0 @@
-# CONFIG_104_QUAD_8 is not set
-CONFIG_32BIT=y
-CONFIG_64BIT_TIME=y
-# CONFIG_6LOWPAN is not set
-# CONFIG_6LOWPAN_DEBUGFS is not set
-# CONFIG_6PACK is not set
-# CONFIG_8139CP is not set
-# CONFIG_8139TOO is not set
-# CONFIG_9P_FS is not set
-# CONFIG_AB3100_CORE is not set
-# CONFIG_AB8500_CORE is not set
-# CONFIG_ABP060MG is not set
-# CONFIG_ABX500_CORE is not set
-# CONFIG_ACCESSIBILITY is not set
-# CONFIG_ACENIC is not set
-# CONFIG_ACERHDF is not set
-# CONFIG_ACER_WIRELESS is not set
-# CONFIG_ACORN_PARTITION is not set
-# CONFIG_ACPI_ALS is not set
-# CONFIG_ACPI_APEI is not set
-# CONFIG_ACPI_APEI_PCIEAER is not set
-# CONFIG_ACPI_BUTTON is not set
-# CONFIG_ACPI_CONFIGFS is not set
-# CONFIG_ACPI_CUSTOM_METHOD is not set
-# CONFIG_ACPI_EXTLOG is not set
-# CONFIG_ACPI_HED is not set
-# CONFIG_ACPI_NFIT is not set
-# CONFIG_ACPI_REDUCED_HARDWARE_ONLY is not set
-# CONFIG_ACPI_TABLE_UPGRADE is not set
-# CONFIG_ACPI_VIDEO is not set
-# CONFIG_AD2S1200 is not set
-# CONFIG_AD2S1210 is not set
-# CONFIG_AD2S90 is not set
-# CONFIG_AD5064 is not set
-# CONFIG_AD5110 is not set
-# CONFIG_AD525X_DPOT is not set
-# CONFIG_AD5272 is not set
-# CONFIG_AD5360 is not set
-# CONFIG_AD5380 is not set
-# CONFIG_AD5421 is not set
-# CONFIG_AD5446 is not set
-# CONFIG_AD5449 is not set
-# CONFIG_AD5504 is not set
-# CONFIG_AD5592R is not set
-# CONFIG_AD5593R is not set
-# CONFIG_AD5624R_SPI is not set
-# CONFIG_AD5686 is not set
-# CONFIG_AD5686_SPI is not set
-# CONFIG_AD5696_I2C is not set
-# CONFIG_AD5755 is not set
-# CONFIG_AD5758 is not set
-# CONFIG_AD5761 is not set
-# CONFIG_AD5764 is not set
-# CONFIG_AD5766 is not set
-# CONFIG_AD5770R is not set
-# CONFIG_AD5791 is not set
-# CONFIG_AD5933 is not set
-# CONFIG_AD7091R5 is not set
-# CONFIG_AD7124 is not set
-# CONFIG_AD7150 is not set
-# CONFIG_AD7152 is not set
-# CONFIG_AD7192 is not set
-# CONFIG_AD7266 is not set
-# CONFIG_AD7280 is not set
-# CONFIG_AD7291 is not set
-# CONFIG_AD7292 is not set
-# CONFIG_AD7298 is not set
-# CONFIG_AD7303 is not set
-# CONFIG_AD7476 is not set
-# CONFIG_AD7606 is not set
-# CONFIG_AD7606_IFACE_PARALLEL is not set
-# CONFIG_AD7606_IFACE_SPI is not set
-# CONFIG_AD7746 is not set
-# CONFIG_AD7766 is not set
-# CONFIG_AD7768_1 is not set
-# CONFIG_AD7780 is not set
-# CONFIG_AD7791 is not set
-# CONFIG_AD7793 is not set
-# CONFIG_AD7816 is not set
-# CONFIG_AD7887 is not set
-# CONFIG_AD7923 is not set
-# CONFIG_AD7949 is not set
-# CONFIG_AD799X is not set
-# CONFIG_AD8366 is not set
-# CONFIG_AD8801 is not set
-# CONFIG_AD9467 is not set
-# CONFIG_AD9523 is not set
-# CONFIG_AD9832 is not set
-# CONFIG_AD9834 is not set
-# CONFIG_ADAPTEC_STARFIRE is not set
-# CONFIG_ADE7854 is not set
-# CONFIG_ADF4350 is not set
-# CONFIG_ADF4371 is not set
-# CONFIG_ADFS_FS is not set
-# CONFIG_ADIN_PHY is not set
-# CONFIG_ADIS16080 is not set
-# CONFIG_ADIS16130 is not set
-# CONFIG_ADIS16136 is not set
-# CONFIG_ADIS16201 is not set
-# CONFIG_ADIS16203 is not set
-# CONFIG_ADIS16209 is not set
-# CONFIG_ADIS16240 is not set
-# CONFIG_ADIS16260 is not set
-# CONFIG_ADIS16400 is not set
-# CONFIG_ADIS16460 is not set
-# CONFIG_ADIS16475 is not set
-# CONFIG_ADIS16480 is not set
-# CONFIG_ADI_AXI_ADC is not set
-# CONFIG_ADJD_S311 is not set
-# CONFIG_ADM6996_PHY is not set
-# CONFIG_ADM8211 is not set
-# CONFIG_ADT7316 is not set
-# CONFIG_ADUX1020 is not set
-CONFIG_ADVISE_SYSCALLS=y
-# CONFIG_ADXL345_I2C is not set
-# CONFIG_ADXL345_SPI is not set
-# CONFIG_ADXL372_I2C is not set
-# CONFIG_ADXL372_SPI is not set
-# CONFIG_ADXRS290 is not set
-# CONFIG_ADXRS450 is not set
-CONFIG_AEABI=y
-# CONFIG_AFE4403 is not set
-# CONFIG_AFE4404 is not set
-# CONFIG_AFFS_FS is not set
-# CONFIG_AFS_DEBUG_CURSOR is not set
-# CONFIG_AFS_FS is not set
-# CONFIG_AF_KCM is not set
-# CONFIG_AF_RXRPC is not set
-# CONFIG_AF_RXRPC_INJECT_LOSS is not set
-# CONFIG_AF_RXRPC_IPV6 is not set
-CONFIG_AF_UNIX_OOB=y
-# CONFIG_AGP is not set
-# CONFIG_AHCI_BRCM is not set
-# CONFIG_AHCI_CEVA is not set
-# CONFIG_AHCI_IMX is not set
-# CONFIG_AHCI_MVEBU is not set
-# CONFIG_AHCI_QORIQ is not set
-# CONFIG_AHCI_XGENE is not set
-CONFIG_AIO=y
-# CONFIG_AIRO is not set
-# CONFIG_AIRO_CS is not set
-# CONFIG_AIX_PARTITION is not set
-# CONFIG_AK09911 is not set
-# CONFIG_AK8974 is not set
-# CONFIG_AK8975 is not set
-# CONFIG_AL3010 is not set
-# CONFIG_AL3320A is not set
-# CONFIG_ALIM7101_WDT is not set
-CONFIG_ALLOW_DEV_COREDUMP=y
-# CONFIG_ALTERA_MBOX is not set
-# CONFIG_ALTERA_MSGDMA is not set
-# CONFIG_ALTERA_STAPL is not set
-# CONFIG_ALTERA_TSE is not set
-# CONFIG_ALX is not set
-# CONFIG_AL_FIC is not set
-# CONFIG_AM2315 is not set
-# CONFIG_AM335X_PHY_USB is not set
-# CONFIG_AMBA_PL08X is not set
-# CONFIG_AMD8111_ETH is not set
-# CONFIG_AMD_MEM_ENCRYPT is not set
-# CONFIG_AMD_PHY is not set
-# CONFIG_AMD_XGBE is not set
-# CONFIG_AMD_XGBE_HAVE_ECC is not set
-# CONFIG_AMIGA_PARTITION is not set
-# CONFIG_AMILO_RFKILL is not set
-# CONFIG_ANDROID is not set
-CONFIG_ANON_INODES=y
-# CONFIG_APDS9300 is not set
-# CONFIG_APDS9802ALS is not set
-# CONFIG_APDS9960 is not set
-# CONFIG_APM8018X is not set
-# CONFIG_APM_EMULATION is not set
-# CONFIG_APPLE_GMUX is not set
-# CONFIG_APPLE_MFI_FASTCHARGE is not set
-# CONFIG_APPLE_PROPERTIES is not set
-# CONFIG_APPLICOM is not set
-# CONFIG_AQTION is not set
-# CONFIG_AQUANTIA_PHY is not set
-# CONFIG_AR5523 is not set
-# CONFIG_AR7 is not set
-# CONFIG_AR8216_PHY is not set
-# CONFIG_AR8216_PHY_LEDS is not set
-# CONFIG_ARCH_ACTIONS is not set
-# CONFIG_ARCH_AGILEX is not set
-# CONFIG_ARCH_ALPINE is not set
-# CONFIG_ARCH_APPLE is not set
-# CONFIG_ARCH_ARTPEC is not set
-# CONFIG_ARCH_ASPEED is not set
-# CONFIG_ARCH_AT91 is not set
-# CONFIG_ARCH_AXXIA is not set
-# CONFIG_ARCH_BCM is not set
-# CONFIG_ARCH_BCM2835 is not set
-# CONFIG_ARCH_BCM4908 is not set
-# CONFIG_ARCH_BCM_21664 is not set
-# CONFIG_ARCH_BCM_23550 is not set
-# CONFIG_ARCH_BCM_281XX is not set
-# CONFIG_ARCH_BCM_5301X is not set
-# CONFIG_ARCH_BCM_53573 is not set
-# CONFIG_ARCH_BCM_63XX is not set
-# CONFIG_ARCH_BCM_CYGNUS is not set
-# CONFIG_ARCH_BCM_IPROC is not set
-# CONFIG_ARCH_BCM_NSP is not set
-# CONFIG_ARCH_BERLIN is not set
-CONFIG_ARCH_BINFMT_ELF_STATE=y
-# CONFIG_ARCH_BITMAIN is not set
-# CONFIG_ARCH_BRCMSTB is not set
-# CONFIG_ARCH_CLPS711X is not set
-# CONFIG_ARCH_CNS3XXX is not set
-# CONFIG_ARCH_DAVINCI is not set
-# CONFIG_ARCH_DIGICOLOR is not set
-# CONFIG_ARCH_DMA_ADDR_T_64BIT is not set
-# CONFIG_ARCH_DOVE is not set
-# CONFIG_ARCH_EBSA110 is not set
-# CONFIG_ARCH_EP93XX is not set
-# CONFIG_ARCH_EXYNOS is not set
-CONFIG_ARCH_FLATMEM_ENABLE=y
-# CONFIG_ARCH_FOOTBRIDGE is not set
-# CONFIG_ARCH_GEMINI is not set
-# CONFIG_ARCH_HI3xxx is not set
-# CONFIG_ARCH_HIGHBANK is not set
-# CONFIG_ARCH_HISI is not set
-# CONFIG_ARCH_INTEGRATOR is not set
-# CONFIG_ARCH_INTEL_SOCFPGA is not set
-# CONFIG_ARCH_IOP13XX is not set
-# CONFIG_ARCH_IOP32X is not set
-# CONFIG_ARCH_IOP33X is not set
-# CONFIG_ARCH_IXP4XX is not set
-# CONFIG_ARCH_K3 is not set
-# CONFIG_ARCH_KEEMBAY is not set
-# CONFIG_ARCH_KEYSTONE is not set
-# CONFIG_ARCH_KS8695 is not set
-# CONFIG_ARCH_LAYERSCAPE is not set
-# CONFIG_ARCH_LG1K is not set
-# CONFIG_ARCH_LPC32XX is not set
-# CONFIG_ARCH_MEDIATEK is not set
-# CONFIG_ARCH_MESON is not set
-# CONFIG_ARCH_MILBEAUT is not set
-CONFIG_ARCH_MMAP_RND_BITS=8
-CONFIG_ARCH_MMAP_RND_BITS_MAX=16
-CONFIG_ARCH_MMAP_RND_BITS_MIN=8
-CONFIG_ARCH_MMAP_RND_COMPAT_BITS_MAX=16
-CONFIG_ARCH_MMAP_RND_COMPAT_BITS_MIN=8
-# CONFIG_ARCH_MMP is not set
-# CONFIG_ARCH_MSTARV7 is not set
-# CONFIG_ARCH_MULTIPLATFORM is not set
-# CONFIG_ARCH_MULTI_V6 is not set
-# CONFIG_ARCH_MULTI_V7 is not set
-# CONFIG_ARCH_MV78XX0 is not set
-# CONFIG_ARCH_MVEBU is not set
-# CONFIG_ARCH_MXC is not set
-# CONFIG_ARCH_MXS is not set
-# CONFIG_ARCH_NEEDS_CPU_IDLE_COUPLED is not set
-# CONFIG_ARCH_NETX is not set
-# CONFIG_ARCH_NOMADIK is not set
-# CONFIG_ARCH_NPCM is not set
-# CONFIG_ARCH_NSPIRE is not set
-# CONFIG_ARCH_OMAP is not set
-# CONFIG_ARCH_OMAP1 is not set
-# CONFIG_ARCH_OMAP2 is not set
-# CONFIG_ARCH_OMAP2PLUS is not set
-# CONFIG_ARCH_OMAP3 is not set
-# CONFIG_ARCH_OMAP4 is not set
-# CONFIG_ARCH_ORION5X is not set
-# CONFIG_ARCH_OXNAS is not set
-# CONFIG_ARCH_PICOXCELL is not set
-# CONFIG_ARCH_PRIMA2 is not set
-# CONFIG_ARCH_PXA is not set
-# CONFIG_ARCH_QCOM is not set
-# CONFIG_ARCH_RANDOM is not set
-# CONFIG_ARCH_RDA is not set
-# CONFIG_ARCH_REALTEK is not set
-# CONFIG_ARCH_REALVIEW is not set
-# CONFIG_ARCH_RENESAS is not set
-# CONFIG_ARCH_ROCKCHIP is not set
-# CONFIG_ARCH_RPC is not set
-# CONFIG_ARCH_S32 is not set
-# CONFIG_ARCH_S3C24XX is not set
-# CONFIG_ARCH_S3C64XX is not set
-# CONFIG_ARCH_S5PV210 is not set
-# CONFIG_ARCH_SA1100 is not set
-# CONFIG_ARCH_SEATTLE is not set
-# CONFIG_ARCH_SHMOBILE is not set
-# CONFIG_ARCH_SIRF is not set
-# CONFIG_ARCH_SOCFPGA is not set
-# CONFIG_ARCH_SPARX5 is not set
-# CONFIG_ARCH_SPRD is not set
-# CONFIG_ARCH_STI is not set
-# CONFIG_ARCH_STM32 is not set
-# CONFIG_ARCH_STRATIX10 is not set
-# CONFIG_ARCH_SUNXI is not set
-# CONFIG_ARCH_SYNQUACER is not set
-# CONFIG_ARCH_TANGO is not set
-# CONFIG_ARCH_TEGRA is not set
-# CONFIG_ARCH_THUNDER is not set
-# CONFIG_ARCH_THUNDER2 is not set
-# CONFIG_ARCH_U300 is not set
-# CONFIG_ARCH_U8500 is not set
-# CONFIG_ARCH_UNIPHIER is not set
-# CONFIG_ARCH_VERSATILE is not set
-# CONFIG_ARCH_VEXPRESS is not set
-# CONFIG_ARCH_VIRT is not set
-# CONFIG_ARCH_VISCONTI is not set
-# CONFIG_ARCH_VT8500 is not set
-# CONFIG_ARCH_VULCAN is not set
-# CONFIG_ARCH_W90X900 is not set
-# CONFIG_ARCH_WANTS_THP_SWAP is not set
-# CONFIG_ARCH_WM8505 is not set
-# CONFIG_ARCH_WM8750 is not set
-# CONFIG_ARCH_WM8850 is not set
-# CONFIG_ARCH_XGENE is not set
-# CONFIG_ARCH_ZX is not set
-# CONFIG_ARCH_ZYNQ is not set
-# CONFIG_ARCH_ZYNQMP is not set
-# CONFIG_ARCNET is not set
-# CONFIG_ARC_EMAC is not set
-# CONFIG_ARC_IRQ_NO_AUTOSAVE is not set
-# CONFIG_ARM64_16K_PAGES is not set
-# CONFIG_ARM64_64K_PAGES is not set
-# CONFIG_ARM64_AMU_EXTN is not set
-# CONFIG_ARM64_BTI is not set
-CONFIG_ARM64_CNP=y
-# CONFIG_ARM64_CRYPTO is not set
-# CONFIG_ARM64_E0PD is not set
-# CONFIG_ARM64_EPAN is not set
-# CONFIG_ARM64_ERRATUM_1024718 is not set
-# CONFIG_ARM64_ERRATUM_1165522 is not set
-# CONFIG_ARM64_ERRATUM_1286807 is not set
-# CONFIG_ARM64_ERRATUM_1319367 is not set
-# CONFIG_ARM64_ERRATUM_1418040 is not set
-# CONFIG_ARM64_ERRATUM_1463225 is not set
-# CONFIG_ARM64_ERRATUM_1508412 is not set
-# CONFIG_ARM64_ERRATUM_1530923 is not set
-# CONFIG_ARM64_ERRATUM_1542419 is not set
-# CONFIG_ARM64_ERRATUM_1742098 is not set
-# CONFIG_ARM64_ERRATUM_2253138 is not set
-# CONFIG_ARM64_ERRATUM_2224489 is not set
-# CONFIG_ARM64_ERRATUM_2054223 is not set
-# CONFIG_ARM64_ERRATUM_2067961 is not set
-# CONFIG_ARM64_ERRATUM_2441007 is not set
-# CONFIG_ARM64_ERRATUM_2441009 is not set
-# CONFIG_ARM64_ERRATUM_819472 is not set
-# CONFIG_ARM64_ERRATUM_824069 is not set
-# CONFIG_ARM64_ERRATUM_826319 is not set
-# CONFIG_ARM64_ERRATUM_827319 is not set
-# CONFIG_ARM64_ERRATUM_832075 is not set
-# CONFIG_ARM64_ERRATUM_834220 is not set
-# CONFIG_ARM64_ERRATUM_843419 is not set
-# CONFIG_ARM64_ERRATUM_845719 is not set
-# CONFIG_ARM64_ERRATUM_858921 is not set
-# CONFIG_ARM64_HW_AFDBM is not set
-# CONFIG_ARM64_LSE_ATOMICS is not set
-CONFIG_ARM64_MODULE_PLTS=y
-# CONFIG_ARM64_MTE is not set
-CONFIG_ARM64_PAN=y
-# CONFIG_ARM64_PMEM is not set
-# CONFIG_ARM64_PSEUDO_NMI is not set
-# CONFIG_ARM64_PTDUMP_DEBUGFS is not set
-# CONFIG_ARM64_PTR_AUTH is not set
-# CONFIG_ARM64_RANDOMIZE_TEXT_OFFSET is not set
-# CONFIG_ARM64_RAS_EXTN is not set
-# CONFIG_ARM64_RELOC_TEST is not set
-# CONFIG_ARM64_SVE is not set
-CONFIG_ARM64_SW_TTBR0_PAN=y
-# CONFIG_ARM64_TLB_RANGE is not set
-# CONFIG_ARM64_UAO is not set
-# CONFIG_ARM64_USE_LSE_ATOMICS is not set
-# CONFIG_ARM64_VA_BITS_48 is not set
-# CONFIG_ARM64_VHE is not set
-# CONFIG_ARM_APPENDED_DTB is not set
-# CONFIG_ARM_ARCH_TIMER is not set
-# CONFIG_ARM_ATAG_DTB_COMPAT_CMDLINE_EXTEND is not set
-# CONFIG_ARM_BIG_LITTLE_CPUFREQ is not set
-# CONFIG_ARM_CCI is not set
-# CONFIG_ARM_CCI400_PMU is not set
-# CONFIG_ARM_CCI5xx_PMU is not set
-# CONFIG_ARM_CCI_PMU is not set
-# CONFIG_ARM_CCN is not set
-# CONFIG_ARM_CMN is not set
-# CONFIG_ARM_CPUIDLE is not set
-CONFIG_ARM_CPU_TOPOLOGY=y
-# CONFIG_ARM_CRYPTO is not set
-CONFIG_ARM_DMA_MEM_BUFFERABLE=y
-# CONFIG_ARM_DSU_PMU is not set
-# CONFIG_ARM_ERRATA_326103 is not set
-# CONFIG_ARM_ERRATA_364296 is not set
-# CONFIG_ARM_ERRATA_411920 is not set
-# CONFIG_ARM_ERRATA_430973 is not set
-# CONFIG_ARM_ERRATA_458693 is not set
-# CONFIG_ARM_ERRATA_460075 is not set
-# CONFIG_ARM_ERRATA_643719 is not set
-# CONFIG_ARM_ERRATA_720789 is not set
-# CONFIG_ARM_ERRATA_742230 is not set
-# CONFIG_ARM_ERRATA_742231 is not set
-# CONFIG_ARM_ERRATA_743622 is not set
-# CONFIG_ARM_ERRATA_751472 is not set
-# CONFIG_ARM_ERRATA_754322 is not set
-# CONFIG_ARM_ERRATA_754327 is not set
-# CONFIG_ARM_ERRATA_764369 is not set
-# CONFIG_ARM_ERRATA_773022 is not set
-# CONFIG_ARM_ERRATA_775420 is not set
-# CONFIG_ARM_ERRATA_798181 is not set
-# CONFIG_ARM_ERRATA_814220 is not set
-# CONFIG_ARM_ERRATA_818325_852422 is not set
-# CONFIG_ARM_ERRATA_821420 is not set
-# CONFIG_ARM_ERRATA_825619 is not set
-# CONFIG_ARM_ERRATA_852421 is not set
-# CONFIG_ARM_ERRATA_852423 is not set
-# CONFIG_ARM_ERRATA_857271 is not set
-# CONFIG_ARM_ERRATA_857272 is not set
-# CONFIG_ARM_FFA_TRANSPORT is not set
-CONFIG_ARM_GIC_MAX_NR=1
-# CONFIG_ARM_KIRKWOOD_CPUFREQ is not set
-# CONFIG_ARM_KPROBES_TEST is not set
-# CONFIG_ARM_LPAE is not set
-# CONFIG_ARM_MEDIATEK_CPUFREQ_HW is not set
-# CONFIG_ARM_MHU is not set
-CONFIG_ARM_MODULE_PLTS=y
-# CONFIG_ARM_PATCH_PHYS_VIRT is not set
-# CONFIG_ARM_PSCI is not set
-# CONFIG_ARM_PSCI_CHECKER is not set
-# CONFIG_ARM_PSCI_CPUIDLE is not set
-# CONFIG_ARM_PTDUMP_DEBUGFS is not set
-# CONFIG_ARM_SBSA_WATCHDOG is not set
-# CONFIG_ARM_SCMI_PROTOCOL is not set
-# CONFIG_ARM_SCPI_PROTOCOL is not set
-# CONFIG_ARM_SDE_INTERFACE is not set
-# CONFIG_ARM_SMCCC_SOC_ID is not set
-# CONFIG_ARM_SMC_WATCHDOG is not set
-# CONFIG_ARM_SP805_WATCHDOG is not set
-# CONFIG_ARM_SPE_PMU is not set
-# CONFIG_ARM_THUMBEE is not set
-# CONFIG_ARM_TIMER_SP804 is not set
-# CONFIG_ARM_UNWIND is not set
-# CONFIG_ARM_VIRT_EXT is not set
-# CONFIG_AS3935 is not set
-# CONFIG_AS73211 is not set
-# CONFIG_ASM9260_TIMER is not set
-# CONFIG_ASN1 is not set
-# CONFIG_ASUS_LAPTOP is not set
-# CONFIG_ASUS_WIRELESS is not set
-# CONFIG_ASYMMETRIC_KEY_TYPE is not set
-# CONFIG_ASYMMETRIC_PUBLIC_KEY_SUBTYPE is not set
-# CONFIG_ASYNC_RAID6_TEST is not set
-# CONFIG_ASYNC_TX_DMA is not set
-# CONFIG_AT76C50X_USB is not set
-# CONFIG_AT803X_PHY is not set
-# CONFIG_AT91_SAMA5D2_ADC is not set
-# CONFIG_ATA is not set
-# CONFIG_ATAGS is not set
-CONFIG_ATAGS_PROC=y
-# CONFIG_ATALK is not set
-# CONFIG_ATARI_PARTITION is not set
-# CONFIG_ATA_ACPI is not set
-CONFIG_ATA_BMDMA=y
-# CONFIG_ATA_FORCE is not set
-# CONFIG_ATA_GENERIC is not set
-# CONFIG_ATA_LEDS is not set
-# CONFIG_ATA_NONSTANDARD is not set
-# CONFIG_ATA_OVER_ETH is not set
-# CONFIG_ATA_PIIX is not set
-CONFIG_ATA_SFF=y
-# CONFIG_ATA_VERBOSE_ERROR is not set
-# CONFIG_ATH10K is not set
-# CONFIG_ATH25 is not set
-# CONFIG_ATH5K is not set
-# CONFIG_ATH6KL is not set
-# CONFIG_ATH79 is not set
-# CONFIG_ATH9K is not set
-# CONFIG_ATH9K_HTC is not set
-# CONFIG_ATH_DEBUG is not set
-# CONFIG_ATL1 is not set
-# CONFIG_ATL1C is not set
-# CONFIG_ATL1E is not set
-# CONFIG_ATL2 is not set
-# CONFIG_ATLAS_EZO_SENSOR is not set
-# CONFIG_ATLAS_PH_SENSOR is not set
-# CONFIG_ATM is not set
-# CONFIG_ATMEL is not set
-# CONFIG_ATMEL_PIT is not set
-# CONFIG_ATMEL_SSC is not set
-# CONFIG_ATM_AMBASSADOR is not set
-# CONFIG_ATM_BR2684 is not set
-CONFIG_ATM_BR2684_IPFILTER=y
-# CONFIG_ATM_CLIP is not set
-CONFIG_ATM_CLIP_NO_ICMP=y
-# CONFIG_ATM_DRIVERS is not set
-# CONFIG_ATM_DUMMY is not set
-# CONFIG_ATM_ENI is not set
-# CONFIG_ATM_FIRESTREAM is not set
-# CONFIG_ATM_FORE200E is not set
-# CONFIG_ATM_HE is not set
-# CONFIG_ATM_HORIZON is not set
-# CONFIG_ATM_IA is not set
-# CONFIG_ATM_IDT77252 is not set
-# CONFIG_ATM_LANAI is not set
-# CONFIG_ATM_LANE is not set
-# CONFIG_ATM_MPOA is not set
-# CONFIG_ATM_NICSTAR is not set
-# CONFIG_ATM_SOLOS is not set
-# CONFIG_ATM_TCP is not set
-# CONFIG_ATM_ZATM is not set
-# CONFIG_ATOMIC64_SELFTEST is not set
-# CONFIG_ATP is not set
-# CONFIG_AUDIT is not set
-# CONFIG_AUDIT_ARCH_COMPAT_GENERIC is not set
-# CONFIG_AURORA_NB8800 is not set
-# CONFIG_AUTOFS4_FS is not set
-# CONFIG_AUTOFS_FS is not set
-# CONFIG_AUTO_ZRELADDR is not set
-# CONFIG_AUXDISPLAY is not set
-# CONFIG_AX25 is not set
-# CONFIG_AX25_DAMA_SLAVE is not set
-# CONFIG_AX88796 is not set
-# CONFIG_AX88796B_PHY is not set
-# CONFIG_AXP20X_ADC is not set
-# CONFIG_AXP20X_POWER is not set
-# CONFIG_AXP288_ADC is not set
-# CONFIG_AXP288_FUEL_GAUGE is not set
-# CONFIG_B43 is not set
-# CONFIG_B43LEGACY is not set
-# CONFIG_B44 is not set
-# CONFIG_B53 is not set
-# CONFIG_B53_MDIO_DRIVER is not set
-# CONFIG_B53_MMAP_DRIVER is not set
-# CONFIG_B53_SERDES is not set
-# CONFIG_B53_SPI_DRIVER is not set
-# CONFIG_B53_SRAB_DRIVER is not set
-# CONFIG_BACKLIGHT_ADP8860 is not set
-# CONFIG_BACKLIGHT_ADP8870 is not set
-# CONFIG_BACKLIGHT_APPLE is not set
-# CONFIG_BACKLIGHT_ARCXCNN is not set
-# CONFIG_BACKLIGHT_BD6107 is not set
-# CONFIG_BACKLIGHT_CLASS_DEVICE is not set
-# CONFIG_BACKLIGHT_GENERIC is not set
-# CONFIG_BACKLIGHT_GPIO is not set
-# CONFIG_BACKLIGHT_KTD253 is not set
-# CONFIG_BACKLIGHT_LCD_SUPPORT is not set
-# CONFIG_BACKLIGHT_LED is not set
-# CONFIG_BACKLIGHT_LM3630A is not set
-# CONFIG_BACKLIGHT_LM3639 is not set
-# CONFIG_BACKLIGHT_LP855X is not set
-# CONFIG_BACKLIGHT_LV5207LP is not set
-# CONFIG_BACKLIGHT_PANDORA is not set
-# CONFIG_BACKLIGHT_PM8941_WLED is not set
-# CONFIG_BACKLIGHT_PWM is not set
-# CONFIG_BACKLIGHT_QCOM_WLED is not set
-# CONFIG_BACKLIGHT_RPI is not set
-# CONFIG_BACKLIGHT_SAHARA is not set
-# CONFIG_BACKTRACE_SELF_TEST is not set
-# CONFIG_BAREUDP is not set
-CONFIG_BASE_FULL=y
-CONFIG_BASE_SMALL=0
-# CONFIG_BATMAN_ADV is not set
-# CONFIG_BATTERY_BQ27XXX is not set
-# CONFIG_BATTERY_BQ27XXX_HDQ is not set
-# CONFIG_BATTERY_CW2015 is not set
-# CONFIG_BATTERY_DS2760 is not set
-# CONFIG_BATTERY_DS2780 is not set
-# CONFIG_BATTERY_DS2781 is not set
-# CONFIG_BATTERY_DS2782 is not set
-# CONFIG_BATTERY_GAUGE_LTC2941 is not set
-# CONFIG_BATTERY_GOLDFISH is not set
-# CONFIG_BATTERY_LEGO_EV3 is not set
-# CONFIG_BATTERY_MAX17040 is not set
-# CONFIG_BATTERY_MAX17042 is not set
-# CONFIG_BATTERY_MAX1721X is not set
-# CONFIG_BATTERY_RT5033 is not set
-# CONFIG_BATTERY_SBS is not set
-# CONFIG_BAYCOM_EPP is not set
-# CONFIG_BAYCOM_PAR is not set
-# CONFIG_BAYCOM_SER_FDX is not set
-# CONFIG_BAYCOM_SER_HDX is not set
-# CONFIG_BCACHE is not set
-# CONFIG_BCM47XX is not set
-# CONFIG_BCM54140_PHY is not set
-# CONFIG_BCM63XX is not set
-# CONFIG_BCM63XX_PHY is not set
-# CONFIG_BCM7038_WDT is not set
-# CONFIG_BCM7XXX_PHY is not set
-# CONFIG_BCM84881_PHY is not set
-# CONFIG_BCM87XX_PHY is not set
-# CONFIG_BCMA is not set
-# CONFIG_BCMA_DRIVER_GPIO is not set
-CONFIG_BCMA_POSSIBLE=y
-# CONFIG_BCMGENET is not set
-# CONFIG_BCM_IPROC_ADC is not set
-# CONFIG_BCM_KONA_USB2_PHY is not set
-# CONFIG_BCM_SBA_RAID is not set
-# CONFIG_BCM_VK is not set
-# CONFIG_BDI_SWITCH is not set
-# CONFIG_BE2ISCSI is not set
-# CONFIG_BE2NET is not set
-# CONFIG_BEFS_FS is not set
-# CONFIG_BFS_FS is not set
-# CONFIG_BGMAC is not set
-# CONFIG_BH1750 is not set
-# CONFIG_BH1780 is not set
-# CONFIG_BIG_KEYS is not set
-# CONFIG_BIG_LITTLE is not set
-CONFIG_BINARY_PRINTF=y
-# CONFIG_BINFMT_AOUT is not set
-CONFIG_BINFMT_ELF=y
-# CONFIG_BINFMT_ELF_FDPIC is not set
-# CONFIG_BINFMT_FLAT is not set
-# CONFIG_BINFMT_MISC is not set
-CONFIG_BINFMT_SCRIPT=y
-CONFIG_BITREVERSE=y
-# CONFIG_BLK_CGROUP_IOCOST is not set
-# CONFIG_BLK_CGROUP_IOLATENCY is not set
-# CONFIG_BLK_CGROUP_IOPRIO is not set
-# CONFIG_BLK_CMDLINE_PARSER is not set
-# CONFIG_BLK_DEBUG_FS is not set
-CONFIG_BLK_DEV=y
-# CONFIG_BLK_DEV_3W_XXXX_RAID is not set
-# CONFIG_BLK_DEV_4DRIVES is not set
-# CONFIG_BLK_DEV_AEC62XX is not set
-# CONFIG_BLK_DEV_ALI14XX is not set
-# CONFIG_BLK_DEV_ALI15X3 is not set
-# CONFIG_BLK_DEV_AMD74XX is not set
-# CONFIG_BLK_DEV_ATIIXP is not set
-# CONFIG_BLK_DEV_BSG is not set
-# CONFIG_BLK_DEV_BSGLIB is not set
-# CONFIG_BLK_DEV_CMD640 is not set
-# CONFIG_BLK_DEV_CMD64X is not set
-# CONFIG_BLK_DEV_COW_COMMON is not set
-# CONFIG_BLK_DEV_CRYPTOLOOP is not set
-# CONFIG_BLK_DEV_CS5520 is not set
-# CONFIG_BLK_DEV_CS5530 is not set
-# CONFIG_BLK_DEV_CS5535 is not set
-# CONFIG_BLK_DEV_CS5536 is not set
-# CONFIG_BLK_DEV_CY82C693 is not set
-# CONFIG_BLK_DEV_DAC960 is not set
-# CONFIG_BLK_DEV_DELKIN is not set
-# CONFIG_BLK_DEV_DM is not set
-# CONFIG_BLK_DEV_DRBD is not set
-# CONFIG_BLK_DEV_DTC2278 is not set
-# CONFIG_BLK_DEV_FD is not set
-# CONFIG_BLK_DEV_GENERIC is not set
-# CONFIG_BLK_DEV_HPT366 is not set
-# CONFIG_BLK_DEV_HT6560B is not set
-# CONFIG_BLK_DEV_IDEACPI is not set
-# CONFIG_BLK_DEV_IDECD is not set
-# CONFIG_BLK_DEV_IDECS is not set
-# CONFIG_BLK_DEV_IDEPCI is not set
-# CONFIG_BLK_DEV_IDEPNP is not set
-# CONFIG_BLK_DEV_IDETAPE is not set
-# CONFIG_BLK_DEV_IDE_AU1XXX is not set
-# CONFIG_BLK_DEV_IDE_SATA is not set
-CONFIG_BLK_DEV_INITRD=y
-# CONFIG_BLK_DEV_INTEGRITY is not set
-# CONFIG_BLK_DEV_IO_TRACE is not set
-# CONFIG_BLK_DEV_IT8172 is not set
-# CONFIG_BLK_DEV_IT8213 is not set
-# CONFIG_BLK_DEV_IT821X is not set
-# CONFIG_BLK_DEV_JMICRON is not set
-# CONFIG_BLK_DEV_LOOP is not set
-CONFIG_BLK_DEV_LOOP_MIN_COUNT=8
-# CONFIG_BLK_DEV_MD is not set
-# CONFIG_BLK_DEV_NBD is not set
-# CONFIG_BLK_DEV_NS87415 is not set
-# CONFIG_BLK_DEV_NULL_BLK is not set
-# CONFIG_BLK_DEV_NVME is not set
-# CONFIG_BLK_DEV_OFFBOARD is not set
-# CONFIG_BLK_DEV_OPTI621 is not set
-# CONFIG_BLK_DEV_PCIESSD_MTIP32XX is not set
-# CONFIG_BLK_DEV_PDC202XX_NEW is not set
-# CONFIG_BLK_DEV_PDC202XX_OLD is not set
-# CONFIG_BLK_DEV_PIIX is not set
-# CONFIG_BLK_DEV_PLATFORM is not set
-# CONFIG_BLK_DEV_PMEM is not set
-# CONFIG_BLK_DEV_QD65XX is not set
-# CONFIG_BLK_DEV_RAM is not set
-# CONFIG_BLK_DEV_RBD is not set
-# CONFIG_BLK_DEV_RSXX is not set
-# CONFIG_BLK_DEV_RZ1000 is not set
-# CONFIG_BLK_DEV_SC1200 is not set
-# CONFIG_BLK_DEV_SD is not set
-# CONFIG_BLK_DEV_SIIMAGE is not set
-# CONFIG_BLK_DEV_SIS5513 is not set
-# CONFIG_BLK_DEV_SKD is not set
-# CONFIG_BLK_DEV_SL82C105 is not set
-# CONFIG_BLK_DEV_SLC90E66 is not set
-# CONFIG_BLK_DEV_SR is not set
-# CONFIG_BLK_DEV_SVWKS is not set
-# CONFIG_BLK_DEV_SX8 is not set
-# CONFIG_BLK_DEV_TC86C001 is not set
-# CONFIG_BLK_DEV_THROTTLING is not set
-# CONFIG_BLK_DEV_TRIFLEX is not set
-# CONFIG_BLK_DEV_TRM290 is not set
-# CONFIG_BLK_DEV_UMC8672 is not set
-# CONFIG_BLK_DEV_UMEM is not set
-# CONFIG_BLK_DEV_VIA82CXXX is not set
-# CONFIG_BLK_DEV_ZONED is not set
-# CONFIG_BLK_INLINE_ENCRYPTION is not set
-# CONFIG_BLK_SED_OPAL is not set
-# CONFIG_BLK_WBT is not set
-CONFIG_BLOCK=y
-# CONFIG_BMA180 is not set
-# CONFIG_BMA220 is not set
-# CONFIG_BMA400 is not set
-# CONFIG_BMC150_ACCEL is not set
-# CONFIG_BMC150_MAGN is not set
-# CONFIG_BMC150_MAGN_I2C is not set
-# CONFIG_BMC150_MAGN_SPI is not set
-# CONFIG_BME680 is not set
-# CONFIG_BMG160 is not set
-# CONFIG_BMI088_ACCEL is not set
-# CONFIG_BMI160_I2C is not set
-# CONFIG_BMI160_SPI is not set
-# CONFIG_BMIPS_GENERIC is not set
-# CONFIG_BMP280 is not set
-# CONFIG_BNA is not set
-# CONFIG_BNX2 is not set
-# CONFIG_BNX2X is not set
-# CONFIG_BNX2X_SRIOV is not set
-# CONFIG_BNXT is not set
-# CONFIG_BONDING is not set
-# CONFIG_BOOKE_WDT is not set
-CONFIG_BOOKE_WDT_DEFAULT_TIMEOUT=3
-# CONFIG_BOOTPARAM_HARDLOCKUP_PANIC is not set
-# CONFIG_BOOTPARAM_HUNG_TASK_PANIC is not set
-# CONFIG_BOOTPARAM_SOFTLOCKUP_PANIC is not set
-# CONFIG_BOOTTIME_TRACING is not set
-# CONFIG_BOOT_CONFIG is not set
-# CONFIG_BOOT_PRINTK_DELAY is not set
-CONFIG_BOOT_RAW=y
-# CONFIG_BOUNCE is not set
-CONFIG_BPF=y
-# CONFIG_BPFILTER is not set
-CONFIG_BPF_JIT=y
-# CONFIG_BPF_JIT_ALWAYS_ON is not set
-CONFIG_BPF_JIT_DEFAULT_ON=y
-# CONFIG_BPF_PRELOAD is not set
-# CONFIG_BPF_STREAM_PARSER is not set
-CONFIG_BPF_SYSCALL=y
-CONFIG_BPF_UNPRIV_DEFAULT_OFF=y
-# CONFIG_BPQETHER is not set
-CONFIG_BQL=y
-CONFIG_BRANCH_PROFILE_NONE=y
-# CONFIG_BRCMFMAC is not set
-# CONFIG_BRCMSMAC is not set
-# CONFIG_BRCMSTB_GISB_ARB is not set
-CONFIG_BRIDGE=y
-# CONFIG_BRIDGE_CFM is not set
-# CONFIG_BRIDGE_EBT_802_3 is not set
-# CONFIG_BRIDGE_EBT_AMONG is not set
-# CONFIG_BRIDGE_EBT_ARP is not set
-# CONFIG_BRIDGE_EBT_ARPREPLY is not set
-# CONFIG_BRIDGE_EBT_BROUTE is not set
-# CONFIG_BRIDGE_EBT_DNAT is not set
-# CONFIG_BRIDGE_EBT_IP is not set
-# CONFIG_BRIDGE_EBT_IP6 is not set
-# CONFIG_BRIDGE_EBT_LIMIT is not set
-# CONFIG_BRIDGE_EBT_LOG is not set
-# CONFIG_BRIDGE_EBT_MARK is not set
-# CONFIG_BRIDGE_EBT_MARK_T is not set
-# CONFIG_BRIDGE_EBT_NFLOG is not set
-# CONFIG_BRIDGE_EBT_PKTTYPE is not set
-# CONFIG_BRIDGE_EBT_REDIRECT is not set
-# CONFIG_BRIDGE_EBT_SNAT is not set
-# CONFIG_BRIDGE_EBT_STP is not set
-# CONFIG_BRIDGE_EBT_T_FILTER is not set
-# CONFIG_BRIDGE_EBT_T_NAT is not set
-# CONFIG_BRIDGE_EBT_VLAN is not set
-CONFIG_BRIDGE_IGMP_SNOOPING=y
-# CONFIG_BRIDGE_MRP is not set
-# CONFIG_BRIDGE_NETFILTER is not set
-# CONFIG_BRIDGE_NF_EBTABLES is not set
-CONFIG_BRIDGE_VLAN_FILTERING=y
-# CONFIG_BROADCOM_PHY is not set
-CONFIG_BROKEN_ON_SMP=y
-# CONFIG_BSD_DISKLABEL is not set
-# CONFIG_BSD_PROCESS_ACCT is not set
-# CONFIG_BSD_PROCESS_ACCT_V3 is not set
-# CONFIG_BT is not set
-# CONFIG_BTRFS_ASSERT is not set
-# CONFIG_BTRFS_DEBUG is not set
-# CONFIG_BTRFS_FS is not set
-# CONFIG_BTRFS_FS_CHECK_INTEGRITY is not set
-# CONFIG_BTRFS_FS_POSIX_ACL is not set
-# CONFIG_BTRFS_FS_REF_VERIFY is not set
-# CONFIG_BTRFS_FS_RUN_SANITY_TESTS is not set
-# CONFIG_BT_AOSPEXT is not set
-# CONFIG_BT_ATH3K is not set
-# CONFIG_BT_BNEP is not set
-CONFIG_BT_BNEP_MC_FILTER=y
-CONFIG_BT_BNEP_PROTO_FILTER=y
-# CONFIG_BT_BREDR is not set
-# CONFIG_BT_CMTP is not set
-# CONFIG_BT_FEATURE_DEBUG is not set
-# CONFIG_BT_HCIBCM203X is not set
-# CONFIG_BT_HCIBFUSB is not set
-# CONFIG_BT_HCIBLUECARD is not set
-# CONFIG_BT_HCIBPA10X is not set
-# CONFIG_BT_HCIBT3C is not set
-# CONFIG_BT_HCIBTSDIO is not set
-# CONFIG_BT_HCIBTUSB is not set
-# CONFIG_BT_HCIBTUSB_AUTOSUSPEND is not set
-# CONFIG_BT_HCIBTUSB_MTK is not set
-# CONFIG_BT_HCIBTUSB_RTL is not set
-# CONFIG_BT_HCIDTL1 is not set
-# CONFIG_BT_HCIUART is not set
-# CONFIG_BT_HCIUART_3WIRE is not set
-# CONFIG_BT_HCIUART_AG6XX is not set
-# CONFIG_BT_HCIUART_ATH3K is not set
-CONFIG_BT_HCIUART_BCSP=y
-CONFIG_BT_HCIUART_H4=y
-# CONFIG_BT_HCIUART_LL is not set
-# CONFIG_BT_HCIUART_MRVL is not set
-# CONFIG_BT_HCIUART_QCA is not set
-# CONFIG_BT_HCIUART_RTL is not set
-# CONFIG_BT_HCIVHCI is not set
-# CONFIG_BT_HIDP is not set
-# CONFIG_BT_HS is not set
-# CONFIG_BT_LE is not set
-# CONFIG_BT_LEDS is not set
-# CONFIG_BT_MRVL is not set
-# CONFIG_BT_MSFTEXT is not set
-# CONFIG_BT_MTKSDIO is not set
-# CONFIG_BT_MTKUART is not set
-# CONFIG_BT_RFCOMM is not set
-CONFIG_BT_RFCOMM_TTY=y
-# CONFIG_BT_SELFTEST is not set
-# CONFIG_BT_VIRTIO is not set
-CONFIG_BUG=y
-# CONFIG_BUG_ON_DATA_CORRUPTION is not set
-CONFIG_BUILDTIME_EXTABLE_SORT=y
-CONFIG_BUILDTIME_TABLE_SORT=y
-# CONFIG_BUILD_BIN2C is not set
-CONFIG_BUILD_SALT=""
-# CONFIG_C2PORT is not set
-CONFIG_CACHE_L2X0_PMU=y
-# CONFIG_CADENCE_WATCHDOG is not set
-# CONFIG_CAIF is not set
-# CONFIG_CAN is not set
-# CONFIG_CAN_BCM is not set
-# CONFIG_CAN_DEBUG_DEVICES is not set
-# CONFIG_CAN_DEV is not set
-# CONFIG_CAN_ETAS_ES58X is not set
-# CONFIG_CAN_GS_USB is not set
-# CONFIG_CAN_GW is not set
-# CONFIG_CAN_HI311X is not set
-# CONFIG_CAN_IFI_CANFD is not set
-# CONFIG_CAN_ISOTP is not set
-# CONFIG_CAN_J1939 is not set
-# CONFIG_CAN_KVASER_PCIEFD is not set
-# CONFIG_CAN_MCBA_USB is not set
-# CONFIG_CAN_MCP251XFD is not set
-# CONFIG_CAN_M_CAN is not set
-# CONFIG_CAN_PEAK_PCIEFD is not set
-# CONFIG_CAN_RAW is not set
-# CONFIG_CAN_RCAR is not set
-# CONFIG_CAN_RCAR_CANFD is not set
-# CONFIG_CAN_SLCAN is not set
-# CONFIG_CAN_SUN4I is not set
-# CONFIG_CAN_UCAN is not set
-# CONFIG_CAN_VCAN is not set
-# CONFIG_CAN_VXCAN is not set
-# CONFIG_CAPI_AVM is not set
-# CONFIG_CAPI_EICON is not set
-# CONFIG_CAPI_TRACE is not set
-CONFIG_CARDBUS=y
-# CONFIG_CARDMAN_4000 is not set
-# CONFIG_CARDMAN_4040 is not set
-# CONFIG_CARL9170 is not set
-# CONFIG_CASSINI is not set
-# CONFIG_CAVIUM_CPT is not set
-# CONFIG_CAVIUM_ERRATUM_22375 is not set
-# CONFIG_CAVIUM_ERRATUM_23144 is not set
-# CONFIG_CAVIUM_ERRATUM_23154 is not set
-# CONFIG_CAVIUM_ERRATUM_27456 is not set
-# CONFIG_CAVIUM_ERRATUM_30115 is not set
-# CONFIG_CAVIUM_OCTEON_SOC is not set
-# CONFIG_CAVIUM_PTP is not set
-# CONFIG_CAVIUM_TX2_ERRATUM_219 is not set
-# CONFIG_CB710_CORE is not set
-# CONFIG_CC10001_ADC is not set
-# CONFIG_CCS811 is not set
-CONFIG_CC_CAN_LINK=y
-CONFIG_CC_OPTIMIZE_FOR_PERFORMANCE=y
-# CONFIG_CC_OPTIMIZE_FOR_SIZE is not set
-# CONFIG_CDROM_PKTCDVD is not set
-# CONFIG_CEPH_FS is not set
-# CONFIG_CEPH_LIB is not set
-# CONFIG_CFG80211 is not set
-# CONFIG_CFG80211_CERTIFICATION_ONUS is not set
-# CONFIG_CGROUPS is not set
-# CONFIG_CGROUP_MISC is not set
-# CONFIG_CHARGER_ADP5061 is not set
-# CONFIG_CHARGER_BD99954 is not set
-# CONFIG_CHARGER_BQ2415X is not set
-# CONFIG_CHARGER_BQ24190 is not set
-# CONFIG_CHARGER_BQ24257 is not set
-# CONFIG_CHARGER_BQ24735 is not set
-# CONFIG_CHARGER_BQ2515X is not set
-# CONFIG_CHARGER_BQ256XX is not set
-# CONFIG_CHARGER_BQ25890 is not set
-# CONFIG_CHARGER_BQ25980 is not set
-# CONFIG_CHARGER_DETECTOR_MAX14656 is not set
-# CONFIG_CHARGER_GPIO is not set
-# CONFIG_CHARGER_ISP1704 is not set
-# CONFIG_CHARGER_LP8727 is not set
-# CONFIG_CHARGER_LT3651 is not set
-# CONFIG_CHARGER_LTC3651 is not set
-# CONFIG_CHARGER_LTC4162L is not set
-# CONFIG_CHARGER_MANAGER is not set
-# CONFIG_CHARGER_MAX8903 is not set
-# CONFIG_CHARGER_QCOM_SMBB is not set
-# CONFIG_CHARGER_RT9455 is not set
-# CONFIG_CHARGER_SBS is not set
-# CONFIG_CHARGER_SMB347 is not set
-# CONFIG_CHARGER_TWL4030 is not set
-# CONFIG_CHARGER_UCS1002 is not set
-# CONFIG_CHASH_SELFTEST is not set
-# CONFIG_CHASH_STATS is not set
-# CONFIG_CHECKPOINT_RESTORE is not set
-# CONFIG_CHELSIO_T1 is not set
-# CONFIG_CHELSIO_T3 is not set
-# CONFIG_CHELSIO_T4 is not set
-# CONFIG_CHELSIO_T4VF is not set
-# CONFIG_CHROME_PLATFORMS is not set
-# CONFIG_CHR_DEV_OSST is not set
-# CONFIG_CHR_DEV_SCH is not set
-# CONFIG_CHR_DEV_SG is not set
-# CONFIG_CHR_DEV_ST is not set
-# CONFIG_CICADA_PHY is not set
-# CONFIG_CIFS is not set
-# CONFIG_CIFS_ACL is not set
-CONFIG_CIFS_ALLOW_INSECURE_LEGACY=y
-# CONFIG_CIFS_DEBUG is not set
-# CONFIG_CIFS_DEBUG2 is not set
-# CONFIG_CIFS_FSCACHE is not set
-# CONFIG_CIFS_NFSD_EXPORT is not set
-CONFIG_CIFS_POSIX=y
-# CONFIG_CIFS_SMB2 is not set
-# CONFIG_CIFS_STATS is not set
-# CONFIG_CIFS_STATS2 is not set
-# CONFIG_CIFS_SWN_UPCALL is not set
-# CONFIG_CIFS_WEAK_PW_HASH is not set
-CONFIG_CIFS_XATTR=y
-# CONFIG_CIO_DAC is not set
-# CONFIG_CLEANCACHE is not set
-# CONFIG_CLKSRC_PISTACHIO is not set
-# CONFIG_CLKSRC_VERSATILE is not set
-# CONFIG_CLK_GFM_LPASS_SM8250 is not set
-# CONFIG_CLK_HSDK is not set
-# CONFIG_CLK_QORIQ is not set
-# CONFIG_CLK_SP810 is not set
-# CONFIG_CLOCK_THERMAL is not set
-CONFIG_CLS_U32_MARK=y
-# CONFIG_CLS_U32_PERF is not set
-# CONFIG_CM32181 is not set
-# CONFIG_CM3232 is not set
-# CONFIG_CM3323 is not set
-# CONFIG_CM3605 is not set
-# CONFIG_CM36651 is not set
-# CONFIG_CMA is not set
-CONFIG_CMDLINE=""
-# CONFIG_CMDLINE_BOOL is not set
-# CONFIG_CMDLINE_EXTEND is not set
-# CONFIG_CMDLINE_FORCE is not set
-# CONFIG_CMDLINE_FROM_BOOTLOADER is not set
-# CONFIG_CMDLINE_PARTITION is not set
-# CONFIG_CNIC is not set
-# CONFIG_CODA_FS is not set
-# CONFIG_CODE_PATCHING_SELFTEST is not set
-# CONFIG_COMEDI is not set
-# CONFIG_COMMON_CLK_AXI_CLKGEN is not set
-# CONFIG_COMMON_CLK_BOSTON is not set
-# CONFIG_COMMON_CLK_CDCE706 is not set
-# CONFIG_COMMON_CLK_CDCE925 is not set
-# CONFIG_COMMON_CLK_CS2000_CP is not set
-# CONFIG_COMMON_CLK_FIXED_MMIO is not set
-# CONFIG_COMMON_CLK_IPROC is not set
-# CONFIG_COMMON_CLK_MAX9485 is not set
-# CONFIG_COMMON_CLK_MT6765 is not set
-# CONFIG_COMMON_CLK_MT8167 is not set
-# CONFIG_COMMON_CLK_MT8167_AUDSYS is not set
-# CONFIG_COMMON_CLK_MT8167_IMGSYS is not set
-# CONFIG_COMMON_CLK_MT8167_MFGCFG is not set
-# CONFIG_COMMON_CLK_MT8167_MMSYS is not set
-# CONFIG_COMMON_CLK_MT8167_VDECSYS is not set
-# CONFIG_COMMON_CLK_MT8192 is not set
-# CONFIG_COMMON_CLK_NXP is not set
-# CONFIG_COMMON_CLK_PIC32 is not set
-# CONFIG_COMMON_CLK_PISTACHIO is not set
-# CONFIG_COMMON_CLK_PWM is not set
-# CONFIG_COMMON_CLK_PXA is not set
-# CONFIG_COMMON_CLK_QCOM is not set
-# CONFIG_COMMON_CLK_SI514 is not set
-# CONFIG_COMMON_CLK_SI5341 is not set
-# CONFIG_COMMON_CLK_SI5351 is not set
-# CONFIG_COMMON_CLK_SI544 is not set
-# CONFIG_COMMON_CLK_SI570 is not set
-# CONFIG_COMMON_CLK_VC5 is not set
-# CONFIG_COMMON_CLK_XGENE is not set
-# CONFIG_COMMON_CLK_XLNX_CLKWZRD is not set
-CONFIG_COMPACTION=y
-# CONFIG_COMPAL_LAPTOP is not set
-# CONFIG_COMPAT is not set
-# CONFIG_COMPAT_BRK is not set
-# CONFIG_COMPILE_TEST is not set
-# CONFIG_CONFIGFS_FS is not set
-# CONFIG_CONNECTOR is not set
-CONFIG_CONSOLE_LOGLEVEL_DEFAULT=7
-CONFIG_CONSOLE_LOGLEVEL_QUIET=4
-CONFIG_CONSTRUCTORS=y
-# CONFIG_CONTEXT_SWITCH_TRACER is not set
-# CONFIG_COPS is not set
-# CONFIG_CORDIC is not set
-# CONFIG_COREDUMP is not set
-# CONFIG_CORESIGHT is not set
-# CONFIG_CORE_DUMP_DEFAULT_ELF_HEADERS is not set
-# CONFIG_CORTINA_PHY is not set
-# CONFIG_COUNTER is not set
-# CONFIG_CPA_DEBUG is not set
-# CONFIG_CPU_BIG_ENDIAN is not set
-# CONFIG_CPU_BPREDICT_DISABLE is not set
-# CONFIG_CPU_DCACHE_DISABLE is not set
-# CONFIG_CPU_FREQ is not set
-# CONFIG_CPU_FREQ_DEFAULT_GOV_CONSERVATIVE is not set
-# CONFIG_CPU_FREQ_DEFAULT_GOV_ONDEMAND is not set
-# CONFIG_CPU_FREQ_DEFAULT_GOV_POWERSAVE is not set
-# CONFIG_CPU_FREQ_DEFAULT_GOV_SCHEDUTIL is not set
-# CONFIG_CPU_FREQ_DEFAULT_GOV_USERSPACE is not set
-# CONFIG_CPU_FREQ_GOV_SCHEDUTIL is not set
-# CONFIG_CPU_FREQ_STAT_DETAILS is not set
-# CONFIG_CPU_FREQ_THERMAL is not set
-# CONFIG_CPU_HOTPLUG_STATE_CONTROL is not set
-# CONFIG_CPU_ICACHE_DISABLE is not set
-# CONFIG_CPU_ICACHE_MISMATCH_WORKAROUND is not set
-# CONFIG_CPU_IDLE is not set
-# CONFIG_CPU_IDLE_GOV_LADDER is not set
-# CONFIG_CPU_IDLE_GOV_MENU is not set
-# CONFIG_CPU_IDLE_GOV_TEO is not set
-# CONFIG_CPU_IDLE_MULTIPLE_DRIVERS is not set
-# CONFIG_CPU_ISOLATION is not set
-# CONFIG_CPU_LITTLE_ENDIAN is not set
-# CONFIG_CPU_NO_EFFICIENT_FFS is not set
-CONFIG_CPU_SW_DOMAIN_PAN=y
-# CONFIG_CPU_THERMAL is not set
-# CONFIG_CRAMFS is not set
-CONFIG_CRAMFS_BLOCKDEV=y
-# CONFIG_CRAMFS_MTD is not set
-# CONFIG_CRASH_DUMP is not set
-# CONFIG_CRC16 is not set
-CONFIG_CRC32=y
-# CONFIG_CRC32_BIT is not set
-# CONFIG_CRC32_SARWATE is not set
-# CONFIG_CRC32_SELFTEST is not set
-# CONFIG_CRC32_SLICEBY4 is not set
-CONFIG_CRC32_SLICEBY8=y
-# CONFIG_CRC4 is not set
-# CONFIG_CRC64 is not set
-# CONFIG_CRC7 is not set
-# CONFIG_CRC8 is not set
-# CONFIG_CRC_CCITT is not set
-# CONFIG_CRC_ITU_T is not set
-# CONFIG_CRC_T10DIF is not set
-CONFIG_CROSS_COMPILE=""
-# CONFIG_CROSS_MEMORY_ATTACH is not set
-CONFIG_CRYPTO=y
-# CONFIG_CRYPTO_842 is not set
-CONFIG_CRYPTO_ACOMP2=y
-# CONFIG_CRYPTO_ADIANTUM is not set
-CONFIG_CRYPTO_AEAD=y
-CONFIG_CRYPTO_AEAD2=y
-# CONFIG_CRYPTO_AEGIS128 is not set
-# CONFIG_CRYPTO_AEGIS128L is not set
-# CONFIG_CRYPTO_AEGIS128L_AESNI_SSE2 is not set
-# CONFIG_CRYPTO_AEGIS128_AESNI_SSE2 is not set
-# CONFIG_CRYPTO_AEGIS256 is not set
-# CONFIG_CRYPTO_AEGIS256_AESNI_SSE2 is not set
-CONFIG_CRYPTO_AES=y
-# CONFIG_CRYPTO_AES_586 is not set
-# CONFIG_CRYPTO_AES_ARM is not set
-# CONFIG_CRYPTO_AES_ARM64 is not set
-# CONFIG_CRYPTO_AES_ARM64_BS is not set
-# CONFIG_CRYPTO_AES_ARM64_CE is not set
-# CONFIG_CRYPTO_AES_ARM64_CE_BLK is not set
-# CONFIG_CRYPTO_AES_ARM64_CE_CCM is not set
-# CONFIG_CRYPTO_AES_ARM64_NEON_BLK is not set
-# CONFIG_CRYPTO_AES_ARM_BS is not set
-# CONFIG_CRYPTO_AES_ARM_CE is not set
-# CONFIG_CRYPTO_AES_NI_INTEL is not set
-# CONFIG_CRYPTO_AES_TI is not set
-CONFIG_CRYPTO_AKCIPHER=y
-CONFIG_CRYPTO_AKCIPHER2=y
-CONFIG_CRYPTO_ALGAPI=y
-CONFIG_CRYPTO_ALGAPI2=y
-# CONFIG_CRYPTO_ANSI_CPRNG is not set
-# CONFIG_CRYPTO_ANUBIS is not set
-# CONFIG_CRYPTO_ARC4 is not set
-# CONFIG_CRYPTO_AUTHENC is not set
-# CONFIG_CRYPTO_BLAKE2B is not set
-# CONFIG_CRYPTO_BLAKE2B_NEON is not set
-# CONFIG_CRYPTO_BLAKE2S_ARM is not set
-# CONFIG_CRYPTO_BLAKE2S_X86 is not set
-# CONFIG_CRYPTO_BLOWFISH is not set
-# CONFIG_CRYPTO_CAMELLIA is not set
-# CONFIG_CRYPTO_CAST5 is not set
-# CONFIG_CRYPTO_CAST6 is not set
-# CONFIG_CRYPTO_CBC is not set
-CONFIG_CRYPTO_CCM=y
-# CONFIG_CRYPTO_CFB is not set
-# CONFIG_CRYPTO_CHACHA20 is not set
-# CONFIG_CRYPTO_CHACHA20POLY1305 is not set
-# CONFIG_CRYPTO_CHACHA20_NEON is not set
-# CONFIG_CRYPTO_CHACHA20_X86_64 is not set
-# CONFIG_CRYPTO_CHACHA_MIPS is not set
-# CONFIG_CRYPTO_CMAC is not set
-# CONFIG_CRYPTO_CRC32 is not set
-# CONFIG_CRYPTO_CRC32C is not set
-# CONFIG_CRYPTO_CRC32C_INTEL is not set
-# CONFIG_CRYPTO_CRC32_ARM_CE is not set
-# CONFIG_CRYPTO_CRCT10DIF is not set
-# CONFIG_CRYPTO_CRCT10DIF_ARM64_CE is not set
-# CONFIG_CRYPTO_CRCT10DIF_ARM_CE is not set
-# CONFIG_CRYPTO_CRYPTD is not set
-CONFIG_CRYPTO_CTR=y
-# CONFIG_CRYPTO_CTS is not set
-# CONFIG_CRYPTO_CURVE25519 is not set
-# CONFIG_CRYPTO_CURVE25519_NEON is not set
-# CONFIG_CRYPTO_CURVE25519_X86 is not set
-# CONFIG_CRYPTO_DEFLATE is not set
-# CONFIG_CRYPTO_DES is not set
-# CONFIG_CRYPTO_DEV_AMLOGIC_GXL is not set
-# CONFIG_CRYPTO_DEV_ATMEL_AES is not set
-# CONFIG_CRYPTO_DEV_ATMEL_AUTHENC is not set
-# CONFIG_CRYPTO_DEV_ATMEL_ECC is not set
-# CONFIG_CRYPTO_DEV_ATMEL_SHA is not set
-# CONFIG_CRYPTO_DEV_ATMEL_SHA204A is not set
-# CONFIG_CRYPTO_DEV_ATMEL_TDES is not set
-# CONFIG_CRYPTO_DEV_CAVIUM_ZIP is not set
-# CONFIG_CRYPTO_DEV_CCP is not set
-# CONFIG_CRYPTO_DEV_CCP_DEBUGFS is not set
-# CONFIG_CRYPTO_DEV_CCREE is not set
-# CONFIG_CRYPTO_DEV_FSL_CAAM is not set
-# CONFIG_CRYPTO_DEV_FSL_CAAM_CRYPTO_API_DESC is not set
-# CONFIG_CRYPTO_DEV_HIFN_795X is not set
-# CONFIG_CRYPTO_DEV_HISI_SEC is not set
-# CONFIG_CRYPTO_DEV_HISI_ZIP is not set
-# CONFIG_CRYPTO_DEV_IMGTEC_HASH is not set
-# CONFIG_CRYPTO_DEV_MARVELL_CESA is not set
-# CONFIG_CRYPTO_DEV_MEDIATEK is not set
-# CONFIG_CRYPTO_DEV_MV_CESA is not set
-# CONFIG_CRYPTO_DEV_MXC_SCC is not set
-# CONFIG_CRYPTO_DEV_MXS_DCP is not set
-# CONFIG_CRYPTO_DEV_NITROX_CNN55XX is not set
-# CONFIG_CRYPTO_DEV_OCTEONTX_CPT is not set
-# CONFIG_CRYPTO_DEV_QAT_4XXX is not set
-# CONFIG_CRYPTO_DEV_QAT_C3XXX is not set
-# CONFIG_CRYPTO_DEV_QAT_C3XXXVF is not set
-# CONFIG_CRYPTO_DEV_QAT_C62X is not set
-# CONFIG_CRYPTO_DEV_QAT_C62XVF is not set
-# CONFIG_CRYPTO_DEV_QAT_DH895xCC is not set
-# CONFIG_CRYPTO_DEV_QAT_DH895xCCVF is not set
-# CONFIG_CRYPTO_DEV_QCE is not set
-# CONFIG_CRYPTO_DEV_S5P is not set
-# CONFIG_CRYPTO_DEV_SAFEXCEL is not set
-# CONFIG_CRYPTO_DEV_SAHARA is not set
-# CONFIG_CRYPTO_DEV_SP_PSP is not set
-# CONFIG_CRYPTO_DEV_TALITOS is not set
-# CONFIG_CRYPTO_DEV_VIRTIO is not set
-# CONFIG_CRYPTO_DH is not set
-# CONFIG_CRYPTO_DRBG_CTR is not set
-# CONFIG_CRYPTO_DRBG_HASH is not set
-# CONFIG_CRYPTO_DRBG_MENU is not set
-# CONFIG_CRYPTO_ECB is not set
-# CONFIG_CRYPTO_ECDH is not set
-# CONFIG_CRYPTO_ECDSA is not set
-# CONFIG_CRYPTO_ECHAINIV is not set
-# CONFIG_CRYPTO_ECRDSA is not set
-# CONFIG_CRYPTO_ESSIV is not set
-# CONFIG_CRYPTO_FCRYPT is not set
-# CONFIG_CRYPTO_FIPS is not set
-CONFIG_CRYPTO_GCM=y
-CONFIG_CRYPTO_GF128MUL=y
-CONFIG_CRYPTO_GHASH=y
-# CONFIG_CRYPTO_GHASH_ARM64_CE is not set
-# CONFIG_CRYPTO_GHASH_ARM_CE is not set
-# CONFIG_CRYPTO_GHASH_CLMUL_NI_INTEL is not set
-CONFIG_CRYPTO_HASH=y
-CONFIG_CRYPTO_HASH2=y
-# CONFIG_CRYPTO_HMAC is not set
-# CONFIG_CRYPTO_HW is not set
-# CONFIG_CRYPTO_JITTERENTROPY is not set
-# CONFIG_CRYPTO_KEYWRAP is not set
-# CONFIG_CRYPTO_KHAZAD is not set
-CONFIG_CRYPTO_KPP=y
-CONFIG_CRYPTO_KPP2=y
-CONFIG_CRYPTO_LIB_AES=y
-CONFIG_CRYPTO_LIB_ARC4=y
-# CONFIG_CRYPTO_LIB_BLAKE2S_GENERIC is not set
-# CONFIG_CRYPTO_LIB_CHACHA is not set
-# CONFIG_CRYPTO_LIB_CHACHA20POLY1305 is not set
-# CONFIG_CRYPTO_LIB_CURVE25519 is not set
-# CONFIG_CRYPTO_LIB_POLY1305 is not set
-CONFIG_CRYPTO_LIB_POLY1305_RSIZE=9
-# CONFIG_CRYPTO_LRW is not set
-# CONFIG_CRYPTO_LZ4 is not set
-# CONFIG_CRYPTO_LZ4HC is not set
-# CONFIG_CRYPTO_LZO is not set
-CONFIG_CRYPTO_MANAGER=y
-CONFIG_CRYPTO_MANAGER2=y
-CONFIG_CRYPTO_MANAGER_DISABLE_TESTS=y
-# CONFIG_CRYPTO_MCRYPTD is not set
-# CONFIG_CRYPTO_MD4 is not set
-# CONFIG_CRYPTO_MD5 is not set
-# CONFIG_CRYPTO_MICHAEL_MIC is not set
-# CONFIG_CRYPTO_MORUS1280 is not set
-# CONFIG_CRYPTO_MORUS1280_AVX2 is not set
-# CONFIG_CRYPTO_MORUS1280_SSE2 is not set
-# CONFIG_CRYPTO_MORUS640 is not set
-# CONFIG_CRYPTO_MORUS640_SSE2 is not set
-# CONFIG_CRYPTO_NHPOLY1305_NEON is not set
-CONFIG_CRYPTO_NULL=y
-CONFIG_CRYPTO_NULL2=y
-# CONFIG_CRYPTO_OFB is not set
-# CONFIG_CRYPTO_PCBC is not set
-# CONFIG_CRYPTO_PCOMP is not set
-# CONFIG_CRYPTO_PCOMP2 is not set
-CONFIG_CRYPTO_PCRYPT=y
-# CONFIG_CRYPTO_POLY1305 is not set
-# CONFIG_CRYPTO_POLY1305_ARM is not set
-# CONFIG_CRYPTO_POLY1305_MIPS is not set
-# CONFIG_CRYPTO_POLY1305_NEON is not set
-# CONFIG_CRYPTO_POLY1305_X86_64 is not set
-# CONFIG_CRYPTO_RMD160 is not set
-# CONFIG_CRYPTO_RNG is not set
-# CONFIG_CRYPTO_RSA is not set
-# CONFIG_CRYPTO_SEED is not set
-# CONFIG_CRYPTO_SEQIV is not set
-# CONFIG_CRYPTO_SERPENT is not set
-# CONFIG_CRYPTO_SHA1 is not set
-# CONFIG_CRYPTO_SHA1_ARM is not set
-# CONFIG_CRYPTO_SHA1_ARM64_CE is not set
-# CONFIG_CRYPTO_SHA1_ARM_CE is not set
-# CONFIG_CRYPTO_SHA1_ARM_NEON is not set
-# CONFIG_CRYPTO_SHA256 is not set
-# CONFIG_CRYPTO_SHA256_ARM is not set
-# CONFIG_CRYPTO_SHA256_ARM64 is not set
-# CONFIG_CRYPTO_SHA2_ARM64_CE is not set
-# CONFIG_CRYPTO_SHA2_ARM_CE is not set
-# CONFIG_CRYPTO_SHA3 is not set
-# CONFIG_CRYPTO_SHA3_ARM64 is not set
-# CONFIG_CRYPTO_SHA512 is not set
-# CONFIG_CRYPTO_SHA512_ARM is not set
-# CONFIG_CRYPTO_SHA512_ARM64 is not set
-# CONFIG_CRYPTO_SHA512_ARM64_CE is not set
-# CONFIG_CRYPTO_SIMD is not set
-CONFIG_CRYPTO_SKCIPHER=y
-CONFIG_CRYPTO_SKCIPHER2=y
-# CONFIG_CRYPTO_SM2 is not set
-# CONFIG_CRYPTO_SM3 is not set
-# CONFIG_CRYPTO_SM3_ARM64_CE is not set
-# CONFIG_CRYPTO_SM4 is not set
-# CONFIG_CRYPTO_SM4_ARM64_CE is not set
-# CONFIG_CRYPTO_SPECK is not set
-# CONFIG_CRYPTO_STATS is not set
-# CONFIG_CRYPTO_STREEBOG is not set
-# CONFIG_CRYPTO_TEA is not set
-# CONFIG_CRYPTO_TEST is not set
-# CONFIG_CRYPTO_TWOFISH is not set
-# CONFIG_CRYPTO_TWOFISH_586 is not set
-# CONFIG_CRYPTO_TWOFISH_COMMON is not set
-# CONFIG_CRYPTO_USER is not set
-# CONFIG_CRYPTO_USER_API_AEAD is not set
-# CONFIG_CRYPTO_USER_API_ENABLE_OBSOLETE is not set
-# CONFIG_CRYPTO_USER_API_HASH is not set
-# CONFIG_CRYPTO_USER_API_RNG is not set
-# CONFIG_CRYPTO_USER_API_RNG_CAVP is not set
-# CONFIG_CRYPTO_USER_API_SKCIPHER is not set
-# CONFIG_CRYPTO_VMAC is not set
-# CONFIG_CRYPTO_WP512 is not set
-# CONFIG_CRYPTO_XCBC is not set
-# CONFIG_CRYPTO_XTS is not set
-# CONFIG_CRYPTO_XXHASH is not set
-# CONFIG_CRYPTO_ZLIB is not set
-# CONFIG_CRYPTO_ZSTD is not set
-# CONFIG_CS5535_MFGPT is not set
-# CONFIG_CS89x0 is not set
-# CONFIG_CS89x0_PLATFORM is not set
-# CONFIG_CSD_LOCK_WAIT_DEBUG is not set
-# CONFIG_CUSE is not set
-# CONFIG_CW1200 is not set
-# CONFIG_CXD2880_SPI_DRV is not set
-# CONFIG_CXL_AFU_DRIVER_OPS is not set
-# CONFIG_CXL_BASE is not set
-# CONFIG_CXL_BUS is not set
-# CONFIG_CXL_EEH is not set
-# CONFIG_CXL_KERNEL_API is not set
-# CONFIG_CXL_LIB is not set
-# CONFIG_CYPRESS_FIRMWARE is not set
-# CONFIG_DA280 is not set
-# CONFIG_DA311 is not set
-# CONFIG_DAMON is not set
-# CONFIG_DAVICOM_PHY is not set
-# CONFIG_DAX is not set
-# CONFIG_DCB is not set
-# CONFIG_DDR is not set
-# CONFIG_DEBUG_ALIGN_RODATA is not set
-# CONFIG_DEBUG_ATOMIC_SLEEP is not set
-# CONFIG_DEBUG_BLOCK_EXT_DEVT is not set
-# CONFIG_DEBUG_BUGVERBOSE is not set
-# CONFIG_DEBUG_CREDENTIALS is not set
-# CONFIG_DEBUG_DEVRES is not set
-# CONFIG_DEBUG_DRIVER is not set
-# CONFIG_DEBUG_EFI is not set
-# CONFIG_DEBUG_FORCE_FUNCTION_ALIGN_32B is not set
-# CONFIG_DEBUG_FORCE_FUNCTION_ALIGN_64B is not set
-# CONFIG_DEBUG_FORCE_WEAK_PER_CPU is not set
-CONFIG_DEBUG_FS=y
-CONFIG_DEBUG_FS_ALLOW_ALL=y
-# CONFIG_DEBUG_FS_ALLOW_NONE is not set
-# CONFIG_DEBUG_FS_DISALLOW_MOUNT is not set
-# CONFIG_DEBUG_GPIO is not set
-# CONFIG_DEBUG_HIGHMEM is not set
-# CONFIG_DEBUG_ICEDCC is not set
-# CONFIG_DEBUG_INFO is not set
-# CONFIG_DEBUG_INFO_BTF is not set
-# CONFIG_DEBUG_INFO_COMPRESSED is not set
-# CONFIG_DEBUG_INFO_DWARF4 is not set
-# CONFIG_DEBUG_INFO_DWARF5 is not set
-CONFIG_DEBUG_INFO_DWARF_TOOLCHAIN_DEFAULT=y
-# CONFIG_DEBUG_INFO_REDUCED is not set
-# CONFIG_DEBUG_INFO_SPLIT is not set
-# CONFIG_DEBUG_IRQFLAGS is not set
-CONFIG_DEBUG_KERNEL=y
-# CONFIG_DEBUG_KMAP_LOCAL is not set
-# CONFIG_DEBUG_KMEMLEAK is not set
-# CONFIG_DEBUG_KOBJECT is not set
-# CONFIG_DEBUG_KOBJECT_RELEASE is not set
-# CONFIG_DEBUG_LIST is not set
-# CONFIG_DEBUG_LL is not set
-# CONFIG_DEBUG_LL_UART_8250 is not set
-# CONFIG_DEBUG_LL_UART_PL01X is not set
-# CONFIG_DEBUG_LOCKDEP is not set
-# CONFIG_DEBUG_LOCKING_API_SELFTESTS is not set
-# CONFIG_DEBUG_LOCK_ALLOC is not set
-# CONFIG_DEBUG_MEMORY_INIT is not set
-# CONFIG_DEBUG_MISC is not set
-# CONFIG_DEBUG_MUTEXES is not set
-# CONFIG_DEBUG_NOTIFIERS is not set
-# CONFIG_DEBUG_NX_TEST is not set
-# CONFIG_DEBUG_OBJECTS is not set
-# CONFIG_DEBUG_PAGEALLOC is not set
-# CONFIG_DEBUG_PAGE_REF is not set
-# CONFIG_DEBUG_PERF_USE_VMALLOC is not set
-# CONFIG_DEBUG_PER_CPU_MAPS is not set
-# CONFIG_DEBUG_PINCTRL is not set
-# CONFIG_DEBUG_PI_LIST is not set
-# CONFIG_DEBUG_PLIST is not set
-# CONFIG_DEBUG_PREEMPT is not set
-# CONFIG_DEBUG_RODATA_TEST is not set
-# CONFIG_DEBUG_RSEQ is not set
-# CONFIG_DEBUG_RT_MUTEXES is not set
-# CONFIG_DEBUG_RWSEMS is not set
-# CONFIG_DEBUG_SECTION_MISMATCH is not set
-# CONFIG_DEBUG_SEMIHOSTING is not set
-# CONFIG_DEBUG_SG is not set
-# CONFIG_DEBUG_SHIRQ is not set
-# CONFIG_DEBUG_SLAB is not set
-# CONFIG_DEBUG_SPINLOCK is not set
-# CONFIG_DEBUG_STACKOVERFLOW is not set
-# CONFIG_DEBUG_STACK_USAGE is not set
-# CONFIG_DEBUG_STRICT_USER_COPY_CHECKS is not set
-# CONFIG_DEBUG_TEST_DRIVER_REMOVE is not set
-# CONFIG_DEBUG_TIMEKEEPING is not set
-# CONFIG_DEBUG_UART_8250_PALMCHIP is not set
-# CONFIG_DEBUG_UART_8250_WORD is not set
-# CONFIG_DEBUG_UART_BCM63XX is not set
-# CONFIG_DEBUG_UART_FLOW_CONTROL is not set
-# CONFIG_DEBUG_USER is not set
-# CONFIG_DEBUG_VIRTUAL is not set
-# CONFIG_DEBUG_VM is not set
-# CONFIG_DEBUG_VM_PGFLAGS is not set
-# CONFIG_DEBUG_VM_PGTABLE is not set
-# CONFIG_DEBUG_VM_RB is not set
-# CONFIG_DEBUG_VM_VMACACHE is not set
-# CONFIG_DEBUG_WQ_FORCE_RR_CPU is not set
-# CONFIG_DEBUG_WW_MUTEX_SLOWPATH is not set
-# CONFIG_DEBUG_WX is not set
-# CONFIG_DEBUG_ZBOOT is not set
-# CONFIG_DECNET is not set
-# CONFIG_DEFAULT_CODEL is not set
-CONFIG_DEFAULT_CUBIC=y
-CONFIG_DEFAULT_DEADLINE=y
-# CONFIG_DEFAULT_FQ is not set
-CONFIG_DEFAULT_FQ_CODEL=y
-# CONFIG_DEFAULT_FQ_PIE is not set
-CONFIG_DEFAULT_HOSTNAME="(none)"
-CONFIG_DEFAULT_HUNG_TASK_TIMEOUT=120
-CONFIG_DEFAULT_INIT=""
-CONFIG_DEFAULT_MMAP_MIN_ADDR=4096
-CONFIG_DEFAULT_NET_SCH="fq_codel"
-# CONFIG_DEFAULT_NOOP is not set
-# CONFIG_DEFAULT_PFIFO_FAST is not set
-# CONFIG_DEFAULT_RENO is not set
-CONFIG_DEFAULT_SECURITY=""
-CONFIG_DEFAULT_SECURITY_DAC=y
-# CONFIG_DEFAULT_SECURITY_SELINUX is not set
-# CONFIG_DEFAULT_SFQ is not set
-CONFIG_DEFAULT_TCP_CONG="cubic"
-CONFIG_DEFCONFIG_LIST="/lib/modules/$UNAME_RELEASE/.config"
-# CONFIG_DEFERRED_STRUCT_PAGE_INIT is not set
-# CONFIG_DELL_LAPTOP is not set
-# CONFIG_DELL_RBTN is not set
-# CONFIG_DELL_SMBIOS is not set
-# CONFIG_DELL_SMO8800 is not set
-# CONFIG_DEPRECATED_PARAM_STRUCT is not set
-# CONFIG_DETECT_HUNG_TASK is not set
-# CONFIG_DEVKMEM is not set
-# CONFIG_DEVMEM is not set
-CONFIG_DEVPORT=y
-# CONFIG_DEVPTS_MULTIPLE_INSTANCES is not set
-# CONFIG_DEVTMPFS is not set
-# CONFIG_DEVTMPFS_MOUNT is not set
-# CONFIG_DEV_DAX is not set
-# CONFIG_DGAP is not set
-# CONFIG_DGNC is not set
-# CONFIG_DHT11 is not set
-# CONFIG_DISCONTIGMEM_MANUAL is not set
-# CONFIG_DISPLAY_CONNECTOR_ANALOG_TV is not set
-# CONFIG_DISPLAY_CONNECTOR_DVI is not set
-# CONFIG_DISPLAY_CONNECTOR_HDMI is not set
-# CONFIG_DISPLAY_ENCODER_TFP410 is not set
-# CONFIG_DISPLAY_ENCODER_TPD12S015 is not set
-# CONFIG_DISPLAY_PANEL_DPI is not set
-# CONFIG_DISPLAY_PANEL_LGPHILIPS_LB035Q02 is not set
-# CONFIG_DISPLAY_PANEL_TPO_TD028TTEC1 is not set
-# CONFIG_DISPLAY_PANEL_TPO_TD043MTEA1 is not set
-# CONFIG_DL2K is not set
-# CONFIG_DLHL60D is not set
-# CONFIG_DLM is not set
-# CONFIG_DM9000 is not set
-# CONFIG_DMABUF_DEBUG is not set
-# CONFIG_DMABUF_HEAPS is not set
-# CONFIG_DMABUF_MOVE_NOTIFY is not set
-# CONFIG_DMABUF_SELFTESTS is not set
-# CONFIG_DMABUF_SYSFS_STATS is not set
-# CONFIG_DMADEVICES is not set
-# CONFIG_DMADEVICES_DEBUG is not set
-# CONFIG_DMARD06 is not set
-# CONFIG_DMARD09 is not set
-# CONFIG_DMARD10 is not set
-# CONFIG_DMASCC is not set
-# CONFIG_DMATEST is not set
-# CONFIG_DMA_API_DEBUG is not set
-CONFIG_DMA_COHERENT_POOL=y
-CONFIG_DMA_DECLARE_COHERENT=y
-# CONFIG_DMA_ENGINE is not set
-# CONFIG_DMA_FENCE_TRACE is not set
-# CONFIG_DMA_JZ4780 is not set
-# CONFIG_DMA_MAP_BENCHMARK is not set
-CONFIG_DMA_NONCOHERENT_MMAP=y
-# CONFIG_DMA_NOOP_OPS is not set
-# CONFIG_DMA_PERNUMA_CMA is not set
-# CONFIG_DMA_RESTRICTED_POOL is not set
-# CONFIG_DMA_SHARED_BUFFER is not set
-# CONFIG_DMA_VIRT_OPS is not set
-# CONFIG_DM_CACHE is not set
-# CONFIG_DM_CLONE is not set
-# CONFIG_DM_DEBUG is not set
-# CONFIG_DM_DELAY is not set
-# CONFIG_DM_DUST is not set
-# CONFIG_DM_EBS is not set
-# CONFIG_DM_ERA is not set
-# CONFIG_DM_FLAKEY is not set
-# CONFIG_DM_INTEGRITY is not set
-# CONFIG_DM_LOG_USERSPACE is not set
-# CONFIG_DM_LOG_WRITES is not set
-# CONFIG_DM_MQ_DEFAULT is not set
-# CONFIG_DM_MULTIPATH is not set
-# CONFIG_DM_RAID is not set
-# CONFIG_DM_SWITCH is not set
-# CONFIG_DM_THIN_PROVISIONING is not set
-# CONFIG_DM_UEVENT is not set
-# CONFIG_DM_UNSTRIPED is not set
-# CONFIG_DM_VERITY is not set
-# CONFIG_DM_WRITECACHE is not set
-# CONFIG_DM_ZERO is not set
-# CONFIG_DNET is not set
-# CONFIG_DNOTIFY is not set
-# CONFIG_DNS_RESOLVER is not set
-CONFIG_DOUBLEFAULT=y
-# CONFIG_DP83640_PHY is not set
-# CONFIG_DP83822_PHY is not set
-# CONFIG_DP83848_PHY is not set
-# CONFIG_DP83867_PHY is not set
-# CONFIG_DP83869_PHY is not set
-# CONFIG_DP83TC811_PHY is not set
-# CONFIG_DPOT_DAC is not set
-# CONFIG_DPS310 is not set
-CONFIG_DQL=y
-# CONFIG_DRAGONRISE_FF is not set
-# CONFIG_DRM is not set
-# CONFIG_DRM_AMDGPU is not set
-# CONFIG_DRM_AMDGPU_CIK is not set
-# CONFIG_DRM_AMDGPU_GART_DEBUGFS is not set
-# CONFIG_DRM_AMDGPU_SI is not set
-# CONFIG_DRM_AMDGPU_USERPTR is not set
-# CONFIG_DRM_AMD_ACP is not set
-# CONFIG_DRM_AMD_DC_DCN2_0 is not set
-# CONFIG_DRM_AMD_DC_DCN3_0 is not set
-# CONFIG_DRM_AMD_DC_HDCP is not set
-# CONFIG_DRM_AMD_DC_SI is not set
-# CONFIG_DRM_AMD_SECURE_DISPLAY is not set
-# CONFIG_DRM_ANALOGIX_ANX6345 is not set
-# CONFIG_DRM_ANALOGIX_ANX7625 is not set
-# CONFIG_DRM_ANALOGIX_ANX78XX is not set
-# CONFIG_DRM_ARCPGU is not set
-# CONFIG_DRM_ARMADA is not set
-# CONFIG_DRM_AST is not set
-# CONFIG_DRM_ATMEL_HLCDC is not set
-# CONFIG_DRM_BOCHS is not set
-# CONFIG_DRM_CDNS_DSI is not set
-# CONFIG_DRM_CDNS_MHDP8546 is not set
-# CONFIG_DRM_CHIPONE_ICN6211 is not set
-# CONFIG_DRM_CHRONTEL_CH7033 is not set
-# CONFIG_DRM_CIRRUS_QEMU is not set
-# CONFIG_DRM_DEBUG_DP_MST_TOPOLOGY_REFS is not set
-# CONFIG_DRM_DEBUG_MM is not set
-# CONFIG_DRM_DEBUG_SELFTEST is not set
-# CONFIG_DRM_DISPLAY_CONNECTOR is not set
-# CONFIG_DRM_DP_AUX_CHARDEV is not set
-# CONFIG_DRM_DP_CEC is not set
-# CONFIG_DRM_DUMB_VGA_DAC is not set
-# CONFIG_DRM_DW_HDMI_CEC is not set
-# CONFIG_DRM_ETNAVIV is not set
-# CONFIG_DRM_EXYNOS is not set
-# CONFIG_DRM_FBDEV_EMULATION is not set
-# CONFIG_DRM_FBDEV_LEAK_PHYS_SMEM is not set
-# CONFIG_DRM_FSL_DCU is not set
-# CONFIG_DRM_GM12U320 is not set
-# CONFIG_DRM_GMA500 is not set
-# CONFIG_DRM_GUD is not set
-# CONFIG_DRM_HDLCD is not set
-# CONFIG_DRM_HISI_HIBMC is not set
-# CONFIG_DRM_HISI_KIRIN is not set
-# CONFIG_DRM_I2C_ADV7511 is not set
-# CONFIG_DRM_I2C_CH7006 is not set
-# CONFIG_DRM_I2C_NXP_TDA9950 is not set
-# CONFIG_DRM_I2C_NXP_TDA998X is not set
-# CONFIG_DRM_I2C_SIL164 is not set
-# CONFIG_DRM_I915 is not set
-# CONFIG_DRM_ITE_IT66121 is not set
-# CONFIG_DRM_KOMEDA is not set
-# CONFIG_DRM_LEGACY is not set
-# CONFIG_DRM_LIB_RANDOM is not set
-# CONFIG_DRM_LIMA is not set
-# CONFIG_DRM_LOAD_EDID_FIRMWARE is not set
-# CONFIG_DRM_LONTIUM_LT8912B is not set
-# CONFIG_DRM_LONTIUM_LT9611 is not set
-# CONFIG_DRM_LONTIUM_LT9611UXC is not set
-# CONFIG_DRM_LVDS_CODEC is not set
-# CONFIG_DRM_LVDS_ENCODER is not set
-# CONFIG_DRM_MALI_DISPLAY is not set
-# CONFIG_DRM_MCDE is not set
-# CONFIG_DRM_MEGACHIPS_STDPXXXX_GE_B850V3_FW is not set
-# CONFIG_DRM_MGAG200 is not set
-# CONFIG_DRM_MXSFB is not set
-# CONFIG_DRM_NOUVEAU is not set
-# CONFIG_DRM_NWL_MIPI_DSI is not set
-# CONFIG_DRM_NXP_PTN3460 is not set
-# CONFIG_DRM_OMAP is not set
-# CONFIG_DRM_PANEL_ABT_Y030XX067A is not set
-# CONFIG_DRM_PANEL_ARM_VERSATILE is not set
-# CONFIG_DRM_PANEL_ASUS_Z00T_TM5P5_NT35596 is not set
-# CONFIG_DRM_PANEL_BOE_HIMAX8279D is not set
-# CONFIG_DRM_PANEL_BOE_TV101WUM_NL6 is not set
-# CONFIG_DRM_PANEL_DSI_CM is not set
-# CONFIG_DRM_PANEL_ELIDA_KD35T133 is not set
-# CONFIG_DRM_PANEL_FEIXIN_K101_IM2BA02 is not set
-# CONFIG_DRM_PANEL_FEIYANG_FY07024DI26A30D is not set
-# CONFIG_DRM_PANEL_ILITEK_IL9322 is not set
-# CONFIG_DRM_PANEL_ILITEK_ILI9341 is not set
-# CONFIG_DRM_PANEL_ILITEK_ILI9806E is not set
-# CONFIG_DRM_PANEL_ILITEK_ILI9881C is not set
-# CONFIG_DRM_PANEL_INNOLUX_EJ030NA is not set
-# CONFIG_DRM_PANEL_INNOLUX_P079ZCA is not set
-# CONFIG_DRM_PANEL_JDI_LT070ME05000 is not set
-# CONFIG_DRM_PANEL_KHADAS_TS050 is not set
-# CONFIG_DRM_PANEL_KINGDISPLAY_KD097D04 is not set
-# CONFIG_DRM_PANEL_LEADTEK_LTK050H3146W is not set
-# CONFIG_DRM_PANEL_LEADTEK_LTK500HD1829 is not set
-# CONFIG_DRM_PANEL_LG_LB035Q02 is not set
-# CONFIG_DRM_PANEL_LG_LG4573 is not set
-# CONFIG_DRM_PANEL_LVDS is not set
-# CONFIG_DRM_PANEL_MANTIX_MLAF057WE51 is not set
-# CONFIG_DRM_PANEL_MIPI_DBI is not set
-# CONFIG_DRM_PANEL_NEC_NL8048HL11 is not set
-# CONFIG_DRM_PANEL_NOVATEK_NT35510 is not set
-# CONFIG_DRM_PANEL_NOVATEK_NT36672A is not set
-# CONFIG_DRM_PANEL_NOVATEK_NT39016 is not set
-# CONFIG_DRM_PANEL_OLIMEX_LCD_OLINUXINO is not set
-# CONFIG_DRM_PANEL_ORISETECH_OTM8009A is not set
-# CONFIG_DRM_PANEL_OSD_OSD101T2587_53TS is not set
-# CONFIG_DRM_PANEL_PANASONIC_VVX10F034N00 is not set
-# CONFIG_DRM_PANEL_RASPBERRYPI_TOUCHSCREEN is not set
-# CONFIG_DRM_PANEL_RAYDIUM_RM67191 is not set
-# CONFIG_DRM_PANEL_RAYDIUM_RM68200 is not set
-# CONFIG_DRM_PANEL_ROCKTECH_JH057N00900 is not set
-# CONFIG_DRM_PANEL_RONBO_RB070D30 is not set
-# CONFIG_DRM_PANEL_SAMSUNG_ATNA33XC20 is not set
-# CONFIG_DRM_PANEL_SAMSUNG_DB7430 is not set
-# CONFIG_DRM_PANEL_SAMSUNG_LD9040 is not set
-# CONFIG_DRM_PANEL_SAMSUNG_S6D16D0 is not set
-# CONFIG_DRM_PANEL_SAMSUNG_S6E3HA2 is not set
-# CONFIG_DRM_PANEL_SAMSUNG_S6E63J0X03 is not set
-# CONFIG_DRM_PANEL_SAMSUNG_S6E63M0 is not set
-# CONFIG_DRM_PANEL_SAMSUNG_S6E88A0_AMS452EF01 is not set
-# CONFIG_DRM_PANEL_SAMSUNG_S6E8AA0 is not set
-# CONFIG_DRM_PANEL_SAMSUNG_SOFEF00 is not set
-# CONFIG_DRM_PANEL_SEIKO_43WVF1G is not set
-# CONFIG_DRM_PANEL_SHARP_LQ101R1SX01 is not set
-# CONFIG_DRM_PANEL_SHARP_LS037V7DW01 is not set
-# CONFIG_DRM_PANEL_SHARP_LS043T1LE01 is not set
-# CONFIG_DRM_PANEL_SIMPLE is not set
-# CONFIG_DRM_PANEL_SITRONIX_ST7701 is not set
-# CONFIG_DRM_PANEL_SITRONIX_ST7703 is not set
-# CONFIG_DRM_PANEL_SITRONIX_ST7789V is not set
-# CONFIG_DRM_PANEL_SONY_ACX424AKP is not set
-# CONFIG_DRM_PANEL_SONY_ACX565AKM is not set
-# CONFIG_DRM_PANEL_TDO_TL070WSH30 is not set
-# CONFIG_DRM_PANEL_TPO_TD028TTEC1 is not set
-# CONFIG_DRM_PANEL_TPO_TD043MTEA1 is not set
-# CONFIG_DRM_PANEL_TPO_TPG110 is not set
-# CONFIG_DRM_PANEL_TPO_Y17P is not set
-# CONFIG_DRM_PANEL_TRULY_NT35597_WQXGA is not set
-# CONFIG_DRM_PANEL_VISIONOX_RM69299 is not set
-# CONFIG_DRM_PANEL_WIDECHIPS_WS2401 is not set
-# CONFIG_DRM_PANEL_XINPENG_XPP055C272 is not set
-# CONFIG_DRM_PANFROST is not set
-# CONFIG_DRM_PARADE_PS8622 is not set
-# CONFIG_DRM_PARADE_PS8640 is not set
-# CONFIG_DRM_PL111 is not set
-# CONFIG_DRM_QXL is not set
-# CONFIG_DRM_RADEON is not set
-# CONFIG_DRM_RADEON_USERPTR is not set
-# CONFIG_DRM_RCAR_DW_HDMI is not set
-# CONFIG_DRM_RCAR_LVDS is not set
-# CONFIG_DRM_RCAR_USE_LVDS is not set
-# CONFIG_DRM_ROCKCHIP is not set
-# CONFIG_DRM_SII902X is not set
-# CONFIG_DRM_SII9234 is not set
-# CONFIG_DRM_SIL_SII8620 is not set
-# CONFIG_DRM_SIMPLEDRM is not set
-# CONFIG_DRM_SIMPLE_BRIDGE is not set
-# CONFIG_DRM_STI is not set
-# CONFIG_DRM_STM is not set
-# CONFIG_DRM_SUN4I is not set
-# CONFIG_DRM_THINE_THC63LVD1024 is not set
-# CONFIG_DRM_TIDSS is not set
-# CONFIG_DRM_TILCDC is not set
-# CONFIG_DRM_TINYDRM is not set
-# CONFIG_DRM_TI_SN65DSI83 is not set
-# CONFIG_DRM_TI_SN65DSI86 is not set
-# CONFIG_DRM_TI_TFP410 is not set
-# CONFIG_DRM_TI_TPD12S015 is not set
-# CONFIG_DRM_TOSHIBA_TC358762 is not set
-# CONFIG_DRM_TOSHIBA_TC358764 is not set
-# CONFIG_DRM_TOSHIBA_TC358767 is not set
-# CONFIG_DRM_TOSHIBA_TC358768 is not set
-# CONFIG_DRM_TOSHIBA_TC358775 is not set
-# CONFIG_DRM_TVE200 is not set
-# CONFIG_DRM_UDL is not set
-# CONFIG_DRM_VBOXVIDEO is not set
-# CONFIG_DRM_VC4_HDMI_CEC is not set
-# CONFIG_DRM_VGEM is not set
-# CONFIG_DRM_VIRTIO_GPU is not set
-# CONFIG_DRM_VKMS is not set
-# CONFIG_DRM_VMWGFX is not set
-# CONFIG_DRM_XEN is not set
-# CONFIG_DRM_XEN_FRONTEND is not set
-# CONFIG_DS1682 is not set
-# CONFIG_DS1803 is not set
-# CONFIG_DS4424 is not set
-# CONFIG_DST_CACHE is not set
-# CONFIG_DTLK is not set
-# CONFIG_DUMMY is not set
-CONFIG_DUMMY_CONSOLE_COLUMNS=80
-CONFIG_DUMMY_CONSOLE_ROWS=25
-# CONFIG_DUMMY_IRQ is not set
-# CONFIG_DVB_A8293 is not set
-# CONFIG_DVB_AF9013 is not set
-# CONFIG_DVB_AF9033 is not set
-# CONFIG_DVB_AS102 is not set
-# CONFIG_DVB_ASCOT2E is not set
-# CONFIG_DVB_ATBM8830 is not set
-# CONFIG_DVB_AU8522_DTV is not set
-# CONFIG_DVB_AU8522_V4L is not set
-# CONFIG_DVB_B2C2_FLEXCOP_PCI is not set
-# CONFIG_DVB_B2C2_FLEXCOP_USB is not set
-# CONFIG_DVB_BCM3510 is not set
-# CONFIG_DVB_BUDGET_CORE is not set
-# CONFIG_DVB_CORE is not set
-# CONFIG_DVB_CX22700 is not set
-# CONFIG_DVB_CX22702 is not set
-# CONFIG_DVB_CX24110 is not set
-# CONFIG_DVB_CX24116 is not set
-# CONFIG_DVB_CX24117 is not set
-# CONFIG_DVB_CX24120 is not set
-# CONFIG_DVB_CX24123 is not set
-# CONFIG_DVB_CXD2099 is not set
-# CONFIG_DVB_CXD2820R is not set
-# CONFIG_DVB_CXD2841ER is not set
-# CONFIG_DVB_CXD2880 is not set
-# CONFIG_DVB_DDBRIDGE is not set
-# CONFIG_DVB_DEMUX_SECTION_LOSS_LOG is not set
-# CONFIG_DVB_DIB3000MB is not set
-# CONFIG_DVB_DIB3000MC is not set
-# CONFIG_DVB_DIB7000M is not set
-# CONFIG_DVB_DIB7000P is not set
-# CONFIG_DVB_DIB8000 is not set
-# CONFIG_DVB_DIB9000 is not set
-# CONFIG_DVB_DRX39XYJ is not set
-# CONFIG_DVB_DRXD is not set
-# CONFIG_DVB_DRXK is not set
-# CONFIG_DVB_DS3000 is not set
-# CONFIG_DVB_DUMMY_FE is not set
-# CONFIG_DVB_DYNAMIC_MINORS is not set
-# CONFIG_DVB_EC100 is not set
-# CONFIG_DVB_FIREDTV is not set
-# CONFIG_DVB_HELENE is not set
-# CONFIG_DVB_HORUS3A is not set
-# CONFIG_DVB_ISL6405 is not set
-# CONFIG_DVB_ISL6421 is not set
-# CONFIG_DVB_ISL6423 is not set
-# CONFIG_DVB_IX2505V is not set
-# CONFIG_DVB_L64781 is not set
-# CONFIG_DVB_LG2160 is not set
-# CONFIG_DVB_LGDT3305 is not set
-# CONFIG_DVB_LGDT3306A is not set
-# CONFIG_DVB_LGDT330X is not set
-# CONFIG_DVB_LGS8GL5 is not set
-# CONFIG_DVB_LGS8GXX is not set
-# CONFIG_DVB_LNBH25 is not set
-# CONFIG_DVB_LNBH29 is not set
-# CONFIG_DVB_LNBP21 is not set
-# CONFIG_DVB_LNBP22 is not set
-# CONFIG_DVB_M88DS3103 is not set
-# CONFIG_DVB_M88RS2000 is not set
-CONFIG_DVB_MAX_ADAPTERS=16
-# CONFIG_DVB_MB86A16 is not set
-# CONFIG_DVB_MB86A20S is not set
-# CONFIG_DVB_MMAP is not set
-# CONFIG_DVB_MN88443X is not set
-# CONFIG_DVB_MN88472 is not set
-# CONFIG_DVB_MN88473 is not set
-# CONFIG_DVB_MT312 is not set
-# CONFIG_DVB_MT352 is not set
-# CONFIG_DVB_MXL5XX is not set
-# CONFIG_DVB_MXL692 is not set
-# CONFIG_DVB_NET is not set
-# CONFIG_DVB_NETUP_UNIDVB is not set
-# CONFIG_DVB_NGENE is not set
-# CONFIG_DVB_NXT200X is not set
-# CONFIG_DVB_NXT6000 is not set
-# CONFIG_DVB_OR51132 is not set
-# CONFIG_DVB_OR51211 is not set
-# CONFIG_DVB_PLATFORM_DRIVERS is not set
-# CONFIG_DVB_PLL is not set
-# CONFIG_DVB_PLUTO2 is not set
-# CONFIG_DVB_PT1 is not set
-# CONFIG_DVB_PT3 is not set
-# CONFIG_DVB_RTL2830 is not set
-# CONFIG_DVB_RTL2832 is not set
-# CONFIG_DVB_RTL2832_SDR is not set
-# CONFIG_DVB_S5H1409 is not set
-# CONFIG_DVB_S5H1411 is not set
-# CONFIG_DVB_S5H1420 is not set
-# CONFIG_DVB_S5H1432 is not set
-# CONFIG_DVB_S921 is not set
-# CONFIG_DVB_SI2165 is not set
-# CONFIG_DVB_SI2168 is not set
-# CONFIG_DVB_SI21XX is not set
-# CONFIG_DVB_SP2 is not set
-# CONFIG_DVB_SP8870 is not set
-# CONFIG_DVB_SP887X is not set
-# CONFIG_DVB_STB0899 is not set
-# CONFIG_DVB_STB6000 is not set
-# CONFIG_DVB_STB6100 is not set
-# CONFIG_DVB_STV0288 is not set
-# CONFIG_DVB_STV0297 is not set
-# CONFIG_DVB_STV0299 is not set
-# CONFIG_DVB_STV0367 is not set
-# CONFIG_DVB_STV0900 is not set
-# CONFIG_DVB_STV090x is not set
-# CONFIG_DVB_STV0910 is not set
-# CONFIG_DVB_STV6110 is not set
-# CONFIG_DVB_STV6110x is not set
-# CONFIG_DVB_STV6111 is not set
-# CONFIG_DVB_TC90522 is not set
-# CONFIG_DVB_TDA10021 is not set
-# CONFIG_DVB_TDA10023 is not set
-# CONFIG_DVB_TDA10048 is not set
-# CONFIG_DVB_TDA1004X is not set
-# CONFIG_DVB_TDA10071 is not set
-# CONFIG_DVB_TDA10086 is not set
-# CONFIG_DVB_TDA18271C2DD is not set
-# CONFIG_DVB_TDA665x is not set
-# CONFIG_DVB_TDA8083 is not set
-# CONFIG_DVB_TDA8261 is not set
-# CONFIG_DVB_TDA826X is not set
-# CONFIG_DVB_TEST_DRIVERS is not set
-# CONFIG_DVB_TS2020 is not set
-# CONFIG_DVB_TTUSB_BUDGET is not set
-# CONFIG_DVB_TTUSB_DEC is not set
-# CONFIG_DVB_TUA6100 is not set
-# CONFIG_DVB_TUNER_CX24113 is not set
-# CONFIG_DVB_TUNER_DIB0070 is not set
-# CONFIG_DVB_TUNER_DIB0090 is not set
-# CONFIG_DVB_TUNER_ITD1000 is not set
-# CONFIG_DVB_ULE_DEBUG is not set
-# CONFIG_DVB_USB is not set
-# CONFIG_DVB_USB_V2 is not set
-# CONFIG_DVB_VES1820 is not set
-# CONFIG_DVB_VES1X93 is not set
-# CONFIG_DVB_ZD1301_DEMOD is not set
-# CONFIG_DVB_ZL10036 is not set
-# CONFIG_DVB_ZL10039 is not set
-# CONFIG_DVB_ZL10353 is not set
-# CONFIG_DWC_XLGMAC is not set
-# CONFIG_DWMAC_DWC_QOS_ETH is not set
-# CONFIG_DWMAC_INTEL_PLAT is not set
-# CONFIG_DWMAC_IPQ806X is not set
-# CONFIG_DWMAC_LOONGSON is not set
-# CONFIG_DWMAC_LPC18XX is not set
-# CONFIG_DWMAC_MESON is not set
-# CONFIG_DWMAC_ROCKCHIP is not set
-# CONFIG_DWMAC_SOCFPGA is not set
-# CONFIG_DWMAC_STI is not set
-# CONFIG_DW_AXI_DMAC is not set
-# CONFIG_DW_DMAC is not set
-# CONFIG_DW_DMAC_PCI is not set
-# CONFIG_DW_EDMA is not set
-# CONFIG_DW_EDMA_PCIE is not set
-# CONFIG_DW_WATCHDOG is not set
-# CONFIG_DW_XDATA_PCIE is not set
-# CONFIG_DYNAMIC_DEBUG is not set
-# CONFIG_DYNAMIC_DEBUG_CORE is not set
-# CONFIG_E100 is not set
-# CONFIG_E1000 is not set
-# CONFIG_E1000E is not set
-# CONFIG_E1000E_HWTS is not set
-# CONFIG_EARLY_PRINTK_8250 is not set
-# CONFIG_EARLY_PRINTK_USB_XDBC is not set
-# CONFIG_EBC_C384_WDT is not set
-# CONFIG_ECHO is not set
-# CONFIG_ECRYPT_FS is not set
-# CONFIG_EDAC is not set
-# CONFIG_EEEPC_LAPTOP is not set
-# CONFIG_EEPROM_93CX6 is not set
-# CONFIG_EEPROM_93XX46 is not set
-# CONFIG_EEPROM_AT24 is not set
-# CONFIG_EEPROM_AT25 is not set
-# CONFIG_EEPROM_DIGSY_MTC_CFG is not set
-# CONFIG_EEPROM_EE1004 is not set
-# CONFIG_EEPROM_IDT_89HPESX is not set
-# CONFIG_EEPROM_LEGACY is not set
-# CONFIG_EEPROM_MAX6875 is not set
-# CONFIG_EFI is not set
-CONFIG_EFI_PARTITION=y
-# CONFIG_EFI_VARS_PSTORE is not set
-# CONFIG_EFS_FS is not set
-CONFIG_ELFCORE=y
-# CONFIG_ELF_CORE is not set
-# CONFIG_EMAC_ROCKCHIP is not set
-CONFIG_EMBEDDED=y
-# CONFIG_EM_TIMER_STI is not set
-CONFIG_ENABLE_WARN_DEPRECATED=y
-# CONFIG_ENA_ETHERNET is not set
-# CONFIG_ENC28J60 is not set
-# CONFIG_ENCLOSURE_SERVICES is not set
-# CONFIG_ENCRYPTED_KEYS is not set
-# CONFIG_ENCX24J600 is not set
-# CONFIG_ENERGY_MODEL is not set
-# CONFIG_ENIC is not set
-# CONFIG_ENVELOPE_DETECTOR is not set
-# CONFIG_EPAPR_PARAVIRT is not set
-# CONFIG_EPIC100 is not set
-CONFIG_EPOLL=y
-# CONFIG_EQUALIZER is not set
-# CONFIG_EROFS_FS is not set
-# CONFIG_ET131X is not set
-CONFIG_ETHERNET=y
-# CONFIG_ETHOC is not set
-CONFIG_ETHTOOL_NETLINK=y
-CONFIG_EVENTFD=y
-# CONFIG_EVM is not set
-# CONFIG_EXFAT_FS is not set
-CONFIG_EXPERT=y
-CONFIG_EXPORTFS=y
-# CONFIG_EXPORTFS_BLOCK_OPS is not set
-# CONFIG_EXT2_FS is not set
-CONFIG_EXT2_FS_XATTR=y
-# CONFIG_EXT3_FS is not set
-# CONFIG_EXT4_DEBUG is not set
-# CONFIG_EXT4_ENCRYPTION is not set
-# CONFIG_EXT4_FS is not set
-# CONFIG_EXT4_FS_POSIX_ACL is not set
-# CONFIG_EXT4_FS_SECURITY is not set
-CONFIG_EXT4_USE_FOR_EXT2=y
-# CONFIG_EXTCON is not set
-# CONFIG_EXTCON_ADC_JACK is not set
-# CONFIG_EXTCON_ARIZONA is not set
-# CONFIG_EXTCON_AXP288 is not set
-# CONFIG_EXTCON_FSA9480 is not set
-# CONFIG_EXTCON_GPIO is not set
-# CONFIG_EXTCON_INTEL_INT3496 is not set
-# CONFIG_EXTCON_MAX3355 is not set
-# CONFIG_EXTCON_PTN5150 is not set
-# CONFIG_EXTCON_QCOM_SPMI_MISC is not set
-# CONFIG_EXTCON_RT8973A is not set
-# CONFIG_EXTCON_SM5502 is not set
-# CONFIG_EXTCON_USBC_TUSB320 is not set
-# CONFIG_EXTCON_USB_GPIO is not set
-CONFIG_EXTRA_FIRMWARE=""
-CONFIG_EXTRA_TARGETS=""
-# CONFIG_EXYNOS_ADC is not set
-# CONFIG_EXYNOS_VIDEO is not set
-# CONFIG_EZCHIP_NPS_MANAGEMENT_ENET is not set
-# CONFIG_EZX_PCAP is not set
-# CONFIG_F2FS_CHECK_FS is not set
-# CONFIG_F2FS_FAULT_INJECTION is not set
-# CONFIG_F2FS_FS is not set
-# CONFIG_F2FS_FS_COMPRESSION is not set
-# CONFIG_F2FS_FS_ENCRYPTION is not set
-# CONFIG_F2FS_FS_POSIX_ACL is not set
-# CONFIG_F2FS_FS_SECURITY is not set
-CONFIG_F2FS_FS_XATTR=y
-# CONFIG_F2FS_IOSTAT is not set
-# CONFIG_F2FS_IO_TRACE is not set
-CONFIG_F2FS_STAT_FS=y
-# CONFIG_FAILOVER is not set
-# CONFIG_FAIR_GROUP_SCHED is not set
-# CONFIG_FANOTIFY is not set
-# CONFIG_FANOTIFY_ACCESS_PERMISSIONS is not set
-CONFIG_FAT_DEFAULT_CODEPAGE=437
-CONFIG_FAT_DEFAULT_IOCHARSET="iso8859-1"
-# CONFIG_FAT_DEFAULT_UTF8 is not set
-# CONFIG_FAT_FS is not set
-# CONFIG_FAULT_INJECTION is not set
-# CONFIG_FB is not set
-# CONFIG_FB_3DFX is not set
-# CONFIG_FB_ARC is not set
-# CONFIG_FB_ARK is not set
-# CONFIG_FB_ARMCLCD is not set
-# CONFIG_FB_ASILIANT is not set
-# CONFIG_FB_ATMEL is not set
-# CONFIG_FB_ATY is not set
-# CONFIG_FB_ATY128 is not set
-# CONFIG_FB_AUO_K190X is not set
-# CONFIG_FB_BACKLIGHT is not set
-# CONFIG_FB_BIG_ENDIAN is not set
-# CONFIG_FB_BOOT_VESA_SUPPORT is not set
-# CONFIG_FB_BOTH_ENDIAN is not set
-# CONFIG_FB_BROADSHEET is not set
-# CONFIG_FB_CARMINE is not set
-# CONFIG_FB_CFB_COPYAREA is not set
-# CONFIG_FB_CFB_FILLRECT is not set
-# CONFIG_FB_CFB_IMAGEBLIT is not set
-# CONFIG_FB_CFB_REV_PIXELS_IN_BYTE is not set
-# CONFIG_FB_CIRRUS is not set
-# CONFIG_FB_CYBER2000 is not set
-# CONFIG_FB_DA8XX is not set
-# CONFIG_FB_DDC is not set
-# CONFIG_FB_FLEX is not set
-# CONFIG_FB_FOREIGN_ENDIAN is not set
-# CONFIG_FB_FSL_DIU is not set
-# CONFIG_FB_GEODE is not set
-# CONFIG_FB_GOLDFISH is not set
-# CONFIG_FB_HGA is not set
-# CONFIG_FB_I740 is not set
-# CONFIG_FB_IBM_GXT4500 is not set
-# CONFIG_FB_IMSTT is not set
-# CONFIG_FB_IMX is not set
-# CONFIG_FB_KYRO is not set
-# CONFIG_FB_LE80578 is not set
-# CONFIG_FB_LITTLE_ENDIAN is not set
-# CONFIG_FB_MACMODES is not set
-# CONFIG_FB_MATROX is not set
-# CONFIG_FB_MB862XX is not set
-# CONFIG_FB_METRONOME is not set
-# CONFIG_FB_MODE_HELPERS is not set
-# CONFIG_FB_MXS is not set
-# CONFIG_FB_N411 is not set
-# CONFIG_FB_NEOMAGIC is not set
-CONFIG_FB_NOTIFY=y
-# CONFIG_FB_NVIDIA is not set
-# CONFIG_FB_OF is not set
-# CONFIG_FB_OMAP2 is not set
-# CONFIG_FB_OPENCORES is not set
-# CONFIG_FB_PM2 is not set
-# CONFIG_FB_PM3 is not set
-# CONFIG_FB_PS3 is not set
-# CONFIG_FB_PXA is not set
-# CONFIG_FB_RADEON is not set
-# CONFIG_FB_RIVA is not set
-# CONFIG_FB_S1D13XXX is not set
-# CONFIG_FB_S3 is not set
-# CONFIG_FB_SAVAGE is not set
-# CONFIG_FB_SIMPLE is not set
-# CONFIG_FB_SIS is not set
-# CONFIG_FB_SM712 is not set
-# CONFIG_FB_SM750 is not set
-# CONFIG_FB_SMSCUFX is not set
-# CONFIG_FB_SSD1307 is not set
-# CONFIG_FB_SVGALIB is not set
-# CONFIG_FB_SYS_COPYAREA is not set
-# CONFIG_FB_SYS_FILLRECT is not set
-# CONFIG_FB_SYS_FOPS is not set
-# CONFIG_FB_SYS_IMAGEBLIT is not set
-# CONFIG_FB_TFT is not set
-# CONFIG_FB_TFT_AGM1264K_FL is not set
-# CONFIG_FB_TFT_BD663474 is not set
-# CONFIG_FB_TFT_FBTFT_DEVICE is not set
-# CONFIG_FB_TFT_HX8340BN is not set
-# CONFIG_FB_TFT_HX8347D is not set
-# CONFIG_FB_TFT_HX8353D is not set
-# CONFIG_FB_TFT_HX8357D is not set
-# CONFIG_FB_TFT_ILI9163 is not set
-# CONFIG_FB_TFT_ILI9320 is not set
-# CONFIG_FB_TFT_ILI9325 is not set
-# CONFIG_FB_TFT_ILI9340 is not set
-# CONFIG_FB_TFT_ILI9341 is not set
-# CONFIG_FB_TFT_ILI9481 is not set
-# CONFIG_FB_TFT_ILI9486 is not set
-# CONFIG_FB_TFT_PCD8544 is not set
-# CONFIG_FB_TFT_RA8875 is not set
-# CONFIG_FB_TFT_S6D02A1 is not set
-# CONFIG_FB_TFT_S6D1121 is not set
-# CONFIG_FB_TFT_SEPS525 is not set
-# CONFIG_FB_TFT_SH1106 is not set
-# CONFIG_FB_TFT_SSD1289 is not set
-# CONFIG_FB_TFT_SSD1305 is not set
-# CONFIG_FB_TFT_SSD1306 is not set
-# CONFIG_FB_TFT_SSD1325 is not set
-# CONFIG_FB_TFT_SSD1331 is not set
-# CONFIG_FB_TFT_SSD1351 is not set
-# CONFIG_FB_TFT_ST7735R is not set
-# CONFIG_FB_TFT_ST7789V is not set
-# CONFIG_FB_TFT_TINYLCD is not set
-# CONFIG_FB_TFT_TLS8204 is not set
-# CONFIG_FB_TFT_UC1611 is not set
-# CONFIG_FB_TFT_UC1701 is not set
-# CONFIG_FB_TFT_UPD161704 is not set
-# CONFIG_FB_TFT_WATTEROTT is not set
-# CONFIG_FB_TILEBLITTING is not set
-# CONFIG_FB_TMIO is not set
-# CONFIG_FB_TRIDENT is not set
-# CONFIG_FB_UDL is not set
-# CONFIG_FB_UVESA is not set
-# CONFIG_FB_VGA16 is not set
-# CONFIG_FB_VIA is not set
-# CONFIG_FB_VIRTUAL is not set
-# CONFIG_FB_VOODOO1 is not set
-# CONFIG_FB_VT8623 is not set
-# CONFIG_FB_XGI is not set
-# CONFIG_FCOE is not set
-# CONFIG_FCOE_FNIC is not set
-# CONFIG_FDDI is not set
-# CONFIG_FEALNX is not set
-# CONFIG_FENCE_TRACE is not set
-# CONFIG_FHANDLE is not set
-CONFIG_FIB_RULES=y
-# CONFIG_FIELDBUS_DEV is not set
-CONFIG_FILE_LOCKING=y
-# CONFIG_FIND_BIT_BENCHMARK is not set
-# CONFIG_FIREWIRE is not set
-# CONFIG_FIREWIRE_NOSY is not set
-# CONFIG_FIREWIRE_SERIAL is not set
-# CONFIG_FIRMWARE_EDID is not set
-# CONFIG_FIRMWARE_IN_KERNEL is not set
-# CONFIG_FIRMWARE_MEMMAP is not set
-# CONFIG_FIXED_PHY is not set
-CONFIG_FLATMEM=y
-CONFIG_FLATMEM_MANUAL=y
-CONFIG_FLAT_NODE_MEM_MAP=y
-# CONFIG_FM10K is not set
-# CONFIG_FMC is not set
-# CONFIG_FONTS is not set
-# CONFIG_FONT_6x8 is not set
-# CONFIG_FONT_TER16x32 is not set
-# CONFIG_FORCEDETH is not set
-CONFIG_FORCE_MAX_ZONEORDER=11
-CONFIG_FORTIFY_SOURCE=y
-# CONFIG_FPGA is not set
-# CONFIG_FRAMEBUFFER_CONSOLE is not set
-# CONFIG_FRAMEBUFFER_CONSOLE_DEFERRED_TAKEOVER is not set
-# CONFIG_FRAMEBUFFER_CONSOLE_LEGACY_ACCELERATION is not set
-# CONFIG_FRAME_POINTER is not set
-# CONFIG_FREEZER is not set
-# CONFIG_FRONTSWAP is not set
-# CONFIG_FSCACHE is not set
-# CONFIG_FSI is not set
-# CONFIG_FSL_DPAA2_SWITCH is not set
-# CONFIG_FSL_EDMA is not set
-# CONFIG_FSL_ENETC is not set
-# CONFIG_FSL_ENETC_IERB is not set
-# CONFIG_FSL_ENETC_MDIO is not set
-# CONFIG_FSL_ENETC_VF is not set
-# CONFIG_FSL_ERRATUM_A008585 is not set
-# CONFIG_FSL_MC_BUS is not set
-# CONFIG_FSL_PQ_MDIO is not set
-# CONFIG_FSL_QDMA is not set
-# CONFIG_FSL_RCPM is not set
-# CONFIG_FSL_XGMAC_MDIO is not set
-CONFIG_FSNOTIFY=y
-# CONFIG_FS_DAX is not set
-# CONFIG_FS_ENCRYPTION is not set
-# CONFIG_FS_POSIX_ACL is not set
-# CONFIG_FS_VERITY is not set
-# CONFIG_FTGMAC100 is not set
-# CONFIG_FTL is not set
-# CONFIG_FTMAC100 is not set
-# CONFIG_FTRACE is not set
-# CONFIG_FTRACE_RECORD_RECURSION is not set
-# CONFIG_FTRACE_STARTUP_TEST is not set
-# CONFIG_FTR_FIXUP_SELFTEST is not set
-# CONFIG_FTWDT010_WATCHDOG is not set
-# CONFIG_FUJITSU_ERRATUM_010001 is not set
-# CONFIG_FUJITSU_ES is not set
-# CONFIG_FUJITSU_LAPTOP is not set
-# CONFIG_FUJITSU_TABLET is not set
-# CONFIG_FUNCTION_ERROR_INJECTION is not set
-# CONFIG_FUNCTION_TRACER is not set
-# CONFIG_FUSE_FS is not set
-# CONFIG_FUSION is not set
-# CONFIG_FUSION_FC is not set
-# CONFIG_FUSION_SAS is not set
-# CONFIG_FUSION_SPI is not set
-CONFIG_FUTEX=y
-CONFIG_FUTEX_PI=y
-# CONFIG_FW_CFG_SYSFS is not set
-CONFIG_FW_LOADER=y
-# CONFIG_FW_LOADER_COMPRESS is not set
-CONFIG_FW_LOADER_USER_HELPER=y
-CONFIG_FW_LOADER_USER_HELPER_FALLBACK=y
-# CONFIG_FXAS21002C is not set
-# CONFIG_FXLS8962AF_I2C is not set
-# CONFIG_FXLS8962AF_SPI is not set
-# CONFIG_FXOS8700_I2C is not set
-# CONFIG_FXOS8700_SPI is not set
-CONFIG_GACT_PROB=y
-# CONFIG_GADGET_UAC1 is not set
-# CONFIG_GAMEPORT is not set
-# CONFIG_GATEWORKS_GW16083 is not set
-# CONFIG_GCC_PLUGINS is not set
-# CONFIG_GCOV is not set
-# CONFIG_GCOV_KERNEL is not set
-# CONFIG_GDB_SCRIPTS is not set
-# CONFIG_GEMINI_ETHERNET is not set
-# CONFIG_GENERIC_ADC_BATTERY is not set
-# CONFIG_GENERIC_ADC_THERMAL is not set
-CONFIG_GENERIC_CALIBRATE_DELAY=y
-# CONFIG_GENERIC_CPU_DEVICES is not set
-CONFIG_GENERIC_HWEIGHT=y
-# CONFIG_GENERIC_IRQ_DEBUGFS is not set
-CONFIG_GENERIC_IRQ_IPI=y
-CONFIG_GENERIC_IRQ_PROBE=y
-CONFIG_GENERIC_NET_UTILS=y
-# CONFIG_GENERIC_PHY is not set
-CONFIG_GENERIC_PTDUMP=y
-CONFIG_GENERIC_VDSO_TIME_NS=y
-# CONFIG_GENEVE is not set
-# CONFIG_GENWQE is not set
-# CONFIG_GFS2_FS is not set
-# CONFIG_GIGASET_CAPI is not set
-# CONFIG_GIGASET_DEBUG is not set
-# CONFIG_GIGASET_DUMMYLL is not set
-# CONFIG_GLOB_SELFTEST is not set
-# CONFIG_GNSS is not set
-# CONFIG_GOLDFISH is not set
-# CONFIG_GOOGLE_FIRMWARE is not set
-# CONFIG_GOOGLE_FRAMEBUFFER_COREBOOT is not set
-# CONFIG_GOOGLE_MEMCONSOLE_X86_LEGACY is not set
-# CONFIG_GOOGLE_SMI is not set
-# CONFIG_GP2AP002 is not set
-# CONFIG_GP2AP020A00F is not set
-# CONFIG_GPD_POCKET_FAN is not set
-CONFIG_GPIOLIB=y
-CONFIG_GPIOLIB_FASTPATH_LIMIT=512
-# CONFIG_GPIO_104_DIO_48E is not set
-# CONFIG_GPIO_104_IDIO_16 is not set
-# CONFIG_GPIO_104_IDI_48 is not set
-# CONFIG_GPIO_74X164 is not set
-# CONFIG_GPIO_74XX_MMIO is not set
-# CONFIG_GPIO_ADNP is not set
-# CONFIG_GPIO_ADP5588 is not set
-# CONFIG_GPIO_AGGREGATOR is not set
-# CONFIG_GPIO_ALTERA is not set
-# CONFIG_GPIO_AMD8111 is not set
-# CONFIG_GPIO_AMDPT is not set
-# CONFIG_GPIO_AMD_FCH is not set
-# CONFIG_GPIO_BCM_KONA is not set
-# CONFIG_GPIO_BT8XX is not set
-# CONFIG_GPIO_CADENCE is not set
-# CONFIG_GPIO_CASCADE is not set
-# CONFIG_GPIO_CDEV is not set
-# CONFIG_GPIO_CDEV_V1 is not set
-# CONFIG_GPIO_CS5535 is not set
-# CONFIG_GPIO_DWAPB is not set
-# CONFIG_GPIO_EM is not set
-# CONFIG_GPIO_EXAR is not set
-# CONFIG_GPIO_F7188X is not set
-# CONFIG_GPIO_FTGPIO010 is not set
-# CONFIG_GPIO_GENERIC_PLATFORM is not set
-# CONFIG_GPIO_GPIO_MM is not set
-# CONFIG_GPIO_GRGPIO is not set
-# CONFIG_GPIO_GW_PLD is not set
-# CONFIG_GPIO_HLWD is not set
-# CONFIG_GPIO_ICH is not set
-# CONFIG_GPIO_IT87 is not set
-# CONFIG_GPIO_LOGICVC is not set
-# CONFIG_GPIO_LYNXPOINT is not set
-# CONFIG_GPIO_MAX3191X is not set
-# CONFIG_GPIO_MAX7300 is not set
-# CONFIG_GPIO_MAX7301 is not set
-# CONFIG_GPIO_MAX732X is not set
-# CONFIG_GPIO_MB86S7X is not set
-# CONFIG_GPIO_MC33880 is not set
-# CONFIG_GPIO_ML_IOH is not set
-# CONFIG_GPIO_MOCKUP is not set
-# CONFIG_GPIO_MPC8XXX is not set
-# CONFIG_GPIO_PCA953X is not set
-# CONFIG_GPIO_PCA953X_IRQ is not set
-# CONFIG_GPIO_PCA9570 is not set
-# CONFIG_GPIO_PCF857X is not set
-# CONFIG_GPIO_PCH is not set
-# CONFIG_GPIO_PCIE_IDIO_24 is not set
-# CONFIG_GPIO_PCI_IDIO_16 is not set
-# CONFIG_GPIO_PISOSR is not set
-# CONFIG_GPIO_PL061 is not set
-# CONFIG_GPIO_PWM is not set
-# CONFIG_GPIO_RCAR is not set
-# CONFIG_GPIO_RDC321X is not set
-# CONFIG_GPIO_SAMA5D2_PIOBU is not set
-# CONFIG_GPIO_SCH is not set
-# CONFIG_GPIO_SCH311X is not set
-# CONFIG_GPIO_SIFIVE is not set
-# CONFIG_GPIO_SX150X is not set
-# CONFIG_GPIO_SYSCON is not set
-CONFIG_GPIO_SYSFS=y
-# CONFIG_GPIO_TPIC2810 is not set
-# CONFIG_GPIO_TS4900 is not set
-# CONFIG_GPIO_TS5500 is not set
-# CONFIG_GPIO_VIRTIO is not set
-# CONFIG_GPIO_VX855 is not set
-# CONFIG_GPIO_WATCHDOG is not set
-# CONFIG_GPIO_WINBOND is not set
-# CONFIG_GPIO_WS16C48 is not set
-# CONFIG_GPIO_XGENE is not set
-# CONFIG_GPIO_XILINX is not set
-# CONFIG_GPIO_XRA1403 is not set
-# CONFIG_GPIO_ZEVIO is not set
-# CONFIG_GPIO_ZX is not set
-# CONFIG_GREENASIA_FF is not set
-# CONFIG_GREYBUS is not set
-# CONFIG_GS_FPGABOOT is not set
-# CONFIG_GTP is not set
-# CONFIG_GUP_BENCHMARK is not set
-# CONFIG_GUP_TEST is not set
-# CONFIG_GVE is not set
-# CONFIG_HABANA_AI is not set
-# CONFIG_HAMACHI is not set
-# CONFIG_HAMRADIO is not set
-# CONFIG_HAPPYMEAL is not set
-CONFIG_HARDENED_USERCOPY=y
-# CONFIG_HARDENED_USERCOPY_FALLBACK is not set
-# CONFIG_HARDENED_USERCOPY_PAGESPAN is not set
-CONFIG_HARDEN_BRANCH_HISTORY=y
-CONFIG_HARDEN_EL2_VECTORS=y
-# CONFIG_HARDLOCKUP_DETECTOR is not set
-# CONFIG_HAVE_ARM_ARCH_TIMER is not set
-# CONFIG_HCALL_STATS is not set
-# CONFIG_HDC100X is not set
-# CONFIG_HDC2010 is not set
-# CONFIG_HDLC is not set
-# CONFIG_HDLC_CISCO is not set
-# CONFIG_HDLC_FR is not set
-# CONFIG_HDLC_PPP is not set
-# CONFIG_HDLC_RAW is not set
-# CONFIG_HDLC_RAW_ETH is not set
-# CONFIG_HDMI_LPE_AUDIO is not set
-# CONFIG_HDQ_MASTER_OMAP is not set
-# CONFIG_HEADERS_CHECK is not set
-# CONFIG_HEADERS_INSTALL is not set
-# CONFIG_HEADER_TEST is not set
-# CONFIG_HERMES is not set
-# CONFIG_HFSPLUS_FS is not set
-# CONFIG_HFSPLUS_FS_POSIX_ACL is not set
-# CONFIG_HFS_FS is not set
-# CONFIG_HFS_FS_POSIX_ACL is not set
-# CONFIG_HI6421V600_IRQ is not set
-# CONFIG_HI8435 is not set
-# CONFIG_HIBERNATION is not set
-# CONFIG_HID is not set
-# CONFIG_HIDRAW is not set
-# CONFIG_HID_A4TECH is not set
-# CONFIG_HID_ACCUTOUCH is not set
-# CONFIG_HID_ACRUX is not set
-# CONFIG_HID_ACRUX_FF is not set
-# CONFIG_HID_ALPS is not set
-# CONFIG_HID_APPLE is not set
-# CONFIG_HID_APPLEIR is not set
-# CONFIG_HID_ASUS is not set
-# CONFIG_HID_AUREAL is not set
-# CONFIG_HID_BATTERY_STRENGTH is not set
-# CONFIG_HID_BELKIN is not set
-# CONFIG_HID_BETOP_FF is not set
-# CONFIG_HID_BIGBEN_FF is not set
-# CONFIG_HID_CHERRY is not set
-# CONFIG_HID_CHICONY is not set
-# CONFIG_HID_CMEDIA is not set
-# CONFIG_HID_CORSAIR is not set
-# CONFIG_HID_COUGAR is not set
-# CONFIG_HID_CP2112 is not set
-# CONFIG_HID_CREATIVE_SB0540 is not set
-# CONFIG_HID_CYPRESS is not set
-# CONFIG_HID_DRAGONRISE is not set
-# CONFIG_HID_ELAN is not set
-# CONFIG_HID_ELECOM is not set
-# CONFIG_HID_ELO is not set
-# CONFIG_HID_EMS_FF is not set
-# CONFIG_HID_EZKEY is not set
-# CONFIG_HID_FT260 is not set
-# CONFIG_HID_GEMBIRD is not set
-# CONFIG_HID_GENERIC is not set
-# CONFIG_HID_GFRM is not set
-# CONFIG_HID_GLORIOUS is not set
-# CONFIG_HID_GOOGLE_HAMMER is not set
-# CONFIG_HID_GREENASIA is not set
-# CONFIG_HID_GT683R is not set
-# CONFIG_HID_GYRATION is not set
-# CONFIG_HID_HOLTEK is not set
-# CONFIG_HID_ICADE is not set
-# CONFIG_HID_ITE is not set
-# CONFIG_HID_JABRA is not set
-# CONFIG_HID_KENSINGTON is not set
-# CONFIG_HID_KEYTOUCH is not set
-# CONFIG_HID_KYE is not set
-# CONFIG_HID_LCPOWER is not set
-# CONFIG_HID_LED is not set
-# CONFIG_HID_LENOVO is not set
-# CONFIG_HID_LOGITECH is not set
-# CONFIG_HID_LOGITECH_DJ is not set
-# CONFIG_HID_LOGITECH_HIDPP is not set
-# CONFIG_HID_MACALLY is not set
-# CONFIG_HID_MAGICMOUSE is not set
-# CONFIG_HID_MALTRON is not set
-# CONFIG_HID_MAYFLASH is not set
-# CONFIG_HID_MCP2221 is not set
-# CONFIG_HID_MICROSOFT is not set
-# CONFIG_HID_MONTEREY is not set
-# CONFIG_HID_MULTITOUCH is not set
-# CONFIG_HID_NTI is not set
-# CONFIG_HID_NTRIG is not set
-# CONFIG_HID_ORTEK is not set
-# CONFIG_HID_PANTHERLORD is not set
-# CONFIG_HID_PENMOUNT is not set
-# CONFIG_HID_PETALYNX is not set
-# CONFIG_HID_PICOLCD is not set
-# CONFIG_HID_PID is not set
-# CONFIG_HID_PLANTRONICS is not set
-# CONFIG_HID_PLAYSTATION is not set
-# CONFIG_HID_PRIMAX is not set
-# CONFIG_HID_PRODIKEYS is not set
-# CONFIG_HID_REDRAGON is not set
-# CONFIG_HID_RETRODE is not set
-# CONFIG_HID_RMI is not set
-# CONFIG_HID_ROCCAT is not set
-# CONFIG_HID_SAITEK is not set
-# CONFIG_HID_SAMSUNG is not set
-# CONFIG_HID_SEMITEK is not set
-# CONFIG_HID_SENSOR_HUB is not set
-# CONFIG_HID_SMARTJOYPLUS is not set
-# CONFIG_HID_SONY is not set
-# CONFIG_HID_SPEEDLINK is not set
-# CONFIG_HID_STEAM is not set
-# CONFIG_HID_STEELSERIES is not set
-# CONFIG_HID_SUNPLUS is not set
-# CONFIG_HID_THINGM is not set
-# CONFIG_HID_THRUSTMASTER is not set
-# CONFIG_HID_TIVO is not set
-# CONFIG_HID_TOPSEED is not set
-# CONFIG_HID_TWINHAN is not set
-# CONFIG_HID_U2FZERO is not set
-# CONFIG_HID_UCLOGIC is not set
-# CONFIG_HID_UDRAW_PS3 is not set
-# CONFIG_HID_VIEWSONIC is not set
-# CONFIG_HID_VIVALDI is not set
-# CONFIG_HID_WACOM is not set
-# CONFIG_HID_WALTOP is not set
-# CONFIG_HID_WIIMOTE is not set
-# CONFIG_HID_XINMO is not set
-# CONFIG_HID_ZEROPLUS is not set
-# CONFIG_HID_ZYDACRON is not set
-# CONFIG_HIGHMEM is not set
-CONFIG_HIGH_RES_TIMERS=y
-# CONFIG_HINIC is not set
-# CONFIG_HIP04_ETH is not set
-# CONFIG_HIPPI is not set
-# CONFIG_HISILICON_ERRATUM_161010101 is not set
-# CONFIG_HISILICON_ERRATUM_161600802 is not set
-# CONFIG_HISI_DMA is not set
-# CONFIG_HISI_FEMAC is not set
-# CONFIG_HISI_HIKEY_USB is not set
-# CONFIG_HIST_TRIGGERS_DEBUG is not set
-# CONFIG_HIX5HD2_GMAC is not set
-# CONFIG_HMC425 is not set
-# CONFIG_HMC6352 is not set
-# CONFIG_HNS is not set
-# CONFIG_HNS3 is not set
-# CONFIG_HNS_DSAF is not set
-# CONFIG_HNS_ENET is not set
-# CONFIG_HOSTAP is not set
-# CONFIG_HOSTAP_CS is not set
-# CONFIG_HOSTAP_PCI is not set
-# CONFIG_HOSTAP_PLX is not set
-# CONFIG_HOTPLUG_CPU is not set
-# CONFIG_HOTPLUG_PCI is not set
-# CONFIG_HOTPLUG_PCI_ACPI_IBM is not set
-# CONFIG_HOTPLUG_PCI_COMPAQ is not set
-# CONFIG_HOTPLUG_PCI_CPCI is not set
-# CONFIG_HOTPLUG_PCI_IBM is not set
-# CONFIG_HOTPLUG_PCI_SHPC is not set
-# CONFIG_HP03 is not set
-# CONFIG_HP100 is not set
-# CONFIG_HP206C is not set
-CONFIG_HPET_MMAP_DEFAULT=y
-# CONFIG_HPFS_FS is not set
-# CONFIG_HP_ILO is not set
-# CONFIG_HP_WIRELESS is not set
-# CONFIG_HSA_AMD is not set
-# CONFIG_HSI is not set
-# CONFIG_HSR is not set
-# CONFIG_HTC_EGPIO is not set
-# CONFIG_HTC_I2CPLD is not set
-# CONFIG_HTC_PASIC3 is not set
-# CONFIG_HTS221 is not set
-# CONFIG_HTU21 is not set
-# CONFIG_HUGETLBFS is not set
-# CONFIG_HUGETLB_PAGE is not set
-# CONFIG_HVC_DCC is not set
-# CONFIG_HVC_UDBG is not set
-# CONFIG_HWLAT_TRACER is not set
-# CONFIG_HWMON is not set
-# CONFIG_HWMON_DEBUG_CHIP is not set
-# CONFIG_HWMON_VID is not set
-# CONFIG_HWSPINLOCK is not set
-# CONFIG_HWSPINLOCK_OMAP is not set
-CONFIG_HW_PERF_EVENTS=y
-# CONFIG_HW_RANDOM is not set
-# CONFIG_HW_RANDOM_AMD is not set
-# CONFIG_HW_RANDOM_ARM_SMCCC_TRNG is not set
-# CONFIG_HW_RANDOM_ATMEL is not set
-# CONFIG_HW_RANDOM_BA431 is not set
-# CONFIG_HW_RANDOM_BCM2835 is not set
-# CONFIG_HW_RANDOM_CAVIUM is not set
-# CONFIG_HW_RANDOM_CCTRNG is not set
-# CONFIG_HW_RANDOM_EXYNOS is not set
-# CONFIG_HW_RANDOM_GEODE is not set
-# CONFIG_HW_RANDOM_INTEL is not set
-# CONFIG_HW_RANDOM_IPROC_RNG200 is not set
-# CONFIG_HW_RANDOM_MTK is not set
-# CONFIG_HW_RANDOM_OMAP is not set
-# CONFIG_HW_RANDOM_OMAP3_ROM is not set
-# CONFIG_HW_RANDOM_PPC4XX is not set
-# CONFIG_HW_RANDOM_TIMERIOMEM is not set
-CONFIG_HW_RANDOM_TPM=y
-# CONFIG_HW_RANDOM_VIA is not set
-# CONFIG_HW_RANDOM_VIRTIO is not set
-# CONFIG_HW_RANDOM_XIPHERA is not set
-# CONFIG_HX711 is not set
-# CONFIG_HYPERV is not set
-# CONFIG_HYPERV_TSCPAGE is not set
-# CONFIG_HYSDN is not set
-CONFIG_HZ=100
-CONFIG_HZ_100=y
-# CONFIG_HZ_1000 is not set
-# CONFIG_HZ_1024 is not set
-# CONFIG_HZ_128 is not set
-# CONFIG_HZ_200 is not set
-# CONFIG_HZ_24 is not set
-# CONFIG_HZ_250 is not set
-# CONFIG_HZ_256 is not set
-# CONFIG_HZ_300 is not set
-# CONFIG_HZ_48 is not set
-# CONFIG_HZ_500 is not set
-# CONFIG_HZ_PERIODIC is not set
-# CONFIG_I2C is not set
-# CONFIG_I2C_ALGOBIT is not set
-# CONFIG_I2C_ALGOPCA is not set
-# CONFIG_I2C_ALGOPCF is not set
-# CONFIG_I2C_ALI1535 is not set
-# CONFIG_I2C_ALI1563 is not set
-# CONFIG_I2C_ALI15X3 is not set
-# CONFIG_I2C_AMD756 is not set
-# CONFIG_I2C_AMD8111 is not set
-# CONFIG_I2C_ARB_GPIO_CHALLENGE is not set
-# CONFIG_I2C_AU1550 is not set
-# CONFIG_I2C_BCM2835 is not set
-# CONFIG_I2C_BCM_IPROC is not set
-# CONFIG_I2C_BRCMSTB is not set
-# CONFIG_I2C_CADENCE is not set
-# CONFIG_I2C_CBUS_GPIO is not set
-# CONFIG_I2C_CHARDEV is not set
-# CONFIG_I2C_COMPAT is not set
-# CONFIG_I2C_CP2615 is not set
-# CONFIG_I2C_DEBUG_ALGO is not set
-# CONFIG_I2C_DEBUG_BUS is not set
-# CONFIG_I2C_DEBUG_CORE is not set
-# CONFIG_I2C_DEMUX_PINCTRL is not set
-# CONFIG_I2C_DESIGNWARE_PCI is not set
-# CONFIG_I2C_DESIGNWARE_PLATFORM is not set
-# CONFIG_I2C_DESIGNWARE_SLAVE is not set
-# CONFIG_I2C_DIOLAN_U2C is not set
-# CONFIG_I2C_EG20T is not set
-# CONFIG_I2C_ELEKTOR is not set
-# CONFIG_I2C_EMEV2 is not set
-# CONFIG_I2C_GPIO is not set
-# CONFIG_I2C_GPIO_FAULT_INJECTOR is not set
-# CONFIG_I2C_HELPER_AUTO is not set
-# CONFIG_I2C_HID is not set
-# CONFIG_I2C_HID_OF is not set
-# CONFIG_I2C_HID_OF_GOODIX is not set
-# CONFIG_I2C_I801 is not set
-# CONFIG_I2C_IBM_IIC is not set
-# CONFIG_I2C_IMG is not set
-# CONFIG_I2C_ISCH is not set
-# CONFIG_I2C_ISMT is not set
-# CONFIG_I2C_JZ4780 is not set
-# CONFIG_I2C_MLXCPLD is not set
-# CONFIG_I2C_MPC is not set
-# CONFIG_I2C_MT65XX is not set
-# CONFIG_I2C_MUX is not set
-# CONFIG_I2C_MUX_GPIO is not set
-# CONFIG_I2C_MUX_GPMUX is not set
-# CONFIG_I2C_MUX_LTC4306 is not set
-# CONFIG_I2C_MUX_MLXCPLD is not set
-# CONFIG_I2C_MUX_PCA9541 is not set
-# CONFIG_I2C_MUX_PCA954x is not set
-# CONFIG_I2C_MUX_PINCTRL is not set
-# CONFIG_I2C_MUX_REG is not set
-# CONFIG_I2C_MV64XXX is not set
-# CONFIG_I2C_NFORCE2 is not set
-# CONFIG_I2C_NOMADIK is not set
-# CONFIG_I2C_NVIDIA_GPU is not set
-# CONFIG_I2C_OCORES is not set
-# CONFIG_I2C_OCTEON is not set
-# CONFIG_I2C_PARPORT is not set
-# CONFIG_I2C_PARPORT_LIGHT is not set
-# CONFIG_I2C_PCA_ISA is not set
-# CONFIG_I2C_PCA_PLATFORM is not set
-# CONFIG_I2C_PIIX4 is not set
-# CONFIG_I2C_PXA_PCI is not set
-# CONFIG_I2C_PXA_SLAVE is not set
-# CONFIG_I2C_RCAR is not set
-# CONFIG_I2C_RK3X is not set
-# CONFIG_I2C_ROBOTFUZZ_OSIF is not set
-# CONFIG_I2C_S3C2410 is not set
-# CONFIG_I2C_SCMI is not set
-# CONFIG_I2C_SH_MOBILE is not set
-# CONFIG_I2C_SIMTEC is not set
-# CONFIG_I2C_SIS5595 is not set
-# CONFIG_I2C_SIS630 is not set
-# CONFIG_I2C_SIS96X is not set
-# CONFIG_I2C_SLAVE is not set
-# CONFIG_I2C_SLAVE_EEPROM is not set
-# CONFIG_I2C_SMBUS is not set
-# CONFIG_I2C_STUB is not set
-# CONFIG_I2C_TAOS_EVM is not set
-# CONFIG_I2C_THUNDERX is not set
-# CONFIG_I2C_TINY_USB is not set
-# CONFIG_I2C_VERSATILE is not set
-# CONFIG_I2C_VIA is not set
-# CONFIG_I2C_VIAPRO is not set
-# CONFIG_I2C_VIRTIO is not set
-# CONFIG_I2C_XILINX is not set
-# CONFIG_I3C is not set
-# CONFIG_I40E is not set
-# CONFIG_I40EVF is not set
-# CONFIG_I6300ESB_WDT is not set
-# CONFIG_I82092 is not set
-# CONFIG_I82365 is not set
-# CONFIG_IAQCORE is not set
-# CONFIG_IBM_ASM is not set
-# CONFIG_IBM_EMAC_DEBUG is not set
-# CONFIG_IBM_EMAC_EMAC4 is not set
-# CONFIG_IBM_EMAC_MAL_CLR_ICINTSTAT is not set
-# CONFIG_IBM_EMAC_MAL_COMMON_ERR is not set
-# CONFIG_IBM_EMAC_NO_FLOW_CTRL is not set
-# CONFIG_IBM_EMAC_RGMII is not set
-# CONFIG_IBM_EMAC_TAH is not set
-# CONFIG_IBM_EMAC_ZMII is not set
-# CONFIG_ICE is not set
-# CONFIG_ICP10100 is not set
-# CONFIG_ICPLUS_PHY is not set
-# CONFIG_ICS932S401 is not set
-# CONFIG_ICST is not set
-# CONFIG_IDE is not set
-# CONFIG_IDEAPAD_LAPTOP is not set
-# CONFIG_IDE_GD is not set
-# CONFIG_IDE_PROC_FS is not set
-# CONFIG_IDE_TASK_IOCTL is not set
-# CONFIG_IDLE_PAGE_TRACKING is not set
-# CONFIG_IEEE802154 is not set
-# CONFIG_IEEE802154_ADF7242 is not set
-# CONFIG_IEEE802154_ATUSB is not set
-# CONFIG_IEEE802154_CA8210 is not set
-# CONFIG_IEEE802154_HWSIM is not set
-# CONFIG_IEEE802154_MCR20A is not set
-# CONFIG_IFB is not set
-# CONFIG_IGB is not set
-# CONFIG_IGBVF is not set
-# CONFIG_IGC is not set
-# CONFIG_IIO is not set
-# CONFIG_IIO_BUFFER is not set
-# CONFIG_IIO_BUFFER_CB is not set
-# CONFIG_IIO_BUFFER_DMA is not set
-# CONFIG_IIO_BUFFER_DMAENGINE is not set
-# CONFIG_IIO_BUFFER_HDC2010 is not set
-# CONFIG_IIO_BUFFER_HW_CONSUMER is not set
-# CONFIG_IIO_CONFIGFS is not set
-CONFIG_IIO_CONSUMERS_PER_TRIGGER=2
-# CONFIG_IIO_CROS_EC_ACCEL_LEGACY is not set
-# CONFIG_IIO_INTERRUPT_TRIGGER is not set
-# CONFIG_IIO_MUX is not set
-# CONFIG_IIO_PERIODIC_RTC_TRIGGER is not set
-# CONFIG_IIO_RESCALE is not set
-# CONFIG_IIO_SIMPLE_DUMMY is not set
-# CONFIG_IIO_SSP_SENSORHUB is not set
-# CONFIG_IIO_ST_ACCEL_3AXIS is not set
-# CONFIG_IIO_ST_GYRO_3AXIS is not set
-# CONFIG_IIO_ST_LSM6DSX is not set
-# CONFIG_IIO_ST_LSM9DS0 is not set
-# CONFIG_IIO_ST_MAGN_3AXIS is not set
-# CONFIG_IIO_ST_PRESS is not set
-# CONFIG_IIO_SW_DEVICE is not set
-# CONFIG_IIO_SW_TRIGGER is not set
-# CONFIG_IIO_SYSFS_TRIGGER is not set
-# CONFIG_IIO_TRIGGER is not set
-# CONFIG_IIO_TRIGGERED_EVENT is not set
-# CONFIG_IKCONFIG is not set
-# CONFIG_IKCONFIG_PROC is not set
-# CONFIG_IKHEADERS is not set
-# CONFIG_IMA is not set
-# CONFIG_IMGPDC_WDT is not set
-# CONFIG_IMG_MDC_DMA is not set
-# CONFIG_IMX7D_ADC is not set
-# CONFIG_IMX_IPUV3_CORE is not set
-# CONFIG_IMX_THERMAL is not set
-# CONFIG_INA2XX_ADC is not set
-# CONFIG_INDIRECT_PIO is not set
-CONFIG_INET=y
-# CONFIG_INET6_AH is not set
-# CONFIG_INET6_ESP is not set
-# CONFIG_INET6_ESPINTCP is not set
-# CONFIG_INET6_IPCOMP is not set
-# CONFIG_INET6_TUNNEL is not set
-# CONFIG_INET6_XFRM_TUNNEL is not set
-# CONFIG_INET_AH is not set
-# CONFIG_INET_DIAG is not set
-# CONFIG_INET_ESP is not set
-# CONFIG_INET_ESPINTCP is not set
-# CONFIG_INET_IPCOMP is not set
-# CONFIG_INET_LRO is not set
-CONFIG_INET_TABLE_PERTURB_ORDER=16
-# CONFIG_INET_TCP_DIAG is not set
-# CONFIG_INET_TUNNEL is not set
-# CONFIG_INET_UDP_DIAG is not set
-# CONFIG_INET_XFRM_TUNNEL is not set
-# CONFIG_INFINIBAND is not set
-# CONFIG_INFTL is not set
-# CONFIG_INGENIC_ADC is not set
-# CONFIG_INGENIC_CGU_JZ4725B is not set
-# CONFIG_INGENIC_CGU_JZ4740 is not set
-# CONFIG_INGENIC_CGU_JZ4760 is not set
-# CONFIG_INGENIC_CGU_JZ4770 is not set
-# CONFIG_INGENIC_CGU_JZ4780 is not set
-# CONFIG_INGENIC_CGU_X1000 is not set
-# CONFIG_INGENIC_CGU_X1830 is not set
-# CONFIG_INGENIC_OST is not set
-# CONFIG_INGENIC_SYSOST is not set
-# CONFIG_INGENIC_TCU_CLK is not set
-# CONFIG_INGENIC_TCU_IRQ is not set
-# CONFIG_INGENIC_TIMER is not set
-CONFIG_INIT_ENV_ARG_LIMIT=32
-# CONFIG_INIT_ON_ALLOC_DEFAULT_ON is not set
-# CONFIG_INIT_ON_FREE_DEFAULT_ON is not set
-# CONFIG_INIT_STACK_ALL_PATTERN is not set
-# CONFIG_INIT_STACK_ALL_ZERO is not set
-CONFIG_INIT_STACK_NONE=y
-CONFIG_INOTIFY_USER=y
-# CONFIG_INPUT is not set
-# CONFIG_INPUT_AD714X is not set
-# CONFIG_INPUT_ADXL34X is not set
-# CONFIG_INPUT_APANEL is not set
-# CONFIG_INPUT_ATI_REMOTE2 is not set
-# CONFIG_INPUT_ATLAS_BTNS is not set
-# CONFIG_INPUT_ATMEL_CAPTOUCH is not set
-# CONFIG_INPUT_AXP20X_PEK is not set
-# CONFIG_INPUT_BMA150 is not set
-# CONFIG_INPUT_CM109 is not set
-# CONFIG_INPUT_CMA3000 is not set
-# CONFIG_INPUT_DA7280_HAPTICS is not set
-# CONFIG_INPUT_DRV260X_HAPTICS is not set
-# CONFIG_INPUT_DRV2665_HAPTICS is not set
-# CONFIG_INPUT_DRV2667_HAPTICS is not set
-# CONFIG_INPUT_E3X0_BUTTON is not set
-# CONFIG_INPUT_EVBUG is not set
-# CONFIG_INPUT_EVDEV is not set
-# CONFIG_INPUT_FF_MEMLESS is not set
-# CONFIG_INPUT_GP2A is not set
-# CONFIG_INPUT_GPIO_BEEPER is not set
-# CONFIG_INPUT_GPIO_DECODER is not set
-# CONFIG_INPUT_GPIO_ROTARY_ENCODER is not set
-# CONFIG_INPUT_GPIO_TILT_POLLED is not set
-# CONFIG_INPUT_GPIO_VIBRA is not set
-# CONFIG_INPUT_IDEAPAD_SLIDEBAR is not set
-# CONFIG_INPUT_IMS_PCU is not set
-# CONFIG_INPUT_IQS269A is not set
-# CONFIG_INPUT_IQS626A is not set
-# CONFIG_INPUT_JOYDEV is not set
-# CONFIG_INPUT_JOYSTICK is not set
-# CONFIG_INPUT_KEYBOARD is not set
-# CONFIG_INPUT_KEYSPAN_REMOTE is not set
-# CONFIG_INPUT_KXTJ9 is not set
-# CONFIG_INPUT_LEDS is not set
-# CONFIG_INPUT_MATRIXKMAP is not set
-# CONFIG_INPUT_MAX8997_HAPTIC is not set
-CONFIG_INPUT_MISC=y
-# CONFIG_INPUT_MMA8450 is not set
-# CONFIG_INPUT_MOUSE is not set
-# CONFIG_INPUT_MOUSEDEV is not set
-# CONFIG_INPUT_MPU3050 is not set
-# CONFIG_INPUT_MSM_VIBRATOR is not set
-# CONFIG_INPUT_PALMAS_PWRBUTTON is not set
-# CONFIG_INPUT_PCF8574 is not set
-# CONFIG_INPUT_PCSPKR is not set
-# CONFIG_INPUT_PM8941_PWRKEY is not set
-# CONFIG_INPUT_PM8XXX_VIBRATOR is not set
-# CONFIG_INPUT_POLLDEV is not set
-# CONFIG_INPUT_POWERMATE is not set
-# CONFIG_INPUT_PWM_BEEPER is not set
-# CONFIG_INPUT_PWM_VIBRA is not set
-# CONFIG_INPUT_REGULATOR_HAPTIC is not set
-# CONFIG_INPUT_SOC_BUTTON_ARRAY is not set
-# CONFIG_INPUT_SPARSEKMAP is not set
-# CONFIG_INPUT_TABLET is not set
-# CONFIG_INPUT_TOUCHSCREEN is not set
-# CONFIG_INPUT_TPS65218_PWRBUTTON is not set
-# CONFIG_INPUT_TWL4030_PWRBUTTON is not set
-# CONFIG_INPUT_TWL4030_VIBRA is not set
-# CONFIG_INPUT_TWL6040_VIBRA is not set
-# CONFIG_INPUT_UINPUT is not set
-# CONFIG_INPUT_WISTRON_BTNS is not set
-# CONFIG_INPUT_YEALINK is not set
-# CONFIG_INT340X_THERMAL is not set
-# CONFIG_INTEGRITY is not set
-# CONFIG_INTEGRITY_AUDIT is not set
-# CONFIG_INTEGRITY_SIGNATURE is not set
-# CONFIG_INTEL_ATOMISP2_LED is not set
-# CONFIG_INTEL_ATOMISP2_PM is not set
-# CONFIG_INTEL_CHT_INT33FE is not set
-# CONFIG_INTEL_HID_EVENT is not set
-# CONFIG_INTEL_IDLE is not set
-# CONFIG_INTEL_IDMA64 is not set
-# CONFIG_INTEL_IDXD is not set
-# CONFIG_INTEL_IDXD_COMPAT is not set
-# CONFIG_INTEL_INT0002_VGPIO is not set
-# CONFIG_INTEL_IOATDMA is not set
-# CONFIG_INTEL_ISH_HID is not set
-# CONFIG_INTEL_MEI is not set
-# CONFIG_INTEL_MEI_ME is not set
-# CONFIG_INTEL_MEI_TXE is not set
-# CONFIG_INTEL_MIC_CARD is not set
-# CONFIG_INTEL_MIC_HOST is not set
-# CONFIG_INTEL_MID_PTI is not set
-# CONFIG_INTEL_OAKTRAIL is not set
-# CONFIG_INTEL_PMC_CORE is not set
-# CONFIG_INTEL_PUNIT_IPC is not set
-# CONFIG_INTEL_RST is not set
-# CONFIG_INTEL_SMARTCONNECT is not set
-# CONFIG_INTEL_SOC_PMIC is not set
-# CONFIG_INTEL_SOC_PMIC_CHTDC_TI is not set
-# CONFIG_INTEL_SOC_PMIC_CHTWC is not set
-# CONFIG_INTEL_TH is not set
-# CONFIG_INTEL_VBTN is not set
-# CONFIG_INTEL_XWAY_PHY is not set
-# CONFIG_INTERCONNECT is not set
-# CONFIG_INTERVAL_TREE_TEST is not set
-# CONFIG_INV_ICM42600_I2C is not set
-# CONFIG_INV_ICM42600_SPI is not set
-# CONFIG_INV_MPU6050_I2C is not set
-# CONFIG_INV_MPU6050_IIO is not set
-# CONFIG_INV_MPU6050_SPI is not set
-# CONFIG_IOMMU_DEFAULT_DMA_LAZY is not set
-# CONFIG_IOMMU_DEFAULT_DMA_STRICT is not set
-# CONFIG_IOMMU_DEFAULT_PASSTHROUGH is not set
-# CONFIG_IOMMU_SUPPORT is not set
-# CONFIG_IONIC is not set
-# CONFIG_IOSCHED_BFQ is not set
-# CONFIG_IOSM is not set
-CONFIG_IO_STRICT_DEVMEM=y
-# CONFIG_IO_URING is not set
-CONFIG_IO_WQ=y
-# CONFIG_IP17XX_PHY is not set
-# CONFIG_IP6_NF_FILTER is not set
-# CONFIG_IP6_NF_IPTABLES is not set
-# CONFIG_IP6_NF_MANGLE is not set
-# CONFIG_IP6_NF_MATCH_AH is not set
-# CONFIG_IP6_NF_MATCH_EUI64 is not set
-# CONFIG_IP6_NF_MATCH_FRAG is not set
-# CONFIG_IP6_NF_MATCH_HL is not set
-# CONFIG_IP6_NF_MATCH_IPV6HEADER is not set
-# CONFIG_IP6_NF_MATCH_MH is not set
-# CONFIG_IP6_NF_MATCH_OPTS is not set
-# CONFIG_IP6_NF_MATCH_RPFILTER is not set
-# CONFIG_IP6_NF_MATCH_RT is not set
-# CONFIG_IP6_NF_MATCH_SRH is not set
-# CONFIG_IP6_NF_NAT is not set
-# CONFIG_IP6_NF_RAW is not set
-# CONFIG_IP6_NF_SECURITY is not set
-# CONFIG_IP6_NF_TARGET_HL is not set
-# CONFIG_IP6_NF_TARGET_MASQUERADE is not set
-# CONFIG_IP6_NF_TARGET_REJECT is not set
-# CONFIG_IP6_NF_TARGET_SYNPROXY is not set
-# CONFIG_IPACK_BUS is not set
-# CONFIG_IPC_NS is not set
-# CONFIG_IPMB_DEVICE_INTERFACE is not set
-# CONFIG_IPMI_HANDLER is not set
-# CONFIG_IPV6 is not set
-# CONFIG_IPV6_FOU is not set
-# CONFIG_IPV6_FOU_TUNNEL is not set
-# CONFIG_IPV6_ILA is not set
-# CONFIG_IPV6_IOAM6_LWTUNNEL is not set
-# CONFIG_IPV6_MIP6 is not set
-# CONFIG_IPV6_MROUTE is not set
-# CONFIG_IPV6_MROUTE_MULTIPLE_TABLES is not set
-# CONFIG_IPV6_MULTIPLE_TABLES is not set
-CONFIG_IPV6_NDISC_NODETYPE=y
-# CONFIG_IPV6_OPTIMISTIC_DAD is not set
-# CONFIG_IPV6_ROUTER_PREF is not set
-# CONFIG_IPV6_ROUTE_INFO is not set
-# CONFIG_IPV6_RPL_LWTUNNEL is not set
-# CONFIG_IPV6_SEG6_HMAC is not set
-# CONFIG_IPV6_SEG6_LWTUNNEL is not set
-# CONFIG_IPV6_SIT is not set
-# CONFIG_IPV6_SIT_6RD is not set
-# CONFIG_IPV6_TUNNEL is not set
-# CONFIG_IPV6_VTI is not set
-# CONFIG_IPVLAN is not set
-# CONFIG_IPVTAP is not set
-# CONFIG_IPW2100 is not set
-# CONFIG_IPW2100_DEBUG is not set
-CONFIG_IPW2100_MONITOR=y
-# CONFIG_IPW2200 is not set
-# CONFIG_IPW2200_DEBUG is not set
-CONFIG_IPW2200_MONITOR=y
-# CONFIG_IPW2200_PROMISCUOUS is not set
-# CONFIG_IPW2200_QOS is not set
-# CONFIG_IPW2200_RADIOTAP is not set
-# CONFIG_IPWIRELESS is not set
-# CONFIG_IPX is not set
-CONFIG_IP_ADVANCED_ROUTER=y
-# CONFIG_IP_DCCP is not set
-# CONFIG_IP_FIB_TRIE_STATS is not set
-# CONFIG_IP_MROUTE is not set
-CONFIG_IP_MROUTE_MULTIPLE_TABLES=y
-CONFIG_IP_MULTICAST=y
-CONFIG_IP_MULTIPLE_TABLES=y
-# CONFIG_IP_NF_ARPFILTER is not set
-# CONFIG_IP_NF_ARPTABLES is not set
-# CONFIG_IP_NF_ARP_MANGLE is not set
-# CONFIG_IP_NF_FILTER is not set
-# CONFIG_IP_NF_IPTABLES is not set
-# CONFIG_IP_NF_MANGLE is not set
-# CONFIG_IP_NF_MATCH_AH is not set
-# CONFIG_IP_NF_MATCH_ECN is not set
-# CONFIG_IP_NF_MATCH_RPFILTER is not set
-# CONFIG_IP_NF_MATCH_TTL is not set
-# CONFIG_IP_NF_RAW is not set
-# CONFIG_IP_NF_SECURITY is not set
-# CONFIG_IP_NF_TARGET_CLUSTERIP is not set
-# CONFIG_IP_NF_TARGET_ECN is not set
-# CONFIG_IP_NF_TARGET_MASQUERADE is not set
-# CONFIG_IP_NF_TARGET_NETMAP is not set
-# CONFIG_IP_NF_TARGET_REDIRECT is not set
-# CONFIG_IP_NF_TARGET_REJECT is not set
-# CONFIG_IP_NF_TARGET_SYNPROXY is not set
-# CONFIG_IP_NF_TARGET_TTL is not set
-# CONFIG_IP_PIMSM_V1 is not set
-# CONFIG_IP_PIMSM_V2 is not set
-# CONFIG_IP_PNP is not set
-CONFIG_IP_ROUTE_MULTIPATH=y
-CONFIG_IP_ROUTE_VERBOSE=y
-# CONFIG_IP_SCTP is not set
-# CONFIG_IP_SET is not set
-# CONFIG_IP_SET_HASH_IPMAC is not set
-# CONFIG_IP_VS is not set
-# CONFIG_IP_VS_MH is not set
-CONFIG_IP_VS_MH_TAB_INDEX=10
-# CONFIG_IP_VS_TWOS is not set
-# CONFIG_IRDA is not set
-# CONFIG_IRQSOFF_TRACER is not set
-# CONFIG_IRQ_ALL_CPUS is not set
-# CONFIG_IRQ_DOMAIN_DEBUG is not set
-# CONFIG_IRQ_POLL is not set
-# CONFIG_IRQ_TIME_ACCOUNTING is not set
-# CONFIG_IR_GPIO_CIR is not set
-# CONFIG_IR_HIX5HD2 is not set
-# CONFIG_IR_IGORPLUGUSB is not set
-# CONFIG_IR_IGUANA is not set
-# CONFIG_IR_IMG is not set
-# CONFIG_IR_IMON is not set
-# CONFIG_IR_IMON_RAW is not set
-# CONFIG_IR_JVC_DECODER is not set
-# CONFIG_IR_LIRC_CODEC is not set
-# CONFIG_IR_MCEUSB is not set
-# CONFIG_IR_NEC_DECODER is not set
-# CONFIG_IR_RC5_DECODER is not set
-# CONFIG_IR_RC6_DECODER is not set
-# CONFIG_IR_REDRAT3 is not set
-# CONFIG_IR_SERIAL is not set
-# CONFIG_IR_SIR is not set
-# CONFIG_IR_SONY_DECODER is not set
-# CONFIG_IR_STREAMZAP is not set
-# CONFIG_IR_TOY is not set
-# CONFIG_IR_TTUSBIR is not set
-# CONFIG_ISA_BUS is not set
-# CONFIG_ISA_BUS_API is not set
-# CONFIG_ISCSI_BOOT_SYSFS is not set
-# CONFIG_ISCSI_TCP is not set
-CONFIG_ISDN=y
-# CONFIG_ISDN_AUDIO is not set
-# CONFIG_ISDN_CAPI is not set
-# CONFIG_ISDN_CAPI_CAPIDRV is not set
-# CONFIG_ISDN_DIVERSION is not set
-# CONFIG_ISDN_DRV_ACT2000 is not set
-# CONFIG_ISDN_DRV_GIGASET is not set
-# CONFIG_ISDN_DRV_HISAX is not set
-# CONFIG_ISDN_DRV_ICN is not set
-# CONFIG_ISDN_DRV_LOOP is not set
-# CONFIG_ISDN_DRV_PCBIT is not set
-# CONFIG_ISDN_DRV_SC is not set
-# CONFIG_ISDN_I4L is not set
-# CONFIG_ISL29003 is not set
-# CONFIG_ISL29020 is not set
-# CONFIG_ISL29125 is not set
-# CONFIG_ISL29501 is not set
-# CONFIG_ISO9660_FS is not set
-# CONFIG_ISS4xx is not set
-# CONFIG_ITG3200 is not set
-# CONFIG_IWL3945 is not set
-# CONFIG_IWLWIFI is not set
-# CONFIG_IXGB is not set
-# CONFIG_IXGBE is not set
-# CONFIG_IXGBEVF is not set
-# CONFIG_JAILHOUSE_GUEST is not set
-# CONFIG_JBD2_DEBUG is not set
-# CONFIG_JFFS2_CMODE_FAVOURLZO is not set
-# CONFIG_JFFS2_CMODE_NONE is not set
-CONFIG_JFFS2_CMODE_PRIORITY=y
-# CONFIG_JFFS2_CMODE_SIZE is not set
-CONFIG_JFFS2_COMPRESSION_OPTIONS=y
-CONFIG_JFFS2_FS=y
-CONFIG_JFFS2_FS_DEBUG=0
-# CONFIG_JFFS2_FS_POSIX_ACL is not set
-# CONFIG_JFFS2_FS_SECURITY is not set
-# CONFIG_JFFS2_FS_WBUF_VERIFY is not set
-CONFIG_JFFS2_FS_WRITEBUFFER=y
-CONFIG_JFFS2_FS_XATTR=y
-CONFIG_JFFS2_LZMA=y
-# CONFIG_JFFS2_LZO is not set
-CONFIG_JFFS2_RTIME=y
-# CONFIG_JFFS2_RUBIN is not set
-CONFIG_JFFS2_SUMMARY=y
-# CONFIG_JFFS2_ZLIB is not set
-# CONFIG_JFS_DEBUG is not set
-# CONFIG_JFS_FS is not set
-# CONFIG_JFS_POSIX_ACL is not set
-# CONFIG_JFS_SECURITY is not set
-# CONFIG_JFS_STATISTICS is not set
-# CONFIG_JME is not set
-CONFIG_JOLIET=y
-# CONFIG_JSA1212 is not set
-# CONFIG_JUMP_LABEL is not set
-# CONFIG_JZ4740_WDT is not set
-# CONFIG_JZ4770_PHY is not set
-# CONFIG_KALLSYMS is not set
-# CONFIG_KALLSYMS_ABSOLUTE_PERCPU is not set
-# CONFIG_KALLSYMS_ALL is not set
-CONFIG_KALLSYMS_BASE_RELATIVE=y
-# CONFIG_KALLSYMS_UNCOMPRESSED is not set
-# CONFIG_KARMA_PARTITION is not set
-# CONFIG_KASAN is not set
-# CONFIG_KASAN_MODULE_TEST is not set
-CONFIG_KASAN_STACK=y
-# CONFIG_KCMP is not set
-# CONFIG_KCOV is not set
-CONFIG_KCOV_IRQ_AREA_SIZE=0x40000
-# CONFIG_KCSAN is not set
-# CONFIG_KERNEL_BZIP2 is not set
-# CONFIG_KERNEL_CAT is not set
-# CONFIG_KERNEL_GZIP is not set
-# CONFIG_KERNEL_LZ4 is not set
-# CONFIG_KERNEL_LZMA is not set
-# CONFIG_KERNEL_LZO is not set
-CONFIG_KERNEL_MODE_NEON=y
-CONFIG_KERNEL_XZ=y
-# CONFIG_KERNEL_ZSTD is not set
-CONFIG_KERNFS=y
-# CONFIG_KEXEC is not set
-# CONFIG_KEXEC_FILE is not set
-# CONFIG_KEXEC_SIG is not set
-# CONFIG_KEYBOARD_ADC is not set
-# CONFIG_KEYBOARD_ADP5588 is not set
-# CONFIG_KEYBOARD_ADP5589 is not set
-# CONFIG_KEYBOARD_APPLESPI is not set
-# CONFIG_KEYBOARD_ATKBD is not set
-# CONFIG_KEYBOARD_BCM is not set
-# CONFIG_KEYBOARD_CAP11XX is not set
-# CONFIG_KEYBOARD_DLINK_DIR685 is not set
-# CONFIG_KEYBOARD_GPIO is not set
-# CONFIG_KEYBOARD_GPIO_POLLED is not set
-# CONFIG_KEYBOARD_LKKBD is not set
-# CONFIG_KEYBOARD_LM8323 is not set
-# CONFIG_KEYBOARD_LM8333 is not set
-# CONFIG_KEYBOARD_MATRIX is not set
-# CONFIG_KEYBOARD_MAX7359 is not set
-# CONFIG_KEYBOARD_MCS is not set
-# CONFIG_KEYBOARD_MPR121 is not set
-# CONFIG_KEYBOARD_NEWTON is not set
-# CONFIG_KEYBOARD_OMAP4 is not set
-# CONFIG_KEYBOARD_OPENCORES is not set
-# CONFIG_KEYBOARD_PXA27x is not set
-# CONFIG_KEYBOARD_QT1050 is not set
-# CONFIG_KEYBOARD_QT1070 is not set
-# CONFIG_KEYBOARD_QT2160 is not set
-# CONFIG_KEYBOARD_SAMSUNG is not set
-# CONFIG_KEYBOARD_SH_KEYSC is not set
-# CONFIG_KEYBOARD_SNVS_PWRKEY is not set
-# CONFIG_KEYBOARD_STMPE is not set
-# CONFIG_KEYBOARD_STOWAWAY is not set
-# CONFIG_KEYBOARD_SUNKBD is not set
-# CONFIG_KEYBOARD_TCA6416 is not set
-# CONFIG_KEYBOARD_TCA8418 is not set
-# CONFIG_KEYBOARD_TEGRA is not set
-# CONFIG_KEYBOARD_TM2_TOUCHKEY is not set
-# CONFIG_KEYBOARD_TWL4030 is not set
-# CONFIG_KEYBOARD_XTKBD is not set
-# CONFIG_KEYS is not set
-# CONFIG_KEYS_REQUEST_CACHE is not set
-# CONFIG_KEY_DH_OPERATIONS is not set
-# CONFIG_KFENCE is not set
-# CONFIG_KGDB is not set
-# CONFIG_KMEMCHECK is not set
-# CONFIG_KMX61 is not set
-# CONFIG_KPC2000 is not set
-# CONFIG_KPROBES is not set
-# CONFIG_KPROBES_SANITY_TEST is not set
-# CONFIG_KPROBE_EVENTS_ON_NOTRACE is not set
-# CONFIG_KPROBE_EVENT_GEN_TEST is not set
-# CONFIG_KS7010 is not set
-# CONFIG_KS8842 is not set
-# CONFIG_KS8851 is not set
-# CONFIG_KS8851_MLL is not set
-# CONFIG_KSM is not set
-# CONFIG_KSZ884X_PCI is not set
-# CONFIG_KUNIT is not set
-CONFIG_KUSER_HELPERS=y
-# CONFIG_KVM_AMD is not set
-# CONFIG_KVM_AMD_SEV is not set
-# CONFIG_KVM_GUEST is not set
-# CONFIG_KVM_INTEL is not set
-# CONFIG_KVM_WERROR is not set
-# CONFIG_KVM_XEN is not set
-# CONFIG_KXCJK1013 is not set
-# CONFIG_KXSD9 is not set
-# CONFIG_L2TP is not set
-# CONFIG_L2TP_ETH is not set
-# CONFIG_L2TP_IP is not set
-# CONFIG_L2TP_V3 is not set
-# CONFIG_LAN743X is not set
-# CONFIG_LANMEDIA is not set
-# CONFIG_LANTIQ is not set
-# CONFIG_LAPB is not set
-# CONFIG_LASAT is not set
-# CONFIG_LATENCYTOP is not set
-# CONFIG_LATTICE_ECP3_CONFIG is not set
-CONFIG_LBDAF=y
-# CONFIG_LCD_AMS369FG06 is not set
-# CONFIG_LCD_CLASS_DEVICE is not set
-# CONFIG_LCD_HX8357 is not set
-# CONFIG_LCD_ILI922X is not set
-# CONFIG_LCD_ILI9320 is not set
-# CONFIG_LCD_L4F00242T03 is not set
-# CONFIG_LCD_LD9040 is not set
-# CONFIG_LCD_LMS283GF05 is not set
-# CONFIG_LCD_LMS501KF03 is not set
-# CONFIG_LCD_LTV350QV is not set
-# CONFIG_LCD_OTM3225A is not set
-# CONFIG_LCD_S6E63M0 is not set
-# CONFIG_LCD_TDO24M is not set
-# CONFIG_LCD_VGG2432A4 is not set
-CONFIG_LDISC_AUTOLOAD=y
-# CONFIG_LDM_PARTITION is not set
-CONFIG_LD_DEAD_CODE_DATA_ELIMINATION=y
-# CONFIG_LD_HEAD_STUB_CATCH is not set
-# CONFIG_LEDS_AN30259A is not set
-# CONFIG_LEDS_APU is not set
-# CONFIG_LEDS_AW2013 is not set
-# CONFIG_LEDS_BCM6328 is not set
-# CONFIG_LEDS_BCM6358 is not set
-# CONFIG_LEDS_BD2802 is not set
-# CONFIG_LEDS_BLINKM is not set
-CONFIG_LEDS_BRIGHTNESS_HW_CHANGED=y
-CONFIG_LEDS_CLASS=y
-# CONFIG_LEDS_CLASS_FLASH is not set
-CONFIG_LEDS_CLASS_MULTICOLOR=y
-# CONFIG_LEDS_CR0014114 is not set
-# CONFIG_LEDS_DAC124S085 is not set
-# CONFIG_LEDS_EL15203000 is not set
-# CONFIG_LEDS_GPIO is not set
-# CONFIG_LEDS_INTEL_SS4200 is not set
-# CONFIG_LEDS_IS31FL319X is not set
-# CONFIG_LEDS_IS31FL32XX is not set
-# CONFIG_LEDS_LM3530 is not set
-# CONFIG_LEDS_LM3532 is not set
-# CONFIG_LEDS_LM355x is not set
-# CONFIG_LEDS_LM3642 is not set
-# CONFIG_LEDS_LM3692X is not set
-# CONFIG_LEDS_LP3944 is not set
-# CONFIG_LEDS_LP3952 is not set
-# CONFIG_LEDS_LP50XX is not set
-# CONFIG_LEDS_LP5521 is not set
-# CONFIG_LEDS_LP5523 is not set
-# CONFIG_LEDS_LP5562 is not set
-# CONFIG_LEDS_LP55XX_COMMON is not set
-# CONFIG_LEDS_LP8501 is not set
-# CONFIG_LEDS_LP8860 is not set
-# CONFIG_LEDS_LT3593 is not set
-# CONFIG_LEDS_MLXCPLD is not set
-# CONFIG_LEDS_MLXREG is not set
-# CONFIG_LEDS_NIC78BX is not set
-# CONFIG_LEDS_NS2 is not set
-# CONFIG_LEDS_OT200 is not set
-# CONFIG_LEDS_PCA9532 is not set
-# CONFIG_LEDS_PCA955X is not set
-# CONFIG_LEDS_PCA963X is not set
-# CONFIG_LEDS_PWM is not set
-# CONFIG_LEDS_REGULATOR is not set
-# CONFIG_LEDS_SPI_BYTE is not set
-# CONFIG_LEDS_SYSCON is not set
-# CONFIG_LEDS_TCA6507 is not set
-# CONFIG_LEDS_TI_LMU_COMMON is not set
-# CONFIG_LEDS_TLC591XX is not set
-CONFIG_LEDS_TRIGGERS=y
-# CONFIG_LEDS_TRIGGER_ACTIVITY is not set
-# CONFIG_LEDS_TRIGGER_AUDIO is not set
-# CONFIG_LEDS_TRIGGER_BACKLIGHT is not set
-# CONFIG_LEDS_TRIGGER_CAMERA is not set
-# CONFIG_LEDS_TRIGGER_CPU is not set
-CONFIG_LEDS_TRIGGER_DEFAULT_ON=y
-# CONFIG_LEDS_TRIGGER_DISK is not set
-# CONFIG_LEDS_TRIGGER_GPIO is not set
-CONFIG_LEDS_TRIGGER_HEARTBEAT=y
-# CONFIG_LEDS_TRIGGER_MTD is not set
-CONFIG_LEDS_TRIGGER_NETDEV=y
-# CONFIG_LEDS_TRIGGER_ONESHOT is not set
-# CONFIG_LEDS_TRIGGER_PANIC is not set
-# CONFIG_LEDS_TRIGGER_PATTERN is not set
-CONFIG_LEDS_TRIGGER_TIMER=y
-# CONFIG_LEDS_TRIGGER_TRANSIENT is not set
-# CONFIG_LEDS_TRIGGER_TTY is not set
-# CONFIG_LEDS_TURRIS_OMNIA is not set
-# CONFIG_LEDS_USER is not set
-# CONFIG_LED_TRIGGER_PHY is not set
-# CONFIG_LEGACY_PTYS is not set
-# CONFIG_LGUEST is not set
-# CONFIG_LIB80211 is not set
-# CONFIG_LIB80211_CRYPT_CCMP is not set
-# CONFIG_LIB80211_CRYPT_TKIP is not set
-# CONFIG_LIB80211_CRYPT_WEP is not set
-# CONFIG_LIB80211_DEBUG is not set
-# CONFIG_LIBCRC32C is not set
-# CONFIG_LIBERTAS is not set
-# CONFIG_LIBERTAS_THINFIRM is not set
-# CONFIG_LIBERTAS_USB is not set
-# CONFIG_LIBFC is not set
-# CONFIG_LIBFCOE is not set
-# CONFIG_LIBIPW_DEBUG is not set
-# CONFIG_LIBNVDIMM is not set
-CONFIG_LIB_MEMNEQ=y
-# CONFIG_LIDAR_LITE_V2 is not set
-CONFIG_LINEAR_RANGES=y
-# CONFIG_LIQUIDIO is not set
-# CONFIG_LIQUIDIO_VF is not set
-# CONFIG_LIRC is not set
-# CONFIG_LIS3L02DQ is not set
-# CONFIG_LITEX_LITEETH is not set
-# CONFIG_LITEX_SOC_CONTROLLER is not set
-# CONFIG_LIVEPATCH is not set
-# CONFIG_LKDTM is not set
-CONFIG_LLC=y
-# CONFIG_LLC2 is not set
-# CONFIG_LMK04832 is not set
-# CONFIG_LMP91000 is not set
-# CONFIG_LNET is not set
-CONFIG_LOCALVERSION=""
-# CONFIG_LOCALVERSION_AUTO is not set
-# CONFIG_LOCKD is not set
-CONFIG_LOCKDEP_BITS=15
-CONFIG_LOCKDEP_CHAINS_BITS=16
-CONFIG_LOCKDEP_CIRCULAR_QUEUE_BITS=12
-CONFIG_LOCKDEP_STACK_TRACE_BITS=19
-CONFIG_LOCKDEP_STACK_TRACE_HASH_BITS=14
-CONFIG_LOCKDEP_SUPPORT=y
-CONFIG_LOCKD_V4=y
-# CONFIG_LOCKUP_DETECTOR is not set
-# CONFIG_LOCK_EVENT_COUNTS is not set
-# CONFIG_LOCK_STAT is not set
-# CONFIG_LOCK_TORTURE_TEST is not set
-# CONFIG_LOGFS is not set
-# CONFIG_LOGIG940_FF is not set
-# CONFIG_LOGIRUMBLEPAD2_FF is not set
-# CONFIG_LOGITECH_FF is not set
-# CONFIG_LOGIWHEELS_FF is not set
-# CONFIG_LOGO is not set
-CONFIG_LOG_BUF_SHIFT=17
-CONFIG_LOG_CPU_MAX_BUF_SHIFT=12
-# CONFIG_LOONGSON_MC146818 is not set
-# CONFIG_LPC_ICH is not set
-# CONFIG_LPC_SCH is not set
-# CONFIG_LP_CONSOLE is not set
-CONFIG_LRU_GEN=y
-CONFIG_LRU_GEN_ENABLED=y
-# CONFIG_LRU_GEN_STATS is not set
-# CONFIG_LSI_ET1011C_PHY is not set
-CONFIG_LSM="lockdown,yama,loadpin,safesetid,integrity"
-CONFIG_LSM_MMAP_MIN_ADDR=65536
-# CONFIG_LTC1660 is not set
-# CONFIG_LTC2471 is not set
-# CONFIG_LTC2485 is not set
-# CONFIG_LTC2496 is not set
-# CONFIG_LTC2497 is not set
-# CONFIG_LTC2632 is not set
-# CONFIG_LTC2983 is not set
-# CONFIG_LTE_GDM724X is not set
-CONFIG_LTO_NONE=y
-# CONFIG_LTPC is not set
-# CONFIG_LTR501 is not set
-# CONFIG_LUSTRE_FS is not set
-# CONFIG_LV0104CS is not set
-# CONFIG_LWTUNNEL is not set
-# CONFIG_LXT_PHY is not set
-# CONFIG_LZ4HC_COMPRESS is not set
-# CONFIG_LZ4_COMPRESS is not set
-# CONFIG_LZ4_DECOMPRESS is not set
-CONFIG_LZMA_COMPRESS=y
-CONFIG_LZMA_DECOMPRESS=y
-# CONFIG_LZO_COMPRESS is not set
-# CONFIG_LZO_DECOMPRESS is not set
-# CONFIG_M62332 is not set
-# CONFIG_MAC80211 is not set
-# CONFIG_MAC80211_MESSAGE_TRACING is not set
-CONFIG_MAC80211_STA_HASH_MAX_SIZE=0
-# CONFIG_MACB is not set
-# CONFIG_MACH_ASM9260 is not set
-# CONFIG_MACH_DECSTATION is not set
-# CONFIG_MACH_INGENIC is not set
-# CONFIG_MACH_INGENIC_SOC is not set
-# CONFIG_MACH_JAZZ is not set
-# CONFIG_MACH_JZ4740 is not set
-# CONFIG_MACH_LOONGSON2EF is not set
-# CONFIG_MACH_LOONGSON32 is not set
-# CONFIG_MACH_LOONGSON64 is not set
-# CONFIG_MACH_NINTENDO64 is not set
-# CONFIG_MACH_PIC32 is not set
-# CONFIG_MACH_PISTACHIO is not set
-# CONFIG_MACH_REALTEK_RTL is not set
-# CONFIG_MACH_TX39XX is not set
-# CONFIG_MACH_TX49XX is not set
-# CONFIG_MACH_VR41XX is not set
-# CONFIG_MACH_XILFPGA is not set
-# CONFIG_MACINTOSH_DRIVERS is not set
-# CONFIG_MACSEC is not set
-# CONFIG_MACVLAN is not set
-# CONFIG_MACVTAP is not set
-# CONFIG_MAC_EMUMOUSEBTN is not set
-# CONFIG_MAC_PARTITION is not set
-# CONFIG_MAG3110 is not set
-# CONFIG_MAGIC_SYSRQ is not set
-CONFIG_MAGIC_SYSRQ_DEFAULT_ENABLE=0x1
-# CONFIG_MAGIC_SYSRQ_SERIAL is not set
-CONFIG_MAGIC_SYSRQ_SERIAL_SEQUENCE=""
-# CONFIG_MAILBOX is not set
-# CONFIG_MANAGER_SBS is not set
-# CONFIG_MANDATORY_FILE_LOCKING is not set
-# CONFIG_MANGLE_BOOTARGS is not set
-# CONFIG_MARVELL_10G_PHY is not set
-# CONFIG_MARVELL_88X2222_PHY is not set
-# CONFIG_MARVELL_PHY is not set
-# CONFIG_MAX1027 is not set
-# CONFIG_MAX11100 is not set
-# CONFIG_MAX1118 is not set
-# CONFIG_MAX1241 is not set
-# CONFIG_MAX1363 is not set
-# CONFIG_MAX30100 is not set
-# CONFIG_MAX30102 is not set
-# CONFIG_MAX31856 is not set
-# CONFIG_MAX44000 is not set
-# CONFIG_MAX44009 is not set
-# CONFIG_MAX517 is not set
-# CONFIG_MAX5432 is not set
-# CONFIG_MAX5481 is not set
-# CONFIG_MAX5487 is not set
-# CONFIG_MAX5821 is not set
-# CONFIG_MAX63XX_WATCHDOG is not set
-# CONFIG_MAX9611 is not set
-# CONFIG_MAXIM_THERMOCOUPLE is not set
-# CONFIG_MAXLINEAR_GPHY is not set
-CONFIG_MAY_USE_DEVLINK=y
-# CONFIG_MB1232 is not set
-# CONFIG_MC3230 is not set
-# CONFIG_MCB is not set
-# CONFIG_MCP320X is not set
-# CONFIG_MCP3422 is not set
-# CONFIG_MCP3911 is not set
-# CONFIG_MCP4018 is not set
-# CONFIG_MCP41010 is not set
-# CONFIG_MCP4131 is not set
-# CONFIG_MCP4531 is not set
-# CONFIG_MCP4725 is not set
-# CONFIG_MCP4922 is not set
-# CONFIG_MCPM is not set
-# CONFIG_MCTP is not set
-# CONFIG_MD is not set
-# CONFIG_MDIO_BCM_UNIMAC is not set
-# CONFIG_MDIO_BITBANG is not set
-# CONFIG_MDIO_BUS_MUX_GPIO is not set
-# CONFIG_MDIO_BUS_MUX_MMIOREG is not set
-# CONFIG_MDIO_BUS_MUX_MULTIPLEXER is not set
-# CONFIG_MDIO_DEVICE is not set
-# CONFIG_MDIO_DEVRES is not set
-# CONFIG_MDIO_HISI_FEMAC is not set
-# CONFIG_MDIO_IPQ4019 is not set
-# CONFIG_MDIO_IPQ8064 is not set
-# CONFIG_MDIO_MSCC_MIIM is not set
-# CONFIG_MDIO_MVUSB is not set
-# CONFIG_MDIO_OCTEON is not set
-# CONFIG_MDIO_THUNDER is not set
-# CONFIG_MDIO_XPCS is not set
-# CONFIG_MDM_GCC_9607 is not set
-# CONFIG_MD_FAULTY is not set
-# CONFIG_MEDIATEK_GE_PHY is not set
-# CONFIG_MEDIATEK_MT6577_AUXADC is not set
-# CONFIG_MEDIA_ANALOG_TV_SUPPORT is not set
-# CONFIG_MEDIA_ATTACH is not set
-# CONFIG_MEDIA_CAMERA_SUPPORT is not set
-# CONFIG_MEDIA_CEC_SUPPORT is not set
-# CONFIG_MEDIA_CONTROLLER is not set
-# CONFIG_MEDIA_CONTROLLER_DVB is not set
-# CONFIG_MEDIA_DIGITAL_TV_SUPPORT is not set
-# CONFIG_MEDIA_PCI_SUPPORT is not set
-# CONFIG_MEDIA_PLATFORM_SUPPORT is not set
-# CONFIG_MEDIA_RADIO_SUPPORT is not set
-# CONFIG_MEDIA_RC_SUPPORT is not set
-# CONFIG_MEDIA_SDR_SUPPORT is not set
-# CONFIG_MEDIA_SUBDRV_AUTOSELECT is not set
-# CONFIG_MEDIA_SUPPORT is not set
-# CONFIG_MEDIA_SUPPORT_FILTER is not set
-# CONFIG_MEDIA_TEST_SUPPORT is not set
-# CONFIG_MEDIA_TUNER_E4000 is not set
-# CONFIG_MEDIA_TUNER_FC0011 is not set
-# CONFIG_MEDIA_TUNER_FC0012 is not set
-# CONFIG_MEDIA_TUNER_FC0013 is not set
-# CONFIG_MEDIA_TUNER_FC2580 is not set
-# CONFIG_MEDIA_TUNER_IT913X is not set
-# CONFIG_MEDIA_TUNER_M88RS6000T is not set
-# CONFIG_MEDIA_TUNER_MAX2165 is not set
-# CONFIG_MEDIA_TUNER_MC44S803 is not set
-# CONFIG_MEDIA_TUNER_MSI001 is not set
-# CONFIG_MEDIA_TUNER_MT2060 is not set
-# CONFIG_MEDIA_TUNER_MT2063 is not set
-# CONFIG_MEDIA_TUNER_MT20XX is not set
-# CONFIG_MEDIA_TUNER_MT2131 is not set
-# CONFIG_MEDIA_TUNER_MT2266 is not set
-# CONFIG_MEDIA_TUNER_MXL301RF is not set
-# CONFIG_MEDIA_TUNER_MXL5005S is not set
-# CONFIG_MEDIA_TUNER_MXL5007T is not set
-# CONFIG_MEDIA_TUNER_QM1D1B0004 is not set
-# CONFIG_MEDIA_TUNER_QM1D1C0042 is not set
-# CONFIG_MEDIA_TUNER_QT1010 is not set
-# CONFIG_MEDIA_TUNER_R820T is not set
-# CONFIG_MEDIA_TUNER_SI2157 is not set
-# CONFIG_MEDIA_TUNER_SIMPLE is not set
-# CONFIG_MEDIA_TUNER_TDA18212 is not set
-# CONFIG_MEDIA_TUNER_TDA18218 is not set
-# CONFIG_MEDIA_TUNER_TDA18250 is not set
-# CONFIG_MEDIA_TUNER_TDA18271 is not set
-# CONFIG_MEDIA_TUNER_TDA827X is not set
-# CONFIG_MEDIA_TUNER_TDA8290 is not set
-# CONFIG_MEDIA_TUNER_TDA9887 is not set
-# CONFIG_MEDIA_TUNER_TEA5761 is not set
-# CONFIG_MEDIA_TUNER_TEA5767 is not set
-# CONFIG_MEDIA_TUNER_TUA9001 is not set
-# CONFIG_MEDIA_TUNER_XC2028 is not set
-# CONFIG_MEDIA_TUNER_XC4000 is not set
-# CONFIG_MEDIA_TUNER_XC5000 is not set
-# CONFIG_MEDIA_USB_SUPPORT is not set
-# CONFIG_MEGARAID_LEGACY is not set
-# CONFIG_MEGARAID_NEWGEN is not set
-# CONFIG_MEGARAID_SAS is not set
-# CONFIG_MELLANOX_PLATFORM is not set
-CONFIG_MEMBARRIER=y
-# CONFIG_MEMORY is not set
-# CONFIG_MEMORY_FAILURE is not set
-# CONFIG_MEMORY_HOTPLUG is not set
-# CONFIG_MEMSTICK is not set
-# CONFIG_MEMTEST is not set
-# CONFIG_MEN_A21_WDT is not set
-# CONFIG_MESON_SM is not set
-CONFIG_MESSAGE_LOGLEVEL_DEFAULT=4
-# CONFIG_MFD_88PM800 is not set
-# CONFIG_MFD_88PM805 is not set
-# CONFIG_MFD_88PM860X is not set
-# CONFIG_MFD_AAT2870_CORE is not set
-# CONFIG_MFD_AC100 is not set
-# CONFIG_MFD_ACT8945A is not set
-# CONFIG_MFD_ARIZONA_I2C is not set
-# CONFIG_MFD_ARIZONA_SPI is not set
-# CONFIG_MFD_AS3711 is not set
-# CONFIG_MFD_AS3722 is not set
-# CONFIG_MFD_ASIC3 is not set
-# CONFIG_MFD_ATC260X_I2C is not set
-# CONFIG_MFD_ATMEL_FLEXCOM is not set
-# CONFIG_MFD_ATMEL_HLCDC is not set
-# CONFIG_MFD_AXP20X is not set
-# CONFIG_MFD_AXP20X_I2C is not set
-# CONFIG_MFD_BCM590XX is not set
-# CONFIG_MFD_BD9571MWV is not set
-# CONFIG_MFD_CORE is not set
-# CONFIG_MFD_CPCAP is not set
-# CONFIG_MFD_CROS_EC is not set
-# CONFIG_MFD_CS5535 is not set
-# CONFIG_MFD_DA9052_I2C is not set
-# CONFIG_MFD_DA9052_SPI is not set
-# CONFIG_MFD_DA9055 is not set
-# CONFIG_MFD_DA9062 is not set
-# CONFIG_MFD_DA9063 is not set
-# CONFIG_MFD_DA9150 is not set
-# CONFIG_MFD_DLN2 is not set
-# CONFIG_MFD_EXYNOS_LPASS is not set
-# CONFIG_MFD_GATEWORKS_GSC is not set
-# CONFIG_MFD_HI6421_PMIC is not set
-# CONFIG_MFD_INTEL_M10_BMC is not set
-# CONFIG_MFD_INTEL_PMT is not set
-# CONFIG_MFD_INTEL_QUARK_I2C_GPIO is not set
-# CONFIG_MFD_IQS62X is not set
-# CONFIG_MFD_JANZ_CMODIO is not set
-# CONFIG_MFD_KEMPLD is not set
-# CONFIG_MFD_LM3533 is not set
-# CONFIG_MFD_LOCHNAGAR is not set
-# CONFIG_MFD_LP3943 is not set
-# CONFIG_MFD_LP8788 is not set
-# CONFIG_MFD_MADERA is not set
-# CONFIG_MFD_MAX14577 is not set
-# CONFIG_MFD_MAX77620 is not set
-# CONFIG_MFD_MAX77650 is not set
-# CONFIG_MFD_MAX77686 is not set
-# CONFIG_MFD_MAX77693 is not set
-# CONFIG_MFD_MAX77843 is not set
-# CONFIG_MFD_MAX8907 is not set
-# CONFIG_MFD_MAX8925 is not set
-# CONFIG_MFD_MAX8997 is not set
-# CONFIG_MFD_MAX8998 is not set
-# CONFIG_MFD_MC13XXX is not set
-# CONFIG_MFD_MC13XXX_I2C is not set
-# CONFIG_MFD_MC13XXX_SPI is not set
-# CONFIG_MFD_MENF21BMC is not set
-# CONFIG_MFD_MP2629 is not set
-# CONFIG_MFD_MT6360 is not set
-# CONFIG_MFD_MT6397 is not set
-# CONFIG_MFD_NTXEC is not set
-# CONFIG_MFD_OMAP_USB_HOST is not set
-# CONFIG_MFD_PALMAS is not set
-# CONFIG_MFD_PCF50633 is not set
-# CONFIG_MFD_PM8921_CORE is not set
-# CONFIG_MFD_PM8XXX is not set
-# CONFIG_MFD_QCOM_PM8008 is not set
-# CONFIG_MFD_RC5T583 is not set
-# CONFIG_MFD_RDC321X is not set
-# CONFIG_MFD_RETU is not set
-# CONFIG_MFD_RK808 is not set
-# CONFIG_MFD_RN5T618 is not set
-# CONFIG_MFD_ROHM_BD70528 is not set
-# CONFIG_MFD_ROHM_BD71828 is not set
-# CONFIG_MFD_ROHM_BD718XX is not set
-# CONFIG_MFD_ROHM_BD957XMUF is not set
-# CONFIG_MFD_RSMU_I2C is not set
-# CONFIG_MFD_RSMU_SPI is not set
-# CONFIG_MFD_RT4831 is not set
-# CONFIG_MFD_RT5033 is not set
-# CONFIG_MFD_RTSX_PCI is not set
-# CONFIG_MFD_RTSX_USB is not set
-# CONFIG_MFD_SEC_CORE is not set
-# CONFIG_MFD_SI476X_CORE is not set
-# CONFIG_MFD_SKY81452 is not set
-# CONFIG_MFD_SL28CPLD is not set
-# CONFIG_MFD_SM501 is not set
-# CONFIG_MFD_SMSC is not set
-# CONFIG_MFD_STMFX is not set
-# CONFIG_MFD_STMPE is not set
-# CONFIG_MFD_STPMIC1 is not set
-# CONFIG_MFD_SYSCON is not set
-# CONFIG_MFD_T7L66XB is not set
-# CONFIG_MFD_TC3589X is not set
-# CONFIG_MFD_TC6387XB is not set
-# CONFIG_MFD_TC6393XB is not set
-# CONFIG_MFD_TIMBERDALE is not set
-# CONFIG_MFD_TI_AM335X_TSCADC is not set
-# CONFIG_MFD_TI_LMU is not set
-# CONFIG_MFD_TI_LP873X is not set
-# CONFIG_MFD_TI_LP87565 is not set
-# CONFIG_MFD_TMIO is not set
-# CONFIG_MFD_TPS65086 is not set
-# CONFIG_MFD_TPS65090 is not set
-# CONFIG_MFD_TPS65217 is not set
-# CONFIG_MFD_TPS65218 is not set
-# CONFIG_MFD_TPS6586X is not set
-# CONFIG_MFD_TPS65910 is not set
-# CONFIG_MFD_TPS65912 is not set
-# CONFIG_MFD_TPS65912_I2C is not set
-# CONFIG_MFD_TPS65912_SPI is not set
-# CONFIG_MFD_TPS68470 is not set
-# CONFIG_MFD_TPS80031 is not set
-# CONFIG_MFD_TQMX86 is not set
-# CONFIG_MFD_VIPERBOARD is not set
-# CONFIG_MFD_VX855 is not set
-# CONFIG_MFD_WL1273_CORE is not set
-# CONFIG_MFD_WM831X is not set
-# CONFIG_MFD_WM831X_I2C is not set
-# CONFIG_MFD_WM831X_SPI is not set
-# CONFIG_MFD_WM8350_I2C is not set
-# CONFIG_MFD_WM8400 is not set
-# CONFIG_MFD_WM8994 is not set
-# CONFIG_MG_DISK is not set
-# CONFIG_MHI_BUS is not set
-# CONFIG_MHI_BUS_DEBUG is not set
-# CONFIG_MHI_BUS_PCI_GENERIC is not set
-# CONFIG_MHI_NET is not set
-# CONFIG_MHI_WWAN_CTRL is not set
-# CONFIG_MHI_WWAN_MBIM is not set
-# CONFIG_MICREL_KS8995MA is not set
-# CONFIG_MICREL_PHY is not set
-# CONFIG_MICROCHIP_KSZ is not set
-# CONFIG_MICROCHIP_PHY is not set
-# CONFIG_MICROCHIP_PIT64B is not set
-# CONFIG_MICROCHIP_T1_PHY is not set
-# CONFIG_MICROSEMI_PHY is not set
-# CONFIG_MIGRATION is not set
-CONFIG_MII=y
-# CONFIG_MIKROTIK is not set
-# CONFIG_MIKROTIK_RB532 is not set
-# CONFIG_MINIX_FS is not set
-# CONFIG_MINIX_FS_NATIVE_ENDIAN is not set
-# CONFIG_MINIX_SUBPARTITION is not set
-# CONFIG_MIPS32_N32 is not set
-# CONFIG_MIPS32_O32 is not set
-# CONFIG_MIPS_ALCHEMY is not set
-# CONFIG_MIPS_CDMM is not set
-# CONFIG_MIPS_CMDLINE_DTB_EXTEND is not set
-# CONFIG_MIPS_CMDLINE_FROM_DTB is not set
-# CONFIG_MIPS_CMP is not set
-# CONFIG_MIPS_COBALT is not set
-# CONFIG_MIPS_CPS is not set
-# CONFIG_MIPS_ELF_APPENDED_DTB is not set
-# CONFIG_MIPS_FPU_EMULATOR is not set
-# CONFIG_MIPS_FP_SUPPORT is not set
-# CONFIG_MIPS_GENERIC is not set
-# CONFIG_MIPS_GENERIC_KERNEL is not set
-# CONFIG_MIPS_MALTA is not set
-# CONFIG_MIPS_O32_FP64_SUPPORT is not set
-# CONFIG_MIPS_PARAVIRT is not set
-# CONFIG_MIPS_PLATFORM_DEVICES is not set
-# CONFIG_MIPS_RAW_APPENDED_DTB is not set
-# CONFIG_MIPS_SEAD3 is not set
-# CONFIG_MIPS_VA_BITS_48 is not set
-# CONFIG_MIPS_VPE_LOADER is not set
-# CONFIG_MISC_ALCOR_PCI is not set
-CONFIG_MISC_FILESYSTEMS=y
-# CONFIG_MISC_RTSX_PCI is not set
-# CONFIG_MISC_RTSX_USB is not set
-# CONFIG_MISDN is not set
-# CONFIG_MISDN_AVMFRITZ is not set
-# CONFIG_MISDN_HFCPCI is not set
-# CONFIG_MISDN_HFCUSB is not set
-# CONFIG_MISDN_INFINEON is not set
-# CONFIG_MISDN_NETJET is not set
-# CONFIG_MISDN_SPEEDFAX is not set
-# CONFIG_MISDN_W6692 is not set
-CONFIG_MITIGATE_SPECTRE_BRANCH_HISTORY=y
-# CONFIG_MKISS is not set
-# CONFIG_MLX4_CORE is not set
-# CONFIG_MLX4_EN is not set
-# CONFIG_MLX5_CORE is not set
-# CONFIG_MLX5_SF is not set
-# CONFIG_MLX90614 is not set
-# CONFIG_MLX90632 is not set
-# CONFIG_MLXFW is not set
-# CONFIG_MLXSW_CORE is not set
-# CONFIG_MLX_CPLD_PLATFORM is not set
-# CONFIG_MLX_PLATFORM is not set
-# CONFIG_MMA7455_I2C is not set
-# CONFIG_MMA7455_SPI is not set
-# CONFIG_MMA7660 is not set
-# CONFIG_MMA8452 is not set
-# CONFIG_MMA9551 is not set
-# CONFIG_MMA9553 is not set
-# CONFIG_MMC is not set
-# CONFIG_MMC35240 is not set
-# CONFIG_MMC_ARMMMCI is not set
-# CONFIG_MMC_AU1X is not set
-# CONFIG_MMC_BLOCK is not set
-CONFIG_MMC_BLOCK_MINORS=8
-# CONFIG_MMC_CAVIUM_THUNDERX is not set
-# CONFIG_MMC_CB710 is not set
-# CONFIG_MMC_CQHCI is not set
-# CONFIG_MMC_DEBUG is not set
-# CONFIG_MMC_DW is not set
-# CONFIG_MMC_HSQ is not set
-# CONFIG_MMC_JZ4740 is not set
-# CONFIG_MMC_MTK is not set
-# CONFIG_MMC_MVSDIO is not set
-# CONFIG_MMC_S3C is not set
-# CONFIG_MMC_SDHCI is not set
-# CONFIG_MMC_SDHCI_ACPI is not set
-# CONFIG_MMC_SDHCI_AM654 is not set
-# CONFIG_MMC_SDHCI_BCM_KONA is not set
-# CONFIG_MMC_SDHCI_BRCMSTB is not set
-# CONFIG_MMC_SDHCI_CADENCE is not set
-# CONFIG_MMC_SDHCI_F_SDH30 is not set
-# CONFIG_MMC_SDHCI_IPROC is not set
-# CONFIG_MMC_SDHCI_MILBEAUT is not set
-# CONFIG_MMC_SDHCI_MSM is not set
-# CONFIG_MMC_SDHCI_OF_ARASAN is not set
-# CONFIG_MMC_SDHCI_OF_ASPEED is not set
-# CONFIG_MMC_SDHCI_OF_AT91 is not set
-# CONFIG_MMC_SDHCI_OF_DWCMSHC is not set
-# CONFIG_MMC_SDHCI_OF_ESDHC is not set
-# CONFIG_MMC_SDHCI_OF_HLWD is not set
-# CONFIG_MMC_SDHCI_OMAP is not set
-# CONFIG_MMC_SDHCI_PXAV2 is not set
-# CONFIG_MMC_SDHCI_PXAV3 is not set
-# CONFIG_MMC_SDHCI_S3C is not set
-# CONFIG_MMC_SDHCI_XENON is not set
-# CONFIG_MMC_SDRICOH_CS is not set
-# CONFIG_MMC_SPI is not set
-# CONFIG_MMC_STM32_SDMMC is not set
-# CONFIG_MMC_TEST is not set
-# CONFIG_MMC_TIFM_SD is not set
-# CONFIG_MMC_TOSHIBA_PCI is not set
-# CONFIG_MMC_USDHI6ROL0 is not set
-# CONFIG_MMC_USHC is not set
-# CONFIG_MMC_VIA_SDMMC is not set
-# CONFIG_MMC_VUB300 is not set
-# CONFIG_MMIOTRACE is not set
-CONFIG_MMU=y
-CONFIG_MMU_GATHER_RCU_TABLE_FREE=y
-CONFIG_MMU_GATHER_TABLE_FREE=y
-CONFIG_MODPROBE_PATH="/sbin/modprobe"
-CONFIG_MODULES=y
-# CONFIG_MODULE_ALLOW_MISSING_NAMESPACE_IMPORTS is not set
-# CONFIG_MODULE_COMPRESS is not set
-# CONFIG_MODULE_COMPRESS_GZIP is not set
-CONFIG_MODULE_COMPRESS_NONE=y
-# CONFIG_MODULE_COMPRESS_XZ is not set
-# CONFIG_MODULE_COMPRESS_ZSTD is not set
-# CONFIG_MODULE_FORCE_LOAD is not set
-# CONFIG_MODULE_FORCE_UNLOAD is not set
-# CONFIG_MODULE_SIG is not set
-# CONFIG_MODULE_SRCVERSION_ALL is not set
-CONFIG_MODULE_STRIPPED=y
-CONFIG_MODULE_UNLOAD=y
-# CONFIG_MODVERSIONS is not set
-# CONFIG_MOST is not set
-# CONFIG_MOTORCOMM_PHY is not set
-# CONFIG_MOUSE_APPLETOUCH is not set
-# CONFIG_MOUSE_ELAN_I2C is not set
-# CONFIG_MOUSE_GPIO is not set
-# CONFIG_MOUSE_INPORT is not set
-# CONFIG_MOUSE_LOGIBM is not set
-# CONFIG_MOUSE_PC110PAD is not set
-# CONFIG_MOUSE_PS2_FOCALTECH is not set
-# CONFIG_MOUSE_PS2_SENTELIC is not set
-# CONFIG_MOUSE_SYNAPTICS_I2C is not set
-# CONFIG_MOUSE_SYNAPTICS_USB is not set
-# CONFIG_MOXTET is not set
-# CONFIG_MPL115 is not set
-# CONFIG_MPL115_I2C is not set
-# CONFIG_MPL115_SPI is not set
-# CONFIG_MPL3115 is not set
-# CONFIG_MPLS is not set
-# CONFIG_MPLS_IPTUNNEL is not set
-# CONFIG_MPLS_ROUTING is not set
-# CONFIG_MPTCP is not set
-# CONFIG_MPU3050_I2C is not set
-# CONFIG_MQ_IOSCHED_DEADLINE is not set
-# CONFIG_MQ_IOSCHED_KYBER is not set
-# CONFIG_MS5611 is not set
-# CONFIG_MS5637 is not set
-# CONFIG_MSCC_OCELOT_SWITCH is not set
-# CONFIG_MSDOS_FS is not set
-CONFIG_MSDOS_PARTITION=y
-# CONFIG_MSI_BITMAP_SELFTEST is not set
-# CONFIG_MSI_LAPTOP is not set
-# CONFIG_MSM_GCC_8953 is not set
-# CONFIG_MSM_MMCC_8994 is not set
-# CONFIG_MST_IRQ is not set
-CONFIG_MTD=y
-# CONFIG_MTD_ABSENT is not set
-# CONFIG_MTD_AFS_PARTS is not set
-# CONFIG_MTD_AR7_PARTS is not set
-CONFIG_MTD_BLKDEVS=y
-CONFIG_MTD_BLOCK=y
-# CONFIG_MTD_BLOCK2MTD is not set
-CONFIG_MTD_CFI=y
-# CONFIG_MTD_CFI_ADV_OPTIONS is not set
-CONFIG_MTD_CFI_AMDSTD=y
-# CONFIG_MTD_CFI_BE_BYTE_SWAP is not set
-CONFIG_MTD_CFI_I1=y
-CONFIG_MTD_CFI_I2=y
-# CONFIG_MTD_CFI_I4 is not set
-# CONFIG_MTD_CFI_I8 is not set
-CONFIG_MTD_CFI_INTELEXT=y
-# CONFIG_MTD_CFI_LE_BYTE_SWAP is not set
-CONFIG_MTD_CFI_NOSWAP=y
-# CONFIG_MTD_CFI_STAA is not set
-CONFIG_MTD_CFI_UTIL=y
-# CONFIG_MTD_CMDLINE_PARTS is not set
-CONFIG_MTD_COMPLEX_MAPPINGS=y
-# CONFIG_MTD_DATAFLASH is not set
-# CONFIG_MTD_DOCG3 is not set
-CONFIG_MTD_GEN_PROBE=y
-# CONFIG_MTD_GPIO_ADDR is not set
-# CONFIG_MTD_HYPERBUS is not set
-# CONFIG_MTD_IMPA7 is not set
-# CONFIG_MTD_INTEL_VR_NOR is not set
-# CONFIG_MTD_JEDECPROBE is not set
-# CONFIG_MTD_LATCH_ADDR is not set
-# CONFIG_MTD_LPDDR is not set
-# CONFIG_MTD_LPDDR2_NVM is not set
-# CONFIG_MTD_M25P80 is not set
-CONFIG_MTD_MAP_BANK_WIDTH_1=y
-# CONFIG_MTD_MAP_BANK_WIDTH_16 is not set
-CONFIG_MTD_MAP_BANK_WIDTH_2=y
-# CONFIG_MTD_MAP_BANK_WIDTH_32 is not set
-CONFIG_MTD_MAP_BANK_WIDTH_4=y
-# CONFIG_MTD_MAP_BANK_WIDTH_8 is not set
-# CONFIG_MTD_MCHP23K256 is not set
-# CONFIG_MTD_MCHP48L640 is not set
-# CONFIG_MTD_MT81xx_NOR is not set
-# CONFIG_MTD_MTDRAM is not set
-# CONFIG_MTD_MYLOADER_PARTS is not set
-# CONFIG_MTD_NAND is not set
-# CONFIG_MTD_NAND_AMS_DELTA is not set
-# CONFIG_MTD_NAND_AR934X is not set
-# CONFIG_MTD_NAND_AR934X_HW_ECC is not set
-# CONFIG_MTD_NAND_ARASAN is not set
-# CONFIG_MTD_NAND_ATMEL is not set
-# CONFIG_MTD_NAND_AU1550 is not set
-# CONFIG_MTD_NAND_BCH is not set
-# CONFIG_MTD_NAND_BF5XX is not set
-# CONFIG_MTD_NAND_BRCMNAND is not set
-# CONFIG_MTD_NAND_CADENCE is not set
-# CONFIG_MTD_NAND_CAFE is not set
-# CONFIG_MTD_NAND_CM_X270 is not set
-# CONFIG_MTD_NAND_CS553X is not set
-# CONFIG_MTD_NAND_DAVINCI is not set
-# CONFIG_MTD_NAND_DENALI is not set
-# CONFIG_MTD_NAND_DENALI_DT is not set
-# CONFIG_MTD_NAND_DENALI_PCI is not set
-CONFIG_MTD_NAND_DENALI_SCRATCH_REG_ADDR=0xff108018
-# CONFIG_MTD_NAND_DISKONCHIP is not set
-# CONFIG_MTD_NAND_DOCG4 is not set
-# CONFIG_MTD_NAND_ECC is not set
-# CONFIG_MTD_NAND_ECC_BCH is not set
-# CONFIG_MTD_NAND_ECC_SMC is not set
-# CONFIG_MTD_NAND_ECC_SW_BCH is not set
-# CONFIG_MTD_NAND_ECC_SW_HAMMING is not set
-# CONFIG_MTD_NAND_ECC_SW_HAMMING_SMC is not set
-# CONFIG_MTD_NAND_FSL_ELBC is not set
-# CONFIG_MTD_NAND_FSL_IFC is not set
-# CONFIG_MTD_NAND_FSL_UPM is not set
-# CONFIG_MTD_NAND_FSMC is not set
-# CONFIG_MTD_NAND_GPIO is not set
-# CONFIG_MTD_NAND_GPMI_NAND is not set
-# CONFIG_MTD_NAND_HISI504 is not set
-CONFIG_MTD_NAND_IDS=y
-# CONFIG_MTD_NAND_INTEL_LGM is not set
-# CONFIG_MTD_NAND_JZ4740 is not set
-# CONFIG_MTD_NAND_MPC5121_NFC is not set
-# CONFIG_MTD_NAND_MTK is not set
-# CONFIG_MTD_NAND_MTK_BMT is not set
-# CONFIG_MTD_NAND_MXC is not set
-# CONFIG_MTD_NAND_MXIC is not set
-# CONFIG_MTD_NAND_NANDSIM is not set
-# CONFIG_MTD_NAND_NDFC is not set
-# CONFIG_MTD_NAND_NUC900 is not set
-# CONFIG_MTD_NAND_OMAP2 is not set
-# CONFIG_MTD_NAND_OMAP_BCH_BUILD is not set
-# CONFIG_MTD_NAND_ORION is not set
-# CONFIG_MTD_NAND_PASEMI is not set
-# CONFIG_MTD_NAND_PLATFORM is not set
-# CONFIG_MTD_NAND_PXA3xx is not set
-# CONFIG_MTD_NAND_RB4XX is not set
-# CONFIG_MTD_NAND_RB750 is not set
-# CONFIG_MTD_NAND_RB91X is not set
-# CONFIG_MTD_NAND_RICOH is not set
-# CONFIG_MTD_NAND_S3C2410 is not set
-# CONFIG_MTD_NAND_SHARPSL is not set
-# CONFIG_MTD_NAND_SH_FLCTL is not set
-# CONFIG_MTD_NAND_SOCRATES is not set
-# CONFIG_MTD_NAND_TMIO is not set
-# CONFIG_MTD_NAND_TXX9NDFMC is not set
-CONFIG_MTD_OF_PARTS=y
-# CONFIG_MTD_ONENAND is not set
-# CONFIG_MTD_OOPS is not set
-# CONFIG_MTD_OTP is not set
-# CONFIG_MTD_PARSER_TRX is not set
-# CONFIG_MTD_PARTITIONED_MASTER is not set
-# CONFIG_MTD_PCI is not set
-# CONFIG_MTD_PCMCIA is not set
-# CONFIG_MTD_PHRAM is not set
-# CONFIG_MTD_PHYSMAP is not set
-# CONFIG_MTD_PHYSMAP_COMPAT is not set
-# CONFIG_MTD_PHYSMAP_GEMINI is not set
-# CONFIG_MTD_PHYSMAP_GPIO_ADDR is not set
-# CONFIG_MTD_PHYSMAP_IXP4XX is not set
-CONFIG_MTD_PHYSMAP_OF=y
-# CONFIG_MTD_PHYSMAP_OF_GEMINI is not set
-# CONFIG_MTD_PHYSMAP_OF_VERSATILE is not set
-# CONFIG_MTD_PHYSMAP_VERSATILE is not set
-# CONFIG_MTD_PLATRAM is not set
-# CONFIG_MTD_PMC551 is not set
-# CONFIG_MTD_RAM is not set
-# CONFIG_MTD_RAW_NAND is not set
-CONFIG_MTD_REDBOOT_DIRECTORY_BLOCK=-1
-# CONFIG_MTD_REDBOOT_PARTS is not set
-# CONFIG_MTD_REDBOOT_PARTS_READONLY is not set
-# CONFIG_MTD_REDBOOT_PARTS_UNALLOCATED is not set
-# CONFIG_MTD_ROM is not set
-CONFIG_MTD_ROOTFS_ROOT_DEV=y
-# CONFIG_MTD_ROUTERBOOT_PARTS is not set
-# CONFIG_MTD_SERCOMM_PARTS is not set
-# CONFIG_MTD_SLRAM is not set
-# CONFIG_MTD_SM_COMMON is not set
-# CONFIG_MTD_SPINAND_MT29F is not set
-# CONFIG_MTD_SPI_NAND is not set
-# CONFIG_MTD_SPI_NOR is not set
-# CONFIG_MTD_SPI_NOR_SWP_DISABLE is not set
-CONFIG_MTD_SPI_NOR_SWP_DISABLE_ON_VOLATILE=y
-# CONFIG_MTD_SPI_NOR_SWP_KEEP is not set
-# CONFIG_MTD_SPI_NOR_USE_4K_SECTORS is not set
-# CONFIG_MTD_SPI_NOR_USE_VARIABLE_ERASE is not set
-CONFIG_MTD_SPLIT=y
-# CONFIG_MTD_SPLIT_BCM63XX_FW is not set
-# CONFIG_MTD_SPLIT_BCM_WFI_FW is not set
-# CONFIG_MTD_SPLIT_BRNIMAGE_FW is not set
-# CONFIG_MTD_SPLIT_ELF_FW is not set
-# CONFIG_MTD_SPLIT_EVA_FW is not set
-# CONFIG_MTD_SPLIT_FIRMWARE is not set
-CONFIG_MTD_SPLIT_FIRMWARE_NAME="firmware"
-# CONFIG_MTD_SPLIT_FIT_FW is not set
-# CONFIG_MTD_SPLIT_H3C_VFS is not set
-# CONFIG_MTD_SPLIT_JIMAGE_FW is not set
-# CONFIG_MTD_SPLIT_LZMA_FW is not set
-# CONFIG_MTD_SPLIT_MINOR_FW is not set
-# CONFIG_MTD_SPLIT_SEAMA_FW is not set
-# CONFIG_MTD_SPLIT_SEIL_FW is not set
-CONFIG_MTD_SPLIT_SQUASHFS_ROOT=y
-CONFIG_MTD_SPLIT_SUPPORT=y
-# CONFIG_MTD_SPLIT_TPLINK_FW is not set
-# CONFIG_MTD_SPLIT_TRX_FW is not set
-# CONFIG_MTD_SPLIT_UIMAGE_FW is not set
-# CONFIG_MTD_SPLIT_WRGG_FW is not set
-# CONFIG_MTD_SST25L is not set
-# CONFIG_MTD_SWAP is not set
-# CONFIG_MTD_TESTS is not set
-# CONFIG_MTD_UBI is not set
-# CONFIG_MTD_UBI_FASTMAP is not set
-# CONFIG_MTD_UBI_GLUEBI is not set
-# CONFIG_MTD_UIMAGE_SPLIT is not set
-# CONFIG_MTD_VIRT_CONCAT is not set
-# CONFIG_MTK_DEVAPC is not set
-# CONFIG_MTK_MMC is not set
-# CONFIG_MTK_MMSYS is not set
-# CONFIG_MTK_THERMAL is not set
-# CONFIG_MULTIPLEXER is not set
-CONFIG_MULTIUSER=y
-# CONFIG_MUTEX_SPIN_ON_OWNER is not set
-# CONFIG_MUX_ADG792A is not set
-# CONFIG_MUX_ADGS1408 is not set
-# CONFIG_MUX_GPIO is not set
-# CONFIG_MUX_MMIO is not set
-# CONFIG_MV643XX_ETH is not set
-# CONFIG_MVMDIO is not set
-# CONFIG_MVNETA_BM is not set
-# CONFIG_MVSW61XX_PHY is not set
-# CONFIG_MV_XOR_V2 is not set
-# CONFIG_MWAVE is not set
-# CONFIG_MWL8K is not set
-# CONFIG_MXC4005 is not set
-# CONFIG_MXC6255 is not set
-# CONFIG_MYRI10GE is not set
-# CONFIG_NAMESPACES is not set
-# CONFIG_NATIONAL_PHY is not set
-# CONFIG_NATSEMI is not set
-# CONFIG_NAU7802 is not set
-# CONFIG_NBPFAXI_DMA is not set
-# CONFIG_NCP_FS is not set
-# CONFIG_NE2000 is not set
-# CONFIG_NE2K_PCI is not set
-# CONFIG_NEC_MARKEINS is not set
-CONFIG_NET=y
-# CONFIG_NETCONSOLE is not set
-CONFIG_NETDEVICES=y
-# CONFIG_NETDEVSIM is not set
-# CONFIG_NETFILTER is not set
-# CONFIG_NETFILTER_ADVANCED is not set
-# CONFIG_NETFILTER_DEBUG is not set
-# CONFIG_NETFILTER_INGRESS is not set
-# CONFIG_NETFILTER_NETLINK is not set
-# CONFIG_NETFILTER_NETLINK_ACCT is not set
-# CONFIG_NETFILTER_NETLINK_GLUE_CT is not set
-# CONFIG_NETFILTER_NETLINK_HOOK is not set
-# CONFIG_NETFILTER_NETLINK_LOG is not set
-# CONFIG_NETFILTER_NETLINK_OSF is not set
-# CONFIG_NETFILTER_NETLINK_QUEUE is not set
-# CONFIG_NETFILTER_XTABLES is not set
-# CONFIG_NETFILTER_XTABLES_COMPAT is not set
-# CONFIG_NETFILTER_XT_CONNMARK is not set
-# CONFIG_NETFILTER_XT_MARK is not set
-# CONFIG_NETFILTER_XT_MATCH_ADDRTYPE is not set
-# CONFIG_NETFILTER_XT_MATCH_BPF is not set
-# CONFIG_NETFILTER_XT_MATCH_CGROUP is not set
-# CONFIG_NETFILTER_XT_MATCH_CLUSTER is not set
-# CONFIG_NETFILTER_XT_MATCH_COMMENT is not set
-# CONFIG_NETFILTER_XT_MATCH_CONNBYTES is not set
-# CONFIG_NETFILTER_XT_MATCH_CONNLABEL is not set
-# CONFIG_NETFILTER_XT_MATCH_CONNLIMIT is not set
-# CONFIG_NETFILTER_XT_MATCH_CONNMARK is not set
-# CONFIG_NETFILTER_XT_MATCH_CONNTRACK is not set
-# CONFIG_NETFILTER_XT_MATCH_CPU is not set
-# CONFIG_NETFILTER_XT_MATCH_DCCP is not set
-# CONFIG_NETFILTER_XT_MATCH_DEVGROUP is not set
-# CONFIG_NETFILTER_XT_MATCH_DSCP is not set
-# CONFIG_NETFILTER_XT_MATCH_ECN is not set
-# CONFIG_NETFILTER_XT_MATCH_ESP is not set
-# CONFIG_NETFILTER_XT_MATCH_HASHLIMIT is not set
-# CONFIG_NETFILTER_XT_MATCH_HELPER is not set
-# CONFIG_NETFILTER_XT_MATCH_HL is not set
-# CONFIG_NETFILTER_XT_MATCH_IPCOMP is not set
-# CONFIG_NETFILTER_XT_MATCH_IPRANGE is not set
-# CONFIG_NETFILTER_XT_MATCH_L2TP is not set
-# CONFIG_NETFILTER_XT_MATCH_LENGTH is not set
-# CONFIG_NETFILTER_XT_MATCH_LIMIT is not set
-# CONFIG_NETFILTER_XT_MATCH_MAC is not set
-# CONFIG_NETFILTER_XT_MATCH_MARK is not set
-# CONFIG_NETFILTER_XT_MATCH_MULTIPORT is not set
-# CONFIG_NETFILTER_XT_MATCH_NFACCT is not set
-# CONFIG_NETFILTER_XT_MATCH_OSF is not set
-# CONFIG_NETFILTER_XT_MATCH_OWNER is not set
-# CONFIG_NETFILTER_XT_MATCH_PHYSDEV is not set
-# CONFIG_NETFILTER_XT_MATCH_PKTTYPE is not set
-# CONFIG_NETFILTER_XT_MATCH_POLICY is not set
-# CONFIG_NETFILTER_XT_MATCH_QUOTA is not set
-# CONFIG_NETFILTER_XT_MATCH_RATEEST is not set
-# CONFIG_NETFILTER_XT_MATCH_REALM is not set
-# CONFIG_NETFILTER_XT_MATCH_RECENT is not set
-# CONFIG_NETFILTER_XT_MATCH_SCTP is not set
-# CONFIG_NETFILTER_XT_MATCH_SOCKET is not set
-# CONFIG_NETFILTER_XT_MATCH_STATE is not set
-# CONFIG_NETFILTER_XT_MATCH_STATISTIC is not set
-# CONFIG_NETFILTER_XT_MATCH_STRING is not set
-# CONFIG_NETFILTER_XT_MATCH_TCPMSS is not set
-# CONFIG_NETFILTER_XT_MATCH_TIME is not set
-# CONFIG_NETFILTER_XT_MATCH_U32 is not set
-# CONFIG_NETFILTER_XT_TARGET_AUDIT is not set
-# CONFIG_NETFILTER_XT_TARGET_CHECKSUM is not set
-# CONFIG_NETFILTER_XT_TARGET_CLASSIFY is not set
-# CONFIG_NETFILTER_XT_TARGET_CONNMARK is not set
-# CONFIG_NETFILTER_XT_TARGET_CT is not set
-# CONFIG_NETFILTER_XT_TARGET_DSCP is not set
-# CONFIG_NETFILTER_XT_TARGET_HL is not set
-# CONFIG_NETFILTER_XT_TARGET_HMARK is not set
-# CONFIG_NETFILTER_XT_TARGET_IDLETIMER is not set
-# CONFIG_NETFILTER_XT_TARGET_LED is not set
-# CONFIG_NETFILTER_XT_TARGET_LOG is not set
-# CONFIG_NETFILTER_XT_TARGET_MARK is not set
-# CONFIG_NETFILTER_XT_TARGET_NETMAP is not set
-# CONFIG_NETFILTER_XT_TARGET_NFLOG is not set
-# CONFIG_NETFILTER_XT_TARGET_NFQUEUE is not set
-# CONFIG_NETFILTER_XT_TARGET_NOTRACK is not set
-# CONFIG_NETFILTER_XT_TARGET_RATEEST is not set
-# CONFIG_NETFILTER_XT_TARGET_REDIRECT is not set
-# CONFIG_NETFILTER_XT_TARGET_SECMARK is not set
-# CONFIG_NETFILTER_XT_TARGET_TCPMSS is not set
-# CONFIG_NETFILTER_XT_TARGET_TCPOPTSTRIP is not set
-# CONFIG_NETFILTER_XT_TARGET_TEE is not set
-# CONFIG_NETFILTER_XT_TARGET_TPROXY is not set
-# CONFIG_NETFILTER_XT_TARGET_TRACE is not set
-# CONFIG_NETLABEL is not set
-# CONFIG_NETLINK_DIAG is not set
-# CONFIG_NETLINK_MMAP is not set
-# CONFIG_NETPOLL is not set
-# CONFIG_NETROM is not set
-CONFIG_NETWORK_FILESYSTEMS=y
-# CONFIG_NETWORK_PHY_TIMESTAMPING is not set
-# CONFIG_NETWORK_SECMARK is not set
-# CONFIG_NETXEN_NIC is not set
-# CONFIG_NET_9P is not set
-# CONFIG_NET_ACT_BPF is not set
-# CONFIG_NET_ACT_CSUM is not set
-# CONFIG_NET_ACT_CT is not set
-# CONFIG_NET_ACT_GACT is not set
-# CONFIG_NET_ACT_GATE is not set
-# CONFIG_NET_ACT_IFE is not set
-# CONFIG_NET_ACT_IPT is not set
-# CONFIG_NET_ACT_MIRRED is not set
-# CONFIG_NET_ACT_MPLS is not set
-# CONFIG_NET_ACT_NAT is not set
-# CONFIG_NET_ACT_PEDIT is not set
-# CONFIG_NET_ACT_POLICE is not set
-# CONFIG_NET_ACT_SAMPLE is not set
-# CONFIG_NET_ACT_SIMP is not set
-# CONFIG_NET_ACT_SKBEDIT is not set
-# CONFIG_NET_ACT_SKBMOD is not set
-# CONFIG_NET_ACT_TUNNEL_KEY is not set
-# CONFIG_NET_ACT_VLAN is not set
-CONFIG_NET_CADENCE=y
-# CONFIG_NET_CALXEDA_XGMAC is not set
-CONFIG_NET_CLS=y
-# CONFIG_NET_CLS_ACT is not set
-# CONFIG_NET_CLS_BASIC is not set
-# CONFIG_NET_CLS_BPF is not set
-# CONFIG_NET_CLS_FLOW is not set
-# CONFIG_NET_CLS_FLOWER is not set
-# CONFIG_NET_CLS_FW is not set
-CONFIG_NET_CLS_IND=y
-# CONFIG_NET_CLS_MATCHALL is not set
-# CONFIG_NET_CLS_ROUTE4 is not set
-# CONFIG_NET_CLS_RSVP is not set
-# CONFIG_NET_CLS_RSVP6 is not set
-# CONFIG_NET_CLS_U32 is not set
-CONFIG_NET_CORE=y
-# CONFIG_NET_DEVLINK is not set
-# CONFIG_NET_DROP_MONITOR is not set
-# CONFIG_NET_DSA is not set
-# CONFIG_NET_DSA_AR9331 is not set
-# CONFIG_NET_DSA_BCM_SF2 is not set
-# CONFIG_NET_DSA_LANTIQ_GSWIP is not set
-# CONFIG_NET_DSA_LEGACY is not set
-# CONFIG_NET_DSA_LOOP is not set
-# CONFIG_NET_DSA_MICROCHIP_KSZ8795 is not set
-# CONFIG_NET_DSA_MICROCHIP_KSZ9477 is not set
-# CONFIG_NET_DSA_MSCC_FELIX is not set
-# CONFIG_NET_DSA_MSCC_SEVILLE is not set
-# CONFIG_NET_DSA_MT7530 is not set
-# CONFIG_NET_DSA_MV88E6060 is not set
-# CONFIG_NET_DSA_MV88E6123_61_65 is not set
-# CONFIG_NET_DSA_MV88E6131 is not set
-# CONFIG_NET_DSA_MV88E6171 is not set
-# CONFIG_NET_DSA_MV88E6352 is not set
-# CONFIG_NET_DSA_MV88E6XXX is not set
-# CONFIG_NET_DSA_MV88E6XXX_NEED_PPU is not set
-# CONFIG_NET_DSA_MV88E6XXX_PTP is not set
-# CONFIG_NET_DSA_QCA8K is not set
-# CONFIG_NET_DSA_QCA8K_LEDS_SUPPORT is not set
-# CONFIG_NET_DSA_REALTEK_SMI is not set
-# CONFIG_NET_DSA_SJA1105 is not set
-# CONFIG_NET_DSA_SMSC_LAN9303_I2C is not set
-# CONFIG_NET_DSA_SMSC_LAN9303_MDIO is not set
-# CONFIG_NET_DSA_TAG_8021Q is not set
-# CONFIG_NET_DSA_TAG_AR9331 is not set
-# CONFIG_NET_DSA_TAG_BRCM is not set
-# CONFIG_NET_DSA_TAG_BRCM_LEGACY is not set
-# CONFIG_NET_DSA_TAG_BRCM_PREPEND is not set
-# CONFIG_NET_DSA_TAG_DSA is not set
-# CONFIG_NET_DSA_TAG_EDSA is not set
-# CONFIG_NET_DSA_TAG_GSWIP is not set
-# CONFIG_NET_DSA_TAG_HELLCREEK is not set
-# CONFIG_NET_DSA_TAG_KSZ is not set
-# CONFIG_NET_DSA_TAG_LAN9303 is not set
-# CONFIG_NET_DSA_TAG_MTK is not set
-# CONFIG_NET_DSA_TAG_OCELOT is not set
-# CONFIG_NET_DSA_TAG_OCELOT_8021Q is not set
-# CONFIG_NET_DSA_TAG_QCA is not set
-# CONFIG_NET_DSA_TAG_RTL4_A is not set
-# CONFIG_NET_DSA_TAG_SJA1105 is not set
-# CONFIG_NET_DSA_TAG_TRAILER is not set
-# CONFIG_NET_DSA_TAG_XRS700X is not set
-# CONFIG_NET_DSA_VITESSE_VSC73XX is not set
-# CONFIG_NET_DSA_VITESSE_VSC73XX_PLATFORM is not set
-# CONFIG_NET_DSA_VITESSE_VSC73XX_SPI is not set
-# CONFIG_NET_DSA_XRS700X_I2C is not set
-# CONFIG_NET_DSA_XRS700X_MDIO is not set
-# CONFIG_NET_EMATCH is not set
-# CONFIG_NET_EMATCH_CANID is not set
-# CONFIG_NET_EMATCH_CMP is not set
-# CONFIG_NET_EMATCH_IPT is not set
-# CONFIG_NET_EMATCH_META is not set
-# CONFIG_NET_EMATCH_NBYTE is not set
-CONFIG_NET_EMATCH_STACK=32
-# CONFIG_NET_EMATCH_TEXT is not set
-# CONFIG_NET_EMATCH_U32 is not set
-# CONFIG_NET_FAILOVER is not set
-# CONFIG_NET_FC is not set
-# CONFIG_NET_FOU is not set
-# CONFIG_NET_FOU_IP_TUNNELS is not set
-# CONFIG_NET_IFE is not set
-# CONFIG_NET_IPGRE is not set
-CONFIG_NET_IPGRE_BROADCAST=y
-# CONFIG_NET_IPGRE_DEMUX is not set
-# CONFIG_NET_IPIP is not set
-# CONFIG_NET_IPVTI is not set
-# CONFIG_NET_IP_TUNNEL is not set
-# CONFIG_NET_KEY is not set
-# CONFIG_NET_KEY_MIGRATE is not set
-# CONFIG_NET_L3_MASTER_DEV is not set
-# CONFIG_NET_MEDIATEK_STAR_EMAC is not set
-# CONFIG_NET_MPLS_GSO is not set
-# CONFIG_NET_NCSI is not set
-# CONFIG_NET_NSH is not set
-# CONFIG_NET_PACKET_ENGINE is not set
-# CONFIG_NET_PKTGEN is not set
-# CONFIG_NET_POLL_CONTROLLER is not set
-# CONFIG_NET_PTP_CLASSIFY is not set
-CONFIG_NET_RX_BUSY_POLL=y
-# CONFIG_NET_SB1000 is not set
-CONFIG_NET_SCHED=y
-# CONFIG_NET_SCH_CAKE is not set
-# CONFIG_NET_SCH_CBS is not set
-# CONFIG_NET_SCH_CHOKE is not set
-# CONFIG_NET_SCH_CODEL is not set
-CONFIG_NET_SCH_DEFAULT=y
-# CONFIG_NET_SCH_DRR is not set
-# CONFIG_NET_SCH_ETF is not set
-# CONFIG_NET_SCH_ETS is not set
-CONFIG_NET_SCH_FIFO=y
-# CONFIG_NET_SCH_FQ is not set
-CONFIG_NET_SCH_FQ_CODEL=y
-# CONFIG_NET_SCH_FQ_PIE is not set
-# CONFIG_NET_SCH_GRED is not set
-# CONFIG_NET_SCH_HFSC is not set
-# CONFIG_NET_SCH_HHF is not set
-# CONFIG_NET_SCH_HTB is not set
-# CONFIG_NET_SCH_INGRESS is not set
-# CONFIG_NET_SCH_MQPRIO is not set
-# CONFIG_NET_SCH_MULTIQ is not set
-# CONFIG_NET_SCH_NETEM is not set
-# CONFIG_NET_SCH_PIE is not set
-# CONFIG_NET_SCH_PLUG is not set
-# CONFIG_NET_SCH_PRIO is not set
-# CONFIG_NET_SCH_QFQ is not set
-# CONFIG_NET_SCH_RED is not set
-# CONFIG_NET_SCH_SFB is not set
-# CONFIG_NET_SCH_SFQ is not set
-# CONFIG_NET_SCH_SKBPRIO is not set
-# CONFIG_NET_SCH_TAPRIO is not set
-# CONFIG_NET_SCH_TBF is not set
-# CONFIG_NET_SCH_TEQL is not set
-# CONFIG_NET_SCTPPROBE is not set
-# CONFIG_NET_SELFTESTS is not set
-CONFIG_NET_SOCK_MSG=y
-# CONFIG_NET_SWITCHDEV is not set
-# CONFIG_NET_TCPPROBE is not set
-# CONFIG_NET_TC_SKB_EXT is not set
-# CONFIG_NET_TEAM is not set
-# CONFIG_NET_TULIP is not set
-# CONFIG_NET_UDP_TUNNEL is not set
-CONFIG_NET_VENDOR_3COM=y
-CONFIG_NET_VENDOR_8390=y
-CONFIG_NET_VENDOR_ADAPTEC=y
-CONFIG_NET_VENDOR_AGERE=y
-CONFIG_NET_VENDOR_ALACRITECH=y
-CONFIG_NET_VENDOR_ALTEON=y
-CONFIG_NET_VENDOR_AMAZON=y
-CONFIG_NET_VENDOR_AMD=y
-CONFIG_NET_VENDOR_AQUANTIA=y
-CONFIG_NET_VENDOR_ARC=y
-CONFIG_NET_VENDOR_ATHEROS=y
-CONFIG_NET_VENDOR_AURORA=y
-CONFIG_NET_VENDOR_BROADCOM=y
-CONFIG_NET_VENDOR_BROCADE=y
-CONFIG_NET_VENDOR_CADENCE=y
-CONFIG_NET_VENDOR_CAVIUM=y
-CONFIG_NET_VENDOR_CHELSIO=y
-CONFIG_NET_VENDOR_CIRRUS=y
-CONFIG_NET_VENDOR_CISCO=y
-CONFIG_NET_VENDOR_CORTINA=y
-CONFIG_NET_VENDOR_DEC=y
-CONFIG_NET_VENDOR_DLINK=y
-CONFIG_NET_VENDOR_EMULEX=y
-CONFIG_NET_VENDOR_EXAR=y
-CONFIG_NET_VENDOR_EZCHIP=y
-CONFIG_NET_VENDOR_FARADAY=y
-CONFIG_NET_VENDOR_FREESCALE=y
-CONFIG_NET_VENDOR_FUJITSU=y
-CONFIG_NET_VENDOR_GOOGLE=y
-CONFIG_NET_VENDOR_HISILICON=y
-CONFIG_NET_VENDOR_HP=y
-CONFIG_NET_VENDOR_HUAWEI=y
-CONFIG_NET_VENDOR_I825XX=y
-CONFIG_NET_VENDOR_IBM=y
-CONFIG_NET_VENDOR_INTEL=y
-# CONFIG_NET_VENDOR_LITEX is not set
-CONFIG_NET_VENDOR_MARVELL=y
-CONFIG_NET_VENDOR_MELLANOX=y
-CONFIG_NET_VENDOR_MICREL=y
-CONFIG_NET_VENDOR_MICROCHIP=y
-CONFIG_NET_VENDOR_MICROSEMI=y
-# CONFIG_NET_VENDOR_MICROSOFT is not set
-CONFIG_NET_VENDOR_MYRI=y
-CONFIG_NET_VENDOR_NATSEMI=y
-CONFIG_NET_VENDOR_NETERION=y
-CONFIG_NET_VENDOR_NETRONOME=y
-CONFIG_NET_VENDOR_NI=y
-CONFIG_NET_VENDOR_NVIDIA=y
-CONFIG_NET_VENDOR_OKI=y
-CONFIG_NET_VENDOR_PACKET_ENGINES=y
-CONFIG_NET_VENDOR_PENSANDO=y
-CONFIG_NET_VENDOR_QLOGIC=y
-CONFIG_NET_VENDOR_QUALCOMM=y
-CONFIG_NET_VENDOR_RDC=y
-CONFIG_NET_VENDOR_REALTEK=y
-CONFIG_NET_VENDOR_RENESAS=y
-CONFIG_NET_VENDOR_ROCKER=y
-CONFIG_NET_VENDOR_SAMSUNG=y
-CONFIG_NET_VENDOR_SEEQ=y
-CONFIG_NET_VENDOR_SILAN=y
-CONFIG_NET_VENDOR_SIS=y
-CONFIG_NET_VENDOR_SMSC=y
-CONFIG_NET_VENDOR_SOCIONEXT=y
-CONFIG_NET_VENDOR_SOLARFLARE=y
-CONFIG_NET_VENDOR_STMICRO=y
-CONFIG_NET_VENDOR_SUN=y
-CONFIG_NET_VENDOR_SYNOPSYS=y
-CONFIG_NET_VENDOR_TEHUTI=y
-CONFIG_NET_VENDOR_TI=y
-CONFIG_NET_VENDOR_TOSHIBA=y
-CONFIG_NET_VENDOR_VIA=y
-CONFIG_NET_VENDOR_WIZNET=y
-CONFIG_NET_VENDOR_XILINX=y
-CONFIG_NET_VENDOR_XIRCOM=y
-# CONFIG_NET_VRF is not set
-# CONFIG_NET_XGENE is not set
-CONFIG_NEW_LEDS=y
-# CONFIG_NFC is not set
-# CONFIG_NFP is not set
-# CONFIG_NFSD is not set
-# CONFIG_NFSD_V2 is not set
-# CONFIG_NFSD_V2_ACL is not set
-CONFIG_NFSD_V3=y
-# CONFIG_NFSD_V3_ACL is not set
-# CONFIG_NFSD_V4 is not set
-# CONFIG_NFS_ACL_SUPPORT is not set
-CONFIG_NFS_COMMON=y
-# CONFIG_NFS_DISABLE_UDP_SUPPORT is not set
-# CONFIG_NFS_FS is not set
-# CONFIG_NFS_FSCACHE is not set
-# CONFIG_NFS_SWAP is not set
-# CONFIG_NFS_V2 is not set
-CONFIG_NFS_V3=y
-# CONFIG_NFS_V3_ACL is not set
-# CONFIG_NFS_V4 is not set
-# CONFIG_NFS_V4_1 is not set
-# CONFIG_NFTL is not set
-# CONFIG_NFT_BRIDGE_META is not set
-# CONFIG_NFT_BRIDGE_REJECT is not set
-# CONFIG_NFT_CONNLIMIT is not set
-# CONFIG_NFT_DUP_IPV4 is not set
-# CONFIG_NFT_DUP_IPV6 is not set
-# CONFIG_NFT_FIB_IPV4 is not set
-# CONFIG_NFT_FIB_IPV6 is not set
-# CONFIG_NFT_FIB_NETDEV is not set
-# CONFIG_NFT_FLOW_OFFLOAD is not set
-# CONFIG_NFT_OBJREF is not set
-# CONFIG_NFT_OSF is not set
-# CONFIG_NFT_REJECT_NETDEV is not set
-# CONFIG_NFT_RT is not set
-# CONFIG_NFT_SET_BITMAP is not set
-# CONFIG_NFT_SOCKET is not set
-# CONFIG_NFT_SYNPROXY is not set
-# CONFIG_NFT_TPROXY is not set
-# CONFIG_NFT_TUNNEL is not set
-# CONFIG_NFT_XFRM is not set
-# CONFIG_NF_CONNTRACK is not set
-# CONFIG_NF_CONNTRACK_AMANDA is not set
-# CONFIG_NF_CONNTRACK_BRIDGE is not set
-# CONFIG_NF_CONNTRACK_EVENTS is not set
-# CONFIG_NF_CONNTRACK_FTP is not set
-# CONFIG_NF_CONNTRACK_H323 is not set
-# CONFIG_NF_CONNTRACK_IRC is not set
-# CONFIG_NF_CONNTRACK_LABELS is not set
-# CONFIG_NF_CONNTRACK_MARK is not set
-# CONFIG_NF_CONNTRACK_NETBIOS_NS is not set
-# CONFIG_NF_CONNTRACK_PPTP is not set
-CONFIG_NF_CONNTRACK_PROCFS=y
-# CONFIG_NF_CONNTRACK_PROC_COMPAT is not set
-# CONFIG_NF_CONNTRACK_SANE is not set
-# CONFIG_NF_CONNTRACK_SECMARK is not set
-# CONFIG_NF_CONNTRACK_SIP is not set
-# CONFIG_NF_CONNTRACK_SNMP is not set
-# CONFIG_NF_CONNTRACK_TFTP is not set
-# CONFIG_NF_CONNTRACK_TIMEOUT is not set
-# CONFIG_NF_CONNTRACK_TIMESTAMP is not set
-# CONFIG_NF_CONNTRACK_ZONES is not set
-# CONFIG_NF_CT_NETLINK is not set
-# CONFIG_NF_CT_NETLINK_HELPER is not set
-# CONFIG_NF_CT_NETLINK_TIMEOUT is not set
-# CONFIG_NF_CT_PROTO_DCCP is not set
-# CONFIG_NF_CT_PROTO_GRE is not set
-# CONFIG_NF_CT_PROTO_SCTP is not set
-# CONFIG_NF_CT_PROTO_UDPLITE is not set
-# CONFIG_NF_DEFRAG_IPV4 is not set
-# CONFIG_NF_DUP_IPV4 is not set
-# CONFIG_NF_DUP_IPV6 is not set
-# CONFIG_NF_FLOW_TABLE is not set
-# CONFIG_NF_FLOW_TABLE_PROCFS is not set
-# CONFIG_NF_LOG_ARP is not set
-# CONFIG_NF_LOG_BRIDGE is not set
-# CONFIG_NF_LOG_IPV4 is not set
-# CONFIG_NF_LOG_NETDEV is not set
-# CONFIG_NF_LOG_SYSLOG is not set
-# CONFIG_NF_NAT is not set
-# CONFIG_NF_NAT_AMANDA is not set
-# CONFIG_NF_NAT_FTP is not set
-# CONFIG_NF_NAT_H323 is not set
-# CONFIG_NF_NAT_IRC is not set
-# CONFIG_NF_NAT_NEEDED is not set
-# CONFIG_NF_NAT_PPTP is not set
-# CONFIG_NF_NAT_PROTO_GRE is not set
-# CONFIG_NF_NAT_SIP is not set
-# CONFIG_NF_NAT_SNMP_BASIC is not set
-# CONFIG_NF_NAT_TFTP is not set
-# CONFIG_NF_REJECT_IPV4 is not set
-# CONFIG_NF_REJECT_IPV6 is not set
-# CONFIG_NF_SOCKET_IPV4 is not set
-# CONFIG_NF_SOCKET_IPV6 is not set
-# CONFIG_NF_TABLES is not set
-CONFIG_NF_TABLES_ARP=y
-CONFIG_NF_TABLES_BRIDGE=y
-CONFIG_NF_TABLES_INET=y
-CONFIG_NF_TABLES_IPV4=y
-CONFIG_NF_TABLES_IPV6=y
-CONFIG_NF_TABLES_NETDEV=y
-# CONFIG_NF_TABLES_SET is not set
-# CONFIG_NF_TPROXY_IPV4 is not set
-# CONFIG_NF_TPROXY_IPV6 is not set
-# CONFIG_NI65 is not set
-# CONFIG_NI903X_WDT is not set
-# CONFIG_NIC7018_WDT is not set
-# CONFIG_NILFS2_FS is not set
-# CONFIG_NIU is not set
-# CONFIG_NI_XGE_MANAGEMENT_ENET is not set
-CONFIG_NLATTR=y
-# CONFIG_NLMON is not set
-# CONFIG_NLM_XLP_BOARD is not set
-# CONFIG_NLM_XLR_BOARD is not set
-# CONFIG_NLS is not set
-# CONFIG_NLS_ASCII is not set
-# CONFIG_NLS_CODEPAGE_1250 is not set
-# CONFIG_NLS_CODEPAGE_1251 is not set
-# CONFIG_NLS_CODEPAGE_437 is not set
-# CONFIG_NLS_CODEPAGE_737 is not set
-# CONFIG_NLS_CODEPAGE_775 is not set
-# CONFIG_NLS_CODEPAGE_850 is not set
-# CONFIG_NLS_CODEPAGE_852 is not set
-# CONFIG_NLS_CODEPAGE_855 is not set
-# CONFIG_NLS_CODEPAGE_857 is not set
-# CONFIG_NLS_CODEPAGE_860 is not set
-# CONFIG_NLS_CODEPAGE_861 is not set
-# CONFIG_NLS_CODEPAGE_862 is not set
-# CONFIG_NLS_CODEPAGE_863 is not set
-# CONFIG_NLS_CODEPAGE_864 is not set
-# CONFIG_NLS_CODEPAGE_865 is not set
-# CONFIG_NLS_CODEPAGE_866 is not set
-# CONFIG_NLS_CODEPAGE_869 is not set
-# CONFIG_NLS_CODEPAGE_874 is not set
-# CONFIG_NLS_CODEPAGE_932 is not set
-# CONFIG_NLS_CODEPAGE_936 is not set
-# CONFIG_NLS_CODEPAGE_949 is not set
-# CONFIG_NLS_CODEPAGE_950 is not set
-CONFIG_NLS_DEFAULT="iso8859-1"
-# CONFIG_NLS_ISO8859_1 is not set
-# CONFIG_NLS_ISO8859_13 is not set
-# CONFIG_NLS_ISO8859_14 is not set
-# CONFIG_NLS_ISO8859_15 is not set
-# CONFIG_NLS_ISO8859_2 is not set
-# CONFIG_NLS_ISO8859_3 is not set
-# CONFIG_NLS_ISO8859_4 is not set
-# CONFIG_NLS_ISO8859_5 is not set
-# CONFIG_NLS_ISO8859_6 is not set
-# CONFIG_NLS_ISO8859_7 is not set
-# CONFIG_NLS_ISO8859_8 is not set
-# CONFIG_NLS_ISO8859_9 is not set
-# CONFIG_NLS_KOI8_R is not set
-# CONFIG_NLS_KOI8_U is not set
-# CONFIG_NLS_MAC_CELTIC is not set
-# CONFIG_NLS_MAC_CENTEURO is not set
-# CONFIG_NLS_MAC_CROATIAN is not set
-# CONFIG_NLS_MAC_CYRILLIC is not set
-# CONFIG_NLS_MAC_GAELIC is not set
-# CONFIG_NLS_MAC_GREEK is not set
-# CONFIG_NLS_MAC_ICELAND is not set
-# CONFIG_NLS_MAC_INUIT is not set
-# CONFIG_NLS_MAC_ROMAN is not set
-# CONFIG_NLS_MAC_ROMANIAN is not set
-# CONFIG_NLS_MAC_TURKISH is not set
-# CONFIG_NLS_UTF8 is not set
-CONFIG_NMI_LOG_BUF_SHIFT=13
-# CONFIG_NOA1305 is not set
-# CONFIG_NOP_USB_XCEIV is not set
-# CONFIG_NORTEL_HERMES is not set
-# CONFIG_NOTIFIER_ERROR_INJECTION is not set
-# CONFIG_NOUVEAU_LEGACY_CTX_SUPPORT is not set
-# CONFIG_NOZOMI is not set
-# CONFIG_NO_BOOTMEM is not set
-# CONFIG_NO_HZ is not set
-# CONFIG_NO_HZ_FULL is not set
-# CONFIG_NO_HZ_IDLE is not set
-# CONFIG_NS83820 is not set
-# CONFIG_NTB is not set
-# CONFIG_NTFS3_64BIT_CLUSTER is not set
-# CONFIG_NTFS3_FS is not set
-# CONFIG_NTFS3_FS_POSIX_ACL is not set
-# CONFIG_NTFS3_LZX_XPRESS is not set
-# CONFIG_NTFS_DEBUG is not set
-# CONFIG_NTFS_FS is not set
-# CONFIG_NTFS_RW is not set
-# CONFIG_NTP_PPS is not set
-# CONFIG_NULL_TTY is not set
-# CONFIG_NUMA is not set
-# CONFIG_NVIDIA_CARMEL_CNP_ERRATUM is not set
-# CONFIG_NVM is not set
-# CONFIG_NVMEM is not set
-# CONFIG_NVMEM_BCM_OCOTP is not set
-# CONFIG_NVMEM_IMX_OCOTP is not set
-# CONFIG_NVMEM_LAYOUT_ONIE_TLV is not set
-# CONFIG_NVMEM_LAYOUT_SL28_VPD is not set
-# CONFIG_NVMEM_LAYOUT_U_BOOT_ENV is not set
-# CONFIG_NVMEM_REBOOT_MODE is not set
-# CONFIG_NVMEM_RMEM is not set
-# CONFIG_NVMEM_SYSFS is not set
-# CONFIG_NVMEM_U_BOOT_ENV is not set
-# CONFIG_NVME_FC is not set
-# CONFIG_NVME_TARGET is not set
-# CONFIG_NVME_TCP is not set
-# CONFIG_NVRAM is not set
-# CONFIG_NV_TCO is not set
-# CONFIG_NXP_C45_TJA11XX_PHY is not set
-# CONFIG_NXP_STB220 is not set
-# CONFIG_NXP_STB225 is not set
-# CONFIG_NXP_TJA11XX_PHY is not set
-# CONFIG_N_GSM is not set
-# CONFIG_OABI_COMPAT is not set
-# CONFIG_OBS600 is not set
-# CONFIG_OCFS2_FS is not set
-# CONFIG_OCTEONTX2_AF is not set
-# CONFIG_OCTEONTX2_PF is not set
-# CONFIG_OF_OVERLAY is not set
-CONFIG_OF_RESERVED_MEM=y
-# CONFIG_OF_UNITTEST is not set
-# CONFIG_OID_REGISTRY is not set
-# CONFIG_OMAP2_DSS_DEBUG is not set
-# CONFIG_OMAP2_DSS_DEBUGFS is not set
-# CONFIG_OMAP2_DSS_SDI is not set
-# CONFIG_OMAP_OCP2SCP is not set
-# CONFIG_OMAP_USB2 is not set
-# CONFIG_OMFS_FS is not set
-# CONFIG_OPENVSWITCH is not set
-# CONFIG_OPROFILE is not set
-# CONFIG_OPROFILE_EVENT_MULTIPLEX is not set
-# CONFIG_OPT3001 is not set
-CONFIG_OPTIMIZE_INLINING=y
-# CONFIG_ORANGEFS_FS is not set
-# CONFIG_ORION_WATCHDOG is not set
-# CONFIG_OSF_PARTITION is not set
-# CONFIG_OSNOISE_TRACER is not set
-CONFIG_OVERLAY_FS=y
-# CONFIG_OVERLAY_FS_INDEX is not set
-# CONFIG_OVERLAY_FS_METACOPY is not set
-CONFIG_OVERLAY_FS_REDIRECT_ALWAYS_FOLLOW=y
-# CONFIG_OVERLAY_FS_REDIRECT_DIR is not set
-CONFIG_OVERLAY_FS_XINO_AUTO=y
-# CONFIG_OWL_LOADER is not set
-# CONFIG_P54_COMMON is not set
-# CONFIG_PA12203001 is not set
-CONFIG_PACKET=y
-# CONFIG_PACKET_DIAG is not set
-# CONFIG_PACKING is not set
-# CONFIG_PAGE_EXTENSION is not set
-# CONFIG_PAGE_OWNER is not set
-# CONFIG_PAGE_POISONING is not set
-# CONFIG_PAGE_POOL is not set
-# CONFIG_PAGE_POOL_STATS is not set
-# CONFIG_PAGE_REPORTING is not set
-# CONFIG_PAGE_SIZE_16KB is not set
-# CONFIG_PAGE_SIZE_32KB is not set
-CONFIG_PAGE_SIZE_4KB=y
-# CONFIG_PAGE_SIZE_64KB is not set
-# CONFIG_PAGE_SIZE_8KB is not set
-# CONFIG_PALMAS_GPADC is not set
-# CONFIG_PANASONIC_LAPTOP is not set
-# CONFIG_PANEL is not set
-CONFIG_PANIC_ON_OOPS=y
-CONFIG_PANIC_ON_OOPS_VALUE=1
-CONFIG_PANIC_TIMEOUT=1
-# CONFIG_PANTHERLORD_FF is not set
-# CONFIG_PARAVIRT is not set
-# CONFIG_PARAVIRT_TIME_ACCOUNTING is not set
-# CONFIG_PARPORT is not set
-# CONFIG_PARPORT_1284 is not set
-# CONFIG_PARPORT_AX88796 is not set
-# CONFIG_PARPORT_GSC is not set
-# CONFIG_PARPORT_PC is not set
-CONFIG_PARTITION_ADVANCED=y
-# CONFIG_PATA_ALI is not set
-# CONFIG_PATA_AMD is not set
-# CONFIG_PATA_ARASAN_CF is not set
-# CONFIG_PATA_ARTOP is not set
-# CONFIG_PATA_ATIIXP is not set
-# CONFIG_PATA_ATP867X is not set
-# CONFIG_PATA_CMD640_PCI is not set
-# CONFIG_PATA_CMD64X is not set
-# CONFIG_PATA_CS5520 is not set
-# CONFIG_PATA_CS5530 is not set
-# CONFIG_PATA_CS5535 is not set
-# CONFIG_PATA_CS5536 is not set
-# CONFIG_PATA_CYPRESS is not set
-# CONFIG_PATA_EFAR is not set
-# CONFIG_PATA_HPT366 is not set
-# CONFIG_PATA_HPT37X is not set
-# CONFIG_PATA_HPT3X2N is not set
-# CONFIG_PATA_HPT3X3 is not set
-# CONFIG_PATA_IMX is not set
-# CONFIG_PATA_ISAPNP is not set
-# CONFIG_PATA_IT8213 is not set
-# CONFIG_PATA_IT821X is not set
-# CONFIG_PATA_JMICRON is not set
-# CONFIG_PATA_LEGACY is not set
-# CONFIG_PATA_MARVELL is not set
-# CONFIG_PATA_MPIIX is not set
-# CONFIG_PATA_NETCELL is not set
-# CONFIG_PATA_NINJA32 is not set
-# CONFIG_PATA_NS87410 is not set
-# CONFIG_PATA_NS87415 is not set
-# CONFIG_PATA_OCTEON_CF is not set
-# CONFIG_PATA_OF_PLATFORM is not set
-# CONFIG_PATA_OLDPIIX is not set
-# CONFIG_PATA_OPTI is not set
-# CONFIG_PATA_OPTIDMA is not set
-# CONFIG_PATA_PCMCIA is not set
-# CONFIG_PATA_PDC2027X is not set
-# CONFIG_PATA_PDC_OLD is not set
-# CONFIG_PATA_PLATFORM is not set
-# CONFIG_PATA_QDI is not set
-# CONFIG_PATA_RADISYS is not set
-# CONFIG_PATA_RDC is not set
-# CONFIG_PATA_RZ1000 is not set
-# CONFIG_PATA_SC1200 is not set
-# CONFIG_PATA_SCH is not set
-# CONFIG_PATA_SERVERWORKS is not set
-# CONFIG_PATA_SIL680 is not set
-# CONFIG_PATA_SIS is not set
-# CONFIG_PATA_TOSHIBA is not set
-# CONFIG_PATA_TRIFLEX is not set
-# CONFIG_PATA_VIA is not set
-# CONFIG_PATA_WINBOND is not set
-# CONFIG_PATA_WINBOND_VLB is not set
-# CONFIG_PC104 is not set
-# CONFIG_PC300TOO is not set
-# CONFIG_PCCARD is not set
-# CONFIG_PCH_DMA is not set
-# CONFIG_PCH_GBE is not set
-# CONFIG_PCH_PHUB is not set
-# CONFIG_PCI is not set
-# CONFIG_PCI200SYN is not set
-# CONFIG_PCIEAER is not set
-# CONFIG_PCIEAER_INJECT is not set
-# CONFIG_PCIEASPM is not set
-# CONFIG_PCIEPORTBUS is not set
-# CONFIG_PCIE_AL is not set
-# CONFIG_PCIE_ALTERA is not set
-# CONFIG_PCIE_ARMADA_8K is not set
-CONFIG_PCIE_BUS_DEFAULT=y
-# CONFIG_PCIE_BUS_PEER2PEER is not set
-# CONFIG_PCIE_BUS_PERFORMANCE is not set
-# CONFIG_PCIE_BUS_SAFE is not set
-# CONFIG_PCIE_BUS_TUNE_OFF is not set
-# CONFIG_PCIE_BW is not set
-# CONFIG_PCIE_CADENCE_HOST is not set
-# CONFIG_PCIE_CADENCE_PLAT_HOST is not set
-# CONFIG_PCIE_DPC is not set
-# CONFIG_PCIE_DW_PLAT is not set
-# CONFIG_PCIE_DW_PLAT_HOST is not set
-# CONFIG_PCIE_ECRC is not set
-# CONFIG_PCIE_IPROC is not set
-# CONFIG_PCIE_KIRIN is not set
-# CONFIG_PCIE_LAYERSCAPE_GEN4 is not set
-# CONFIG_PCIE_MEDIATEK_GEN3 is not set
-# CONFIG_PCIE_MICROCHIP_HOST is not set
-# CONFIG_PCIE_PTM is not set
-# CONFIG_PCIE_XILINX is not set
-# CONFIG_PCIPCWATCHDOG is not set
-# CONFIG_PCI_ATMEL is not set
-# CONFIG_PCI_CNB20LE_QUIRK is not set
-# CONFIG_PCI_DEBUG is not set
-# CONFIG_PCI_DISABLE_COMMON_QUIRKS is not set
-# CONFIG_PCI_ENDPOINT is not set
-# CONFIG_PCI_ENDPOINT_TEST is not set
-# CONFIG_PCI_FTPCI100 is not set
-# CONFIG_PCI_HERMES is not set
-# CONFIG_PCI_HISI is not set
-# CONFIG_PCI_HOST_GENERIC is not set
-# CONFIG_PCI_HOST_THUNDER_ECAM is not set
-# CONFIG_PCI_HOST_THUNDER_PEM is not set
-# CONFIG_PCI_IOV is not set
-# CONFIG_PCI_J721E_HOST is not set
-# CONFIG_PCI_LAYERSCAPE is not set
-# CONFIG_PCI_MESON is not set
-# CONFIG_PCI_MSI is not set
-# CONFIG_PCI_PASID is not set
-# CONFIG_PCI_PF_STUB is not set
-# CONFIG_PCI_PRI is not set
-CONFIG_PCI_QUIRKS=y
-# CONFIG_PCI_REALLOC_ENABLE_AUTO is not set
-# CONFIG_PCI_STUB is not set
-# CONFIG_PCI_SW_SWITCHTEC is not set
-CONFIG_PCI_SYSCALL=y
-# CONFIG_PCI_V3_SEMI is not set
-# CONFIG_PCI_XGENE is not set
-# CONFIG_PCMCIA is not set
-# CONFIG_PCMCIA_3C574 is not set
-# CONFIG_PCMCIA_3C589 is not set
-# CONFIG_PCMCIA_AHA152X is not set
-# CONFIG_PCMCIA_ATMEL is not set
-# CONFIG_PCMCIA_AXNET is not set
-# CONFIG_PCMCIA_DEBUG is not set
-# CONFIG_PCMCIA_FDOMAIN is not set
-# CONFIG_PCMCIA_FMVJ18X is not set
-# CONFIG_PCMCIA_HERMES is not set
-# CONFIG_PCMCIA_LOAD_CIS is not set
-# CONFIG_PCMCIA_NINJA_SCSI is not set
-# CONFIG_PCMCIA_NMCLAN is not set
-# CONFIG_PCMCIA_PCNET is not set
-# CONFIG_PCMCIA_QLOGIC is not set
-# CONFIG_PCMCIA_RAYCS is not set
-# CONFIG_PCMCIA_SMC91C92 is not set
-# CONFIG_PCMCIA_SPECTRUM is not set
-# CONFIG_PCMCIA_SYM53C500 is not set
-# CONFIG_PCMCIA_WL3501 is not set
-# CONFIG_PCMCIA_XIRC2PS is not set
-# CONFIG_PCMCIA_XIRCOM is not set
-# CONFIG_PCNET32 is not set
-# CONFIG_PCPU_DEV_REFCNT is not set
-# CONFIG_PCSPKR_PLATFORM is not set
-# CONFIG_PCS_XPCS is not set
-# CONFIG_PD6729 is not set
-# CONFIG_PDA_POWER is not set
-# CONFIG_PDC_ADMA is not set
-# CONFIG_PERCPU_STATS is not set
-# CONFIG_PERCPU_TEST is not set
-# CONFIG_PERF_EVENTS is not set
-# CONFIG_PERF_EVENTS_AMD_POWER is not set
-# CONFIG_PERSISTENT_KEYRINGS is not set
-# CONFIG_PHANTOM is not set
-# CONFIG_PHONET is not set
-# CONFIG_PHYLIB is not set
-# CONFIG_PHYS_ADDR_T_64BIT is not set
-# CONFIG_PHY_CADENCE_DP is not set
-# CONFIG_PHY_CADENCE_DPHY is not set
-# CONFIG_PHY_CADENCE_SALVO is not set
-# CONFIG_PHY_CADENCE_SIERRA is not set
-# CONFIG_PHY_CADENCE_TORRENT is not set
-# CONFIG_PHY_CAN_TRANSCEIVER is not set
-# CONFIG_PHY_CPCAP_USB is not set
-# CONFIG_PHY_EXYNOS_DP_VIDEO is not set
-# CONFIG_PHY_EXYNOS_MIPI_VIDEO is not set
-# CONFIG_PHY_FSL_IMX8MQ_USB is not set
-# CONFIG_PHY_INGENIC_USB is not set
-# CONFIG_PHY_INTEL_KEEMBAY_EMMC is not set
-# CONFIG_PHY_MAPPHONE_MDM6600 is not set
-# CONFIG_PHY_MIXEL_MIPI_DPHY is not set
-# CONFIG_PHY_MTK_HDMI is not set
-# CONFIG_PHY_MTK_MIPI_DSI is not set
-# CONFIG_PHY_MVEBU_CP110_UTMI is not set
-# CONFIG_PHY_OCELOT_SERDES is not set
-# CONFIG_PHY_PISTACHIO_USB is not set
-# CONFIG_PHY_PXA_28NM_HSIC is not set
-# CONFIG_PHY_PXA_28NM_USB2 is not set
-# CONFIG_PHY_QCOM_DWC3 is not set
-# CONFIG_PHY_QCOM_USB_HS is not set
-# CONFIG_PHY_QCOM_USB_HSIC is not set
-# CONFIG_PHY_SAMSUNG_USB2 is not set
-# CONFIG_PHY_TUSB1210 is not set
-# CONFIG_PHY_XGENE is not set
-# CONFIG_PI433 is not set
-# CONFIG_PID_IN_CONTEXTIDR is not set
-# CONFIG_PID_NS is not set
-CONFIG_PINCONF=y
-# CONFIG_PINCTRL is not set
-# CONFIG_PINCTRL_AMD is not set
-# CONFIG_PINCTRL_AXP209 is not set
-# CONFIG_PINCTRL_CEDARFORK is not set
-# CONFIG_PINCTRL_EXYNOS is not set
-# CONFIG_PINCTRL_EXYNOS5440 is not set
-# CONFIG_PINCTRL_ICELAKE is not set
-# CONFIG_PINCTRL_INGENIC is not set
-# CONFIG_PINCTRL_LPASS_LPI is not set
-# CONFIG_PINCTRL_MCP23S08 is not set
-# CONFIG_PINCTRL_MDM9607 is not set
-# CONFIG_PINCTRL_MICROCHIP_SGPIO is not set
-# CONFIG_PINCTRL_MSM8953 is not set
-# CONFIG_PINCTRL_MSM8X74 is not set
-# CONFIG_PINCTRL_MT6779 is not set
-# CONFIG_PINCTRL_MT8167 is not set
-# CONFIG_PINCTRL_MT8192 is not set
-# CONFIG_PINCTRL_MT8195 is not set
-# CONFIG_PINCTRL_MT8365 is not set
-# CONFIG_PINCTRL_MTK_V2 is not set
-# CONFIG_PINCTRL_OCELOT is not set
-# CONFIG_PINCTRL_PISTACHIO is not set
-# CONFIG_PINCTRL_SC7280 is not set
-# CONFIG_PINCTRL_SC8180X is not set
-# CONFIG_PINCTRL_SDX55 is not set
-CONFIG_PINCTRL_SINGLE=y
-# CONFIG_PINCTRL_SM6115 is not set
-# CONFIG_PINCTRL_SM6125 is not set
-# CONFIG_PINCTRL_SM8350 is not set
-# CONFIG_PINCTRL_STMFX is not set
-# CONFIG_PINCTRL_SX150X is not set
-# CONFIG_PING is not set
-CONFIG_PINMUX=y
-# CONFIG_PKCS7_MESSAGE_PARSER is not set
-# CONFIG_PL310_ERRATA_588369 is not set
-# CONFIG_PL310_ERRATA_727915 is not set
-# CONFIG_PL310_ERRATA_753970 is not set
-# CONFIG_PL310_ERRATA_769419 is not set
-# CONFIG_PL320_MBOX is not set
-# CONFIG_PL330_DMA is not set
-# CONFIG_PLATFORM_MHU is not set
-# CONFIG_PLAT_SPEAR is not set
-# CONFIG_PLIP is not set
-# CONFIG_PLX_DMA is not set
-# CONFIG_PLX_HERMES is not set
-# CONFIG_PM is not set
-# CONFIG_PMBUS is not set
-# CONFIG_PMC_MSP is not set
-# CONFIG_PMIC_ADP5520 is not set
-# CONFIG_PMIC_DA903X is not set
-# CONFIG_PMS7003 is not set
-# CONFIG_PM_AUTOSLEEP is not set
-# CONFIG_PM_DEBUG is not set
-# CONFIG_PM_DEVFREQ is not set
-# CONFIG_PM_WAKELOCKS is not set
-# CONFIG_POSIX_MQUEUE is not set
-CONFIG_POSIX_TIMERS=y
-# CONFIG_POWERCAP is not set
-# CONFIG_POWER_AVS is not set
-# CONFIG_POWER_RESET is not set
-# CONFIG_POWER_RESET_BRCMKONA is not set
-# CONFIG_POWER_RESET_BRCMSTB is not set
-# CONFIG_POWER_RESET_GPIO is not set
-# CONFIG_POWER_RESET_GPIO_RESTART is not set
-# CONFIG_POWER_RESET_LINKSTATION is not set
-# CONFIG_POWER_RESET_LTC2952 is not set
-# CONFIG_POWER_RESET_PIIX4_POWEROFF is not set
-# CONFIG_POWER_RESET_QNAP is not set
-# CONFIG_POWER_RESET_REGULATOR is not set
-# CONFIG_POWER_RESET_RESTART is not set
-# CONFIG_POWER_RESET_SYSCON is not set
-# CONFIG_POWER_RESET_SYSCON_POWEROFF is not set
-# CONFIG_POWER_RESET_VERSATILE is not set
-# CONFIG_POWER_RESET_XGENE is not set
-# CONFIG_POWER_SUPPLY is not set
-# CONFIG_POWER_SUPPLY_DEBUG is not set
-# CONFIG_POWER_SUPPLY_HWMON is not set
-# CONFIG_PPC4xx_GPIO is not set
-# CONFIG_PPC_16K_PAGES is not set
-# CONFIG_PPC_256K_PAGES is not set
-CONFIG_PPC_4K_PAGES=y
-# CONFIG_PPC_64K_PAGES is not set
-# CONFIG_PPC_DISABLE_WERROR is not set
-# CONFIG_PPC_EMULATED_STATS is not set
-# CONFIG_PPC_EPAPR_HV_BYTECHAN is not set
-# CONFIG_PPC_QUEUED_SPINLOCKS is not set
-# CONFIG_PPP is not set
-# CONFIG_PPPOATM is not set
-# CONFIG_PPPOE is not set
-# CONFIG_PPPOL2TP is not set
-# CONFIG_PPP_ASYNC is not set
-# CONFIG_PPP_BSDCOMP is not set
-# CONFIG_PPP_DEFLATE is not set
-CONFIG_PPP_FILTER=y
-# CONFIG_PPP_MPPE is not set
-CONFIG_PPP_MULTILINK=y
-# CONFIG_PPP_SYNC_TTY is not set
-# CONFIG_PPS is not set
-# CONFIG_PPS_CLIENT_GPIO is not set
-# CONFIG_PPS_CLIENT_KTIMER is not set
-# CONFIG_PPS_CLIENT_LDISC is not set
-# CONFIG_PPS_CLIENT_PARPORT is not set
-# CONFIG_PPS_DEBUG is not set
-# CONFIG_PPTP is not set
-# CONFIG_PREEMPT is not set
-# CONFIG_PREEMPTIRQ_DELAY_TEST is not set
-# CONFIG_PREEMPTIRQ_EVENTS is not set
-CONFIG_PREEMPT_NONE=y
-# CONFIG_PREEMPT_TRACER is not set
-# CONFIG_PREEMPT_VOLUNTARY is not set
-# CONFIG_PRESTERA is not set
-CONFIG_PREVENT_FIRMWARE_BUILD=y
-# CONFIG_PRIME_NUMBERS is not set
-CONFIG_PRINTK=y
-# CONFIG_PRINTK_CALLER is not set
-# CONFIG_PRINTK_INDEX is not set
-CONFIG_PRINTK_NMI=y
-CONFIG_PRINTK_SAFE_LOG_BUF_SHIFT=13
-# CONFIG_PRINTK_TIME is not set
-CONFIG_PRINT_STACK_DEPTH=64
-# CONFIG_PRISM2_USB is not set
-# CONFIG_PRISM54 is not set
-# CONFIG_PROC_CHILDREN is not set
-CONFIG_PROC_FS=y
-# CONFIG_PROC_KCORE is not set
-# CONFIG_PROC_PAGE_MONITOR is not set
-# CONFIG_PROC_STRIPPED is not set
-CONFIG_PROC_SYSCTL=y
-# CONFIG_PROC_VMCORE_DEVICE_DUMP is not set
-# CONFIG_PROFILE_ALL_BRANCHES is not set
-# CONFIG_PROFILE_ANNOTATED_BRANCHES is not set
-# CONFIG_PROFILING is not set
-# CONFIG_PROVE_LOCKING is not set
-# CONFIG_PROVE_RAW_LOCK_NESTING is not set
-# CONFIG_PROVE_RCU is not set
-# CONFIG_PROVE_RCU_LIST is not set
-# CONFIG_PROVE_RCU_REPEATEDLY is not set
-# CONFIG_PSAMPLE is not set
-# CONFIG_PSB6970_PHY is not set
-# CONFIG_PSI is not set
-# CONFIG_PSTORE is not set
-# CONFIG_PSTORE_842_COMPRESS is not set
-# CONFIG_PSTORE_BLK is not set
-# CONFIG_PSTORE_COMPRESS is not set
-# CONFIG_PSTORE_CONSOLE is not set
-CONFIG_PSTORE_DEFAULT_KMSG_BYTES=10240
-# CONFIG_PSTORE_DEFLATE_COMPRESS is not set
-# CONFIG_PSTORE_DEFLATE_COMPRESS_DEFAULT is not set
-# CONFIG_PSTORE_FTRACE is not set
-# CONFIG_PSTORE_LZ4HC_COMPRESS is not set
-# CONFIG_PSTORE_LZ4_COMPRESS is not set
-# CONFIG_PSTORE_LZO_COMPRESS is not set
-# CONFIG_PSTORE_PMSG is not set
-# CONFIG_PSTORE_RAM is not set
-# CONFIG_PSTORE_ZSTD_COMPRESS is not set
-# CONFIG_PTDUMP_DEBUGFS is not set
-# CONFIG_PTP_1588_CLOCK is not set
-# CONFIG_PTP_1588_CLOCK_IDT82P33 is not set
-# CONFIG_PTP_1588_CLOCK_IDTCM is not set
-# CONFIG_PTP_1588_CLOCK_IXP46X is not set
-# CONFIG_PTP_1588_CLOCK_KVM is not set
-# CONFIG_PTP_1588_CLOCK_OCP is not set
-# CONFIG_PTP_1588_CLOCK_PCH is not set
-# CONFIG_PTP_1588_CLOCK_VMW is not set
-# CONFIG_PUBLIC_KEY_ALGO_RSA is not set
-# CONFIG_PVPANIC is not set
-# CONFIG_PWM is not set
-# CONFIG_PWM_ATMEL_TCB is not set
-# CONFIG_PWM_DEBUG is not set
-# CONFIG_PWM_DWC is not set
-# CONFIG_PWM_FSL_FTM is not set
-# CONFIG_PWM_IMG is not set
-# CONFIG_PWM_JZ4740 is not set
-# CONFIG_PWM_MEDIATEK is not set
-# CONFIG_PWM_PCA9685 is not set
-# CONFIG_PWM_RASPBERRYPI_POE is not set
-CONFIG_PWRSEQ_EMMC=y
-# CONFIG_PWRSEQ_SD8787 is not set
-CONFIG_PWRSEQ_SIMPLE=y
-# CONFIG_QCA7000 is not set
-# CONFIG_QCA7000_SPI is not set
-# CONFIG_QCA7000_UART is not set
-# CONFIG_QCOM_A7PLL is not set
-# CONFIG_QCOM_EMAC is not set
-# CONFIG_QCOM_FALKOR_ERRATUM_1003 is not set
-# CONFIG_QCOM_FALKOR_ERRATUM_1009 is not set
-# CONFIG_QCOM_FALKOR_ERRATUM_E1041 is not set
-# CONFIG_QCOM_GPI_DMA is not set
-# CONFIG_QCOM_HIDMA is not set
-# CONFIG_QCOM_HIDMA_MGMT is not set
-# CONFIG_QCOM_LMH is not set
-# CONFIG_QCOM_QDF2400_ERRATUM_0065 is not set
-# CONFIG_QCOM_SPMI_ADC5 is not set
-# CONFIG_QCOM_SPMI_ADC_TM5 is not set
-# CONFIG_QCOM_SPMI_IADC is not set
-# CONFIG_QCOM_SPMI_TEMP_ALARM is not set
-# CONFIG_QCOM_SPMI_VADC is not set
-# CONFIG_QED is not set
-# CONFIG_QFMT_V1 is not set
-# CONFIG_QLA3XXX is not set
-# CONFIG_QLCNIC is not set
-# CONFIG_QLGE is not set
-# CONFIG_QNX4FS_FS is not set
-# CONFIG_QNX6FS_FS is not set
-# CONFIG_QORIQ_CPUFREQ is not set
-# CONFIG_QORIQ_THERMAL is not set
-# CONFIG_QRTR is not set
-# CONFIG_QRTR_MHI is not set
-# CONFIG_QRTR_TUN is not set
-# CONFIG_QSEMI_PHY is not set
-# CONFIG_QUEUED_LOCK_STAT is not set
-# CONFIG_QUICC_ENGINE is not set
-# CONFIG_QUOTA is not set
-# CONFIG_QUOTACTL is not set
-# CONFIG_QUOTA_DEBUG is not set
-# CONFIG_QUOTA_NETLINK_INTERFACE is not set
-# CONFIG_R3964 is not set
-# CONFIG_R6040 is not set
-# CONFIG_R8169 is not set
-# CONFIG_R8188EU is not set
-# CONFIG_R8712U is not set
-# CONFIG_R8723AU is not set
-# CONFIG_RADIO_ADAPTERS is not set
-# CONFIG_RADIO_AZTECH is not set
-# CONFIG_RADIO_CADET is not set
-# CONFIG_RADIO_GEMTEK is not set
-# CONFIG_RADIO_MAXIRADIO is not set
-# CONFIG_RADIO_RTRACK is not set
-# CONFIG_RADIO_RTRACK2 is not set
-# CONFIG_RADIO_SF16FMI is not set
-# CONFIG_RADIO_SF16FMR2 is not set
-# CONFIG_RADIO_TERRATEC is not set
-# CONFIG_RADIO_TRUST is not set
-# CONFIG_RADIO_TYPHOON is not set
-# CONFIG_RADIO_ZOLTRIX is not set
-# CONFIG_RAID6_PQ_BENCHMARK is not set
-# CONFIG_RAID_ATTRS is not set
-# CONFIG_RALINK is not set
-# CONFIG_RANDOM32_SELFTEST is not set
-# CONFIG_RANDOMIZE_BASE is not set
-# CONFIG_RANDOMIZE_KSTACK_OFFSET_DEFAULT is not set
-CONFIG_RANDOM_TRUST_BOOTLOADER=y
-CONFIG_RANDOM_TRUST_CPU=y
-# CONFIG_RAPIDIO is not set
-# CONFIG_RAS is not set
-# CONFIG_RBTREE_TEST is not set
-# CONFIG_RCU_BOOST is not set
-CONFIG_RCU_CPU_STALL_TIMEOUT=60
-# CONFIG_RCU_EQS_DEBUG is not set
-# CONFIG_RCU_EXPEDITE_BOOT is not set
-# CONFIG_RCU_EXPERT is not set
-CONFIG_RCU_KTHREAD_PRIO=0
-CONFIG_RCU_NEED_SEGCBLIST=y
-# CONFIG_RCU_PERF_TEST is not set
-# CONFIG_RCU_REF_SCALE_TEST is not set
-# CONFIG_RCU_SCALE_TEST is not set
-CONFIG_RCU_STALL_COMMON=y
-# CONFIG_RCU_STRICT_GRACE_PERIOD is not set
-# CONFIG_RCU_TORTURE_TEST is not set
-CONFIG_RCU_TORTURE_TEST_SLOW_INIT_DELAY=3
-# CONFIG_RCU_TRACE is not set
-# CONFIG_RC_ATI_REMOTE is not set
-# CONFIG_RC_CORE is not set
-# CONFIG_RC_DECODERS is not set
-# CONFIG_RC_LOOPBACK is not set
-# CONFIG_RC_MAP is not set
-# CONFIG_RC_XBOX_DVD is not set
-# CONFIG_RDS is not set
-# CONFIG_RD_BZIP2 is not set
-# CONFIG_RD_GZIP is not set
-# CONFIG_RD_LZ4 is not set
-# CONFIG_RD_LZMA is not set
-# CONFIG_RD_LZO is not set
-# CONFIG_RD_XZ is not set
-# CONFIG_RD_ZSTD is not set
-# CONFIG_READABLE_ASM is not set
-# CONFIG_READ_ONLY_THP_FOR_FS is not set
-# CONFIG_REALTEK_PHY is not set
-# CONFIG_REDWOOD is not set
-# CONFIG_REED_SOLOMON is not set
-# CONFIG_REED_SOLOMON_DEC8 is not set
-# CONFIG_REED_SOLOMON_ENC8 is not set
-# CONFIG_REED_SOLOMON_TEST is not set
-# CONFIG_REGMAP is not set
-# CONFIG_REGMAP_I2C is not set
-# CONFIG_REGMAP_MMIO is not set
-# CONFIG_REGMAP_SPI is not set
-# CONFIG_REGULATOR is not set
-# CONFIG_REGULATOR_88PG86X is not set
-# CONFIG_REGULATOR_ACT8865 is not set
-# CONFIG_REGULATOR_AD5398 is not set
-# CONFIG_REGULATOR_ANATOP is not set
-# CONFIG_REGULATOR_DA9121 is not set
-# CONFIG_REGULATOR_DA9210 is not set
-# CONFIG_REGULATOR_DA9211 is not set
-# CONFIG_REGULATOR_DEBUG is not set
-# CONFIG_REGULATOR_FAN53555 is not set
-# CONFIG_REGULATOR_FAN53880 is not set
-# CONFIG_REGULATOR_FIXED_VOLTAGE is not set
-# CONFIG_REGULATOR_GPIO is not set
-# CONFIG_REGULATOR_ISL6271A is not set
-# CONFIG_REGULATOR_ISL9305 is not set
-# CONFIG_REGULATOR_LP3971 is not set
-# CONFIG_REGULATOR_LP3972 is not set
-# CONFIG_REGULATOR_LP872X is not set
-# CONFIG_REGULATOR_LP8755 is not set
-# CONFIG_REGULATOR_LTC3589 is not set
-# CONFIG_REGULATOR_LTC3676 is not set
-# CONFIG_REGULATOR_MAX1586 is not set
-# CONFIG_REGULATOR_MAX77620 is not set
-# CONFIG_REGULATOR_MAX77826 is not set
-# CONFIG_REGULATOR_MAX8649 is not set
-# CONFIG_REGULATOR_MAX8660 is not set
-# CONFIG_REGULATOR_MAX8893 is not set
-# CONFIG_REGULATOR_MAX8952 is not set
-# CONFIG_REGULATOR_MAX8973 is not set
-# CONFIG_REGULATOR_MCP16502 is not set
-# CONFIG_REGULATOR_MP5416 is not set
-# CONFIG_REGULATOR_MP8859 is not set
-# CONFIG_REGULATOR_MP886X is not set
-# CONFIG_REGULATOR_MPQ7920 is not set
-# CONFIG_REGULATOR_MT6311 is not set
-# CONFIG_REGULATOR_MT6315 is not set
-# CONFIG_REGULATOR_MT6359 is not set
-# CONFIG_REGULATOR_PCA9450 is not set
-# CONFIG_REGULATOR_PF8X00 is not set
-# CONFIG_REGULATOR_PFUZE100 is not set
-# CONFIG_REGULATOR_PV88060 is not set
-# CONFIG_REGULATOR_PV88080 is not set
-# CONFIG_REGULATOR_PV88090 is not set
-# CONFIG_REGULATOR_PWM is not set
-# CONFIG_REGULATOR_RASPBERRYPI_TOUCHSCREEN_ATTINY is not set
-# CONFIG_REGULATOR_RT4801 is not set
-# CONFIG_REGULATOR_RT6160 is not set
-# CONFIG_REGULATOR_RT6245 is not set
-# CONFIG_REGULATOR_RTMV20 is not set
-# CONFIG_REGULATOR_RTQ2134 is not set
-# CONFIG_REGULATOR_RTQ6752 is not set
-# CONFIG_REGULATOR_SLG51000 is not set
-# CONFIG_REGULATOR_SY8106A is not set
-# CONFIG_REGULATOR_SY8824X is not set
-# CONFIG_REGULATOR_SY8827N is not set
-# CONFIG_REGULATOR_TI_ABB is not set
-# CONFIG_REGULATOR_TPS51632 is not set
-# CONFIG_REGULATOR_TPS62360 is not set
-# CONFIG_REGULATOR_TPS65023 is not set
-# CONFIG_REGULATOR_TPS6507X is not set
-# CONFIG_REGULATOR_TPS65132 is not set
-# CONFIG_REGULATOR_TPS6524X is not set
-# CONFIG_REGULATOR_USERSPACE_CONSUMER is not set
-# CONFIG_REGULATOR_VCTRL is not set
-# CONFIG_REGULATOR_VIRTUAL_CONSUMER is not set
-# CONFIG_REISERFS_CHECK is not set
-# CONFIG_REISERFS_FS is not set
-# CONFIG_REISERFS_FS_POSIX_ACL is not set
-# CONFIG_REISERFS_FS_SECURITY is not set
-CONFIG_REISERFS_FS_XATTR=y
-# CONFIG_REISERFS_PROC_INFO is not set
-# CONFIG_RELAY is not set
-# CONFIG_RELOCATABLE is not set
-CONFIG_RELR=y
-# CONFIG_REMOTEPROC is not set
-# CONFIG_RENESAS_PHY is not set
-# CONFIG_RESET_ATH79 is not set
-# CONFIG_RESET_BERLIN is not set
-# CONFIG_RESET_BRCMSTB_RESCAL is not set
-# CONFIG_RESET_CONTROLLER is not set
-# CONFIG_RESET_IMX7 is not set
-# CONFIG_RESET_INTEL_GW is not set
-# CONFIG_RESET_LANTIQ is not set
-# CONFIG_RESET_LPC18XX is not set
-# CONFIG_RESET_MESON is not set
-# CONFIG_RESET_PISTACHIO is not set
-# CONFIG_RESET_SOCFPGA is not set
-# CONFIG_RESET_STM32 is not set
-# CONFIG_RESET_SUNXI is not set
-# CONFIG_RESET_TEGRA_BPMP is not set
-# CONFIG_RESET_TI_SYSCON is not set
-# CONFIG_RESET_ZYNQ is not set
-# CONFIG_RFD77402 is not set
-# CONFIG_RFD_FTL is not set
-CONFIG_RFKILL=y
-# CONFIG_RFKILL_FULL is not set
-# CONFIG_RFKILL_GPIO is not set
-# CONFIG_RFKILL_INPUT is not set
-# CONFIG_RFKILL_LEDS is not set
-# CONFIG_RFKILL_REGULATOR is not set
-# CONFIG_RING_BUFFER_BENCHMARK is not set
-# CONFIG_RING_BUFFER_STARTUP_TEST is not set
-# CONFIG_RING_BUFFER_VALIDATE_TIME_DELTAS is not set
-# CONFIG_RMI4_CORE is not set
-# CONFIG_RMNET is not set
-# CONFIG_ROCKCHIP_PHY is not set
-# CONFIG_ROCKER is not set
-# CONFIG_ROMFS_FS is not set
-# CONFIG_ROSE is not set
-# CONFIG_RPCSEC_GSS_KRB5 is not set
-# CONFIG_RPMSG_QCOM_GLINK_RPM is not set
-# CONFIG_RPMSG_VIRTIO is not set
-# CONFIG_RPMSG_WWAN_CTRL is not set
-# CONFIG_RPR0521 is not set
-# CONFIG_RSEQ is not set
-# CONFIG_RT2X00 is not set
-# CONFIG_RTC_CLASS is not set
-# CONFIG_RTC_DEBUG is not set
-# CONFIG_RTC_DRV_ABB5ZES3 is not set
-# CONFIG_RTC_DRV_ABEOZ9 is not set
-# CONFIG_RTC_DRV_ABX80X is not set
-# CONFIG_RTC_DRV_ARMADA38X is not set
-# CONFIG_RTC_DRV_AU1XXX is not set
-# CONFIG_RTC_DRV_BQ32K is not set
-# CONFIG_RTC_DRV_BQ4802 is not set
-# CONFIG_RTC_DRV_CADENCE is not set
-CONFIG_RTC_DRV_CMOS=y
-# CONFIG_RTC_DRV_DS1286 is not set
-# CONFIG_RTC_DRV_DS1302 is not set
-# CONFIG_RTC_DRV_DS1305 is not set
-# CONFIG_RTC_DRV_DS1307 is not set
-# CONFIG_RTC_DRV_DS1307_CENTURY is not set
-# CONFIG_RTC_DRV_DS1307_HWMON is not set
-# CONFIG_RTC_DRV_DS1343 is not set
-# CONFIG_RTC_DRV_DS1347 is not set
-# CONFIG_RTC_DRV_DS1374 is not set
-# CONFIG_RTC_DRV_DS1390 is not set
-# CONFIG_RTC_DRV_DS1511 is not set
-# CONFIG_RTC_DRV_DS1553 is not set
-# CONFIG_RTC_DRV_DS1672 is not set
-# CONFIG_RTC_DRV_DS1685_FAMILY is not set
-# CONFIG_RTC_DRV_DS1742 is not set
-# CONFIG_RTC_DRV_DS2404 is not set
-# CONFIG_RTC_DRV_DS3232 is not set
-# CONFIG_RTC_DRV_DS3234 is not set
-# CONFIG_RTC_DRV_EM3027 is not set
-# CONFIG_RTC_DRV_EP93XX is not set
-# CONFIG_RTC_DRV_FM3130 is not set
-# CONFIG_RTC_DRV_FTRTC010 is not set
-# CONFIG_RTC_DRV_GENERIC is not set
-# CONFIG_RTC_DRV_GOLDFISH is not set
-# CONFIG_RTC_DRV_HID_SENSOR_TIME is not set
-# CONFIG_RTC_DRV_HYM8563 is not set
-# CONFIG_RTC_DRV_ISL12022 is not set
-# CONFIG_RTC_DRV_ISL12026 is not set
-# CONFIG_RTC_DRV_ISL12057 is not set
-# CONFIG_RTC_DRV_ISL1208 is not set
-# CONFIG_RTC_DRV_JZ4740 is not set
-# CONFIG_RTC_DRV_M41T80 is not set
-# CONFIG_RTC_DRV_M41T93 is not set
-# CONFIG_RTC_DRV_M41T94 is not set
-# CONFIG_RTC_DRV_M48T35 is not set
-# CONFIG_RTC_DRV_M48T59 is not set
-# CONFIG_RTC_DRV_M48T86 is not set
-# CONFIG_RTC_DRV_MAX6900 is not set
-# CONFIG_RTC_DRV_MAX6902 is not set
-# CONFIG_RTC_DRV_MAX6916 is not set
-# CONFIG_RTC_DRV_MAX77686 is not set
-# CONFIG_RTC_DRV_MCP795 is not set
-# CONFIG_RTC_DRV_MOXART is not set
-# CONFIG_RTC_DRV_MPC5121 is not set
-# CONFIG_RTC_DRV_MSM6242 is not set
-# CONFIG_RTC_DRV_MT2712 is not set
-# CONFIG_RTC_DRV_OMAP is not set
-# CONFIG_RTC_DRV_PCF2123 is not set
-# CONFIG_RTC_DRV_PCF2127 is not set
-# CONFIG_RTC_DRV_PCF85063 is not set
-# CONFIG_RTC_DRV_PCF8523 is not set
-# CONFIG_RTC_DRV_PCF85363 is not set
-# CONFIG_RTC_DRV_PCF8563 is not set
-# CONFIG_RTC_DRV_PCF8583 is not set
-# CONFIG_RTC_DRV_PL030 is not set
-# CONFIG_RTC_DRV_PL031 is not set
-# CONFIG_RTC_DRV_PS3 is not set
-# CONFIG_RTC_DRV_PT7C4338 is not set
-# CONFIG_RTC_DRV_R7301 is not set
-# CONFIG_RTC_DRV_R9701 is not set
-# CONFIG_RTC_DRV_RP5C01 is not set
-# CONFIG_RTC_DRV_RS5C348 is not set
-# CONFIG_RTC_DRV_RS5C372 is not set
-# CONFIG_RTC_DRV_RTC7301 is not set
-# CONFIG_RTC_DRV_RV3028 is not set
-# CONFIG_RTC_DRV_RV3029C2 is not set
-# CONFIG_RTC_DRV_RV3032 is not set
-# CONFIG_RTC_DRV_RV8803 is not set
-# CONFIG_RTC_DRV_RX4581 is not set
-# CONFIG_RTC_DRV_RX6110 is not set
-# CONFIG_RTC_DRV_RX8010 is not set
-# CONFIG_RTC_DRV_RX8025 is not set
-# CONFIG_RTC_DRV_RX8581 is not set
-# CONFIG_RTC_DRV_S35390A is not set
-# CONFIG_RTC_DRV_SD3078 is not set
-# CONFIG_RTC_DRV_SNVS is not set
-# CONFIG_RTC_DRV_STK17TA8 is not set
-# CONFIG_RTC_DRV_SUN6I is not set
-# CONFIG_RTC_DRV_TEGRA is not set
-# CONFIG_RTC_DRV_TEST is not set
-# CONFIG_RTC_DRV_V3020 is not set
-# CONFIG_RTC_DRV_X1205 is not set
-# CONFIG_RTC_DRV_XGENE is not set
-# CONFIG_RTC_DRV_ZYNQMP is not set
-CONFIG_RTC_HCTOSYS=y
-CONFIG_RTC_HCTOSYS_DEVICE="rtc0"
-CONFIG_RTC_INTF_DEV=y
-# CONFIG_RTC_INTF_DEV_UIE_EMUL is not set
-CONFIG_RTC_INTF_PROC=y
-CONFIG_RTC_INTF_SYSFS=y
-CONFIG_RTC_LIB=y
-# CONFIG_RTC_NVMEM is not set
-CONFIG_RTC_SYSTOHC=y
-CONFIG_RTC_SYSTOHC_DEVICE="rtc0"
-# CONFIG_RTL8180 is not set
-# CONFIG_RTL8187 is not set
-# CONFIG_RTL8192E is not set
-# CONFIG_RTL8192U is not set
-# CONFIG_RTL8306_PHY is not set
-# CONFIG_RTL8366RB_PHY is not set
-# CONFIG_RTL8366S_PHY is not set
-# CONFIG_RTL8366_SMI is not set
-# CONFIG_RTL8366_SMI_DEBUG_FS is not set
-# CONFIG_RTL8367B_PHY is not set
-# CONFIG_RTL8367_PHY is not set
-# CONFIG_RTLLIB is not set
-# CONFIG_RTL_CARDS is not set
-# CONFIG_RTS5208 is not set
-CONFIG_RT_MUTEXES=y
-# CONFIG_RUNTIME_DEBUG is not set
-CONFIG_RUNTIME_TESTING_MENU=y
-CONFIG_RWSEM_GENERIC_SPINLOCK=y
-CONFIG_RXKAD=y
-# CONFIG_S2IO is not set
-# CONFIG_SAMPLES is not set
-# CONFIG_SAMSUNG_LAPTOP is not set
-# CONFIG_SATA_ACARD_AHCI is not set
-# CONFIG_SATA_AHCI is not set
-# CONFIG_SATA_AHCI_PLATFORM is not set
-# CONFIG_SATA_DWC is not set
-# CONFIG_SATA_DWC_DEBUG is not set
-# CONFIG_SATA_DWC_OLD_DMA is not set
-# CONFIG_SATA_FSL is not set
-# CONFIG_SATA_HIGHBANK is not set
-# CONFIG_SATA_HOST is not set
-# CONFIG_SATA_INIC162X is not set
-CONFIG_SATA_MOBILE_LPM_POLICY=0
-# CONFIG_SATA_MV is not set
-# CONFIG_SATA_NV is not set
-# CONFIG_SATA_PMP is not set
-# CONFIG_SATA_PROMISE is not set
-# CONFIG_SATA_QSTOR is not set
-# CONFIG_SATA_RCAR is not set
-# CONFIG_SATA_SIL is not set
-# CONFIG_SATA_SIL24 is not set
-# CONFIG_SATA_SIS is not set
-# CONFIG_SATA_SVW is not set
-# CONFIG_SATA_SX4 is not set
-# CONFIG_SATA_ULI is not set
-# CONFIG_SATA_VIA is not set
-# CONFIG_SATA_VITESSE is not set
-# CONFIG_SBC_FITPC2_WATCHDOG is not set
-CONFIG_SBITMAP=y
-# CONFIG_SC92031 is not set
-# CONFIG_SCA3000 is not set
-# CONFIG_SCA3300 is not set
-# CONFIG_SCACHE_DEBUGFS is not set
-# CONFIG_SCC is not set
-# CONFIG_SCD30_CORE is not set
-# CONFIG_SCF_TORTURE_TEST is not set
-# CONFIG_SCHEDSTATS is not set
-# CONFIG_SCHED_AUTOGROUP is not set
-# CONFIG_SCHED_DEBUG is not set
-CONFIG_SCHED_HRTICK=y
-# CONFIG_SCHED_MC is not set
-CONFIG_SCHED_OMIT_FRAME_POINTER=y
-# CONFIG_SCHED_SMT is not set
-CONFIG_SCHED_STACK_END_CHECK=y
-# CONFIG_SCHED_TRACER is not set
-# CONFIG_SCR24X is not set
-# CONFIG_SCSI is not set
-# CONFIG_SCSI_3W_9XXX is not set
-# CONFIG_SCSI_3W_SAS is not set
-# CONFIG_SCSI_7000FASST is not set
-# CONFIG_SCSI_AACRAID is not set
-# CONFIG_SCSI_ACARD is not set
-# CONFIG_SCSI_ADVANSYS is not set
-# CONFIG_SCSI_AHA152X is not set
-# CONFIG_SCSI_AHA1542 is not set
-# CONFIG_SCSI_AIC79XX is not set
-# CONFIG_SCSI_AIC7XXX is not set
-# CONFIG_SCSI_AIC94XX is not set
-# CONFIG_SCSI_AM53C974 is not set
-# CONFIG_SCSI_ARCMSR is not set
-# CONFIG_SCSI_BFA_FC is not set
-# CONFIG_SCSI_BNX2X_FCOE is not set
-# CONFIG_SCSI_BNX2_ISCSI is not set
-# CONFIG_SCSI_BUSLOGIC is not set
-# CONFIG_SCSI_CHELSIO_FCOE is not set
-# CONFIG_SCSI_CONSTANTS is not set
-# CONFIG_SCSI_CXGB3_ISCSI is not set
-# CONFIG_SCSI_CXGB4_ISCSI is not set
-# CONFIG_SCSI_DC395x is not set
-# CONFIG_SCSI_DEBUG is not set
-# CONFIG_SCSI_DH is not set
-CONFIG_SCSI_DMA=y
-# CONFIG_SCSI_DMX3191D is not set
-# CONFIG_SCSI_DPT_I2O is not set
-# CONFIG_SCSI_DTC3280 is not set
-# CONFIG_SCSI_EATA is not set
-# CONFIG_SCSI_ESAS2R is not set
-# CONFIG_SCSI_FC_ATTRS is not set
-# CONFIG_SCSI_FDOMAIN_PCI is not set
-# CONFIG_SCSI_FUTURE_DOMAIN is not set
-# CONFIG_SCSI_GDTH is not set
-# CONFIG_SCSI_GENERIC_NCR5380 is not set
-# CONFIG_SCSI_GENERIC_NCR5380_MMIO is not set
-# CONFIG_SCSI_HISI_SAS is not set
-# CONFIG_SCSI_HPSA is not set
-# CONFIG_SCSI_HPTIOP is not set
-# CONFIG_SCSI_IN2000 is not set
-# CONFIG_SCSI_INIA100 is not set
-# CONFIG_SCSI_INITIO is not set
-# CONFIG_SCSI_IPR is not set
-# CONFIG_SCSI_IPS is not set
-# CONFIG_SCSI_ISCI is not set
-# CONFIG_SCSI_ISCSI_ATTRS is not set
-# CONFIG_SCSI_LOGGING is not set
-CONFIG_SCSI_LOWLEVEL=y
-# CONFIG_SCSI_LOWLEVEL_PCMCIA is not set
-# CONFIG_SCSI_LPFC is not set
-CONFIG_SCSI_MOD=y
-# CONFIG_SCSI_MPI3MR is not set
-# CONFIG_SCSI_MPT2SAS is not set
-# CONFIG_SCSI_MPT3SAS is not set
-# CONFIG_SCSI_MQ_DEFAULT is not set
-# CONFIG_SCSI_MVSAS is not set
-# CONFIG_SCSI_MVSAS_DEBUG is not set
-# CONFIG_SCSI_MVUMI is not set
-# CONFIG_SCSI_MYRB is not set
-# CONFIG_SCSI_MYRS is not set
-# CONFIG_SCSI_NCR53C406A is not set
-# CONFIG_SCSI_NETLINK is not set
-# CONFIG_SCSI_NSP32 is not set
-# CONFIG_SCSI_OSD_INITIATOR is not set
-# CONFIG_SCSI_PAS16 is not set
-# CONFIG_SCSI_PM8001 is not set
-# CONFIG_SCSI_PMCRAID is not set
-CONFIG_SCSI_PROC_FS=y
-# CONFIG_SCSI_QLA_FC is not set
-# CONFIG_SCSI_QLA_ISCSI is not set
-# CONFIG_SCSI_QLOGIC_1280 is not set
-# CONFIG_SCSI_QLOGIC_FAS is not set
-# CONFIG_SCSI_SAS_ATTRS is not set
-# CONFIG_SCSI_SAS_LIBSAS is not set
-# CONFIG_SCSI_SCAN_ASYNC is not set
-# CONFIG_SCSI_SMARTPQI is not set
-# CONFIG_SCSI_SNIC is not set
-# CONFIG_SCSI_SPI_ATTRS is not set
-# CONFIG_SCSI_SRP_ATTRS is not set
-# CONFIG_SCSI_STEX is not set
-# CONFIG_SCSI_SYM53C416 is not set
-# CONFIG_SCSI_SYM53C8XX_2 is not set
-# CONFIG_SCSI_T128 is not set
-# CONFIG_SCSI_U14_34F is not set
-# CONFIG_SCSI_UFSHCD is not set
-# CONFIG_SCSI_ULTRASTOR is not set
-# CONFIG_SCSI_VIRTIO is not set
-# CONFIG_SCSI_WD719X is not set
-# CONFIG_SC_CAMCC_7180 is not set
-# CONFIG_SC_DISPCC_7280 is not set
-# CONFIG_SC_GCC_7280 is not set
-# CONFIG_SC_GCC_8180X is not set
-# CONFIG_SC_GPUCC_7280 is not set
-# CONFIG_SC_VIDEOCC_7280 is not set
-# CONFIG_SCx200_ACB is not set
-# CONFIG_SDIO_UART is not set
-# CONFIG_SDM_GPUCC_660 is not set
-# CONFIG_SDM_MMCC_660 is not set
-# CONFIG_SDR_MAX2175 is not set
-# CONFIG_SDR_PLATFORM_DRIVERS is not set
-# CONFIG_SDX_GCC_55 is not set
-# CONFIG_SD_ADC_MODULATOR is not set
-# CONFIG_SECCOMP is not set
-# CONFIG_SECCOMP_CACHE_DEBUG is not set
-CONFIG_SECTION_MISMATCH_WARN_ONLY=y
-# CONFIG_SECURITY is not set
-# CONFIG_SECURITYFS is not set
-# CONFIG_SECURITY_APPARMOR is not set
-CONFIG_SECURITY_DMESG_RESTRICT=y
-# CONFIG_SECURITY_LANDLOCK is not set
-# CONFIG_SECURITY_LOADPIN is not set
-# CONFIG_SECURITY_LOCKDOWN_LSM is not set
-# CONFIG_SECURITY_NETWORK_XFRM is not set
-# CONFIG_SECURITY_PATH is not set
-# CONFIG_SECURITY_SAFESETID is not set
-# CONFIG_SECURITY_SELINUX_AVC_STATS is not set
-# CONFIG_SECURITY_SELINUX_BOOTPARAM is not set
-CONFIG_SECURITY_SELINUX_CHECKREQPROT_VALUE=0
-# CONFIG_SECURITY_SELINUX_DEVELOP is not set
-# CONFIG_SECURITY_SELINUX_DISABLE is not set
-# CONFIG_SECURITY_SMACK is not set
-# CONFIG_SECURITY_TOMOYO is not set
-# CONFIG_SECURITY_YAMA is not set
-CONFIG_SELECT_MEMORY_MODEL=y
-# CONFIG_SENSIRION_SGP30 is not set
-# CONFIG_SENSIRION_SGP40 is not set
-# CONFIG_SENSORS_ABITUGURU is not set
-# CONFIG_SENSORS_ABITUGURU3 is not set
-# CONFIG_SENSORS_ACPI_POWER is not set
-# CONFIG_SENSORS_AD7314 is not set
-# CONFIG_SENSORS_AD7414 is not set
-# CONFIG_SENSORS_AD7418 is not set
-# CONFIG_SENSORS_ADC128D818 is not set
-# CONFIG_SENSORS_ADCXX is not set
-# CONFIG_SENSORS_ADM1021 is not set
-# CONFIG_SENSORS_ADM1025 is not set
-# CONFIG_SENSORS_ADM1026 is not set
-# CONFIG_SENSORS_ADM1029 is not set
-# CONFIG_SENSORS_ADM1031 is not set
-# CONFIG_SENSORS_ADM1177 is not set
-# CONFIG_SENSORS_ADM1266 is not set
-# CONFIG_SENSORS_ADM1275 is not set
-# CONFIG_SENSORS_ADM9240 is not set
-# CONFIG_SENSORS_ADS1015 is not set
-# CONFIG_SENSORS_ADS7828 is not set
-# CONFIG_SENSORS_ADS7871 is not set
-# CONFIG_SENSORS_ADT7310 is not set
-# CONFIG_SENSORS_ADT7410 is not set
-# CONFIG_SENSORS_ADT7411 is not set
-# CONFIG_SENSORS_ADT7462 is not set
-# CONFIG_SENSORS_ADT7470 is not set
-# CONFIG_SENSORS_ADT7475 is not set
-# CONFIG_SENSORS_AHT10 is not set
-# CONFIG_SENSORS_AMC6821 is not set
-# CONFIG_SENSORS_APDS990X is not set
-# CONFIG_SENSORS_APPLESMC is not set
-# CONFIG_SENSORS_AQUACOMPUTER_D5NEXT is not set
-# CONFIG_SENSORS_AS370 is not set
-# CONFIG_SENSORS_ASB100 is not set
-# CONFIG_SENSORS_ASC7621 is not set
-# CONFIG_SENSORS_ASPEED is not set
-# CONFIG_SENSORS_ATK0110 is not set
-# CONFIG_SENSORS_ATXP1 is not set
-# CONFIG_SENSORS_AXI_FAN_CONTROL is not set
-# CONFIG_SENSORS_BEL_PFE is not set
-# CONFIG_SENSORS_BH1770 is not set
-# CONFIG_SENSORS_BH1780 is not set
-# CONFIG_SENSORS_BPA_RS600 is not set
-# CONFIG_SENSORS_CORETEMP is not set
-# CONFIG_SENSORS_CORSAIR_CPRO is not set
-# CONFIG_SENSORS_CORSAIR_PSU is not set
-# CONFIG_SENSORS_DELL_SMM is not set
-# CONFIG_SENSORS_DME1737 is not set
-# CONFIG_SENSORS_DPS920AB is not set
-# CONFIG_SENSORS_DRIVETEMP is not set
-# CONFIG_SENSORS_DS1621 is not set
-# CONFIG_SENSORS_DS620 is not set
-# CONFIG_SENSORS_EMC1403 is not set
-# CONFIG_SENSORS_EMC2103 is not set
-# CONFIG_SENSORS_EMC2305 is not set
-# CONFIG_SENSORS_EMC6W201 is not set
-# CONFIG_SENSORS_F71805F is not set
-# CONFIG_SENSORS_F71882FG is not set
-# CONFIG_SENSORS_F75375S is not set
-# CONFIG_SENSORS_FAM15H_POWER is not set
-# CONFIG_SENSORS_FSCHMD is not set
-# CONFIG_SENSORS_FSP_3Y is not set
-# CONFIG_SENSORS_FTSTEUTATES is not set
-# CONFIG_SENSORS_G760A is not set
-# CONFIG_SENSORS_G762 is not set
-# CONFIG_SENSORS_GL518SM is not set
-# CONFIG_SENSORS_GL520SM is not set
-# CONFIG_SENSORS_GPIO_FAN is not set
-# CONFIG_SENSORS_GSC is not set
-# CONFIG_SENSORS_HDAPS is not set
-# CONFIG_SENSORS_HIH6130 is not set
-# CONFIG_SENSORS_HMC5843 is not set
-# CONFIG_SENSORS_HMC5843_I2C is not set
-# CONFIG_SENSORS_HMC5843_SPI is not set
-# CONFIG_SENSORS_HTU21 is not set
-# CONFIG_SENSORS_I5500 is not set
-# CONFIG_SENSORS_I5K_AMB is not set
-# CONFIG_SENSORS_IBM_CFFPS is not set
-# CONFIG_SENSORS_IIO_HWMON is not set
-# CONFIG_SENSORS_INA209 is not set
-# CONFIG_SENSORS_INA2XX is not set
-# CONFIG_SENSORS_INA3221 is not set
-# CONFIG_SENSORS_INSPUR_IPSPS is not set
-# CONFIG_SENSORS_IR35221 is not set
-# CONFIG_SENSORS_IR36021 is not set
-# CONFIG_SENSORS_IR38064 is not set
-# CONFIG_SENSORS_IRPS5401 is not set
-# CONFIG_SENSORS_ISL29018 is not set
-# CONFIG_SENSORS_ISL29028 is not set
-# CONFIG_SENSORS_ISL68137 is not set
-# CONFIG_SENSORS_IT87 is not set
-# CONFIG_SENSORS_JC42 is not set
-# CONFIG_SENSORS_K10TEMP is not set
-# CONFIG_SENSORS_K8TEMP is not set
-# CONFIG_SENSORS_LINEAGE is not set
-# CONFIG_SENSORS_LIS3LV02D is not set
-# CONFIG_SENSORS_LIS3_I2C is not set
-# CONFIG_SENSORS_LIS3_SPI is not set
-# CONFIG_SENSORS_LM25066 is not set
-# CONFIG_SENSORS_LM63 is not set
-# CONFIG_SENSORS_LM70 is not set
-# CONFIG_SENSORS_LM73 is not set
-# CONFIG_SENSORS_LM75 is not set
-# CONFIG_SENSORS_LM77 is not set
-# CONFIG_SENSORS_LM78 is not set
-# CONFIG_SENSORS_LM80 is not set
-# CONFIG_SENSORS_LM83 is not set
-# CONFIG_SENSORS_LM85 is not set
-# CONFIG_SENSORS_LM87 is not set
-# CONFIG_SENSORS_LM90 is not set
-# CONFIG_SENSORS_LM92 is not set
-# CONFIG_SENSORS_LM93 is not set
-# CONFIG_SENSORS_LM95234 is not set
-# CONFIG_SENSORS_LM95241 is not set
-# CONFIG_SENSORS_LM95245 is not set
-# CONFIG_SENSORS_LTC2945 is not set
-# CONFIG_SENSORS_LTC2947_I2C is not set
-# CONFIG_SENSORS_LTC2947_SPI is not set
-# CONFIG_SENSORS_LTC2978 is not set
-# CONFIG_SENSORS_LTC2990 is not set
-# CONFIG_SENSORS_LTC2992 is not set
-# CONFIG_SENSORS_LTC3815 is not set
-# CONFIG_SENSORS_LTC4151 is not set
-# CONFIG_SENSORS_LTC4215 is not set
-# CONFIG_SENSORS_LTC4222 is not set
-# CONFIG_SENSORS_LTC4245 is not set
-# CONFIG_SENSORS_LTC4260 is not set
-# CONFIG_SENSORS_LTC4261 is not set
-# CONFIG_SENSORS_LTQ_CPUTEMP is not set
-# CONFIG_SENSORS_MAX1111 is not set
-# CONFIG_SENSORS_MAX127 is not set
-# CONFIG_SENSORS_MAX15301 is not set
-# CONFIG_SENSORS_MAX16064 is not set
-# CONFIG_SENSORS_MAX16065 is not set
-# CONFIG_SENSORS_MAX1619 is not set
-# CONFIG_SENSORS_MAX16601 is not set
-# CONFIG_SENSORS_MAX1668 is not set
-# CONFIG_SENSORS_MAX197 is not set
-# CONFIG_SENSORS_MAX20730 is not set
-# CONFIG_SENSORS_MAX20751 is not set
-# CONFIG_SENSORS_MAX31722 is not set
-# CONFIG_SENSORS_MAX31730 is not set
-# CONFIG_SENSORS_MAX31785 is not set
-# CONFIG_SENSORS_MAX31790 is not set
-# CONFIG_SENSORS_MAX34440 is not set
-# CONFIG_SENSORS_MAX6621 is not set
-# CONFIG_SENSORS_MAX6639 is not set
-# CONFIG_SENSORS_MAX6642 is not set
-# CONFIG_SENSORS_MAX6650 is not set
-# CONFIG_SENSORS_MAX6697 is not set
-# CONFIG_SENSORS_MAX8688 is not set
-# CONFIG_SENSORS_MCP3021 is not set
-# CONFIG_SENSORS_MP2888 is not set
-# CONFIG_SENSORS_MP2975 is not set
-# CONFIG_SENSORS_MR75203 is not set
-# CONFIG_SENSORS_NCT6683 is not set
-# CONFIG_SENSORS_NCT6775 is not set
-# CONFIG_SENSORS_NCT7802 is not set
-# CONFIG_SENSORS_NCT7904 is not set
-# CONFIG_SENSORS_NPCM7XX is not set
-# CONFIG_SENSORS_NSA320 is not set
-# CONFIG_SENSORS_NTC_THERMISTOR is not set
-# CONFIG_SENSORS_NZXT_KRAKEN2 is not set
-# CONFIG_SENSORS_OCC_P8_I2C is not set
-# CONFIG_SENSORS_PC87360 is not set
-# CONFIG_SENSORS_PC87427 is not set
-# CONFIG_SENSORS_PCF8591 is not set
-# CONFIG_SENSORS_PIM4328 is not set
-# CONFIG_SENSORS_PM6764TR is not set
-# CONFIG_SENSORS_PMBUS is not set
-# CONFIG_SENSORS_POWR1220 is not set
-# CONFIG_SENSORS_PWM_FAN is not set
-# CONFIG_SENSORS_PXE1610 is not set
-# CONFIG_SENSORS_Q54SJ108A2 is not set
-# CONFIG_SENSORS_RM3100_I2C is not set
-# CONFIG_SENSORS_RM3100_SPI is not set
-# CONFIG_SENSORS_SBRMI is not set
-# CONFIG_SENSORS_SBTSI is not set
-# CONFIG_SENSORS_SCH5627 is not set
-# CONFIG_SENSORS_SCH5636 is not set
-# CONFIG_SENSORS_SCH56XX_COMMON is not set
-# CONFIG_SENSORS_SHT15 is not set
-# CONFIG_SENSORS_SHT21 is not set
-# CONFIG_SENSORS_SHT3x is not set
-# CONFIG_SENSORS_SHT4x is not set
-# CONFIG_SENSORS_SHTC1 is not set
-# CONFIG_SENSORS_SIS5595 is not set
-# CONFIG_SENSORS_SMM665 is not set
-# CONFIG_SENSORS_SMSC47B397 is not set
-# CONFIG_SENSORS_SMSC47M1 is not set
-# CONFIG_SENSORS_SMSC47M192 is not set
-# CONFIG_SENSORS_STPDDC60 is not set
-# CONFIG_SENSORS_STTS751 is not set
-# CONFIG_SENSORS_TC654 is not set
-# CONFIG_SENSORS_TC74 is not set
-# CONFIG_SENSORS_THMC50 is not set
-# CONFIG_SENSORS_TMP102 is not set
-# CONFIG_SENSORS_TMP103 is not set
-# CONFIG_SENSORS_TMP108 is not set
-# CONFIG_SENSORS_TMP401 is not set
-# CONFIG_SENSORS_TMP421 is not set
-# CONFIG_SENSORS_TMP513 is not set
-# CONFIG_SENSORS_TPS23861 is not set
-# CONFIG_SENSORS_TPS40422 is not set
-# CONFIG_SENSORS_TPS53679 is not set
-# CONFIG_SENSORS_TSL2550 is not set
-# CONFIG_SENSORS_TSL2563 is not set
-# CONFIG_SENSORS_UCD9000 is not set
-# CONFIG_SENSORS_UCD9200 is not set
-# CONFIG_SENSORS_VEXPRESS is not set
-# CONFIG_SENSORS_VIA686A is not set
-# CONFIG_SENSORS_VIA_CPUTEMP is not set
-# CONFIG_SENSORS_VT1211 is not set
-# CONFIG_SENSORS_VT8231 is not set
-# CONFIG_SENSORS_W83627EHF is not set
-# CONFIG_SENSORS_W83627HF is not set
-# CONFIG_SENSORS_W83773G is not set
-# CONFIG_SENSORS_W83781D is not set
-# CONFIG_SENSORS_W83791D is not set
-# CONFIG_SENSORS_W83792D is not set
-# CONFIG_SENSORS_W83793 is not set
-# CONFIG_SENSORS_W83795 is not set
-# CONFIG_SENSORS_W83L785TS is not set
-# CONFIG_SENSORS_W83L786NG is not set
-# CONFIG_SENSORS_XDPE122 is not set
-# CONFIG_SENSORS_XGENE is not set
-# CONFIG_SENSORS_ZL6100 is not set
-CONFIG_SERIAL_8250=y
-CONFIG_SERIAL_8250_16550A_VARIANTS=y
-# CONFIG_SERIAL_8250_ACCENT is not set
-# CONFIG_SERIAL_8250_ASPEED_VUART is not set
-# CONFIG_SERIAL_8250_BOCA is not set
-CONFIG_SERIAL_8250_CONSOLE=y
-# CONFIG_SERIAL_8250_CS is not set
-# CONFIG_SERIAL_8250_DEPRECATED_OPTIONS is not set
-# CONFIG_SERIAL_8250_DETECT_IRQ is not set
-CONFIG_SERIAL_8250_DMA=y
-# CONFIG_SERIAL_8250_DW is not set
-# CONFIG_SERIAL_8250_EM is not set
-# CONFIG_SERIAL_8250_EXAR is not set
-# CONFIG_SERIAL_8250_EXAR_ST16C554 is not set
-# CONFIG_SERIAL_8250_EXTENDED is not set
-# CONFIG_SERIAL_8250_FINTEK is not set
-# CONFIG_SERIAL_8250_FOURPORT is not set
-# CONFIG_SERIAL_8250_HUB6 is not set
-# CONFIG_SERIAL_8250_INGENIC is not set
-# CONFIG_SERIAL_8250_LPSS is not set
-# CONFIG_SERIAL_8250_MANY_PORTS is not set
-# CONFIG_SERIAL_8250_MID is not set
-# CONFIG_SERIAL_8250_MOXA is not set
-CONFIG_SERIAL_8250_NR_UARTS=2
-# CONFIG_SERIAL_8250_PCI is not set
-# CONFIG_SERIAL_8250_RSA is not set
-# CONFIG_SERIAL_8250_RT288X is not set
-CONFIG_SERIAL_8250_RUNTIME_UARTS=2
-# CONFIG_SERIAL_ALTERA_JTAGUART is not set
-# CONFIG_SERIAL_ALTERA_UART is not set
-# CONFIG_SERIAL_AMBA_PL010 is not set
-# CONFIG_SERIAL_AMBA_PL011 is not set
-# CONFIG_SERIAL_ARC is not set
-# CONFIG_SERIAL_BCM63XX is not set
-# CONFIG_SERIAL_CONEXANT_DIGICOLOR is not set
-CONFIG_SERIAL_CORE=y
-CONFIG_SERIAL_CORE_CONSOLE=y
-# CONFIG_SERIAL_DEV_BUS is not set
-CONFIG_SERIAL_EARLYCON=y
-# CONFIG_SERIAL_EARLYCON_ARM_SEMIHOST is not set
-# CONFIG_SERIAL_FSL_LINFLEXUART is not set
-# CONFIG_SERIAL_FSL_LPUART is not set
-# CONFIG_SERIAL_GRLIB_GAISLER_APBUART is not set
-# CONFIG_SERIAL_IFX6X60 is not set
-# CONFIG_SERIAL_JSM is not set
-# CONFIG_SERIAL_MAX3100 is not set
-# CONFIG_SERIAL_MAX310X is not set
-# CONFIG_SERIAL_NONSTANDARD is not set
-# CONFIG_SERIAL_OF_PLATFORM is not set
-# CONFIG_SERIAL_OF_PLATFORM_NWPSERIAL is not set
-# CONFIG_SERIAL_PCH_UART is not set
-# CONFIG_SERIAL_RP2 is not set
-# CONFIG_SERIAL_SC16IS7XX is not set
-# CONFIG_SERIAL_SCCNXP is not set
-# CONFIG_SERIAL_SH_SCI is not set
-# CONFIG_SERIAL_SIFIVE is not set
-# CONFIG_SERIAL_SPRD is not set
-# CONFIG_SERIAL_STM32 is not set
-# CONFIG_SERIAL_ST_ASC is not set
-# CONFIG_SERIAL_TIMBERDALE is not set
-# CONFIG_SERIAL_UARTLITE is not set
-# CONFIG_SERIAL_XILINX_PS_UART is not set
-# CONFIG_SERIO is not set
-# CONFIG_SERIO_ALTERA_PS2 is not set
-# CONFIG_SERIO_AMBAKMI is not set
-# CONFIG_SERIO_APBPS2 is not set
-# CONFIG_SERIO_ARC_PS2 is not set
-# CONFIG_SERIO_CT82C710 is not set
-# CONFIG_SERIO_GPIO_PS2 is not set
-# CONFIG_SERIO_I8042 is not set
-# CONFIG_SERIO_LIBPS2 is not set
-# CONFIG_SERIO_PARKBD is not set
-# CONFIG_SERIO_PCIPS2 is not set
-# CONFIG_SERIO_PS2MULT is not set
-# CONFIG_SERIO_RAW is not set
-# CONFIG_SERIO_SERPORT is not set
-# CONFIG_SERIO_SUN4I_PS2 is not set
-# CONFIG_SFC is not set
-# CONFIG_SFC_FALCON is not set
-# CONFIG_SFI is not set
-# CONFIG_SFP is not set
-# CONFIG_SF_PDMA is not set
-# CONFIG_SGETMASK_SYSCALL is not set
-# CONFIG_SGI_IOC4 is not set
-# CONFIG_SGI_IP22 is not set
-# CONFIG_SGI_IP27 is not set
-# CONFIG_SGI_IP28 is not set
-# CONFIG_SGI_IP30 is not set
-# CONFIG_SGI_IP32 is not set
-# CONFIG_SGI_MFD_IOC3 is not set
-# CONFIG_SGI_PARTITION is not set
-# CONFIG_SG_POOL is not set
-# CONFIG_SG_SPLIT is not set
-CONFIG_SHMEM=y
-# CONFIG_SHUFFLE_PAGE_ALLOCATOR is not set
-# CONFIG_SH_ETH is not set
-# CONFIG_SH_TIMER_CMT is not set
-# CONFIG_SH_TIMER_MTU2 is not set
-# CONFIG_SH_TIMER_TMU is not set
-# CONFIG_SI1133 is not set
-# CONFIG_SI1145 is not set
-# CONFIG_SI7005 is not set
-# CONFIG_SI7020 is not set
-# CONFIG_SIBYTE_BIGSUR is not set
-# CONFIG_SIBYTE_CARMEL is not set
-# CONFIG_SIBYTE_CRHINE is not set
-# CONFIG_SIBYTE_CRHONE is not set
-# CONFIG_SIBYTE_LITTLESUR is not set
-# CONFIG_SIBYTE_RHONE is not set
-# CONFIG_SIBYTE_SENTOSA is not set
-# CONFIG_SIBYTE_SWARM is not set
-CONFIG_SIGNALFD=y
-# CONFIG_SIGNED_PE_FILE_VERIFICATION is not set
-# CONFIG_SIMPLE_GPIO is not set
-# CONFIG_SIMPLE_PM_BUS is not set
-# CONFIG_SIOX is not set
-# CONFIG_SIS190 is not set
-# CONFIG_SIS900 is not set
-# CONFIG_SKGE is not set
-# CONFIG_SKY2 is not set
-# CONFIG_SKY2_DEBUG is not set
-# CONFIG_SLAB is not set
-CONFIG_SLABINFO=y
-CONFIG_SLAB_FREELIST_HARDENED=y
-CONFIG_SLAB_FREELIST_RANDOM=y
-CONFIG_SLAB_MERGE_DEFAULT=y
-# CONFIG_SLHC is not set
-# CONFIG_SLICOSS is not set
-# CONFIG_SLIMBUS is not set
-# CONFIG_SLIP is not set
-# CONFIG_SLOB is not set
-CONFIG_SLUB=y
-CONFIG_SLUB_CPU_PARTIAL=y
-# CONFIG_SLUB_DEBUG is not set
-# CONFIG_SLUB_DEBUG_ON is not set
-# CONFIG_SLUB_MEMCG_SYSFS_ON is not set
-# CONFIG_SLUB_STATS is not set
-# CONFIG_SMARTJOYPLUS_FF is not set
-# CONFIG_SMB_SERVER is not set
-# CONFIG_SMC911X is not set
-# CONFIG_SMC9194 is not set
-# CONFIG_SMC91X is not set
-# CONFIG_SMP is not set
-# CONFIG_SMSC911X is not set
-# CONFIG_SMSC9420 is not set
-# CONFIG_SMSC_PHY is not set
-# CONFIG_SMS_SDIO_DRV is not set
-# CONFIG_SMS_USB_DRV is not set
-# CONFIG_SM_CAMCC_8250 is not set
-# CONFIG_SM_FTL is not set
-# CONFIG_SM_GCC_6115 is not set
-# CONFIG_SM_GCC_6125 is not set
-# CONFIG_SM_GCC_6350 is not set
-# CONFIG_SM_GCC_8350 is not set
-# CONFIG_SND is not set
-# CONFIG_SND_AC97_POWER_SAVE is not set
-# CONFIG_SND_AD1816A is not set
-# CONFIG_SND_AD1848 is not set
-# CONFIG_SND_AD1889 is not set
-# CONFIG_SND_ADLIB is not set
-# CONFIG_SND_ALI5451 is not set
-# CONFIG_SND_ALOOP is not set
-# CONFIG_SND_ALS100 is not set
-# CONFIG_SND_ALS300 is not set
-# CONFIG_SND_ALS4000 is not set
-# CONFIG_SND_ARM is not set
-# CONFIG_SND_ASIHPI is not set
-# CONFIG_SND_ATIIXP is not set
-# CONFIG_SND_ATIIXP_MODEM is not set
-# CONFIG_SND_ATMEL_AC97C is not set
-# CONFIG_SND_ATMEL_SOC is not set
-# CONFIG_SND_AU8810 is not set
-# CONFIG_SND_AU8820 is not set
-# CONFIG_SND_AU8830 is not set
-# CONFIG_SND_AUDIO_GRAPH_CARD is not set
-# CONFIG_SND_AUDIO_GRAPH_SCU_CARD is not set
-# CONFIG_SND_AW2 is not set
-# CONFIG_SND_AZT2320 is not set
-# CONFIG_SND_AZT3328 is not set
-# CONFIG_SND_BCD2000 is not set
-# CONFIG_SND_BCM63XX_I2S_WHISTLER is not set
-# CONFIG_SND_BT87X is not set
-# CONFIG_SND_CA0106 is not set
-# CONFIG_SND_CMI8330 is not set
-# CONFIG_SND_CMIPCI is not set
-# CONFIG_SND_CS4231 is not set
-# CONFIG_SND_CS4236 is not set
-# CONFIG_SND_CS4281 is not set
-# CONFIG_SND_CS46XX is not set
-# CONFIG_SND_CS5530 is not set
-# CONFIG_SND_CS5535AUDIO is not set
-# CONFIG_SND_CTXFI is not set
-# CONFIG_SND_DARLA20 is not set
-# CONFIG_SND_DARLA24 is not set
-# CONFIG_SND_DEBUG is not set
-# CONFIG_SND_DESIGNWARE_I2S is not set
-CONFIG_SND_DRIVERS=y
-# CONFIG_SND_DUMMY is not set
-# CONFIG_SND_DYNAMIC_MINORS is not set
-# CONFIG_SND_ECHO3G is not set
-# CONFIG_SND_EDMA_SOC is not set
-# CONFIG_SND_EMU10K1 is not set
-# CONFIG_SND_EMU10K1X is not set
-# CONFIG_SND_EMU10K1_SEQ is not set
-# CONFIG_SND_ENS1370 is not set
-# CONFIG_SND_ENS1371 is not set
-# CONFIG_SND_ES1688 is not set
-# CONFIG_SND_ES18XX is not set
-# CONFIG_SND_ES1938 is not set
-# CONFIG_SND_ES1968 is not set
-# CONFIG_SND_FIREWIRE is not set
-# CONFIG_SND_FM801 is not set
-# CONFIG_SND_GINA20 is not set
-# CONFIG_SND_GINA24 is not set
-# CONFIG_SND_GUSCLASSIC is not set
-# CONFIG_SND_GUSEXTREME is not set
-# CONFIG_SND_GUSMAX is not set
-# CONFIG_SND_HDA_CODEC_CS8409 is not set
-# CONFIG_SND_HDA_INTEL is not set
-# CONFIG_SND_HDA_INTEL_DETECT_DMIC is not set
-# CONFIG_SND_HDA_INTEL_HDMI_SILENT_STREAM is not set
-CONFIG_SND_HDA_POWER_SAVE_DEFAULT=0
-CONFIG_SND_HDA_PREALLOC_SIZE=64
-# CONFIG_SND_HDSP is not set
-# CONFIG_SND_HDSPM is not set
-# CONFIG_SND_HRTIMER is not set
-# CONFIG_SND_HWDEP is not set
-# CONFIG_SND_I2S_HI6210_I2S is not set
-# CONFIG_SND_ICE1712 is not set
-# CONFIG_SND_ICE1724 is not set
-# CONFIG_SND_INDIGO is not set
-# CONFIG_SND_INDIGODJ is not set
-# CONFIG_SND_INDIGODJX is not set
-# CONFIG_SND_INDIGOIO is not set
-# CONFIG_SND_INDIGOIOX is not set
-# CONFIG_SND_INTEL8X0 is not set
-# CONFIG_SND_INTEL8X0M is not set
-# CONFIG_SND_INTERWAVE is not set
-# CONFIG_SND_INTERWAVE_STB is not set
-# CONFIG_SND_ISA is not set
-# CONFIG_SND_JZ4740_SOC_I2S is not set
-# CONFIG_SND_KIRKWOOD_SOC is not set
-# CONFIG_SND_KORG1212 is not set
-# CONFIG_SND_LAYLA20 is not set
-# CONFIG_SND_LAYLA24 is not set
-# CONFIG_SND_LOLA is not set
-# CONFIG_SND_LX6464ES is not set
-# CONFIG_SND_MAESTRO3 is not set
-CONFIG_SND_MAX_CARDS=16
-# CONFIG_SND_MIA is not set
-# CONFIG_SND_MIPS is not set
-# CONFIG_SND_MIRO is not set
-# CONFIG_SND_MIXART is not set
-# CONFIG_SND_MIXER_OSS is not set
-# CONFIG_SND_MONA is not set
-# CONFIG_SND_MPC52xx_SOC_EFIKA is not set
-# CONFIG_SND_MPU401 is not set
-# CONFIG_SND_MTPAV is not set
-# CONFIG_SND_MTS64 is not set
-# CONFIG_SND_MXS_SOC is not set
-# CONFIG_SND_NM256 is not set
-# CONFIG_SND_OPL3SA2 is not set
-# CONFIG_SND_OPL3_LIB_SEQ is not set
-# CONFIG_SND_OPL4_LIB_SEQ is not set
-# CONFIG_SND_OPTI92X_AD1848 is not set
-# CONFIG_SND_OPTI92X_CS4231 is not set
-# CONFIG_SND_OPTI93X is not set
-CONFIG_SND_OSSEMUL=y
-# CONFIG_SND_OXYGEN is not set
-CONFIG_SND_PCI=y
-# CONFIG_SND_PCM is not set
-# CONFIG_SND_PCMCIA is not set
-# CONFIG_SND_PCM_OSS is not set
-CONFIG_SND_PCM_OSS_PLUGINS=y
-# CONFIG_SND_PCM_TIMER is not set
-# CONFIG_SND_PCM_XRUN_DEBUG is not set
-# CONFIG_SND_PCXHR is not set
-# CONFIG_SND_PDAUDIOCF is not set
-# CONFIG_SND_PORTMAN2X4 is not set
-# CONFIG_SND_POWERPC_SOC is not set
-# CONFIG_SND_PPC is not set
-CONFIG_SND_PROC_FS=y
-# CONFIG_SND_RAWMIDI is not set
-# CONFIG_SND_RAWMIDI_SEQ is not set
-# CONFIG_SND_RIPTIDE is not set
-# CONFIG_SND_RME32 is not set
-# CONFIG_SND_RME96 is not set
-# CONFIG_SND_RME9652 is not set
-# CONFIG_SND_RTCTIMER is not set
-# CONFIG_SND_SB16 is not set
-# CONFIG_SND_SB8 is not set
-# CONFIG_SND_SBAWE is not set
-# CONFIG_SND_SBAWE_SEQ is not set
-# CONFIG_SND_SE6X is not set
-# CONFIG_SND_SEQUENCER is not set
-# CONFIG_SND_SERIAL_U16550 is not set
-# CONFIG_SND_SIMPLE_CARD is not set
-# CONFIG_SND_SIMPLE_SCU_CARD is not set
-# CONFIG_SND_SIS7019 is not set
-# CONFIG_SND_SOC is not set
-# CONFIG_SND_SOC_AC97_CODEC is not set
-# CONFIG_SND_SOC_AD193X_I2C is not set
-# CONFIG_SND_SOC_AD193X_SPI is not set
-# CONFIG_SND_SOC_ADAU1372_I2C is not set
-# CONFIG_SND_SOC_ADAU1372_SPI is not set
-# CONFIG_SND_SOC_ADAU1701 is not set
-# CONFIG_SND_SOC_ADAU1761_I2C is not set
-# CONFIG_SND_SOC_ADAU1761_SPI is not set
-# CONFIG_SND_SOC_ADAU7002 is not set
-# CONFIG_SND_SOC_ADAU7118_HW is not set
-# CONFIG_SND_SOC_ADAU7118_I2C is not set
-# CONFIG_SND_SOC_ADI is not set
-# CONFIG_SND_SOC_AK4104 is not set
-# CONFIG_SND_SOC_AK4118 is not set
-# CONFIG_SND_SOC_AK4458 is not set
-# CONFIG_SND_SOC_AK4554 is not set
-# CONFIG_SND_SOC_AK4613 is not set
-# CONFIG_SND_SOC_AK4642 is not set
-# CONFIG_SND_SOC_AK5386 is not set
-# CONFIG_SND_SOC_AK5558 is not set
-# CONFIG_SND_SOC_ALC5623 is not set
-# CONFIG_SND_SOC_AMD_ACP is not set
-# CONFIG_SND_SOC_AMD_ACP3x is not set
-# CONFIG_SND_SOC_AMD_ACP5x is not set
-# CONFIG_SND_SOC_AMD_RENOIR is not set
-# CONFIG_SND_SOC_AU1XAUDIO is not set
-# CONFIG_SND_SOC_AU1XPSC is not set
-# CONFIG_SND_SOC_BD28623 is not set
-# CONFIG_SND_SOC_BT_SCO is not set
-# CONFIG_SND_SOC_CS35L32 is not set
-# CONFIG_SND_SOC_CS35L33 is not set
-# CONFIG_SND_SOC_CS35L34 is not set
-# CONFIG_SND_SOC_CS35L35 is not set
-# CONFIG_SND_SOC_CS35L36 is not set
-# CONFIG_SND_SOC_CS4234 is not set
-# CONFIG_SND_SOC_CS4265 is not set
-# CONFIG_SND_SOC_CS4270 is not set
-# CONFIG_SND_SOC_CS4271 is not set
-# CONFIG_SND_SOC_CS4271_I2C is not set
-# CONFIG_SND_SOC_CS4271_SPI is not set
-# CONFIG_SND_SOC_CS42L42 is not set
-# CONFIG_SND_SOC_CS42L51_I2C is not set
-# CONFIG_SND_SOC_CS42L52 is not set
-# CONFIG_SND_SOC_CS42L56 is not set
-# CONFIG_SND_SOC_CS42L73 is not set
-# CONFIG_SND_SOC_CS42XX8_I2C is not set
-# CONFIG_SND_SOC_CS43130 is not set
-# CONFIG_SND_SOC_CS4341 is not set
-# CONFIG_SND_SOC_CS4349 is not set
-# CONFIG_SND_SOC_CS53L30 is not set
-# CONFIG_SND_SOC_CX2072X is not set
-# CONFIG_SND_SOC_DA7213 is not set
-# CONFIG_SND_SOC_DIO2125 is not set
-# CONFIG_SND_SOC_DMIC is not set
-# CONFIG_SND_SOC_ES7134 is not set
-# CONFIG_SND_SOC_ES7241 is not set
-# CONFIG_SND_SOC_ES8316 is not set
-# CONFIG_SND_SOC_ES8328 is not set
-# CONFIG_SND_SOC_ES8328_I2C is not set
-# CONFIG_SND_SOC_ES8328_SPI is not set
-# CONFIG_SND_SOC_EUKREA_TLV320 is not set
-# CONFIG_SND_SOC_FSL_ASOC_CARD is not set
-# CONFIG_SND_SOC_FSL_ASRC is not set
-# CONFIG_SND_SOC_FSL_AUD2HTX is not set
-# CONFIG_SND_SOC_FSL_AUDMIX is not set
-# CONFIG_SND_SOC_FSL_ESAI is not set
-# CONFIG_SND_SOC_FSL_MICFIL is not set
-# CONFIG_SND_SOC_FSL_RPMSG is not set
-# CONFIG_SND_SOC_FSL_SAI is not set
-# CONFIG_SND_SOC_FSL_SPDIF is not set
-# CONFIG_SND_SOC_FSL_SSI is not set
-# CONFIG_SND_SOC_FSL_XCVR is not set
-# CONFIG_SND_SOC_GTM601 is not set
-# CONFIG_SND_SOC_ICS43432 is not set
-# CONFIG_SND_SOC_IMG is not set
-# CONFIG_SND_SOC_IMX_AUDMIX is not set
-# CONFIG_SND_SOC_IMX_AUDMUX is not set
-# CONFIG_SND_SOC_IMX_CARD is not set
-# CONFIG_SND_SOC_IMX_ES8328 is not set
-# CONFIG_SND_SOC_IMX_HDMI is not set
-# CONFIG_SND_SOC_IMX_RPMSG is not set
-# CONFIG_SND_SOC_IMX_SPDIF is not set
-# CONFIG_SND_SOC_IMX_WM8962 is not set
-# CONFIG_SND_SOC_INNO_RK3036 is not set
-# CONFIG_SND_SOC_INTEL_APL is not set
-# CONFIG_SND_SOC_INTEL_BAYTRAIL is not set
-# CONFIG_SND_SOC_INTEL_BDW_RT5677_MACH is not set
-# CONFIG_SND_SOC_INTEL_BXT_DA7219_MAX98357A_MACH is not set
-# CONFIG_SND_SOC_INTEL_BXT_RT298_MACH is not set
-# CONFIG_SND_SOC_INTEL_BYTCR_RT5640_MACH is not set
-# CONFIG_SND_SOC_INTEL_BYTCR_RT5651_MACH is not set
-# CONFIG_SND_SOC_INTEL_BYT_CHT_DA7213_MACH is not set
-# CONFIG_SND_SOC_INTEL_BYT_CHT_ES8316_MACH is not set
-# CONFIG_SND_SOC_INTEL_BYT_CHT_NOCODEC_MACH is not set
-# CONFIG_SND_SOC_INTEL_BYT_MAX98090_MACH is not set
-# CONFIG_SND_SOC_INTEL_BYT_RT5640_MACH is not set
-# CONFIG_SND_SOC_INTEL_CATPT is not set
-# CONFIG_SND_SOC_INTEL_CFL is not set
-# CONFIG_SND_SOC_INTEL_CHT_BSW_MAX98090_TI_MACH is not set
-# CONFIG_SND_SOC_INTEL_CHT_BSW_NAU8824_MACH is not set
-# CONFIG_SND_SOC_INTEL_CHT_BSW_RT5645_MACH is not set
-# CONFIG_SND_SOC_INTEL_CHT_BSW_RT5672_MACH is not set
-# CONFIG_SND_SOC_INTEL_CML_H is not set
-# CONFIG_SND_SOC_INTEL_CML_LP is not set
-# CONFIG_SND_SOC_INTEL_CNL is not set
-# CONFIG_SND_SOC_INTEL_GLK is not set
-# CONFIG_SND_SOC_INTEL_HASWELL is not set
-# CONFIG_SND_SOC_INTEL_KBL is not set
-# CONFIG_SND_SOC_INTEL_KBL_RT5663_MAX98927_MACH is not set
-# CONFIG_SND_SOC_INTEL_KBL_RT5663_RT5514_MAX98927_MACH is not set
-# CONFIG_SND_SOC_INTEL_KEEMBAY is not set
-# CONFIG_SND_SOC_INTEL_SKL is not set
-# CONFIG_SND_SOC_INTEL_SKL_NAU88L25_MAX98357A_MACH is not set
-# CONFIG_SND_SOC_INTEL_SKL_NAU88L25_SSM4567_MACH is not set
-# CONFIG_SND_SOC_INTEL_SKL_RT286_MACH is not set
-# CONFIG_SND_SOC_INTEL_SKYLAKE is not set
-# CONFIG_SND_SOC_INTEL_SST is not set
-CONFIG_SND_SOC_INTEL_SST_TOPLEVEL=y
-# CONFIG_SND_SOC_INTEL_USER_FRIENDLY_LONG_NAMES is not set
-# CONFIG_SND_SOC_JZ4725B_CODEC is not set
-# CONFIG_SND_SOC_JZ4740_CODEC is not set
-# CONFIG_SND_SOC_JZ4770_CODEC is not set
-# CONFIG_SND_SOC_LPASS_RX_MACRO is not set
-# CONFIG_SND_SOC_LPASS_TX_MACRO is not set
-# CONFIG_SND_SOC_LPASS_VA_MACRO is not set
-# CONFIG_SND_SOC_LPASS_WSA_MACRO is not set
-# CONFIG_SND_SOC_MA120X0P is not set
-# CONFIG_SND_SOC_MAX9759 is not set
-# CONFIG_SND_SOC_MAX98088 is not set
-# CONFIG_SND_SOC_MAX98357A is not set
-# CONFIG_SND_SOC_MAX98373 is not set
-# CONFIG_SND_SOC_MAX98373_I2C is not set
-# CONFIG_SND_SOC_MAX98390 is not set
-# CONFIG_SND_SOC_MAX98504 is not set
-# CONFIG_SND_SOC_MAX9860 is not set
-# CONFIG_SND_SOC_MAX9867 is not set
-# CONFIG_SND_SOC_MAX98927 is not set
-# CONFIG_SND_SOC_MEDIATEK is not set
-# CONFIG_SND_SOC_MPC5200_AC97 is not set
-# CONFIG_SND_SOC_MPC5200_I2S is not set
-# CONFIG_SND_SOC_MSM8916_WCD_ANALOG is not set
-# CONFIG_SND_SOC_MSM8916_WCD_DIGITAL is not set
-# CONFIG_SND_SOC_MT2701 is not set
-# CONFIG_SND_SOC_MT6351 is not set
-# CONFIG_SND_SOC_MT6358 is not set
-# CONFIG_SND_SOC_MT6359 is not set
-# CONFIG_SND_SOC_MT6359_ACCDET is not set
-# CONFIG_SND_SOC_MT6660 is not set
-# CONFIG_SND_SOC_MT6797 is not set
-# CONFIG_SND_SOC_MT8173 is not set
-# CONFIG_SND_SOC_MT8183 is not set
-# CONFIG_SND_SOC_MT8192 is not set
-# CONFIG_SND_SOC_MT8195 is not set
-# CONFIG_SND_SOC_MTK_BTCVSD is not set
-# CONFIG_SND_SOC_NAU8315 is not set
-# CONFIG_SND_SOC_NAU8540 is not set
-# CONFIG_SND_SOC_NAU8810 is not set
-# CONFIG_SND_SOC_NAU8822 is not set
-# CONFIG_SND_SOC_NAU8824 is not set
-# CONFIG_SND_SOC_PCM1681 is not set
-# CONFIG_SND_SOC_PCM1789_I2C is not set
-# CONFIG_SND_SOC_PCM1792A is not set
-# CONFIG_SND_SOC_PCM179X_I2C is not set
-# CONFIG_SND_SOC_PCM179X_SPI is not set
-# CONFIG_SND_SOC_PCM186X_I2C is not set
-# CONFIG_SND_SOC_PCM186X_SPI is not set
-# CONFIG_SND_SOC_PCM3060_I2C is not set
-# CONFIG_SND_SOC_PCM3060_SPI is not set
-# CONFIG_SND_SOC_PCM3168A_I2C is not set
-# CONFIG_SND_SOC_PCM3168A_SPI is not set
-# CONFIG_SND_SOC_PCM5102A is not set
-# CONFIG_SND_SOC_PCM512x_I2C is not set
-# CONFIG_SND_SOC_PCM512x_SPI is not set
-# CONFIG_SND_SOC_QCOM is not set
-# CONFIG_SND_SOC_RK3328 is not set
-# CONFIG_SND_SOC_RK817 is not set
-# CONFIG_SND_SOC_ROCKCHIP is not set
-# CONFIG_SND_SOC_RT5616 is not set
-# CONFIG_SND_SOC_RT5631 is not set
-# CONFIG_SND_SOC_RT5640 is not set
-# CONFIG_SND_SOC_RT5659 is not set
-# CONFIG_SND_SOC_RT5677_SPI is not set
-# CONFIG_SND_SOC_SGTL5000 is not set
-# CONFIG_SND_SOC_SIMPLE_AMPLIFIER is not set
-# CONFIG_SND_SOC_SIMPLE_MUX is not set
-# CONFIG_SND_SOC_SIRF_AUDIO_CODEC is not set
-# CONFIG_SND_SOC_SOF_TOPLEVEL is not set
-# CONFIG_SND_SOC_SPDIF is not set
-# CONFIG_SND_SOC_SSM2305 is not set
-# CONFIG_SND_SOC_SSM2518 is not set
-# CONFIG_SND_SOC_SSM2602_I2C is not set
-# CONFIG_SND_SOC_SSM2602_SPI is not set
-# CONFIG_SND_SOC_SSM4567 is not set
-# CONFIG_SND_SOC_STA32X is not set
-# CONFIG_SND_SOC_STA350 is not set
-# CONFIG_SND_SOC_STI_SAS is not set
-# CONFIG_SND_SOC_TAS2552 is not set
-# CONFIG_SND_SOC_TAS2562 is not set
-# CONFIG_SND_SOC_TAS2764 is not set
-# CONFIG_SND_SOC_TAS2770 is not set
-# CONFIG_SND_SOC_TAS5086 is not set
-# CONFIG_SND_SOC_TAS571X is not set
-# CONFIG_SND_SOC_TAS5720 is not set
-# CONFIG_SND_SOC_TAS6424 is not set
-# CONFIG_SND_SOC_TDA7419 is not set
-# CONFIG_SND_SOC_TFA9879 is not set
-# CONFIG_SND_SOC_TFA989X is not set
-# CONFIG_SND_SOC_TLV320ADCX140 is not set
-# CONFIG_SND_SOC_TLV320AIC23_I2C is not set
-# CONFIG_SND_SOC_TLV320AIC23_SPI is not set
-# CONFIG_SND_SOC_TLV320AIC31XX is not set
-# CONFIG_SND_SOC_TLV320AIC32X4_I2C is not set
-# CONFIG_SND_SOC_TLV320AIC32X4_SPI is not set
-# CONFIG_SND_SOC_TLV320AIC3X is not set
-# CONFIG_SND_SOC_TLV320AIC3X_I2C is not set
-# CONFIG_SND_SOC_TLV320AIC3X_SPI is not set
-# CONFIG_SND_SOC_TPA6130A2 is not set
-# CONFIG_SND_SOC_TS3A227E is not set
-# CONFIG_SND_SOC_TSCS42XX is not set
-# CONFIG_SND_SOC_TSCS454 is not set
-# CONFIG_SND_SOC_UDA1334 is not set
-# CONFIG_SND_SOC_WM8510 is not set
-# CONFIG_SND_SOC_WM8523 is not set
-# CONFIG_SND_SOC_WM8524 is not set
-# CONFIG_SND_SOC_WM8580 is not set
-# CONFIG_SND_SOC_WM8711 is not set
-# CONFIG_SND_SOC_WM8728 is not set
-# CONFIG_SND_SOC_WM8731 is not set
-# CONFIG_SND_SOC_WM8737 is not set
-# CONFIG_SND_SOC_WM8741 is not set
-# CONFIG_SND_SOC_WM8750 is not set
-# CONFIG_SND_SOC_WM8753 is not set
-# CONFIG_SND_SOC_WM8770 is not set
-# CONFIG_SND_SOC_WM8776 is not set
-# CONFIG_SND_SOC_WM8782 is not set
-# CONFIG_SND_SOC_WM8804_I2C is not set
-# CONFIG_SND_SOC_WM8804_SPI is not set
-# CONFIG_SND_SOC_WM8903 is not set
-# CONFIG_SND_SOC_WM8904 is not set
-# CONFIG_SND_SOC_WM8960 is not set
-# CONFIG_SND_SOC_WM8962 is not set
-# CONFIG_SND_SOC_WM8974 is not set
-# CONFIG_SND_SOC_WM8978 is not set
-# CONFIG_SND_SOC_WM8985 is not set
-# CONFIG_SND_SOC_XILINX_AUDIO_FORMATTER is not set
-# CONFIG_SND_SOC_XILINX_I2S is not set
-# CONFIG_SND_SOC_XILINX_SPDIF is not set
-# CONFIG_SND_SOC_XTFPGA_I2S is not set
-# CONFIG_SND_SOC_ZL38060 is not set
-# CONFIG_SND_SOC_ZX_AUD96P22 is not set
-# CONFIG_SND_SONICVIBES is not set
-# CONFIG_SND_SPI is not set
-# CONFIG_SND_SSCAPE is not set
-# CONFIG_SND_SST_ATOM_HIFI2_PLATFORM_ACPI is not set
-# CONFIG_SND_SST_ATOM_HIFI2_PLATFORM_PCI is not set
-# CONFIG_SND_SUN4I_CODEC is not set
-# CONFIG_SND_SUPPORT_OLD_API is not set
-# CONFIG_SND_TIMER is not set
-# CONFIG_SND_TRIDENT is not set
-CONFIG_SND_USB=y
-# CONFIG_SND_USB_6FIRE is not set
-# CONFIG_SND_USB_AUDIO is not set
-# CONFIG_SND_USB_CAIAQ is not set
-# CONFIG_SND_USB_HIFACE is not set
-# CONFIG_SND_USB_POD is not set
-# CONFIG_SND_USB_PODHD is not set
-# CONFIG_SND_USB_TONEPORT is not set
-# CONFIG_SND_USB_UA101 is not set
-# CONFIG_SND_USB_US122L is not set
-# CONFIG_SND_USB_USX2Y is not set
-# CONFIG_SND_USB_VARIAX is not set
-# CONFIG_SND_VERBOSE_PRINTK is not set
-CONFIG_SND_VERBOSE_PROCFS=y
-# CONFIG_SND_VIA82XX is not set
-# CONFIG_SND_VIA82XX_MODEM is not set
-# CONFIG_SND_VIRTIO is not set
-# CONFIG_SND_VIRTUOSO is not set
-# CONFIG_SND_VX222 is not set
-# CONFIG_SND_VXPOCKET is not set
-# CONFIG_SND_WAVEFRONT is not set
-CONFIG_SND_X86=y
-# CONFIG_SND_XEN_FRONTEND is not set
-# CONFIG_SND_YMFPCI is not set
-# CONFIG_SNI_RM is not set
-# CONFIG_SOCIONEXT_SYNQUACER_PREITS is not set
-# CONFIG_SOCK_CGROUP_DATA is not set
-# CONFIG_SOC_AM33XX is not set
-# CONFIG_SOC_AM43XX is not set
-# CONFIG_SOC_BRCMSTB is not set
-# CONFIG_SOC_CAMERA is not set
-# CONFIG_SOC_DRA7XX is not set
-# CONFIG_SOC_HAS_OMAP2_SDRC is not set
-# CONFIG_SOC_OMAP5 is not set
-# CONFIG_SOC_TI is not set
-# CONFIG_SOFTLOCKUP_DETECTOR is not set
-# CONFIG_SOFT_WATCHDOG is not set
-# CONFIG_SOLARIS_X86_PARTITION is not set
-# CONFIG_SONYPI is not set
-# CONFIG_SONY_LAPTOP is not set
-# CONFIG_SOUND is not set
-# CONFIG_SOUNDWIRE is not set
-# CONFIG_SOUND_OSS_CORE is not set
-# CONFIG_SOUND_OSS_CORE_PRECLAIM is not set
-# CONFIG_SOUND_PRIME is not set
-# CONFIG_SP5100_TCO is not set
-# CONFIG_SPARSEMEM_MANUAL is not set
-# CONFIG_SPARSEMEM_STATIC is not set
-# CONFIG_SPARSEMEM_VMEMMAP_ENABLE is not set
-# CONFIG_SPARSE_IRQ is not set
-# CONFIG_SPARSE_RCU_POINTER is not set
-# CONFIG_SPEAKUP is not set
-# CONFIG_SPI is not set
-# CONFIG_SPINLOCK_TEST is not set
-# CONFIG_SPI_ALTERA is not set
-# CONFIG_SPI_AMD is not set
-# CONFIG_SPI_AU1550 is not set
-# CONFIG_SPI_AXI_SPI_ENGINE is not set
-# CONFIG_SPI_BCM2835 is not set
-# CONFIG_SPI_BCM_QSPI is not set
-# CONFIG_SPI_BITBANG is not set
-# CONFIG_SPI_BUTTERFLY is not set
-# CONFIG_SPI_CADENCE is not set
-# CONFIG_SPI_CADENCE_QUADSPI is not set
-# CONFIG_SPI_DEBUG is not set
-# CONFIG_SPI_DESIGNWARE is not set
-# CONFIG_SPI_FSL_DSPI is not set
-# CONFIG_SPI_FSL_ESPI is not set
-# CONFIG_SPI_FSL_SPI is not set
-# CONFIG_SPI_GPIO is not set
-# CONFIG_SPI_GPIO_OLD is not set
-# CONFIG_SPI_IMG_SPFI is not set
-# CONFIG_SPI_LANTIQ_SSC is not set
-# CONFIG_SPI_LM70_LLP is not set
-# CONFIG_SPI_LOOPBACK_TEST is not set
-# CONFIG_SPI_MASTER is not set
-# CONFIG_SPI_MEM is not set
-# CONFIG_SPI_MPC52xx is not set
-# CONFIG_SPI_MPC52xx_PSC is not set
-# CONFIG_SPI_MTK_QUADSPI is not set
-# CONFIG_SPI_MUX is not set
-# CONFIG_SPI_MXIC is not set
-# CONFIG_SPI_NXP_FLEXSPI is not set
-# CONFIG_SPI_OCTEON is not set
-# CONFIG_SPI_OC_TINY is not set
-# CONFIG_SPI_ORION is not set
-# CONFIG_SPI_PL022 is not set
-# CONFIG_SPI_PPC4xx is not set
-# CONFIG_SPI_PXA2XX is not set
-# CONFIG_SPI_PXA2XX_PCI is not set
-# CONFIG_SPI_QCOM_QSPI is not set
-# CONFIG_SPI_ROCKCHIP is not set
-# CONFIG_SPI_S3C64XX is not set
-# CONFIG_SPI_SC18IS602 is not set
-# CONFIG_SPI_SIFIVE is not set
-# CONFIG_SPI_SLAVE is not set
-# CONFIG_SPI_SPIDEV is not set
-# CONFIG_SPI_THUNDERX is not set
-# CONFIG_SPI_TI_QSPI is not set
-# CONFIG_SPI_TLE62X0 is not set
-# CONFIG_SPI_TOPCLIFF_PCH is not set
-# CONFIG_SPI_XCOMM is not set
-# CONFIG_SPI_XILINX is not set
-# CONFIG_SPI_XWAY is not set
-# CONFIG_SPI_ZYNQMP_GQSPI is not set
-CONFIG_SPLIT_PTLOCK_CPUS=4
-# CONFIG_SPMI is not set
-# CONFIG_SPS30 is not set
-# CONFIG_SPS30_I2C is not set
-# CONFIG_SPS30_SERIAL is not set
-CONFIG_SQUASHFS=y
-# CONFIG_SQUASHFS_4K_DEVBLK_SIZE is not set
-# CONFIG_SQUASHFS_DECOMP_MULTI is not set
-CONFIG_SQUASHFS_DECOMP_MULTI_PERCPU=y
-# CONFIG_SQUASHFS_DECOMP_SINGLE is not set
-CONFIG_SQUASHFS_EMBEDDED=y
-# CONFIG_SQUASHFS_FILE_CACHE is not set
-CONFIG_SQUASHFS_FILE_DIRECT=y
-CONFIG_SQUASHFS_FRAGMENT_CACHE_SIZE=3
-# CONFIG_SQUASHFS_LZ4 is not set
-# CONFIG_SQUASHFS_LZO is not set
-# CONFIG_SQUASHFS_XATTR is not set
-CONFIG_SQUASHFS_XZ=y
-# CONFIG_SQUASHFS_ZLIB is not set
-# CONFIG_SQUASHFS_ZSTD is not set
-# CONFIG_SRAM is not set
-# CONFIG_SRF04 is not set
-# CONFIG_SRF08 is not set
-# CONFIG_SSB is not set
-# CONFIG_SSB_DEBUG is not set
-# CONFIG_SSB_DRIVER_GPIO is not set
-# CONFIG_SSB_HOST_SOC is not set
-# CONFIG_SSB_PCMCIAHOST is not set
-CONFIG_SSB_POSSIBLE=y
-# CONFIG_SSB_SDIOHOST is not set
-# CONFIG_SSB_SILENT is not set
-# CONFIG_SSFDC is not set
-# CONFIG_STACKPROTECTOR is not set
-# CONFIG_STACKPROTECTOR_STRONG is not set
-# CONFIG_STACKTRACE is not set
-# CONFIG_STACKTRACE_BUILD_ID is not set
-CONFIG_STACKTRACE_SUPPORT=y
-CONFIG_STACK_HASH_ORDER=20
-# CONFIG_STACK_TRACER is not set
-# CONFIG_STACK_VALIDATION is not set
-CONFIG_STAGING=y
-# CONFIG_STAGING_BOARD is not set
-# CONFIG_STAGING_GASKET_FRAMEWORK is not set
-# CONFIG_STAGING_MEDIA is not set
-CONFIG_STANDALONE=y
-# CONFIG_STATIC_KEYS_SELFTEST is not set
-# CONFIG_STATIC_USERMODEHELPER is not set
-CONFIG_STDBINUTILS=y
-# CONFIG_STE10XP is not set
-# CONFIG_STE_MODEM_RPROC is not set
-# CONFIG_STK3310 is not set
-# CONFIG_STK8312 is not set
-# CONFIG_STK8BA50 is not set
-# CONFIG_STM is not set
-# CONFIG_STMMAC_ETH is not set
-# CONFIG_STMMAC_PCI is not set
-# CONFIG_STMMAC_PLATFORM is not set
-# CONFIG_STMMAC_SELFTESTS is not set
-# CONFIG_STM_DUMMY is not set
-# CONFIG_STM_SOURCE_CONSOLE is not set
-CONFIG_STP=y
-# CONFIG_STREAM_PARSER is not set
-# CONFIG_STRICT_DEVMEM is not set
-CONFIG_STRICT_KERNEL_RWX=y
-CONFIG_STRICT_MODULE_RWX=y
-# CONFIG_STRING_SELFTEST is not set
-CONFIG_STRIP_ASM_SYMS=y
-# CONFIG_STX104 is not set
-# CONFIG_ST_UVIS25 is not set
-# CONFIG_SUN4I_GPADC is not set
-# CONFIG_SUN50I_DE2_BUS is not set
-# CONFIG_SUN50I_ERRATUM_UNKNOWN1 is not set
-# CONFIG_SUNDANCE is not set
-# CONFIG_SUNGEM is not set
-# CONFIG_SUNRPC is not set
-# CONFIG_SUNRPC_DEBUG is not set
-CONFIG_SUNRPC_DISABLE_INSECURE_ENCTYPES=y
-# CONFIG_SUNRPC_GSS is not set
-# CONFIG_SUNXI_SRAM is not set
-# CONFIG_SUN_PARTITION is not set
-# CONFIG_SURFACE_3_BUTTON is not set
-# CONFIG_SUSPEND is not set
-# CONFIG_SUSPEND_SKIP_SYNC is not set
-CONFIG_SWAP=y
-# CONFIG_SWCONFIG is not set
-# CONFIG_SWCONFIG_B53 is not set
-# CONFIG_SWCONFIG_B53_MDIO_DRIVER is not set
-# CONFIG_SWCONFIG_B53_MMAP_DRIVER is not set
-# CONFIG_SWCONFIG_B53_SPI_DRIVER is not set
-# CONFIG_SWCONFIG_B53_SRAB_DRIVER is not set
-# CONFIG_SWCONFIG_LEDS is not set
-# CONFIG_SW_SYNC is not set
-# CONFIG_SX9310 is not set
-# CONFIG_SX9500 is not set
-# CONFIG_SXGBE_ETH is not set
-CONFIG_SYMBOLIC_ERRNAME=y
-# CONFIG_SYNCLINK_CS is not set
-# CONFIG_SYNC_FILE is not set
-# CONFIG_SYNOPSYS_DWC_ETH_QOS is not set
-# CONFIG_SYNTH_EVENTS is not set
-# CONFIG_SYNTH_EVENT_GEN_TEST is not set
-CONFIG_SYN_COOKIES=y
-# CONFIG_SYSCON_REBOOT_MODE is not set
-CONFIG_SYSCTL=y
-# CONFIG_SYSCTL_SYSCALL is not set
-CONFIG_SYSFS=y
-# CONFIG_SYSFS_DEPRECATED is not set
-# CONFIG_SYSFS_DEPRECATED_V2 is not set
-# CONFIG_SYSFS_SYSCALL is not set
-# CONFIG_SYSTEMPORT is not set
-# CONFIG_SYSTEM_BLACKLIST_KEYRING is not set
-# CONFIG_SYSTEM_DATA_VERIFICATION is not set
-# CONFIG_SYSTEM_TRUSTED_KEYRING is not set
-CONFIG_SYSTEM_TRUSTED_KEYS=""
-# CONFIG_SYSV68_PARTITION is not set
-CONFIG_SYSVIPC=y
-CONFIG_SYSVIPC_SYSCTL=y
-# CONFIG_SYSV_FS is not set
-# CONFIG_SYS_HYPERVISOR is not set
-# CONFIG_T5403 is not set
-# CONFIG_TARGET_CORE is not set
-# CONFIG_TASKSTATS is not set
-# CONFIG_TASKS_RCU is not set
-# CONFIG_TASK_XACCT is not set
-# CONFIG_TC35815 is not set
-# CONFIG_TCG_ATMEL is not set
-# CONFIG_TCG_CRB is not set
-# CONFIG_TCG_FTPM_TEE is not set
-# CONFIG_TCG_INFINEON is not set
-# CONFIG_TCG_NSC is not set
-# CONFIG_TCG_ST33_I2C is not set
-# CONFIG_TCG_TIS is not set
-# CONFIG_TCG_TIS_I2C_ATMEL is not set
-# CONFIG_TCG_TIS_I2C_CR50 is not set
-# CONFIG_TCG_TIS_I2C_INFINEON is not set
-# CONFIG_TCG_TIS_I2C_NUVOTON is not set
-# CONFIG_TCG_TIS_SPI is not set
-# CONFIG_TCG_TIS_ST33ZP24_I2C is not set
-# CONFIG_TCG_TIS_ST33ZP24_SPI is not set
-# CONFIG_TCG_TPM is not set
-# CONFIG_TCG_VTPM_PROXY is not set
-# CONFIG_TCG_XEN is not set
-# CONFIG_TCIC is not set
-CONFIG_TCP_CONG_ADVANCED=y
-# CONFIG_TCP_CONG_BBR is not set
-# CONFIG_TCP_CONG_BIC is not set
-# CONFIG_TCP_CONG_CDG is not set
-CONFIG_TCP_CONG_CUBIC=y
-# CONFIG_TCP_CONG_DCTCP is not set
-# CONFIG_TCP_CONG_HSTCP is not set
-# CONFIG_TCP_CONG_HTCP is not set
-# CONFIG_TCP_CONG_HYBLA is not set
-# CONFIG_TCP_CONG_ILLINOIS is not set
-# CONFIG_TCP_CONG_LP is not set
-# CONFIG_TCP_CONG_NV is not set
-# CONFIG_TCP_CONG_SCALABLE is not set
-# CONFIG_TCP_CONG_VEGAS is not set
-# CONFIG_TCP_CONG_VENO is not set
-# CONFIG_TCP_CONG_WESTWOOD is not set
-# CONFIG_TCP_CONG_YEAH is not set
-# CONFIG_TCP_MD5SIG is not set
-# CONFIG_TCS3414 is not set
-# CONFIG_TCS3472 is not set
-# CONFIG_TEE is not set
-# CONFIG_TEGRA210_ADMA is not set
-# CONFIG_TEGRA_ACONNECT is not set
-# CONFIG_TEGRA_AHB is not set
-# CONFIG_TEGRA_HOST1X is not set
-# CONFIG_TEHUTI is not set
-# CONFIG_TERANETICS_PHY is not set
-# CONFIG_TEST_ASYNC_DRIVER_PROBE is not set
-# CONFIG_TEST_BITFIELD is not set
-# CONFIG_TEST_BITMAP is not set
-# CONFIG_TEST_BITOPS is not set
-# CONFIG_TEST_BLACKHOLE_DEV is not set
-# CONFIG_TEST_BPF is not set
-# CONFIG_TEST_CLOCKSOURCE_WATCHDOG is not set
-# CONFIG_TEST_DEBUG_VIRTUAL is not set
-# CONFIG_TEST_DIV64 is not set
-# CONFIG_TEST_FIRMWARE is not set
-# CONFIG_TEST_FREE_PAGES is not set
-# CONFIG_TEST_HASH is not set
-# CONFIG_TEST_HEXDUMP is not set
-# CONFIG_TEST_IDA is not set
-# CONFIG_TEST_KASAN_MODULE is not set
-# CONFIG_TEST_KMOD is not set
-# CONFIG_TEST_KSTRTOX is not set
-# CONFIG_TEST_LIST_SORT is not set
-# CONFIG_TEST_LKM is not set
-# CONFIG_TEST_LOCKUP is not set
-# CONFIG_TEST_MEMCAT_P is not set
-# CONFIG_TEST_MEMINIT is not set
-# CONFIG_TEST_MIN_HEAP is not set
-# CONFIG_TEST_OVERFLOW is not set
-# CONFIG_TEST_POWER is not set
-# CONFIG_TEST_PRINTF is not set
-# CONFIG_TEST_RHASHTABLE is not set
-# CONFIG_TEST_SCANF is not set
-# CONFIG_TEST_SORT is not set
-# CONFIG_TEST_STACKINIT is not set
-# CONFIG_TEST_STATIC_KEYS is not set
-# CONFIG_TEST_STRING_HELPERS is not set
-# CONFIG_TEST_STRSCPY is not set
-# CONFIG_TEST_SYSCTL is not set
-# CONFIG_TEST_UBSAN is not set
-# CONFIG_TEST_UDELAY is not set
-# CONFIG_TEST_USER_COPY is not set
-# CONFIG_TEST_UUID is not set
-# CONFIG_TEST_VMALLOC is not set
-# CONFIG_TEST_XARRAY is not set
-CONFIG_TEXTSEARCH=y
-# CONFIG_TEXTSEARCH_BM is not set
-# CONFIG_TEXTSEARCH_FSM is not set
-# CONFIG_TEXTSEARCH_KMP is not set
-# CONFIG_THERMAL is not set
-# CONFIG_THERMAL_DEFAULT_GOV_FAIR_SHARE is not set
-# CONFIG_THERMAL_DEFAULT_GOV_POWER_ALLOCATOR is not set
-# CONFIG_THERMAL_DEFAULT_GOV_USER_SPACE is not set
-# CONFIG_THERMAL_EMULATION is not set
-# CONFIG_THERMAL_GOV_BANG_BANG is not set
-# CONFIG_THERMAL_GOV_FAIR_SHARE is not set
-# CONFIG_THERMAL_GOV_POWER_ALLOCATOR is not set
-# CONFIG_THERMAL_GOV_USER_SPACE is not set
-# CONFIG_THERMAL_HWMON is not set
-# CONFIG_THERMAL_MMIO is not set
-# CONFIG_THERMAL_NETLINK is not set
-# CONFIG_THERMAL_STATISTICS is not set
-# CONFIG_THERMAL_WRITABLE_TRIPS is not set
-# CONFIG_THINKPAD_ACPI is not set
-CONFIG_THIN_ARCHIVES=y
-# CONFIG_THRUSTMASTER_FF is not set
-# CONFIG_THUMB2_KERNEL is not set
-# CONFIG_THUNDERBOLT is not set
-# CONFIG_THUNDER_NIC_BGX is not set
-# CONFIG_THUNDER_NIC_PF is not set
-# CONFIG_THUNDER_NIC_RGX is not set
-# CONFIG_THUNDER_NIC_VF is not set
-# CONFIG_TICK_CPU_ACCOUNTING is not set
-CONFIG_TICK_ONESHOT=y
-# CONFIG_TIFM_CORE is not set
-# CONFIG_TIGON3 is not set
-# CONFIG_TIMB_DMA is not set
-CONFIG_TIMERFD=y
-# CONFIG_TIMERLAT_TRACER is not set
-# CONFIG_TIMER_STATS is not set
-# CONFIG_TIME_NS is not set
-# CONFIG_TINYDRM_HX8357D is not set
-# CONFIG_TINYDRM_ILI9225 is not set
-# CONFIG_TINYDRM_ILI9341 is not set
-# CONFIG_TINYDRM_ILI9486 is not set
-# CONFIG_TINYDRM_MI0283QT is not set
-# CONFIG_TINYDRM_REPAPER is not set
-# CONFIG_TINYDRM_ST7586 is not set
-# CONFIG_TINYDRM_ST7735R is not set
-CONFIG_TINY_RCU=y
-# CONFIG_TIPC is not set
-# CONFIG_TI_ADC081C is not set
-# CONFIG_TI_ADC0832 is not set
-# CONFIG_TI_ADC084S021 is not set
-# CONFIG_TI_ADC108S102 is not set
-# CONFIG_TI_ADC12138 is not set
-# CONFIG_TI_ADC128S052 is not set
-# CONFIG_TI_ADC161S626 is not set
-# CONFIG_TI_ADS1015 is not set
-# CONFIG_TI_ADS124S08 is not set
-# CONFIG_TI_ADS131E08 is not set
-# CONFIG_TI_ADS7950 is not set
-# CONFIG_TI_ADS8344 is not set
-# CONFIG_TI_ADS8688 is not set
-# CONFIG_TI_AM335X_ADC is not set
-# CONFIG_TI_CPSW is not set
-# CONFIG_TI_CPSW_ALE is not set
-# CONFIG_TI_CPSW_PHY_SEL is not set
-# CONFIG_TI_CPTS is not set
-# CONFIG_TI_DAC082S085 is not set
-# CONFIG_TI_DAC5571 is not set
-# CONFIG_TI_DAC7311 is not set
-# CONFIG_TI_DAC7512 is not set
-# CONFIG_TI_DAC7612 is not set
-# CONFIG_TI_DAVINCI_CPDMA is not set
-# CONFIG_TI_DAVINCI_MDIO is not set
-# CONFIG_TI_ST is not set
-# CONFIG_TI_SYSCON_RESET is not set
-# CONFIG_TI_TLC4541 is not set
-# CONFIG_TI_TSC2046 is not set
-# CONFIG_TLAN is not set
-# CONFIG_TLS is not set
-# CONFIG_TLS_DEVICE is not set
-# CONFIG_TLS_TOE is not set
-# CONFIG_TMD_HERMES is not set
-# CONFIG_TMP006 is not set
-# CONFIG_TMP007 is not set
-# CONFIG_TMP117 is not set
-CONFIG_TMPFS=y
-# CONFIG_TMPFS_INODE64 is not set
-# CONFIG_TMPFS_POSIX_ACL is not set
-CONFIG_TMPFS_XATTR=y
-# CONFIG_TOPSTAR_LAPTOP is not set
-# CONFIG_TORTURE_TEST is not set
-# CONFIG_TOSHIBA_HAPS is not set
-# CONFIG_TOUCHSCREEN_88PM860X is not set
-# CONFIG_TOUCHSCREEN_AD7877 is not set
-# CONFIG_TOUCHSCREEN_AD7879 is not set
-# CONFIG_TOUCHSCREEN_AD7879_I2C is not set
-# CONFIG_TOUCHSCREEN_AD7879_SPI is not set
-# CONFIG_TOUCHSCREEN_ADC is not set
-# CONFIG_TOUCHSCREEN_ADS7846 is not set
-# CONFIG_TOUCHSCREEN_AR1021_I2C is not set
-# CONFIG_TOUCHSCREEN_ATMEL_MXT is not set
-# CONFIG_TOUCHSCREEN_ATMEL_MXT_T37 is not set
-# CONFIG_TOUCHSCREEN_AUO_PIXCIR is not set
-# CONFIG_TOUCHSCREEN_BU21013 is not set
-# CONFIG_TOUCHSCREEN_BU21029 is not set
-# CONFIG_TOUCHSCREEN_CHIPONE_ICN8318 is not set
-# CONFIG_TOUCHSCREEN_CHIPONE_ICN8505 is not set
-# CONFIG_TOUCHSCREEN_COLIBRI_VF50 is not set
-# CONFIG_TOUCHSCREEN_CY8CTMA140 is not set
-# CONFIG_TOUCHSCREEN_CY8CTMG110 is not set
-# CONFIG_TOUCHSCREEN_CYTTSP4_CORE is not set
-# CONFIG_TOUCHSCREEN_CYTTSP4_I2C is not set
-# CONFIG_TOUCHSCREEN_CYTTSP4_SPI is not set
-# CONFIG_TOUCHSCREEN_CYTTSP_CORE is not set
-# CONFIG_TOUCHSCREEN_CYTTSP_I2C is not set
-# CONFIG_TOUCHSCREEN_CYTTSP_SPI is not set
-# CONFIG_TOUCHSCREEN_DA9034 is not set
-# CONFIG_TOUCHSCREEN_DA9052 is not set
-# CONFIG_TOUCHSCREEN_DYNAPRO is not set
-# CONFIG_TOUCHSCREEN_EDT_FT5X06 is not set
-# CONFIG_TOUCHSCREEN_EETI is not set
-# CONFIG_TOUCHSCREEN_EGALAX is not set
-# CONFIG_TOUCHSCREEN_EGALAX_SERIAL is not set
-# CONFIG_TOUCHSCREEN_EKTF2127 is not set
-# CONFIG_TOUCHSCREEN_ELAN is not set
-# CONFIG_TOUCHSCREEN_ELO is not set
-# CONFIG_TOUCHSCREEN_EXC3000 is not set
-# CONFIG_TOUCHSCREEN_FUJITSU is not set
-# CONFIG_TOUCHSCREEN_GOODIX is not set
-# CONFIG_TOUCHSCREEN_GUNZE is not set
-# CONFIG_TOUCHSCREEN_HAMPSHIRE is not set
-# CONFIG_TOUCHSCREEN_HIDEEP is not set
-# CONFIG_TOUCHSCREEN_HP600 is not set
-# CONFIG_TOUCHSCREEN_HP7XX is not set
-# CONFIG_TOUCHSCREEN_HTCPEN is not set
-# CONFIG_TOUCHSCREEN_HYCON_HY46XX is not set
-# CONFIG_TOUCHSCREEN_ILI210X is not set
-# CONFIG_TOUCHSCREEN_ILITEK is not set
-# CONFIG_TOUCHSCREEN_IMX6UL_TSC is not set
-# CONFIG_TOUCHSCREEN_INEXIO is not set
-# CONFIG_TOUCHSCREEN_IPAQ_MICRO is not set
-# CONFIG_TOUCHSCREEN_IPROC is not set
-# CONFIG_TOUCHSCREEN_IQS5XX is not set
-# CONFIG_TOUCHSCREEN_LPC32XX is not set
-# CONFIG_TOUCHSCREEN_MAX11801 is not set
-# CONFIG_TOUCHSCREEN_MC13783 is not set
-# CONFIG_TOUCHSCREEN_MCS5000 is not set
-# CONFIG_TOUCHSCREEN_MELFAS_MIP4 is not set
-# CONFIG_TOUCHSCREEN_MIGOR is not set
-# CONFIG_TOUCHSCREEN_MK712 is not set
-# CONFIG_TOUCHSCREEN_MMS114 is not set
-# CONFIG_TOUCHSCREEN_MSG2638 is not set
-# CONFIG_TOUCHSCREEN_MTOUCH is not set
-# CONFIG_TOUCHSCREEN_MX25 is not set
-# CONFIG_TOUCHSCREEN_MXS_LRADC is not set
-# CONFIG_TOUCHSCREEN_PCAP is not set
-# CONFIG_TOUCHSCREEN_PENMOUNT is not set
-# CONFIG_TOUCHSCREEN_PIXCIR is not set
-# CONFIG_TOUCHSCREEN_PROPERTIES is not set
-# CONFIG_TOUCHSCREEN_RASPBERRYPI_FW is not set
-# CONFIG_TOUCHSCREEN_RM_TS is not set
-# CONFIG_TOUCHSCREEN_ROHM_BU21023 is not set
-# CONFIG_TOUCHSCREEN_RPI_FT5406 is not set
-# CONFIG_TOUCHSCREEN_S3C2410 is not set
-# CONFIG_TOUCHSCREEN_S6SY761 is not set
-# CONFIG_TOUCHSCREEN_SILEAD is not set
-# CONFIG_TOUCHSCREEN_SIS_I2C is not set
-# CONFIG_TOUCHSCREEN_ST1232 is not set
-# CONFIG_TOUCHSCREEN_STMFTS is not set
-# CONFIG_TOUCHSCREEN_STMPE is not set
-# CONFIG_TOUCHSCREEN_SUN4I is not set
-# CONFIG_TOUCHSCREEN_SUR40 is not set
-# CONFIG_TOUCHSCREEN_SURFACE3_SPI is not set
-# CONFIG_TOUCHSCREEN_SX8654 is not set
-# CONFIG_TOUCHSCREEN_TI_AM335X_TSC is not set
-# CONFIG_TOUCHSCREEN_TOUCHIT213 is not set
-# CONFIG_TOUCHSCREEN_TOUCHRIGHT is not set
-# CONFIG_TOUCHSCREEN_TOUCHWIN is not set
-# CONFIG_TOUCHSCREEN_TPS6507X is not set
-# CONFIG_TOUCHSCREEN_TS4800 is not set
-# CONFIG_TOUCHSCREEN_TSC2004 is not set
-# CONFIG_TOUCHSCREEN_TSC2005 is not set
-# CONFIG_TOUCHSCREEN_TSC2007 is not set
-# CONFIG_TOUCHSCREEN_TSC2007_IIO is not set
-# CONFIG_TOUCHSCREEN_TSC200X_CORE is not set
-# CONFIG_TOUCHSCREEN_TSC_SERIO is not set
-# CONFIG_TOUCHSCREEN_UCB1400 is not set
-# CONFIG_TOUCHSCREEN_USB_3M is not set
-# CONFIG_TOUCHSCREEN_USB_COMPOSITE is not set
-# CONFIG_TOUCHSCREEN_USB_DMC_TSC10 is not set
-# CONFIG_TOUCHSCREEN_USB_E2I is not set
-# CONFIG_TOUCHSCREEN_USB_EASYTOUCH is not set
-# CONFIG_TOUCHSCREEN_USB_EGALAX is not set
-# CONFIG_TOUCHSCREEN_USB_ELO is not set
-# CONFIG_TOUCHSCREEN_USB_ETT_TC45USB is not set
-# CONFIG_TOUCHSCREEN_USB_ETURBO is not set
-# CONFIG_TOUCHSCREEN_USB_GENERAL_TOUCH is not set
-# CONFIG_TOUCHSCREEN_USB_GOTOP is not set
-# CONFIG_TOUCHSCREEN_USB_GUNZE is not set
-# CONFIG_TOUCHSCREEN_USB_IDEALTEK is not set
-# CONFIG_TOUCHSCREEN_USB_IRTOUCH is not set
-# CONFIG_TOUCHSCREEN_USB_ITM is not set
-# CONFIG_TOUCHSCREEN_USB_JASTEC is not set
-# CONFIG_TOUCHSCREEN_USB_NEXIO is not set
-# CONFIG_TOUCHSCREEN_USB_PANJIT is not set
-# CONFIG_TOUCHSCREEN_USB_ZYTRONIC is not set
-# CONFIG_TOUCHSCREEN_W90X900 is not set
-# CONFIG_TOUCHSCREEN_WACOM_I2C is not set
-# CONFIG_TOUCHSCREEN_WACOM_W8001 is not set
-# CONFIG_TOUCHSCREEN_WDT87XX_I2C is not set
-# CONFIG_TOUCHSCREEN_WM831X is not set
-# CONFIG_TOUCHSCREEN_WM9705 is not set
-# CONFIG_TOUCHSCREEN_WM9712 is not set
-# CONFIG_TOUCHSCREEN_WM9713 is not set
-# CONFIG_TOUCHSCREEN_WM97XX is not set
-# CONFIG_TOUCHSCREEN_WM97XX_MAINSTONE is not set
-# CONFIG_TOUCHSCREEN_WM97XX_ZYLONITE is not set
-# CONFIG_TOUCHSCREEN_ZET6223 is not set
-# CONFIG_TOUCHSCREEN_ZFORCE is not set
-# CONFIG_TOUCHSCREEN_ZINITIX is not set
-# CONFIG_TPL0102 is not set
-# CONFIG_TPS6105X is not set
-# CONFIG_TPS65010 is not set
-# CONFIG_TPS6507X is not set
-# CONFIG_TRACEPOINT_BENCHMARK is not set
-# CONFIG_TRACER_SNAPSHOT is not set
-# CONFIG_TRACER_SNAPSHOT_PER_CPU_SWAP is not set
-# CONFIG_TRACE_BRANCH_PROFILING is not set
-# CONFIG_TRACE_EVAL_MAP_FILE is not set
-# CONFIG_TRACE_EVENT_INJECT is not set
-CONFIG_TRACE_IRQFLAGS_SUPPORT=y
-# CONFIG_TRACE_SINK is not set
-# CONFIG_TRACING_EVENTS_GPIO is not set
-CONFIG_TRACING_SUPPORT=y
-CONFIG_TRAD_SIGNALS=y
-# CONFIG_TRANSPARENT_HUGEPAGE is not set
-# CONFIG_TREE_RCU is not set
-# CONFIG_TREE_RCU_TRACE is not set
-# CONFIG_TRIM_UNUSED_KSYMS is not set
-# CONFIG_TRUSTED_FOUNDATIONS is not set
-# CONFIG_TRUSTED_KEYS is not set
-# CONFIG_TSL2583 is not set
-# CONFIG_TSL2591 is not set
-# CONFIG_TSL2772 is not set
-# CONFIG_TSL2x7x is not set
-# CONFIG_TSL4531 is not set
-# CONFIG_TSYS01 is not set
-# CONFIG_TSYS02D is not set
-# CONFIG_TTPCI_EEPROM is not set
-CONFIG_TTY=y
-# CONFIG_TTY_PRINTK is not set
-# CONFIG_TUN is not set
-# CONFIG_TUN_VNET_CROSS_LE is not set
-# CONFIG_TWL4030_CORE is not set
-# CONFIG_TWL4030_MADC is not set
-# CONFIG_TWL6030_GPADC is not set
-# CONFIG_TWL6040_CORE is not set
-# CONFIG_TYPEC is not set
-# CONFIG_TYPEC_TCPM is not set
-# CONFIG_TYPEC_UCSI is not set
-# CONFIG_TYPHOON is not set
-# CONFIG_UACCESS_WITH_MEMCPY is not set
-# CONFIG_UBIFS_ATIME_SUPPORT is not set
-# CONFIG_UBIFS_FS_ADVANCED_COMPR is not set
-# CONFIG_UBIFS_FS_AUTHENTICATION is not set
-# CONFIG_UBIFS_FS_ENCRYPTION is not set
-CONFIG_UBIFS_FS_LZO=y
-# CONFIG_UBIFS_FS_SECURITY is not set
-CONFIG_UBIFS_FS_XATTR=y
-CONFIG_UBIFS_FS_ZLIB=y
-CONFIG_UBIFS_FS_ZSTD=y
-# CONFIG_UBSAN is not set
-CONFIG_UBSAN_ALIGNMENT=y
-CONFIG_UBSAN_BOOL=y
-# CONFIG_UBSAN_DIV_ZERO is not set
-CONFIG_UBSAN_ENUM=y
-# CONFIG_UBSAN_MISC is not set
-CONFIG_UBSAN_SHIFT=y
-# CONFIG_UBSAN_UNREACHABLE is not set
-# CONFIG_UCB1400_CORE is not set
-# CONFIG_UCSI is not set
-# CONFIG_UDF_FS is not set
-# CONFIG_UDMABUF is not set
-CONFIG_UEVENT_HELPER=y
-CONFIG_UEVENT_HELPER_PATH="/sbin/hotplug"
-# CONFIG_UFS_FS is not set
-# CONFIG_UHID is not set
-CONFIG_UID16=y
-# CONFIG_UIO is not set
-# CONFIG_ULTRA is not set
-# CONFIG_ULTRIX_PARTITION is not set
-# CONFIG_UNICODE is not set
-# CONFIG_UNISYSSPAR is not set
-# CONFIG_UNISYS_VISORBUS is not set
-CONFIG_UNIX=y
-CONFIG_UNIX98_PTYS=y
-# CONFIG_UNIXWARE_DISKLABEL is not set
-# CONFIG_UNIX_DIAG is not set
-CONFIG_UNIX_SCM=y
-# CONFIG_UNUSED_SYMBOLS is not set
-# CONFIG_UNWINDER_FRAME_POINTER is not set
-# CONFIG_UPROBES is not set
-# CONFIG_UPROBE_EVENTS is not set
-# CONFIG_US5182D is not set
-# CONFIG_USB is not set
-# CONFIG_USB4 is not set
-# CONFIG_USBIP_CORE is not set
-CONFIG_USBIP_VHCI_HC_PORTS=8
-CONFIG_USBIP_VHCI_NR_HCS=1
-# CONFIG_USBIP_VUDC is not set
-# CONFIG_USBPCWATCHDOG is not set
-# CONFIG_USB_ACM is not set
-# CONFIG_USB_ADUTUX is not set
-# CONFIG_USB_AIRSPY is not set
-CONFIG_USB_ALI_M5632=y
-# CONFIG_USB_AMD5536UDC is not set
-CONFIG_USB_AN2720=y
-# CONFIG_USB_ANNOUNCE_NEW_DEVICES is not set
-# CONFIG_USB_APPLEDISPLAY is not set
-CONFIG_USB_ARCH_HAS_HCD=y
-CONFIG_USB_ARMLINUX=y
-# CONFIG_USB_ATM is not set
-# CONFIG_USB_AUDIO is not set
-CONFIG_USB_AUTOSUSPEND_DELAY=2
-# CONFIG_USB_BDC_UDC is not set
-CONFIG_USB_BELKIN=y
-# CONFIG_USB_C67X00_HCD is not set
-# CONFIG_USB_CATC is not set
-# CONFIG_USB_CDC_COMPOSITE is not set
-# CONFIG_USB_CDNS3 is not set
-# CONFIG_USB_CDNS3_IMX is not set
-# CONFIG_USB_CDNS3_PCI_WRAP is not set
-# CONFIG_USB_CDNS_SUPPORT is not set
-# CONFIG_USB_CDNSP_PCI is not set
-# CONFIG_USB_CHAOSKEY is not set
-# CONFIG_USB_CHIPIDEA is not set
-# CONFIG_USB_CHIPIDEA_GENERIC is not set
-# CONFIG_USB_CHIPIDEA_IMX is not set
-# CONFIG_USB_CHIPIDEA_MSM is not set
-# CONFIG_USB_CHIPIDEA_PCI is not set
-# CONFIG_USB_CHIPIDEA_TEGRA is not set
-# CONFIG_USB_CONFIGFS is not set
-# CONFIG_USB_CONN_GPIO is not set
-# CONFIG_USB_CXACRU is not set
-# CONFIG_USB_CYPRESS_CY7C63 is not set
-# CONFIG_USB_CYTHERM is not set
-CONFIG_USB_DEFAULT_PERSIST=y
-# CONFIG_USB_DSBR is not set
-# CONFIG_USB_DUMMY_HCD is not set
-# CONFIG_USB_DWC2 is not set
-# CONFIG_USB_DWC2_DEBUG is not set
-# CONFIG_USB_DWC2_DUAL_ROLE is not set
-# CONFIG_USB_DWC2_HOST is not set
-# CONFIG_USB_DWC2_PERIPHERAL is not set
-# CONFIG_USB_DWC2_TRACK_MISSED_SOFS is not set
-# CONFIG_USB_DWC3 is not set
-# CONFIG_USB_DWC3_EXYNOS is not set
-# CONFIG_USB_DWC3_HAPS is not set
-# CONFIG_USB_DWC3_KEYSTONE is not set
-# CONFIG_USB_DWC3_OF_SIMPLE is not set
-# CONFIG_USB_DWC3_PCI is not set
-# CONFIG_USB_DWC3_QCOM is not set
-# CONFIG_USB_DWC3_ULPI is not set
-# CONFIG_USB_DYNAMIC_MINORS is not set
-# CONFIG_USB_EG20T is not set
-# CONFIG_USB_EHCI_ATH79 is not set
-# CONFIG_USB_EHCI_FSL is not set
-# CONFIG_USB_EHCI_HCD is not set
-# CONFIG_USB_EHCI_HCD_AT91 is not set
-# CONFIG_USB_EHCI_HCD_OMAP is not set
-# CONFIG_USB_EHCI_HCD_PPC_OF is not set
-# CONFIG_USB_EHCI_MSM is not set
-# CONFIG_USB_EHCI_MV is not set
-CONFIG_USB_EHCI_ROOT_HUB_TT=y
-CONFIG_USB_EHCI_TT_NEWSCHED=y
-# CONFIG_USB_EHSET_TEST_FIXTURE is not set
-# CONFIG_USB_EMI26 is not set
-# CONFIG_USB_EMI62 is not set
-# CONFIG_USB_EPSON2888 is not set
-# CONFIG_USB_ETH is not set
-# CONFIG_USB_EZUSB_FX2 is not set
-# CONFIG_USB_FEW_INIT_RETRIES is not set
-# CONFIG_USB_FOTG210_HCD is not set
-# CONFIG_USB_FOTG210_UDC is not set
-# CONFIG_USB_FSL_USB2 is not set
-# CONFIG_USB_FTDI_ELAN is not set
-# CONFIG_USB_FUNCTIONFS is not set
-# CONFIG_USB_FUSB300 is not set
-# CONFIG_USB_GADGET is not set
-# CONFIG_USB_GADGETFS is not set
-# CONFIG_USB_GADGET_DEBUG is not set
-# CONFIG_USB_GADGET_DEBUG_FILES is not set
-# CONFIG_USB_GADGET_DEBUG_FS is not set
-CONFIG_USB_GADGET_STORAGE_NUM_BUFFERS=2
-CONFIG_USB_GADGET_VBUS_DRAW=2
-# CONFIG_USB_GADGET_XILINX is not set
-# CONFIG_USB_GL860 is not set
-# CONFIG_USB_GOKU is not set
-# CONFIG_USB_GPIO_VBUS is not set
-# CONFIG_USB_GR_UDC is not set
-# CONFIG_USB_GSPCA is not set
-# CONFIG_USB_GSPCA_BENQ is not set
-# CONFIG_USB_GSPCA_CONEX is not set
-# CONFIG_USB_GSPCA_CPIA1 is not set
-# CONFIG_USB_GSPCA_DTCS033 is not set
-# CONFIG_USB_GSPCA_ETOMS is not set
-# CONFIG_USB_GSPCA_FINEPIX is not set
-# CONFIG_USB_GSPCA_JEILINJ is not set
-# CONFIG_USB_GSPCA_JL2005BCD is not set
-# CONFIG_USB_GSPCA_KINECT is not set
-# CONFIG_USB_GSPCA_KONICA is not set
-# CONFIG_USB_GSPCA_MARS is not set
-# CONFIG_USB_GSPCA_MR97310A is not set
-# CONFIG_USB_GSPCA_NW80X is not set
-# CONFIG_USB_GSPCA_OV519 is not set
-# CONFIG_USB_GSPCA_OV534 is not set
-# CONFIG_USB_GSPCA_OV534_9 is not set
-# CONFIG_USB_GSPCA_PAC207 is not set
-# CONFIG_USB_GSPCA_PAC7302 is not set
-# CONFIG_USB_GSPCA_PAC7311 is not set
-# CONFIG_USB_GSPCA_SE401 is not set
-# CONFIG_USB_GSPCA_SN9C2028 is not set
-# CONFIG_USB_GSPCA_SN9C20X is not set
-# CONFIG_USB_GSPCA_SONIXB is not set
-# CONFIG_USB_GSPCA_SONIXJ is not set
-# CONFIG_USB_GSPCA_SPCA1528 is not set
-# CONFIG_USB_GSPCA_SPCA500 is not set
-# CONFIG_USB_GSPCA_SPCA501 is not set
-# CONFIG_USB_GSPCA_SPCA505 is not set
-# CONFIG_USB_GSPCA_SPCA506 is not set
-# CONFIG_USB_GSPCA_SPCA508 is not set
-# CONFIG_USB_GSPCA_SPCA561 is not set
-# CONFIG_USB_GSPCA_SQ905 is not set
-# CONFIG_USB_GSPCA_SQ905C is not set
-# CONFIG_USB_GSPCA_SQ930X is not set
-# CONFIG_USB_GSPCA_STK014 is not set
-# CONFIG_USB_GSPCA_STK1135 is not set
-# CONFIG_USB_GSPCA_STV0680 is not set
-# CONFIG_USB_GSPCA_SUNPLUS is not set
-# CONFIG_USB_GSPCA_T613 is not set
-# CONFIG_USB_GSPCA_TOPRO is not set
-# CONFIG_USB_GSPCA_TOUPTEK is not set
-# CONFIG_USB_GSPCA_TV8532 is not set
-# CONFIG_USB_GSPCA_VC032X is not set
-# CONFIG_USB_GSPCA_VICAM is not set
-# CONFIG_USB_GSPCA_XIRLINK_CIT is not set
-# CONFIG_USB_GSPCA_ZC3XX is not set
-# CONFIG_USB_G_ACM_MS is not set
-# CONFIG_USB_G_DBGP is not set
-# CONFIG_USB_G_HID is not set
-# CONFIG_USB_G_MULTI is not set
-# CONFIG_USB_G_NCM is not set
-# CONFIG_USB_G_NOKIA is not set
-# CONFIG_USB_G_PRINTER is not set
-# CONFIG_USB_G_SERIAL is not set
-# CONFIG_USB_G_WEBCAM is not set
-# CONFIG_USB_HACKRF is not set
-# CONFIG_USB_HCD_TEST_MODE is not set
-# CONFIG_USB_HID is not set
-# CONFIG_USB_HIDDEV is not set
-# CONFIG_USB_HSIC_USB3503 is not set
-# CONFIG_USB_HSIC_USB4604 is not set
-# CONFIG_USB_HSO is not set
-# CONFIG_USB_HUB_USB251XB is not set
-# CONFIG_USB_HWA_HCD is not set
-# CONFIG_USB_IDMOUSE is not set
-# CONFIG_USB_IMX21_HCD is not set
-# CONFIG_USB_IOWARRIOR is not set
-# CONFIG_USB_IPHETH is not set
-# CONFIG_USB_ISIGHTFW is not set
-# CONFIG_USB_ISP116X_HCD is not set
-# CONFIG_USB_ISP1301 is not set
-# CONFIG_USB_ISP1362_HCD is not set
-# CONFIG_USB_ISP1760 is not set
-# CONFIG_USB_ISP1760_HCD is not set
-# CONFIG_USB_KAWETH is not set
-# CONFIG_USB_KBD is not set
-# CONFIG_USB_KC2190 is not set
-# CONFIG_USB_LAN78XX is not set
-# CONFIG_USB_LCD is not set
-# CONFIG_USB_LD is not set
-# CONFIG_USB_LED is not set
-# CONFIG_USB_LEDS_TRIGGER_USBPORT is not set
-# CONFIG_USB_LED_TRIG is not set
-# CONFIG_USB_LEGOTOWER is not set
-# CONFIG_USB_LGM_PHY is not set
-# CONFIG_USB_LINK_LAYER_TEST is not set
-# CONFIG_USB_M5602 is not set
-# CONFIG_USB_M66592 is not set
-# CONFIG_USB_MASS_STORAGE is not set
-# CONFIG_USB_MAX3420_UDC is not set
-# CONFIG_USB_MAX3421_HCD is not set
-# CONFIG_USB_MDC800 is not set
-# CONFIG_USB_MICROTEK is not set
-# CONFIG_USB_MIDI_GADGET is not set
-# CONFIG_USB_MON is not set
-# CONFIG_USB_MOUSE is not set
-# CONFIG_USB_MSI2500 is not set
-# CONFIG_USB_MSM_OTG is not set
-# CONFIG_USB_MTU3 is not set
-# CONFIG_USB_MUSB_GADGET is not set
-# CONFIG_USB_MUSB_HDRC is not set
-# CONFIG_USB_MUSB_HOST is not set
-# CONFIG_USB_MV_U3D is not set
-# CONFIG_USB_MV_UDC is not set
-# CONFIG_USB_MXS_PHY is not set
-# CONFIG_USB_NET2272 is not set
-# CONFIG_USB_NET2280 is not set
-# CONFIG_USB_NET_AQC111 is not set
-# CONFIG_USB_NET_AX88179_178A is not set
-# CONFIG_USB_NET_AX8817X is not set
-# CONFIG_USB_NET_CDCETHER is not set
-# CONFIG_USB_NET_CDC_EEM is not set
-# CONFIG_USB_NET_CDC_MBIM is not set
-# CONFIG_USB_NET_CDC_NCM is not set
-# CONFIG_USB_NET_CDC_SUBSET is not set
-# CONFIG_USB_NET_CH9200 is not set
-# CONFIG_USB_NET_CX82310_ETH is not set
-# CONFIG_USB_NET_DM9601 is not set
-# CONFIG_USB_NET_DRIVERS is not set
-# CONFIG_USB_NET_GL620A is not set
-# CONFIG_USB_NET_HUAWEI_CDC_NCM is not set
-# CONFIG_USB_NET_INT51X1 is not set
-# CONFIG_USB_NET_KALMIA is not set
-# CONFIG_USB_NET_MCS7830 is not set
-# CONFIG_USB_NET_NET1080 is not set
-# CONFIG_USB_NET_PLUSB is not set
-# CONFIG_USB_NET_QMI_WWAN is not set
-# CONFIG_USB_NET_RNDIS_HOST is not set
-# CONFIG_USB_NET_RNDIS_WLAN is not set
-# CONFIG_USB_NET_SMSC75XX is not set
-# CONFIG_USB_NET_SMSC95XX is not set
-# CONFIG_USB_NET_SR9700 is not set
-# CONFIG_USB_NET_SR9800 is not set
-# CONFIG_USB_NET_ZAURUS is not set
-# CONFIG_USB_OHCI_HCD is not set
-# CONFIG_USB_OHCI_HCD_PCI is not set
-# CONFIG_USB_OHCI_HCD_PPC_OF is not set
-# CONFIG_USB_OHCI_HCD_PPC_OF_BE is not set
-# CONFIG_USB_OHCI_HCD_PPC_OF_LE is not set
-# CONFIG_USB_OHCI_HCD_SSB is not set
-CONFIG_USB_OHCI_LITTLE_ENDIAN=y
-# CONFIG_USB_OTG is not set
-# CONFIG_USB_OTG_BLACKLIST_HUB is not set
-# CONFIG_USB_OTG_DISABLE_EXTERNAL_HUB is not set
-# CONFIG_USB_OTG_FSM is not set
-# CONFIG_USB_OTG_PRODUCTLIST is not set
-# CONFIG_USB_OTG_WHITELIST is not set
-# CONFIG_USB_OXU210HP_HCD is not set
-# CONFIG_USB_PCI is not set
-# CONFIG_USB_PEGASUS is not set
-# CONFIG_USB_PHY is not set
-# CONFIG_USB_PRINTER is not set
-# CONFIG_USB_PWC_INPUT_EVDEV is not set
-# CONFIG_USB_PXA27X is not set
-# CONFIG_USB_R8A66597 is not set
-# CONFIG_USB_R8A66597_HCD is not set
-# CONFIG_USB_RAW_GADGET is not set
-# CONFIG_USB_RCAR_PHY is not set
-# CONFIG_USB_RENESAS_USBHS is not set
-# CONFIG_USB_RIO500 is not set
-# CONFIG_USB_ROLES_INTEL_XHCI is not set
-# CONFIG_USB_ROLE_SWITCH is not set
-# CONFIG_USB_RTL8150 is not set
-# CONFIG_USB_RTL8152 is not set
-# CONFIG_USB_RTL8153_ECM is not set
-# CONFIG_USB_S2255 is not set
-# CONFIG_USB_SERIAL is not set
-# CONFIG_USB_SERIAL_AIRCABLE is not set
-# CONFIG_USB_SERIAL_ARK3116 is not set
-# CONFIG_USB_SERIAL_BELKIN is not set
-# CONFIG_USB_SERIAL_CH341 is not set
-# CONFIG_USB_SERIAL_CP210X is not set
-# CONFIG_USB_SERIAL_CYBERJACK is not set
-# CONFIG_USB_SERIAL_CYPRESS_M8 is not set
-# CONFIG_USB_SERIAL_DEBUG is not set
-# CONFIG_USB_SERIAL_DIGI_ACCELEPORT is not set
-# CONFIG_USB_SERIAL_EDGEPORT is not set
-# CONFIG_USB_SERIAL_EDGEPORT_TI is not set
-# CONFIG_USB_SERIAL_EMPEG is not set
-# CONFIG_USB_SERIAL_F81232 is not set
-# CONFIG_USB_SERIAL_F8153X is not set
-# CONFIG_USB_SERIAL_FTDI_SIO is not set
-# CONFIG_USB_SERIAL_GARMIN is not set
-CONFIG_USB_SERIAL_GENERIC=y
-# CONFIG_USB_SERIAL_IPAQ is not set
-# CONFIG_USB_SERIAL_IPW is not set
-# CONFIG_USB_SERIAL_IR is not set
-# CONFIG_USB_SERIAL_IUU is not set
-# CONFIG_USB_SERIAL_KEYSPAN is not set
-CONFIG_USB_SERIAL_KEYSPAN_MPR=y
-# CONFIG_USB_SERIAL_KEYSPAN_PDA is not set
-CONFIG_USB_SERIAL_KEYSPAN_USA18X=y
-CONFIG_USB_SERIAL_KEYSPAN_USA19=y
-CONFIG_USB_SERIAL_KEYSPAN_USA19QI=y
-CONFIG_USB_SERIAL_KEYSPAN_USA19QW=y
-CONFIG_USB_SERIAL_KEYSPAN_USA19W=y
-CONFIG_USB_SERIAL_KEYSPAN_USA28=y
-CONFIG_USB_SERIAL_KEYSPAN_USA28X=y
-CONFIG_USB_SERIAL_KEYSPAN_USA28XA=y
-CONFIG_USB_SERIAL_KEYSPAN_USA28XB=y
-CONFIG_USB_SERIAL_KEYSPAN_USA49W=y
-CONFIG_USB_SERIAL_KEYSPAN_USA49WLC=y
-# CONFIG_USB_SERIAL_KLSI is not set
-# CONFIG_USB_SERIAL_KOBIL_SCT is not set
-# CONFIG_USB_SERIAL_MCT_U232 is not set
-# CONFIG_USB_SERIAL_METRO is not set
-# CONFIG_USB_SERIAL_MOS7715_PARPORT is not set
-# CONFIG_USB_SERIAL_MOS7720 is not set
-# CONFIG_USB_SERIAL_MOS7840 is not set
-# CONFIG_USB_SERIAL_MXUPORT is not set
-# CONFIG_USB_SERIAL_NAVMAN is not set
-# CONFIG_USB_SERIAL_OMNINET is not set
-# CONFIG_USB_SERIAL_OPTICON is not set
-# CONFIG_USB_SERIAL_OPTION is not set
-# CONFIG_USB_SERIAL_OTI6858 is not set
-# CONFIG_USB_SERIAL_PL2303 is not set
-# CONFIG_USB_SERIAL_QCAUX is not set
-# CONFIG_USB_SERIAL_QT2 is not set
-# CONFIG_USB_SERIAL_QUALCOMM is not set
-# CONFIG_USB_SERIAL_SAFE is not set
-CONFIG_USB_SERIAL_SAFE_PADDED=y
-# CONFIG_USB_SERIAL_SIERRAWIRELESS is not set
-# CONFIG_USB_SERIAL_SIMPLE is not set
-# CONFIG_USB_SERIAL_SPCP8X5 is not set
-# CONFIG_USB_SERIAL_SSU100 is not set
-# CONFIG_USB_SERIAL_SYMBOL is not set
-# CONFIG_USB_SERIAL_TI is not set
-# CONFIG_USB_SERIAL_UPD78F0730 is not set
-# CONFIG_USB_SERIAL_VISOR is not set
-# CONFIG_USB_SERIAL_WHITEHEAT is not set
-# CONFIG_USB_SERIAL_WISHBONE is not set
-# CONFIG_USB_SERIAL_XIRCOM is not set
-# CONFIG_USB_SERIAL_XR is not set
-# CONFIG_USB_SERIAL_XSENS_MT is not set
-# CONFIG_USB_SEVSEG is not set
-# CONFIG_USB_SIERRA_NET is not set
-# CONFIG_USB_SISUSBVGA is not set
-# CONFIG_USB_SL811_HCD is not set
-# CONFIG_USB_SNP_UDC_PLAT is not set
-# CONFIG_USB_SPEEDTOUCH is not set
-# CONFIG_USB_STKWEBCAM is not set
-# CONFIG_USB_STORAGE is not set
-# CONFIG_USB_STORAGE_ALAUDA is not set
-# CONFIG_USB_STORAGE_CYPRESS_ATACB is not set
-# CONFIG_USB_STORAGE_DATAFAB is not set
-# CONFIG_USB_STORAGE_DEBUG is not set
-# CONFIG_USB_STORAGE_ENE_UB6250 is not set
-# CONFIG_USB_STORAGE_FREECOM is not set
-# CONFIG_USB_STORAGE_ISD200 is not set
-# CONFIG_USB_STORAGE_JUMPSHOT is not set
-# CONFIG_USB_STORAGE_KARMA is not set
-# CONFIG_USB_STORAGE_ONETOUCH is not set
-# CONFIG_USB_STORAGE_REALTEK is not set
-# CONFIG_USB_STORAGE_SDDR09 is not set
-# CONFIG_USB_STORAGE_SDDR55 is not set
-# CONFIG_USB_STORAGE_USBAT is not set
-# CONFIG_USB_STV06XX is not set
-# CONFIG_USB_SUPPORT is not set
-# CONFIG_USB_SWITCH_FSA9480 is not set
-# CONFIG_USB_TEST is not set
-# CONFIG_USB_TMC is not set
-# CONFIG_USB_TRANCEVIBRATOR is not set
-# CONFIG_USB_UAS is not set
-# CONFIG_USB_UEAGLEATM is not set
-# CONFIG_USB_ULPI is not set
-# CONFIG_USB_ULPI_BUS is not set
-# CONFIG_USB_USBNET is not set
-# CONFIG_USB_USS720 is not set
-# CONFIG_USB_VIDEO_CLASS is not set
-CONFIG_USB_VIDEO_CLASS_INPUT_EVDEV=y
-# CONFIG_USB_VL600 is not set
-# CONFIG_USB_WDM is not set
-# CONFIG_USB_WHCI_HCD is not set
-# CONFIG_USB_WUSB is not set
-# CONFIG_USB_WUSB_CBAF is not set
-# CONFIG_USB_XHCI_DBGCAP is not set
-# CONFIG_USB_XHCI_HCD is not set
-# CONFIG_USB_XHCI_MVEBU is not set
-# CONFIG_USB_XHCI_PCI_RENESAS is not set
-# CONFIG_USB_XUSBATM is not set
-# CONFIG_USB_YUREX is not set
-# CONFIG_USB_ZD1201 is not set
-# CONFIG_USB_ZERO is not set
-# CONFIG_USB_ZR364XX is not set
-# CONFIG_USELIB is not set
-# CONFIG_USERFAULTFD is not set
-# CONFIG_USERIO is not set
-# CONFIG_USE_OF is not set
-# CONFIG_UTS_NS is not set
-# CONFIG_UWB is not set
-# CONFIG_U_SERIAL_CONSOLE is not set
-# CONFIG_V4L_MEM2MEM_DRIVERS is not set
-# CONFIG_V4L_PLATFORM_DRIVERS is not set
-# CONFIG_V4L_TEST_DRIVERS is not set
-# CONFIG_VALIDATE_FS_PARSER is not set
-# CONFIG_VBOXGUEST is not set
-# CONFIG_VCNL3020 is not set
-# CONFIG_VCNL4000 is not set
-# CONFIG_VCNL4035 is not set
-# CONFIG_VDPA is not set
-CONFIG_VDSO=y
-# CONFIG_VEML6030 is not set
-# CONFIG_VEML6070 is not set
-# CONFIG_VETH is not set
-# CONFIG_VEXPRESS_CONFIG is not set
-# CONFIG_VF610_ADC is not set
-# CONFIG_VF610_DAC is not set
-# CONFIG_VFAT_FS is not set
-# CONFIG_VFIO is not set
-# CONFIG_VGASTATE is not set
-# CONFIG_VGA_ARB is not set
-# CONFIG_VGA_CONSOLE is not set
-# CONFIG_VGA_SWITCHEROO is not set
-# CONFIG_VHOST_CROSS_ENDIAN_LEGACY is not set
-CONFIG_VHOST_MENU=y
-# CONFIG_VHOST_NET is not set
-# CONFIG_VHOST_VSOCK is not set
-# CONFIG_VIA_RHINE is not set
-# CONFIG_VIA_VELOCITY is not set
-# CONFIG_VIDEO_AD5398 is not set
-# CONFIG_VIDEO_AD5820 is not set
-# CONFIG_VIDEO_AD9389B is not set
-# CONFIG_VIDEO_ADP1653 is not set
-# CONFIG_VIDEO_ADV7170 is not set
-# CONFIG_VIDEO_ADV7175 is not set
-# CONFIG_VIDEO_ADV7180 is not set
-# CONFIG_VIDEO_ADV7183 is not set
-# CONFIG_VIDEO_ADV7343 is not set
-# CONFIG_VIDEO_ADV7393 is not set
-# CONFIG_VIDEO_ADV748X is not set
-# CONFIG_VIDEO_ADV7511 is not set
-# CONFIG_VIDEO_ADV7604 is not set
-# CONFIG_VIDEO_ADV7842 is not set
-# CONFIG_VIDEO_ADV_DEBUG is not set
-# CONFIG_VIDEO_AK7375 is not set
-# CONFIG_VIDEO_AK881X is not set
-# CONFIG_VIDEO_AM437X_VPFE is not set
-# CONFIG_VIDEO_ASPEED is not set
-# CONFIG_VIDEO_ATMEL_ISC is not set
-# CONFIG_VIDEO_ATMEL_ISI is not set
-# CONFIG_VIDEO_AU0828 is not set
-# CONFIG_VIDEO_BT819 is not set
-# CONFIG_VIDEO_BT848 is not set
-# CONFIG_VIDEO_BT856 is not set
-# CONFIG_VIDEO_BT866 is not set
-# CONFIG_VIDEO_CADENCE is not set
-# CONFIG_VIDEO_CAFE_CCIC is not set
-# CONFIG_VIDEO_CCS is not set
-# CONFIG_VIDEO_COBALT is not set
-# CONFIG_VIDEO_CODA is not set
-# CONFIG_VIDEO_CS3308 is not set
-# CONFIG_VIDEO_CS5345 is not set
-# CONFIG_VIDEO_CS53L32A is not set
-# CONFIG_VIDEO_CX231XX is not set
-# CONFIG_VIDEO_CX2341X is not set
-# CONFIG_VIDEO_CX25821 is not set
-# CONFIG_VIDEO_CX25840 is not set
-# CONFIG_VIDEO_CX88 is not set
-# CONFIG_VIDEO_DEV is not set
-# CONFIG_VIDEO_DM6446_CCDC is not set
-# CONFIG_VIDEO_DT3155 is not set
-# CONFIG_VIDEO_DW9714 is not set
-# CONFIG_VIDEO_DW9768 is not set
-# CONFIG_VIDEO_DW9807_VCM is not set
-# CONFIG_VIDEO_EM28XX is not set
-# CONFIG_VIDEO_ET8EK8 is not set
-# CONFIG_VIDEO_FIXED_MINOR_RANGES is not set
-# CONFIG_VIDEO_GO7007 is not set
-# CONFIG_VIDEO_GS1662 is not set
-# CONFIG_VIDEO_HDPVR is not set
-# CONFIG_VIDEO_HEXIUM_GEMINI is not set
-# CONFIG_VIDEO_HEXIUM_ORION is not set
-# CONFIG_VIDEO_HI556 is not set
-# CONFIG_VIDEO_I2C is not set
-# CONFIG_VIDEO_IMX208 is not set
-# CONFIG_VIDEO_IMX214 is not set
-# CONFIG_VIDEO_IMX219 is not set
-# CONFIG_VIDEO_IMX258 is not set
-# CONFIG_VIDEO_IMX274 is not set
-# CONFIG_VIDEO_IMX290 is not set
-# CONFIG_VIDEO_IMX319 is not set
-# CONFIG_VIDEO_IMX334 is not set
-# CONFIG_VIDEO_IMX335 is not set
-# CONFIG_VIDEO_IMX355 is not set
-# CONFIG_VIDEO_IMX412 is not set
-# CONFIG_VIDEO_IMX477 is not set
-# CONFIG_VIDEO_IMX8_JPEG is not set
-# CONFIG_VIDEO_IMX_PXP is not set
-# CONFIG_VIDEO_IPU3_CIO2 is not set
-# CONFIG_VIDEO_IRS1125 is not set
-# CONFIG_VIDEO_IR_I2C is not set
-# CONFIG_VIDEO_IVTV is not set
-# CONFIG_VIDEO_KS0127 is not set
-# CONFIG_VIDEO_LM3560 is not set
-# CONFIG_VIDEO_LM3646 is not set
-# CONFIG_VIDEO_M52790 is not set
-# CONFIG_VIDEO_M5MOLS is not set
-# CONFIG_VIDEO_MAX9286 is not set
-# CONFIG_VIDEO_MEM2MEM_DEINTERLACE is not set
-# CONFIG_VIDEO_ML86V7667 is not set
-# CONFIG_VIDEO_MSP3400 is not set
-# CONFIG_VIDEO_MT9M001 is not set
-# CONFIG_VIDEO_MT9M032 is not set
-# CONFIG_VIDEO_MT9M111 is not set
-# CONFIG_VIDEO_MT9P031 is not set
-# CONFIG_VIDEO_MT9T001 is not set
-# CONFIG_VIDEO_MT9T112 is not set
-# CONFIG_VIDEO_MT9V011 is not set
-# CONFIG_VIDEO_MT9V032 is not set
-# CONFIG_VIDEO_MT9V111 is not set
-# CONFIG_VIDEO_MUX is not set
-# CONFIG_VIDEO_MXB is not set
-# CONFIG_VIDEO_NOON010PC30 is not set
-# CONFIG_VIDEO_OMAP2_VOUT is not set
-# CONFIG_VIDEO_OV02A10 is not set
-# CONFIG_VIDEO_OV13858 is not set
-# CONFIG_VIDEO_OV2311 is not set
-# CONFIG_VIDEO_OV2640 is not set
-# CONFIG_VIDEO_OV2659 is not set
-# CONFIG_VIDEO_OV2680 is not set
-# CONFIG_VIDEO_OV2685 is not set
-# CONFIG_VIDEO_OV2740 is not set
-# CONFIG_VIDEO_OV5640 is not set
-# CONFIG_VIDEO_OV5645 is not set
-# CONFIG_VIDEO_OV5647 is not set
-# CONFIG_VIDEO_OV5648 is not set
-# CONFIG_VIDEO_OV5670 is not set
-# CONFIG_VIDEO_OV5675 is not set
-# CONFIG_VIDEO_OV5695 is not set
-# CONFIG_VIDEO_OV6650 is not set
-# CONFIG_VIDEO_OV7251 is not set
-# CONFIG_VIDEO_OV7640 is not set
-# CONFIG_VIDEO_OV7670 is not set
-# CONFIG_VIDEO_OV772X is not set
-# CONFIG_VIDEO_OV7740 is not set
-# CONFIG_VIDEO_OV8856 is not set
-# CONFIG_VIDEO_OV8865 is not set
-# CONFIG_VIDEO_OV9281 is not set
-# CONFIG_VIDEO_OV9282 is not set
-# CONFIG_VIDEO_OV9640 is not set
-# CONFIG_VIDEO_OV9650 is not set
-# CONFIG_VIDEO_OV9734 is not set
-# CONFIG_VIDEO_PVRUSB2 is not set
-# CONFIG_VIDEO_RDACM20 is not set
-# CONFIG_VIDEO_RDACM21 is not set
-# CONFIG_VIDEO_RJ54N1 is not set
-# CONFIG_VIDEO_ROCKCHIP_ISP1 is not set
-# CONFIG_VIDEO_S5C73M3 is not set
-# CONFIG_VIDEO_S5K4ECGX is not set
-# CONFIG_VIDEO_S5K5BAF is not set
-# CONFIG_VIDEO_S5K6A3 is not set
-# CONFIG_VIDEO_S5K6AA is not set
-# CONFIG_VIDEO_SAA6588 is not set
-# CONFIG_VIDEO_SAA6752HS is not set
-# CONFIG_VIDEO_SAA7110 is not set
-# CONFIG_VIDEO_SAA711X is not set
-# CONFIG_VIDEO_SAA7127 is not set
-# CONFIG_VIDEO_SAA7134 is not set
-# CONFIG_VIDEO_SAA7164 is not set
-# CONFIG_VIDEO_SAA717X is not set
-# CONFIG_VIDEO_SAA7185 is not set
-# CONFIG_VIDEO_SH_MOBILE_CEU is not set
-# CONFIG_VIDEO_SMIAPP is not set
-# CONFIG_VIDEO_SOLO6X10 is not set
-# CONFIG_VIDEO_SONY_BTF_MPX is not set
-# CONFIG_VIDEO_SR030PC30 is not set
-# CONFIG_VIDEO_STK1160_COMMON is not set
-# CONFIG_VIDEO_ST_MIPID02 is not set
-# CONFIG_VIDEO_TC358743 is not set
-# CONFIG_VIDEO_TDA1997X is not set
-# CONFIG_VIDEO_TDA7432 is not set
-# CONFIG_VIDEO_TDA9840 is not set
-# CONFIG_VIDEO_TEA6415C is not set
-# CONFIG_VIDEO_TEA6420 is not set
-# CONFIG_VIDEO_THS7303 is not set
-# CONFIG_VIDEO_THS8200 is not set
-# CONFIG_VIDEO_TIMBERDALE is not set
-# CONFIG_VIDEO_TLV320AIC23B is not set
-# CONFIG_VIDEO_TM6000 is not set
-# CONFIG_VIDEO_TVAUDIO is not set
-# CONFIG_VIDEO_TVP514X is not set
-# CONFIG_VIDEO_TVP5150 is not set
-# CONFIG_VIDEO_TVP7002 is not set
-# CONFIG_VIDEO_TW2804 is not set
-# CONFIG_VIDEO_TW5864 is not set
-# CONFIG_VIDEO_TW68 is not set
-# CONFIG_VIDEO_TW9903 is not set
-# CONFIG_VIDEO_TW9906 is not set
-# CONFIG_VIDEO_TW9910 is not set
-# CONFIG_VIDEO_UDA1342 is not set
-# CONFIG_VIDEO_UPD64031A is not set
-# CONFIG_VIDEO_UPD64083 is not set
-# CONFIG_VIDEO_USBTV is not set
-# CONFIG_VIDEO_USBVISION is not set
-# CONFIG_VIDEO_V4L2 is not set
-# CONFIG_VIDEO_VP27SMPX is not set
-# CONFIG_VIDEO_VPX3220 is not set
-# CONFIG_VIDEO_VS6624 is not set
-# CONFIG_VIDEO_WM8739 is not set
-# CONFIG_VIDEO_WM8775 is not set
-# CONFIG_VIDEO_XILINX is not set
-# CONFIG_VIDEO_ZORAN is not set
-# CONFIG_VIRTIO_BALLOON is not set
-# CONFIG_VIRTIO_BLK_SCSI is not set
-# CONFIG_VIRTIO_CONSOLE is not set
-# CONFIG_VIRTIO_FS is not set
-# CONFIG_VIRTIO_INPUT is not set
-# CONFIG_VIRTIO_IOMMU is not set
-CONFIG_VIRTIO_MENU=y
-# CONFIG_VIRTIO_MMIO is not set
-# CONFIG_VIRTIO_MMIO_CMDLINE_DEVICES is not set
-# CONFIG_VIRTIO_PCI is not set
-# CONFIG_VIRTUALIZATION is not set
-# CONFIG_VIRT_CPU_ACCOUNTING_GEN is not set
-# CONFIG_VIRT_DRIVERS is not set
-CONFIG_VIRT_TO_BUS=y
-# CONFIG_VITESSE_PHY is not set
-# CONFIG_VL53L0X_I2C is not set
-# CONFIG_VL6180 is not set
-CONFIG_VLAN_8021Q=y
-# CONFIG_VLAN_8021Q_GVRP is not set
-# CONFIG_VLAN_8021Q_MVRP is not set
-# CONFIG_VME_BUS is not set
-# CONFIG_VMLINUX_MAP is not set
-# CONFIG_VMSPLIT_1G is not set
-# CONFIG_VMSPLIT_2G is not set
-# CONFIG_VMSPLIT_2G_OPT is not set
-CONFIG_VMSPLIT_3G=y
-# CONFIG_VMSPLIT_3G_OPT is not set
-# CONFIG_VMWARE_PVSCSI is not set
-# CONFIG_VMXNET3 is not set
-# CONFIG_VM_EVENT_COUNTERS is not set
-# CONFIG_VOP_BUS is not set
-# CONFIG_VORTEX is not set
-# CONFIG_VSOCKETS is not set
-# CONFIG_VSOCKETS_DIAG is not set
-# CONFIG_VT is not set
-# CONFIG_VT6655 is not set
-# CONFIG_VT6656 is not set
-# CONFIG_VXFS_FS is not set
-# CONFIG_VXGE is not set
-# CONFIG_VXLAN is not set
-# CONFIG_VZ89X is not set
-# CONFIG_W1 is not set
-# CONFIG_W1_CON is not set
-# CONFIG_W1_MASTER_DS1WM is not set
-# CONFIG_W1_MASTER_DS2482 is not set
-# CONFIG_W1_MASTER_DS2490 is not set
-# CONFIG_W1_MASTER_GPIO is not set
-# CONFIG_W1_MASTER_MATROX is not set
-# CONFIG_W1_MASTER_SGI is not set
-# CONFIG_W1_SLAVE_DS2405 is not set
-# CONFIG_W1_SLAVE_DS2406 is not set
-# CONFIG_W1_SLAVE_DS2408 is not set
-# CONFIG_W1_SLAVE_DS2413 is not set
-# CONFIG_W1_SLAVE_DS2423 is not set
-# CONFIG_W1_SLAVE_DS2430 is not set
-# CONFIG_W1_SLAVE_DS2431 is not set
-# CONFIG_W1_SLAVE_DS2433 is not set
-# CONFIG_W1_SLAVE_DS2438 is not set
-# CONFIG_W1_SLAVE_DS250X is not set
-# CONFIG_W1_SLAVE_DS2780 is not set
-# CONFIG_W1_SLAVE_DS2781 is not set
-# CONFIG_W1_SLAVE_DS2805 is not set
-# CONFIG_W1_SLAVE_DS28E04 is not set
-# CONFIG_W1_SLAVE_DS28E17 is not set
-# CONFIG_W1_SLAVE_SMEM is not set
-# CONFIG_W1_SLAVE_THERM is not set
-# CONFIG_W83627HF_WDT is not set
-# CONFIG_W83877F_WDT is not set
-# CONFIG_W83977F_WDT is not set
-# CONFIG_WAN is not set
-# CONFIG_WANXL is not set
-# CONFIG_WARN_ALL_UNSEEDED_RANDOM is not set
-CONFIG_WATCHDOG=y
-# CONFIG_WATCHDOG_CORE is not set
-CONFIG_WATCHDOG_HANDLE_BOOT_ENABLED=y
-# CONFIG_WATCHDOG_HRTIMER_PRETIMEOUT is not set
-# CONFIG_WATCHDOG_NOWAYOUT is not set
-CONFIG_WATCHDOG_OPEN_TIMEOUT=0
-# CONFIG_WATCHDOG_PRETIMEOUT_GOV is not set
-# CONFIG_WATCHDOG_SYSFS is not set
-# CONFIG_WATCH_QUEUE is not set
-# CONFIG_WD80x3 is not set
-# CONFIG_WDAT_WDT is not set
-# CONFIG_WDTPCI is not set
-# CONFIG_WERROR is not set
-# CONFIG_WEXT_CORE is not set
-# CONFIG_WEXT_PRIV is not set
-# CONFIG_WEXT_PROC is not set
-# CONFIG_WEXT_SPY is not set
-CONFIG_WILINK_PLATFORM_DATA=y
-# CONFIG_WIMAX is not set
-# CONFIG_WIREGUARD is not set
-CONFIG_WIRELESS=y
-# CONFIG_WIRELESS_EXT is not set
-# CONFIG_WIRELESS_WDS is not set
-# CONFIG_WIZNET_W5100 is not set
-# CONFIG_WIZNET_W5300 is not set
-# CONFIG_WL1251 is not set
-# CONFIG_WL12XX is not set
-# CONFIG_WL18XX is not set
-CONFIG_WLAN=y
-# CONFIG_WLAN_VENDOR_ADMTEK is not set
-# CONFIG_WLAN_VENDOR_ATH is not set
-# CONFIG_WLAN_VENDOR_ATMEL is not set
-# CONFIG_WLAN_VENDOR_BROADCOM is not set
-# CONFIG_WLAN_VENDOR_CISCO is not set
-# CONFIG_WLAN_VENDOR_INTEL is not set
-# CONFIG_WLAN_VENDOR_INTERSIL is not set
-# CONFIG_WLAN_VENDOR_MARVELL is not set
-# CONFIG_WLAN_VENDOR_MEDIATEK is not set
-# CONFIG_WLAN_VENDOR_MICROCHIP is not set
-# CONFIG_WLAN_VENDOR_QUANTENNA is not set
-# CONFIG_WLAN_VENDOR_RALINK is not set
-# CONFIG_WLAN_VENDOR_REALTEK is not set
-# CONFIG_WLAN_VENDOR_RSI is not set
-# CONFIG_WLAN_VENDOR_ST is not set
-# CONFIG_WLAN_VENDOR_TI is not set
-# CONFIG_WLAN_VENDOR_ZYDAS is not set
-# CONFIG_WLCORE is not set
-CONFIG_WQ_POWER_EFFICIENT_DEFAULT=y
-# CONFIG_WQ_WATCHDOG is not set
-# CONFIG_WWAN is not set
-# CONFIG_WWAN_HWSIM is not set
-# CONFIG_WW_MUTEX_SELFTEST is not set
-# CONFIG_X25 is not set
-# CONFIG_X509_CERTIFICATE_PARSER is not set
-# CONFIG_X86_PKG_TEMP_THERMAL is not set
-CONFIG_X86_SYSFB=y
-# CONFIG_XDP_SOCKETS is not set
-# CONFIG_XEN is not set
-# CONFIG_XEN_GRANT_DMA_ALLOC is not set
-# CONFIG_XEN_PVCALLS_FRONTEND is not set
-CONFIG_XEN_SCRUB_PAGES_DEFAULT=y
-CONFIG_XFRM=y
-# CONFIG_XFRM_INTERFACE is not set
-# CONFIG_XFRM_IPCOMP is not set
-# CONFIG_XFRM_MIGRATE is not set
-# CONFIG_XFRM_STATISTICS is not set
-# CONFIG_XFRM_SUB_POLICY is not set
-# CONFIG_XFRM_USER is not set
-# CONFIG_XFS_DEBUG is not set
-# CONFIG_XFS_FS is not set
-# CONFIG_XFS_ONLINE_SCRUB is not set
-# CONFIG_XFS_POSIX_ACL is not set
-# CONFIG_XFS_QUOTA is not set
-# CONFIG_XFS_RT is not set
-# CONFIG_XFS_SUPPORT_V4 is not set
-# CONFIG_XFS_WARN is not set
-# CONFIG_XILINX_AXI_EMAC is not set
-# CONFIG_XILINX_DMA is not set
-# CONFIG_XILINX_EMACLITE is not set
-# CONFIG_XILINX_GMII2RGMII is not set
-# CONFIG_XILINX_LL_TEMAC is not set
-# CONFIG_XILINX_SDFEC is not set
-# CONFIG_XILINX_VCU is not set
-# CONFIG_XILINX_WATCHDOG is not set
-# CONFIG_XILINX_XADC is not set
-# CONFIG_XILINX_ZYNQMP_DMA is not set
-# CONFIG_XILINX_ZYNQMP_DPDMA is not set
-# CONFIG_XILLYBUS is not set
-# CONFIG_XILLYUSB is not set
-# CONFIG_XIL_AXIS_FIFO is not set
-# CONFIG_XIP_KERNEL is not set
-# CONFIG_XMON is not set
-CONFIG_XZ_DEC=y
-# CONFIG_XZ_DEC_ARM is not set
-# CONFIG_XZ_DEC_ARMTHUMB is not set
-# CONFIG_XZ_DEC_BCJ is not set
-# CONFIG_XZ_DEC_IA64 is not set
-# CONFIG_XZ_DEC_POWERPC is not set
-# CONFIG_XZ_DEC_SPARC is not set
-# CONFIG_XZ_DEC_TEST is not set
-# CONFIG_XZ_DEC_X86 is not set
-# CONFIG_YAM is not set
-# CONFIG_YAMAHA_YAS530 is not set
-# CONFIG_YELLOWFIN is not set
-# CONFIG_YENTA is not set
-# CONFIG_YENTA_O2 is not set
-# CONFIG_YENTA_RICOH is not set
-# CONFIG_YENTA_TI is not set
-# CONFIG_YENTA_TOSHIBA is not set
-# CONFIG_ZBUD is not set
-# CONFIG_ZD1211RW is not set
-# CONFIG_ZD1211RW_DEBUG is not set
-# CONFIG_ZEROPLUS_FF is not set
-# CONFIG_ZERO_CALL_USED_REGS is not set
-# CONFIG_ZIIRAVE_WATCHDOG is not set
-# CONFIG_ZISOFS is not set
-# CONFIG_ZLIB_DEFLATE is not set
-# CONFIG_ZLIB_INFLATE is not set
-CONFIG_ZONE_DMA=y
-# CONFIG_ZOPT2201 is not set
-# CONFIG_ZPA2326 is not set
-# CONFIG_ZPOOL is not set
-# CONFIG_ZRAM is not set
-# CONFIG_ZRAM_DEF_COMP_842 is not set
-# CONFIG_ZRAM_DEF_COMP_LZ4 is not set
-# CONFIG_ZRAM_DEF_COMP_LZ4HC is not set
-# CONFIG_ZRAM_DEF_COMP_LZO is not set
-# CONFIG_ZRAM_DEF_COMP_LZORLE is not set
-# CONFIG_ZRAM_DEF_COMP_ZSTD is not set
-# CONFIG_ZRAM_MEMORY_TRACKING is not set
-# CONFIG_ZSMALLOC is not set
-# CONFIG_ZX_TDM is not set
diff --git a/target/linux/generic/hack-5.15/204-module_strip.patch b/target/linux/generic/hack-5.15/204-module_strip.patch
deleted file mode 100644 (file)
index e650c1b..0000000
+++ /dev/null
@@ -1,212 +0,0 @@
-From a779a482fb9b9f8fcdf8b2519c789b4b9bb5dd05 Mon Sep 17 00:00:00 2001
-From: Felix Fietkau <[email protected]>
-Date: Fri, 7 Jul 2017 16:56:48 +0200
-Subject: build: add a hack for removing non-essential module info
-
-Signed-off-by: Felix Fietkau <[email protected]>
----
- include/linux/module.h      | 13 ++++++++-----
- include/linux/moduleparam.h | 15 ++++++++++++---
- init/Kconfig                |  7 +++++++
- kernel/module.c             |  5 ++++-
- scripts/mod/modpost.c       | 12 ++++++++++++
- 5 files changed, 43 insertions(+), 9 deletions(-)
-
---- a/include/linux/module.h
-+++ b/include/linux/module.h
-@@ -164,6 +164,7 @@ extern void cleanup_module(void);
- /* Generic info of form tag = "info" */
- #define MODULE_INFO(tag, info) __MODULE_INFO(tag, tag, info)
-+#define MODULE_INFO_STRIP(tag, info) __MODULE_INFO_STRIP(tag, tag, info)
- /* For userspace: you can also call me... */
- #define MODULE_ALIAS(_alias) MODULE_INFO(alias, _alias)
-@@ -233,12 +234,12 @@ extern void cleanup_module(void);
-  * Author(s), use "Name <email>" or just "Name", for multiple
-  * authors use multiple MODULE_AUTHOR() statements/lines.
-  */
--#define MODULE_AUTHOR(_author) MODULE_INFO(author, _author)
-+#define MODULE_AUTHOR(_author) MODULE_INFO_STRIP(author, _author)
- /* What your module does. */
--#define MODULE_DESCRIPTION(_description) MODULE_INFO(description, _description)
-+#define MODULE_DESCRIPTION(_description) MODULE_INFO_STRIP(description, _description)
--#ifdef MODULE
-+#if defined(MODULE) && !defined(CONFIG_MODULE_STRIPPED)
- /* Creates an alias so file2alias.c can find device table. */
- #define MODULE_DEVICE_TABLE(type, name)                                       \
- extern typeof(name) __mod_##type##__##name##_device_table             \
-@@ -265,7 +266,9 @@ extern typeof(name) __mod_##type##__##na
-  */
- #if defined(MODULE) || !defined(CONFIG_SYSFS)
--#define MODULE_VERSION(_version) MODULE_INFO(version, _version)
-+#define MODULE_VERSION(_version) MODULE_INFO_STRIP(version, _version)
-+#elif defined(CONFIG_MODULE_STRIPPED)
-+#define MODULE_VERSION(_version) __MODULE_INFO_DISABLED(version)
- #else
- #define MODULE_VERSION(_version)                                      \
-       MODULE_INFO(version, _version);                                 \
-@@ -288,7 +291,7 @@ extern typeof(name) __mod_##type##__##na
- /* Optional firmware file (or files) needed by the module
-  * format is simply firmware file name.  Multiple firmware
-  * files require multiple MODULE_FIRMWARE() specifiers */
--#define MODULE_FIRMWARE(_firmware) MODULE_INFO(firmware, _firmware)
-+#define MODULE_FIRMWARE(_firmware) MODULE_INFO_STRIP(firmware, _firmware)
- #define MODULE_IMPORT_NS(ns) MODULE_INFO(import_ns, #ns)
---- a/include/linux/moduleparam.h
-+++ b/include/linux/moduleparam.h
-@@ -20,6 +20,16 @@
- /* Chosen so that structs with an unsigned long line up. */
- #define MAX_PARAM_PREFIX_LEN (64 - sizeof(unsigned long))
-+/* This struct is here for syntactic coherency, it is not used */
-+#define __MODULE_INFO_DISABLED(name)                                    \
-+  struct __UNIQUE_ID(name) {}
-+
-+#ifdef CONFIG_MODULE_STRIPPED
-+#define __MODULE_INFO_STRIP(tag, name, info) __MODULE_INFO_DISABLED(name)
-+#else
-+#define __MODULE_INFO_STRIP(tag, name, info) __MODULE_INFO(tag, name, info)
-+#endif
-+
- #define __MODULE_INFO(tag, name, info)                                          \
-       static const char __UNIQUE_ID(name)[]                             \
-               __used __section(".modinfo") __aligned(1)                 \
-@@ -31,7 +41,7 @@
- /* One for each parameter, describing how to use it.  Some files do
-    multiple of these per line, so can't just use MODULE_INFO. */
- #define MODULE_PARM_DESC(_parm, desc) \
--      __MODULE_INFO(parm, _parm, #_parm ":" desc)
-+      __MODULE_INFO_STRIP(parm, _parm, #_parm ":" desc)
- struct kernel_param;
---- a/init/Kconfig
-+++ b/init/Kconfig
-@@ -2356,6 +2356,13 @@ config UNUSED_KSYMS_WHITELIST
-         one per line. The path can be absolute, or relative to the kernel
-         source tree.
-+config MODULE_STRIPPED
-+      bool "Reduce module size"
-+      depends on MODULES
-+      help
-+        Remove module parameter descriptions, author info, version, aliases,
-+        device tables, etc.
-+
- endif # MODULES
- config MODULES_TREE_LOOKUP
---- a/kernel/module.c
-+++ b/kernel/module.c
-@@ -1218,6 +1218,7 @@ static struct module_attribute *modinfo_
- static const char vermagic[] = VERMAGIC_STRING;
-+#if defined(CONFIG_MODVERSIONS) || !defined(CONFIG_MODULE_STRIPPED)
- static int try_to_force_load(struct module *mod, const char *reason)
- {
- #ifdef CONFIG_MODULE_FORCE_LOAD
-@@ -1229,6 +1230,7 @@ static int try_to_force_load(struct modu
-       return -ENOEXEC;
- #endif
- }
-+#endif
- #ifdef CONFIG_MODVERSIONS
-@@ -3274,9 +3276,11 @@ static int setup_load_info(struct load_i
- static int check_modinfo(struct module *mod, struct load_info *info, int flags)
- {
--      const char *modmagic = get_modinfo(info, "vermagic");
-       int err;
-+#ifndef CONFIG_MODULE_STRIPPED
-+      const char *modmagic = get_modinfo(info, "vermagic");
-+
-       if (flags & MODULE_INIT_IGNORE_VERMAGIC)
-               modmagic = NULL;
-@@ -3297,6 +3301,7 @@ static int check_modinfo(struct module *
-                               mod->name);
-               add_taint_module(mod, TAINT_OOT_MODULE, LOCKDEP_STILL_OK);
-       }
-+#endif
-       check_modinfo_retpoline(mod, info);
---- a/scripts/mod/modpost.c
-+++ b/scripts/mod/modpost.c
-@@ -2000,7 +2000,9 @@ static void read_symbols(const char *mod
-               symname = remove_dot(info.strtab + sym->st_name);
-               handle_symbol(mod, &info, sym, symname);
-+#ifndef CONFIG_MODULE_STRIPPED
-               handle_moddevtable(mod, &info, sym, symname);
-+#endif
-       }
-       for (sym = info.symtab_start; sym < info.symtab_stop; sym++) {
-@@ -2179,8 +2181,10 @@ static void add_header(struct buffer *b,
-       buf_printf(b, "BUILD_SALT;\n");
-       buf_printf(b, "BUILD_LTO_INFO;\n");
-       buf_printf(b, "\n");
-+#ifndef CONFIG_MODULE_STRIPPED
-       buf_printf(b, "MODULE_INFO(vermagic, VERMAGIC_STRING);\n");
-       buf_printf(b, "MODULE_INFO(name, KBUILD_MODNAME);\n");
-+#endif
-       buf_printf(b, "\n");
-       buf_printf(b, "__visible struct module __this_module\n");
-       buf_printf(b, "__section(\".gnu.linkonce.this_module\") = {\n");
-@@ -2197,8 +2201,10 @@ static void add_header(struct buffer *b,
- static void add_intree_flag(struct buffer *b, int is_intree)
- {
-+#ifndef CONFIG_MODULE_STRIPPED
-       if (is_intree)
-               buf_printf(b, "\nMODULE_INFO(intree, \"Y\");\n");
-+#endif
- }
- /* Cannot check for assembler */
-@@ -2211,8 +2217,10 @@ static void add_retpoline(struct buffer
- static void add_staging_flag(struct buffer *b, const char *name)
- {
-+#ifndef CONFIG_MODULE_STRIPPED
-       if (strstarts(name, "drivers/staging"))
-               buf_printf(b, "\nMODULE_INFO(staging, \"Y\");\n");
-+#endif
- }
- /**
-@@ -2292,11 +2300,13 @@ static void add_depends(struct buffer *b
- static void add_srcversion(struct buffer *b, struct module *mod)
- {
-+#ifndef CONFIG_MODULE_STRIPPED
-       if (mod->srcversion[0]) {
-               buf_printf(b, "\n");
-               buf_printf(b, "MODULE_INFO(srcversion, \"%s\");\n",
-                          mod->srcversion);
-       }
-+#endif
- }
- static void write_buf(struct buffer *b, const char *fname)
-@@ -2545,7 +2555,9 @@ int main(int argc, char **argv)
-               add_staging_flag(&buf, mod->name);
-               add_versions(&buf, mod);
-               add_depends(&buf, mod);
-+#ifndef CONFIG_MODULE_STRIPPED
-               add_moddevtable(&buf, mod);
-+#endif
-               add_srcversion(&buf, mod);
-               sprintf(fname, "%s.mod.c", mod->name);
diff --git a/target/linux/generic/hack-5.15/205-kconfig-abort-configuration-on-unset-symbol.patch b/target/linux/generic/hack-5.15/205-kconfig-abort-configuration-on-unset-symbol.patch
deleted file mode 100644 (file)
index a87c7a5..0000000
+++ /dev/null
@@ -1,41 +0,0 @@
-From 310e8e04a05d9eb43fa9dd7f00143300afcaa37a Mon Sep 17 00:00:00 2001
-From: David Bauer <[email protected]>
-Date: Fri, 11 Nov 2022 13:33:44 +0100
-Subject: [PATCH] kconfig: abort configuration on unset symbol
-
-When a target configuration has unset Kconfig symbols, the build will
-fail when OpenWrt is compiled with V=s and stdin is connected to a tty.
-
-In case OpenWrt is compiled without either of these preconditions, the
-build will succeed with the symbols in question being unset.
-
-Modify the kernel configuration in a way it fails on unset symbols
-regardless of the aforementioned preconditions.
-
-Signed-off-by: David Bauer <[email protected]>
----
- scripts/kconfig/conf.c | 6 ++++++
- 1 file changed, 6 insertions(+)
-
---- a/scripts/kconfig/conf.c
-+++ b/scripts/kconfig/conf.c
-@@ -341,6 +341,9 @@ static int conf_askvalue(struct symbol *
-               }
-               /* fall through */
-       default:
-+              if (!tty_stdio && getenv("FAIL_ON_UNCONFIGURED")) {
-+                      exit(1);
-+              }
-               fflush(stdout);
-               xfgets(line, sizeof(line), stdin);
-               break;
-@@ -523,6 +526,9 @@ static int conf_choice(struct menu *menu
-                       }
-                       /* fall through */
-               case oldaskconfig:
-+                      if (!tty_stdio && getenv("FAIL_ON_UNCONFIGURED")) {
-+                              exit(1);
-+                      }
-                       fflush(stdout);
-                       xfgets(line, sizeof(line), stdin);
-                       strip(line);
diff --git a/target/linux/generic/hack-5.15/210-darwin_scripts_include.patch b/target/linux/generic/hack-5.15/210-darwin_scripts_include.patch
deleted file mode 100644 (file)
index be6adc0..0000000
+++ /dev/null
@@ -1,3053 +0,0 @@
-From db7c30dcd9a0391bf13b62c9f91e144d762ef43a Mon Sep 17 00:00:00 2001
-From: Florian Fainelli <[email protected]>
-Date: Fri, 7 Jul 2017 17:00:49 +0200
-Subject: Add an OSX specific patch to make the kernel be compiled
-
-lede-commit: 3fc2a24f0422b2f55f9ed43f116db3111f700526
-Signed-off-by: Florian Fainelli <[email protected]>
----
- scripts/kconfig/Makefile   |    3 +
- scripts/mod/elf.h          | 3007 ++++++++++++++++++++++++++++++++++++++++++++
- scripts/mod/mk_elfconfig.c |    4 +
- scripts/mod/modpost.h      |    4 +
- 4 files changed, 3018 insertions(+)
- create mode 100644 scripts/mod/elf.h
-
---- /dev/null
-+++ b/scripts/mod/elf.h
-@@ -0,0 +1,3007 @@
-+/* This file defines standard ELF types, structures, and macros.
-+   Copyright (C) 1995-2012 Free Software Foundation, Inc.
-+   This file is part of the GNU C Library.
-+
-+   The GNU C Library is free software; you can redistribute it and/or
-+   modify it under the terms of the GNU Lesser General Public
-+   License as published by the Free Software Foundation; either
-+   version 2.1 of the License, or (at your option) any later version.
-+
-+   The GNU C Library is distributed in the hope that it will be useful,
-+   but WITHOUT ANY WARRANTY; without even the implied warranty of
-+   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
-+   Lesser General Public License for more details.
-+
-+   You should have received a copy of the GNU Lesser General Public
-+   License along with the GNU C Library; if not, see
-+   <http://www.gnu.org/licenses/>.  */
-+
-+#ifndef _ELF_H
-+#define       _ELF_H 1
-+
-+/* Standard ELF types.  */
-+
-+#include <stdint.h>
-+
-+/* Type for a 16-bit quantity.  */
-+typedef uint16_t Elf32_Half;
-+typedef uint16_t Elf64_Half;
-+
-+/* Types for signed and unsigned 32-bit quantities.  */
-+typedef uint32_t Elf32_Word;
-+typedef       int32_t  Elf32_Sword;
-+typedef uint32_t Elf64_Word;
-+typedef       int32_t  Elf64_Sword;
-+
-+/* Types for signed and unsigned 64-bit quantities.  */
-+typedef uint64_t Elf32_Xword;
-+typedef       int64_t  Elf32_Sxword;
-+typedef uint64_t Elf64_Xword;
-+typedef       int64_t  Elf64_Sxword;
-+
-+/* Type of addresses.  */
-+typedef uint32_t Elf32_Addr;
-+typedef uint64_t Elf64_Addr;
-+
-+/* Type of file offsets.  */
-+typedef uint32_t Elf32_Off;
-+typedef uint64_t Elf64_Off;
-+
-+/* Type for section indices, which are 16-bit quantities.  */
-+typedef uint16_t Elf32_Section;
-+typedef uint16_t Elf64_Section;
-+
-+/* Type for version symbol information.  */
-+typedef Elf32_Half Elf32_Versym;
-+typedef Elf64_Half Elf64_Versym;
-+
-+
-+/* The ELF file header.  This appears at the start of every ELF file.  */
-+
-+#define EI_NIDENT (16)
-+
-+typedef struct
-+{
-+  unsigned char       e_ident[EI_NIDENT];     /* Magic number and other info */
-+  Elf32_Half  e_type;                 /* Object file type */
-+  Elf32_Half  e_machine;              /* Architecture */
-+  Elf32_Word  e_version;              /* Object file version */
-+  Elf32_Addr  e_entry;                /* Entry point virtual address */
-+  Elf32_Off   e_phoff;                /* Program header table file offset */
-+  Elf32_Off   e_shoff;                /* Section header table file offset */
-+  Elf32_Word  e_flags;                /* Processor-specific flags */
-+  Elf32_Half  e_ehsize;               /* ELF header size in bytes */
-+  Elf32_Half  e_phentsize;            /* Program header table entry size */
-+  Elf32_Half  e_phnum;                /* Program header table entry count */
-+  Elf32_Half  e_shentsize;            /* Section header table entry size */
-+  Elf32_Half  e_shnum;                /* Section header table entry count */
-+  Elf32_Half  e_shstrndx;             /* Section header string table index */
-+} Elf32_Ehdr;
-+
-+typedef struct
-+{
-+  unsigned char       e_ident[EI_NIDENT];     /* Magic number and other info */
-+  Elf64_Half  e_type;                 /* Object file type */
-+  Elf64_Half  e_machine;              /* Architecture */
-+  Elf64_Word  e_version;              /* Object file version */
-+  Elf64_Addr  e_entry;                /* Entry point virtual address */
-+  Elf64_Off   e_phoff;                /* Program header table file offset */
-+  Elf64_Off   e_shoff;                /* Section header table file offset */
-+  Elf64_Word  e_flags;                /* Processor-specific flags */
-+  Elf64_Half  e_ehsize;               /* ELF header size in bytes */
-+  Elf64_Half  e_phentsize;            /* Program header table entry size */
-+  Elf64_Half  e_phnum;                /* Program header table entry count */
-+  Elf64_Half  e_shentsize;            /* Section header table entry size */
-+  Elf64_Half  e_shnum;                /* Section header table entry count */
-+  Elf64_Half  e_shstrndx;             /* Section header string table index */
-+} Elf64_Ehdr;
-+
-+/* Fields in the e_ident array.  The EI_* macros are indices into the
-+   array.  The macros under each EI_* macro are the values the byte
-+   may have.  */
-+
-+#define EI_MAG0               0               /* File identification byte 0 index */
-+#define ELFMAG0               0x7f            /* Magic number byte 0 */
-+
-+#define EI_MAG1               1               /* File identification byte 1 index */
-+#define ELFMAG1               'E'             /* Magic number byte 1 */
-+
-+#define EI_MAG2               2               /* File identification byte 2 index */
-+#define ELFMAG2               'L'             /* Magic number byte 2 */
-+
-+#define EI_MAG3               3               /* File identification byte 3 index */
-+#define ELFMAG3               'F'             /* Magic number byte 3 */
-+
-+/* Conglomeration of the identification bytes, for easy testing as a word.  */
-+#define       ELFMAG          "\177ELF"
-+#define       SELFMAG         4
-+
-+#define EI_CLASS      4               /* File class byte index */
-+#define ELFCLASSNONE  0               /* Invalid class */
-+#define ELFCLASS32    1               /* 32-bit objects */
-+#define ELFCLASS64    2               /* 64-bit objects */
-+#define ELFCLASSNUM   3
-+
-+#define EI_DATA               5               /* Data encoding byte index */
-+#define ELFDATANONE   0               /* Invalid data encoding */
-+#define ELFDATA2LSB   1               /* 2's complement, little endian */
-+#define ELFDATA2MSB   2               /* 2's complement, big endian */
-+#define ELFDATANUM    3
-+
-+#define EI_VERSION    6               /* File version byte index */
-+                                      /* Value must be EV_CURRENT */
-+
-+#define EI_OSABI      7               /* OS ABI identification */
-+#define ELFOSABI_NONE         0       /* UNIX System V ABI */
-+#define ELFOSABI_SYSV         0       /* Alias.  */
-+#define ELFOSABI_HPUX         1       /* HP-UX */
-+#define ELFOSABI_NETBSD               2       /* NetBSD.  */
-+#define ELFOSABI_GNU          3       /* Object uses GNU ELF extensions.  */
-+#define ELFOSABI_LINUX                ELFOSABI_GNU /* Compatibility alias.  */
-+#define ELFOSABI_SOLARIS      6       /* Sun Solaris.  */
-+#define ELFOSABI_AIX          7       /* IBM AIX.  */
-+#define ELFOSABI_IRIX         8       /* SGI Irix.  */
-+#define ELFOSABI_FREEBSD      9       /* FreeBSD.  */
-+#define ELFOSABI_TRU64                10      /* Compaq TRU64 UNIX.  */
-+#define ELFOSABI_MODESTO      11      /* Novell Modesto.  */
-+#define ELFOSABI_OPENBSD      12      /* OpenBSD.  */
-+#define ELFOSABI_ARM_AEABI    64      /* ARM EABI */
-+#define ELFOSABI_ARM          97      /* ARM */
-+#define ELFOSABI_STANDALONE   255     /* Standalone (embedded) application */
-+
-+#define EI_ABIVERSION 8               /* ABI version */
-+
-+#define EI_PAD                9               /* Byte index of padding bytes */
-+
-+/* Legal values for e_type (object file type).  */
-+
-+#define ET_NONE               0               /* No file type */
-+#define ET_REL                1               /* Relocatable file */
-+#define ET_EXEC               2               /* Executable file */
-+#define ET_DYN                3               /* Shared object file */
-+#define ET_CORE               4               /* Core file */
-+#define       ET_NUM          5               /* Number of defined types */
-+#define ET_LOOS               0xfe00          /* OS-specific range start */
-+#define ET_HIOS               0xfeff          /* OS-specific range end */
-+#define ET_LOPROC     0xff00          /* Processor-specific range start */
-+#define ET_HIPROC     0xffff          /* Processor-specific range end */
-+
-+/* Legal values for e_machine (architecture).  */
-+
-+#define EM_NONE                0              /* No machine */
-+#define EM_M32                 1              /* AT&T WE 32100 */
-+#define EM_SPARC       2              /* SUN SPARC */
-+#define EM_386                 3              /* Intel 80386 */
-+#define EM_68K                 4              /* Motorola m68k family */
-+#define EM_88K                 5              /* Motorola m88k family */
-+#define EM_860                 7              /* Intel 80860 */
-+#define EM_MIPS                8              /* MIPS R3000 big-endian */
-+#define EM_S370                9              /* IBM System/370 */
-+#define EM_MIPS_RS3_LE        10              /* MIPS R3000 little-endian */
-+
-+#define EM_PARISC     15              /* HPPA */
-+#define EM_VPP500     17              /* Fujitsu VPP500 */
-+#define EM_SPARC32PLUS        18              /* Sun's "v8plus" */
-+#define EM_960                19              /* Intel 80960 */
-+#define EM_PPC                20              /* PowerPC */
-+#define EM_PPC64      21              /* PowerPC 64-bit */
-+#define EM_S390               22              /* IBM S390 */
-+
-+#define EM_V800               36              /* NEC V800 series */
-+#define EM_FR20               37              /* Fujitsu FR20 */
-+#define EM_RH32               38              /* TRW RH-32 */
-+#define EM_RCE                39              /* Motorola RCE */
-+#define EM_ARM                40              /* ARM */
-+#define EM_FAKE_ALPHA 41              /* Digital Alpha */
-+#define EM_SH         42              /* Hitachi SH */
-+#define EM_SPARCV9    43              /* SPARC v9 64-bit */
-+#define EM_TRICORE    44              /* Siemens Tricore */
-+#define EM_ARC                45              /* Argonaut RISC Core */
-+#define EM_H8_300     46              /* Hitachi H8/300 */
-+#define EM_H8_300H    47              /* Hitachi H8/300H */
-+#define EM_H8S                48              /* Hitachi H8S */
-+#define EM_H8_500     49              /* Hitachi H8/500 */
-+#define EM_IA_64      50              /* Intel Merced */
-+#define EM_MIPS_X     51              /* Stanford MIPS-X */
-+#define EM_COLDFIRE   52              /* Motorola Coldfire */
-+#define EM_68HC12     53              /* Motorola M68HC12 */
-+#define EM_MMA                54              /* Fujitsu MMA Multimedia Accelerator*/
-+#define EM_PCP                55              /* Siemens PCP */
-+#define EM_NCPU               56              /* Sony nCPU embeeded RISC */
-+#define EM_NDR1               57              /* Denso NDR1 microprocessor */
-+#define EM_STARCORE   58              /* Motorola Start*Core processor */
-+#define EM_ME16               59              /* Toyota ME16 processor */
-+#define EM_ST100      60              /* STMicroelectronic ST100 processor */
-+#define EM_TINYJ      61              /* Advanced Logic Corp. Tinyj emb.fam*/
-+#define EM_X86_64     62              /* AMD x86-64 architecture */
-+#define EM_PDSP               63              /* Sony DSP Processor */
-+
-+#define EM_FX66               66              /* Siemens FX66 microcontroller */
-+#define EM_ST9PLUS    67              /* STMicroelectronics ST9+ 8/16 mc */
-+#define EM_ST7                68              /* STmicroelectronics ST7 8 bit mc */
-+#define EM_68HC16     69              /* Motorola MC68HC16 microcontroller */
-+#define EM_68HC11     70              /* Motorola MC68HC11 microcontroller */
-+#define EM_68HC08     71              /* Motorola MC68HC08 microcontroller */
-+#define EM_68HC05     72              /* Motorola MC68HC05 microcontroller */
-+#define EM_SVX                73              /* Silicon Graphics SVx */
-+#define EM_ST19               74              /* STMicroelectronics ST19 8 bit mc */
-+#define EM_VAX                75              /* Digital VAX */
-+#define EM_CRIS               76              /* Axis Communications 32-bit embedded processor */
-+#define EM_JAVELIN    77              /* Infineon Technologies 32-bit embedded processor */
-+#define EM_FIREPATH   78              /* Element 14 64-bit DSP Processor */
-+#define EM_ZSP                79              /* LSI Logic 16-bit DSP Processor */
-+#define EM_MMIX               80              /* Donald Knuth's educational 64-bit processor */
-+#define EM_HUANY      81              /* Harvard University machine-independent object files */
-+#define EM_PRISM      82              /* SiTera Prism */
-+#define EM_AVR                83              /* Atmel AVR 8-bit microcontroller */
-+#define EM_FR30               84              /* Fujitsu FR30 */
-+#define EM_D10V               85              /* Mitsubishi D10V */
-+#define EM_D30V               86              /* Mitsubishi D30V */
-+#define EM_V850               87              /* NEC v850 */
-+#define EM_M32R               88              /* Mitsubishi M32R */
-+#define EM_MN10300    89              /* Matsushita MN10300 */
-+#define EM_MN10200    90              /* Matsushita MN10200 */
-+#define EM_PJ         91              /* picoJava */
-+#define EM_OPENRISC   92              /* OpenRISC 32-bit embedded processor */
-+#define EM_ARC_A5     93              /* ARC Cores Tangent-A5 */
-+#define EM_XTENSA     94              /* Tensilica Xtensa Architecture */
-+#define EM_TILEPRO    188             /* Tilera TILEPro */
-+#define EM_TILEGX     191             /* Tilera TILE-Gx */
-+#define EM_NUM                192
-+
-+/* If it is necessary to assign new unofficial EM_* values, please
-+   pick large random numbers (0x8523, 0xa7f2, etc.) to minimize the
-+   chances of collision with official or non-GNU unofficial values.  */
-+
-+#define EM_ALPHA      0x9026
-+
-+/* Legal values for e_version (version).  */
-+
-+#define EV_NONE               0               /* Invalid ELF version */
-+#define EV_CURRENT    1               /* Current version */
-+#define EV_NUM                2
-+
-+/* Section header.  */
-+
-+typedef struct
-+{
-+  Elf32_Word  sh_name;                /* Section name (string tbl index) */
-+  Elf32_Word  sh_type;                /* Section type */
-+  Elf32_Word  sh_flags;               /* Section flags */
-+  Elf32_Addr  sh_addr;                /* Section virtual addr at execution */
-+  Elf32_Off   sh_offset;              /* Section file offset */
-+  Elf32_Word  sh_size;                /* Section size in bytes */
-+  Elf32_Word  sh_link;                /* Link to another section */
-+  Elf32_Word  sh_info;                /* Additional section information */
-+  Elf32_Word  sh_addralign;           /* Section alignment */
-+  Elf32_Word  sh_entsize;             /* Entry size if section holds table */
-+} Elf32_Shdr;
-+
-+typedef struct
-+{
-+  Elf64_Word  sh_name;                /* Section name (string tbl index) */
-+  Elf64_Word  sh_type;                /* Section type */
-+  Elf64_Xword sh_flags;               /* Section flags */
-+  Elf64_Addr  sh_addr;                /* Section virtual addr at execution */
-+  Elf64_Off   sh_offset;              /* Section file offset */
-+  Elf64_Xword sh_size;                /* Section size in bytes */
-+  Elf64_Word  sh_link;                /* Link to another section */
-+  Elf64_Word  sh_info;                /* Additional section information */
-+  Elf64_Xword sh_addralign;           /* Section alignment */
-+  Elf64_Xword sh_entsize;             /* Entry size if section holds table */
-+} Elf64_Shdr;
-+
-+/* Special section indices.  */
-+
-+#define SHN_UNDEF     0               /* Undefined section */
-+#define SHN_LORESERVE 0xff00          /* Start of reserved indices */
-+#define SHN_LOPROC    0xff00          /* Start of processor-specific */
-+#define SHN_BEFORE    0xff00          /* Order section before all others
-+                                         (Solaris).  */
-+#define SHN_AFTER     0xff01          /* Order section after all others
-+                                         (Solaris).  */
-+#define SHN_HIPROC    0xff1f          /* End of processor-specific */
-+#define SHN_LOOS      0xff20          /* Start of OS-specific */
-+#define SHN_HIOS      0xff3f          /* End of OS-specific */
-+#define SHN_ABS               0xfff1          /* Associated symbol is absolute */
-+#define SHN_COMMON    0xfff2          /* Associated symbol is common */
-+#define SHN_XINDEX    0xffff          /* Index is in extra table.  */
-+#define SHN_HIRESERVE 0xffff          /* End of reserved indices */
-+
-+/* Legal values for sh_type (section type).  */
-+
-+#define SHT_NULL        0             /* Section header table entry unused */
-+#define SHT_PROGBITS    1             /* Program data */
-+#define SHT_SYMTAB      2             /* Symbol table */
-+#define SHT_STRTAB      3             /* String table */
-+#define SHT_RELA        4             /* Relocation entries with addends */
-+#define SHT_HASH        5             /* Symbol hash table */
-+#define SHT_DYNAMIC     6             /* Dynamic linking information */
-+#define SHT_NOTE        7             /* Notes */
-+#define SHT_NOBITS      8             /* Program space with no data (bss) */
-+#define SHT_REL                 9             /* Relocation entries, no addends */
-+#define SHT_SHLIB       10            /* Reserved */
-+#define SHT_DYNSYM      11            /* Dynamic linker symbol table */
-+#define SHT_INIT_ARRAY          14            /* Array of constructors */
-+#define SHT_FINI_ARRAY          15            /* Array of destructors */
-+#define SHT_PREINIT_ARRAY 16          /* Array of pre-constructors */
-+#define SHT_GROUP       17            /* Section group */
-+#define SHT_SYMTAB_SHNDX  18          /* Extended section indeces */
-+#define       SHT_NUM           19            /* Number of defined types.  */
-+#define SHT_LOOS        0x60000000    /* Start OS-specific.  */
-+#define SHT_GNU_ATTRIBUTES 0x6ffffff5 /* Object attributes.  */
-+#define SHT_GNU_HASH    0x6ffffff6    /* GNU-style hash table.  */
-+#define SHT_GNU_LIBLIST         0x6ffffff7    /* Prelink library list */
-+#define SHT_CHECKSUM    0x6ffffff8    /* Checksum for DSO content.  */
-+#define SHT_LOSUNW      0x6ffffffa    /* Sun-specific low bound.  */
-+#define SHT_SUNW_move   0x6ffffffa
-+#define SHT_SUNW_COMDAT   0x6ffffffb
-+#define SHT_SUNW_syminfo  0x6ffffffc
-+#define SHT_GNU_verdef          0x6ffffffd    /* Version definition section.  */
-+#define SHT_GNU_verneed         0x6ffffffe    /* Version needs section.  */
-+#define SHT_GNU_versym          0x6fffffff    /* Version symbol table.  */
-+#define SHT_HISUNW      0x6fffffff    /* Sun-specific high bound.  */
-+#define SHT_HIOS        0x6fffffff    /* End OS-specific type */
-+#define SHT_LOPROC      0x70000000    /* Start of processor-specific */
-+#define SHT_HIPROC      0x7fffffff    /* End of processor-specific */
-+#define SHT_LOUSER      0x80000000    /* Start of application-specific */
-+#define SHT_HIUSER      0x8fffffff    /* End of application-specific */
-+
-+/* Legal values for sh_flags (section flags).  */
-+
-+#define SHF_WRITE          (1 << 0)   /* Writable */
-+#define SHF_ALLOC          (1 << 1)   /* Occupies memory during execution */
-+#define SHF_EXECINSTR      (1 << 2)   /* Executable */
-+#define SHF_MERGE          (1 << 4)   /* Might be merged */
-+#define SHF_STRINGS        (1 << 5)   /* Contains nul-terminated strings */
-+#define SHF_INFO_LINK      (1 << 6)   /* `sh_info' contains SHT index */
-+#define SHF_LINK_ORDER             (1 << 7)   /* Preserve order after combining */
-+#define SHF_OS_NONCONFORMING (1 << 8) /* Non-standard OS specific handling
-+                                         required */
-+#define SHF_GROUP          (1 << 9)   /* Section is member of a group.  */
-+#define SHF_TLS                    (1 << 10)  /* Section hold thread-local data.  */
-+#define SHF_MASKOS         0x0ff00000 /* OS-specific.  */
-+#define SHF_MASKPROC       0xf0000000 /* Processor-specific */
-+#define SHF_ORDERED        (1 << 30)  /* Special ordering requirement
-+                                         (Solaris).  */
-+#define SHF_EXCLUDE        (1 << 31)  /* Section is excluded unless
-+                                         referenced or allocated (Solaris).*/
-+
-+/* Section group handling.  */
-+#define GRP_COMDAT    0x1             /* Mark group as COMDAT.  */
-+
-+/* Symbol table entry.  */
-+
-+typedef struct
-+{
-+  Elf32_Word  st_name;                /* Symbol name (string tbl index) */
-+  Elf32_Addr  st_value;               /* Symbol value */
-+  Elf32_Word  st_size;                /* Symbol size */
-+  unsigned char       st_info;                /* Symbol type and binding */
-+  unsigned char       st_other;               /* Symbol visibility */
-+  Elf32_Section       st_shndx;               /* Section index */
-+} Elf32_Sym;
-+
-+typedef struct
-+{
-+  Elf64_Word  st_name;                /* Symbol name (string tbl index) */
-+  unsigned char       st_info;                /* Symbol type and binding */
-+  unsigned char st_other;             /* Symbol visibility */
-+  Elf64_Section       st_shndx;               /* Section index */
-+  Elf64_Addr  st_value;               /* Symbol value */
-+  Elf64_Xword st_size;                /* Symbol size */
-+} Elf64_Sym;
-+
-+/* The syminfo section if available contains additional information about
-+   every dynamic symbol.  */
-+
-+typedef struct
-+{
-+  Elf32_Half si_boundto;              /* Direct bindings, symbol bound to */
-+  Elf32_Half si_flags;                        /* Per symbol flags */
-+} Elf32_Syminfo;
-+
-+typedef struct
-+{
-+  Elf64_Half si_boundto;              /* Direct bindings, symbol bound to */
-+  Elf64_Half si_flags;                        /* Per symbol flags */
-+} Elf64_Syminfo;
-+
-+/* Possible values for si_boundto.  */
-+#define SYMINFO_BT_SELF               0xffff  /* Symbol bound to self */
-+#define SYMINFO_BT_PARENT     0xfffe  /* Symbol bound to parent */
-+#define SYMINFO_BT_LOWRESERVE 0xff00  /* Beginning of reserved entries */
-+
-+/* Possible bitmasks for si_flags.  */
-+#define SYMINFO_FLG_DIRECT    0x0001  /* Direct bound symbol */
-+#define SYMINFO_FLG_PASSTHRU  0x0002  /* Pass-thru symbol for translator */
-+#define SYMINFO_FLG_COPY      0x0004  /* Symbol is a copy-reloc */
-+#define SYMINFO_FLG_LAZYLOAD  0x0008  /* Symbol bound to object to be lazy
-+                                         loaded */
-+/* Syminfo version values.  */
-+#define SYMINFO_NONE          0
-+#define SYMINFO_CURRENT               1
-+#define SYMINFO_NUM           2
-+
-+
-+/* How to extract and insert information held in the st_info field.  */
-+
-+#define ELF32_ST_BIND(val)            (((unsigned char) (val)) >> 4)
-+#define ELF32_ST_TYPE(val)            ((val) & 0xf)
-+#define ELF32_ST_INFO(bind, type)     (((bind) << 4) + ((type) & 0xf))
-+
-+/* Both Elf32_Sym and Elf64_Sym use the same one-byte st_info field.  */
-+#define ELF64_ST_BIND(val)            ELF32_ST_BIND (val)
-+#define ELF64_ST_TYPE(val)            ELF32_ST_TYPE (val)
-+#define ELF64_ST_INFO(bind, type)     ELF32_ST_INFO ((bind), (type))
-+
-+/* Legal values for ST_BIND subfield of st_info (symbol binding).  */
-+
-+#define STB_LOCAL     0               /* Local symbol */
-+#define STB_GLOBAL    1               /* Global symbol */
-+#define STB_WEAK      2               /* Weak symbol */
-+#define       STB_NUM         3               /* Number of defined types.  */
-+#define STB_LOOS      10              /* Start of OS-specific */
-+#define STB_GNU_UNIQUE        10              /* Unique symbol.  */
-+#define STB_HIOS      12              /* End of OS-specific */
-+#define STB_LOPROC    13              /* Start of processor-specific */
-+#define STB_HIPROC    15              /* End of processor-specific */
-+
-+/* Legal values for ST_TYPE subfield of st_info (symbol type).  */
-+
-+#define STT_NOTYPE    0               /* Symbol type is unspecified */
-+#define STT_OBJECT    1               /* Symbol is a data object */
-+#define STT_FUNC      2               /* Symbol is a code object */
-+#define STT_SECTION   3               /* Symbol associated with a section */
-+#define STT_FILE      4               /* Symbol's name is file name */
-+#define STT_COMMON    5               /* Symbol is a common data object */
-+#define STT_TLS               6               /* Symbol is thread-local data object*/
-+#define       STT_NUM         7               /* Number of defined types.  */
-+#define STT_LOOS      10              /* Start of OS-specific */
-+#define STT_GNU_IFUNC 10              /* Symbol is indirect code object */
-+#define STT_HIOS      12              /* End of OS-specific */
-+#define STT_LOPROC    13              /* Start of processor-specific */
-+#define STT_HIPROC    15              /* End of processor-specific */
-+
-+
-+/* Symbol table indices are found in the hash buckets and chain table
-+   of a symbol hash table section.  This special index value indicates
-+   the end of a chain, meaning no further symbols are found in that bucket.  */
-+
-+#define STN_UNDEF     0               /* End of a chain.  */
-+
-+
-+/* How to extract and insert information held in the st_other field.  */
-+
-+#define ELF32_ST_VISIBILITY(o)        ((o) & 0x03)
-+
-+/* For ELF64 the definitions are the same.  */
-+#define ELF64_ST_VISIBILITY(o)        ELF32_ST_VISIBILITY (o)
-+
-+/* Symbol visibility specification encoded in the st_other field.  */
-+#define STV_DEFAULT   0               /* Default symbol visibility rules */
-+#define STV_INTERNAL  1               /* Processor specific hidden class */
-+#define STV_HIDDEN    2               /* Sym unavailable in other modules */
-+#define STV_PROTECTED 3               /* Not preemptible, not exported */
-+
-+
-+/* Relocation table entry without addend (in section of type SHT_REL).  */
-+
-+typedef struct
-+{
-+  Elf32_Addr  r_offset;               /* Address */
-+  Elf32_Word  r_info;                 /* Relocation type and symbol index */
-+} Elf32_Rel;
-+
-+/* I have seen two different definitions of the Elf64_Rel and
-+   Elf64_Rela structures, so we'll leave them out until Novell (or
-+   whoever) gets their act together.  */
-+/* The following, at least, is used on Sparc v9, MIPS, and Alpha.  */
-+
-+typedef struct
-+{
-+  Elf64_Addr  r_offset;               /* Address */
-+  Elf64_Xword r_info;                 /* Relocation type and symbol index */
-+} Elf64_Rel;
-+
-+/* Relocation table entry with addend (in section of type SHT_RELA).  */
-+
-+typedef struct
-+{
-+  Elf32_Addr  r_offset;               /* Address */
-+  Elf32_Word  r_info;                 /* Relocation type and symbol index */
-+  Elf32_Sword r_addend;               /* Addend */
-+} Elf32_Rela;
-+
-+typedef struct
-+{
-+  Elf64_Addr  r_offset;               /* Address */
-+  Elf64_Xword r_info;                 /* Relocation type and symbol index */
-+  Elf64_Sxword        r_addend;               /* Addend */
-+} Elf64_Rela;
-+
-+/* How to extract and insert information held in the r_info field.  */
-+
-+#define ELF32_R_SYM(val)              ((val) >> 8)
-+#define ELF32_R_TYPE(val)             ((val) & 0xff)
-+#define ELF32_R_INFO(sym, type)               (((sym) << 8) + ((type) & 0xff))
-+
-+#define ELF64_R_SYM(i)                        ((i) >> 32)
-+#define ELF64_R_TYPE(i)                       ((i) & 0xffffffff)
-+#define ELF64_R_INFO(sym,type)                ((((Elf64_Xword) (sym)) << 32) + (type))
-+
-+/* Program segment header.  */
-+
-+typedef struct
-+{
-+  Elf32_Word  p_type;                 /* Segment type */
-+  Elf32_Off   p_offset;               /* Segment file offset */
-+  Elf32_Addr  p_vaddr;                /* Segment virtual address */
-+  Elf32_Addr  p_paddr;                /* Segment physical address */
-+  Elf32_Word  p_filesz;               /* Segment size in file */
-+  Elf32_Word  p_memsz;                /* Segment size in memory */
-+  Elf32_Word  p_flags;                /* Segment flags */
-+  Elf32_Word  p_align;                /* Segment alignment */
-+} Elf32_Phdr;
-+
-+typedef struct
-+{
-+  Elf64_Word  p_type;                 /* Segment type */
-+  Elf64_Word  p_flags;                /* Segment flags */
-+  Elf64_Off   p_offset;               /* Segment file offset */
-+  Elf64_Addr  p_vaddr;                /* Segment virtual address */
-+  Elf64_Addr  p_paddr;                /* Segment physical address */
-+  Elf64_Xword p_filesz;               /* Segment size in file */
-+  Elf64_Xword p_memsz;                /* Segment size in memory */
-+  Elf64_Xword p_align;                /* Segment alignment */
-+} Elf64_Phdr;
-+
-+/* Special value for e_phnum.  This indicates that the real number of
-+   program headers is too large to fit into e_phnum.  Instead the real
-+   value is in the field sh_info of section 0.  */
-+
-+#define PN_XNUM               0xffff
-+
-+/* Legal values for p_type (segment type).  */
-+
-+#define       PT_NULL         0               /* Program header table entry unused */
-+#define PT_LOAD               1               /* Loadable program segment */
-+#define PT_DYNAMIC    2               /* Dynamic linking information */
-+#define PT_INTERP     3               /* Program interpreter */
-+#define PT_NOTE               4               /* Auxiliary information */
-+#define PT_SHLIB      5               /* Reserved */
-+#define PT_PHDR               6               /* Entry for header table itself */
-+#define PT_TLS                7               /* Thread-local storage segment */
-+#define       PT_NUM          8               /* Number of defined types */
-+#define PT_LOOS               0x60000000      /* Start of OS-specific */
-+#define PT_GNU_EH_FRAME       0x6474e550      /* GCC .eh_frame_hdr segment */
-+#define PT_GNU_STACK  0x6474e551      /* Indicates stack executability */
-+#define PT_GNU_RELRO  0x6474e552      /* Read-only after relocation */
-+#define PT_LOSUNW     0x6ffffffa
-+#define PT_SUNWBSS    0x6ffffffa      /* Sun Specific segment */
-+#define PT_SUNWSTACK  0x6ffffffb      /* Stack segment */
-+#define PT_HISUNW     0x6fffffff
-+#define PT_HIOS               0x6fffffff      /* End of OS-specific */
-+#define PT_LOPROC     0x70000000      /* Start of processor-specific */
-+#define PT_HIPROC     0x7fffffff      /* End of processor-specific */
-+
-+/* Legal values for p_flags (segment flags).  */
-+
-+#define PF_X          (1 << 0)        /* Segment is executable */
-+#define PF_W          (1 << 1)        /* Segment is writable */
-+#define PF_R          (1 << 2)        /* Segment is readable */
-+#define PF_MASKOS     0x0ff00000      /* OS-specific */
-+#define PF_MASKPROC   0xf0000000      /* Processor-specific */
-+
-+/* Legal values for note segment descriptor types for core files. */
-+
-+#define NT_PRSTATUS   1               /* Contains copy of prstatus struct */
-+#define NT_FPREGSET   2               /* Contains copy of fpregset struct */
-+#define NT_PRPSINFO   3               /* Contains copy of prpsinfo struct */
-+#define NT_PRXREG     4               /* Contains copy of prxregset struct */
-+#define NT_TASKSTRUCT 4               /* Contains copy of task structure */
-+#define NT_PLATFORM   5               /* String from sysinfo(SI_PLATFORM) */
-+#define NT_AUXV               6               /* Contains copy of auxv array */
-+#define NT_GWINDOWS   7               /* Contains copy of gwindows struct */
-+#define NT_ASRS               8               /* Contains copy of asrset struct */
-+#define NT_PSTATUS    10              /* Contains copy of pstatus struct */
-+#define NT_PSINFO     13              /* Contains copy of psinfo struct */
-+#define NT_PRCRED     14              /* Contains copy of prcred struct */
-+#define NT_UTSNAME    15              /* Contains copy of utsname struct */
-+#define NT_LWPSTATUS  16              /* Contains copy of lwpstatus struct */
-+#define NT_LWPSINFO   17              /* Contains copy of lwpinfo struct */
-+#define NT_PRFPXREG   20              /* Contains copy of fprxregset struct */
-+#define NT_PRXFPREG   0x46e62b7f      /* Contains copy of user_fxsr_struct */
-+#define NT_PPC_VMX    0x100           /* PowerPC Altivec/VMX registers */
-+#define NT_PPC_SPE    0x101           /* PowerPC SPE/EVR registers */
-+#define NT_PPC_VSX    0x102           /* PowerPC VSX registers */
-+#define NT_386_TLS    0x200           /* i386 TLS slots (struct user_desc) */
-+#define NT_386_IOPERM 0x201           /* x86 io permission bitmap (1=deny) */
-+#define NT_X86_XSTATE 0x202           /* x86 extended state using xsave */
-+
-+/* Legal values for the note segment descriptor types for object files.  */
-+
-+#define NT_VERSION    1               /* Contains a version string.  */
-+
-+
-+/* Dynamic section entry.  */
-+
-+typedef struct
-+{
-+  Elf32_Sword d_tag;                  /* Dynamic entry type */
-+  union
-+    {
-+      Elf32_Word d_val;                       /* Integer value */
-+      Elf32_Addr d_ptr;                       /* Address value */
-+    } d_un;
-+} Elf32_Dyn;
-+
-+typedef struct
-+{
-+  Elf64_Sxword        d_tag;                  /* Dynamic entry type */
-+  union
-+    {
-+      Elf64_Xword d_val;              /* Integer value */
-+      Elf64_Addr d_ptr;                       /* Address value */
-+    } d_un;
-+} Elf64_Dyn;
-+
-+/* Legal values for d_tag (dynamic entry type).  */
-+
-+#define DT_NULL               0               /* Marks end of dynamic section */
-+#define DT_NEEDED     1               /* Name of needed library */
-+#define DT_PLTRELSZ   2               /* Size in bytes of PLT relocs */
-+#define DT_PLTGOT     3               /* Processor defined value */
-+#define DT_HASH               4               /* Address of symbol hash table */
-+#define DT_STRTAB     5               /* Address of string table */
-+#define DT_SYMTAB     6               /* Address of symbol table */
-+#define DT_RELA               7               /* Address of Rela relocs */
-+#define DT_RELASZ     8               /* Total size of Rela relocs */
-+#define DT_RELAENT    9               /* Size of one Rela reloc */
-+#define DT_STRSZ      10              /* Size of string table */
-+#define DT_SYMENT     11              /* Size of one symbol table entry */
-+#define DT_INIT               12              /* Address of init function */
-+#define DT_FINI               13              /* Address of termination function */
-+#define DT_SONAME     14              /* Name of shared object */
-+#define DT_RPATH      15              /* Library search path (deprecated) */
-+#define DT_SYMBOLIC   16              /* Start symbol search here */
-+#define DT_REL                17              /* Address of Rel relocs */
-+#define DT_RELSZ      18              /* Total size of Rel relocs */
-+#define DT_RELENT     19              /* Size of one Rel reloc */
-+#define DT_PLTREL     20              /* Type of reloc in PLT */
-+#define DT_DEBUG      21              /* For debugging; unspecified */
-+#define DT_TEXTREL    22              /* Reloc might modify .text */
-+#define DT_JMPREL     23              /* Address of PLT relocs */
-+#define       DT_BIND_NOW     24              /* Process relocations of object */
-+#define       DT_INIT_ARRAY   25              /* Array with addresses of init fct */
-+#define       DT_FINI_ARRAY   26              /* Array with addresses of fini fct */
-+#define       DT_INIT_ARRAYSZ 27              /* Size in bytes of DT_INIT_ARRAY */
-+#define       DT_FINI_ARRAYSZ 28              /* Size in bytes of DT_FINI_ARRAY */
-+#define DT_RUNPATH    29              /* Library search path */
-+#define DT_FLAGS      30              /* Flags for the object being loaded */
-+#define DT_ENCODING   32              /* Start of encoded range */
-+#define DT_PREINIT_ARRAY 32           /* Array with addresses of preinit fct*/
-+#define DT_PREINIT_ARRAYSZ 33         /* size in bytes of DT_PREINIT_ARRAY */
-+#define       DT_NUM          34              /* Number used */
-+#define DT_LOOS               0x6000000d      /* Start of OS-specific */
-+#define DT_HIOS               0x6ffff000      /* End of OS-specific */
-+#define DT_LOPROC     0x70000000      /* Start of processor-specific */
-+#define DT_HIPROC     0x7fffffff      /* End of processor-specific */
-+#define       DT_PROCNUM      DT_MIPS_NUM     /* Most used by any processor */
-+
-+/* DT_* entries which fall between DT_VALRNGHI & DT_VALRNGLO use the
-+   Dyn.d_un.d_val field of the Elf*_Dyn structure.  This follows Sun's
-+   approach.  */
-+#define DT_VALRNGLO   0x6ffffd00
-+#define DT_GNU_PRELINKED 0x6ffffdf5   /* Prelinking timestamp */
-+#define DT_GNU_CONFLICTSZ 0x6ffffdf6  /* Size of conflict section */
-+#define DT_GNU_LIBLISTSZ 0x6ffffdf7   /* Size of library list */
-+#define DT_CHECKSUM   0x6ffffdf8
-+#define DT_PLTPADSZ   0x6ffffdf9
-+#define DT_MOVEENT    0x6ffffdfa
-+#define DT_MOVESZ     0x6ffffdfb
-+#define DT_FEATURE_1  0x6ffffdfc      /* Feature selection (DTF_*).  */
-+#define DT_POSFLAG_1  0x6ffffdfd      /* Flags for DT_* entries, effecting
-+                                         the following DT_* entry.  */
-+#define DT_SYMINSZ    0x6ffffdfe      /* Size of syminfo table (in bytes) */
-+#define DT_SYMINENT   0x6ffffdff      /* Entry size of syminfo */
-+#define DT_VALRNGHI   0x6ffffdff
-+#define DT_VALTAGIDX(tag)     (DT_VALRNGHI - (tag))   /* Reverse order! */
-+#define DT_VALNUM 12
-+
-+/* DT_* entries which fall between DT_ADDRRNGHI & DT_ADDRRNGLO use the
-+   Dyn.d_un.d_ptr field of the Elf*_Dyn structure.
-+
-+   If any adjustment is made to the ELF object after it has been
-+   built these entries will need to be adjusted.  */
-+#define DT_ADDRRNGLO  0x6ffffe00
-+#define DT_GNU_HASH   0x6ffffef5      /* GNU-style hash table.  */
-+#define DT_TLSDESC_PLT        0x6ffffef6
-+#define DT_TLSDESC_GOT        0x6ffffef7
-+#define DT_GNU_CONFLICT       0x6ffffef8      /* Start of conflict section */
-+#define DT_GNU_LIBLIST        0x6ffffef9      /* Library list */
-+#define DT_CONFIG     0x6ffffefa      /* Configuration information.  */
-+#define DT_DEPAUDIT   0x6ffffefb      /* Dependency auditing.  */
-+#define DT_AUDIT      0x6ffffefc      /* Object auditing.  */
-+#define       DT_PLTPAD       0x6ffffefd      /* PLT padding.  */
-+#define       DT_MOVETAB      0x6ffffefe      /* Move table.  */
-+#define DT_SYMINFO    0x6ffffeff      /* Syminfo table.  */
-+#define DT_ADDRRNGHI  0x6ffffeff
-+#define DT_ADDRTAGIDX(tag)    (DT_ADDRRNGHI - (tag))  /* Reverse order! */
-+#define DT_ADDRNUM 11
-+
-+/* The versioning entry types.  The next are defined as part of the
-+   GNU extension.  */
-+#define DT_VERSYM     0x6ffffff0
-+
-+#define DT_RELACOUNT  0x6ffffff9
-+#define DT_RELCOUNT   0x6ffffffa
-+
-+/* These were chosen by Sun.  */
-+#define DT_FLAGS_1    0x6ffffffb      /* State flags, see DF_1_* below.  */
-+#define       DT_VERDEF       0x6ffffffc      /* Address of version definition
-+                                         table */
-+#define       DT_VERDEFNUM    0x6ffffffd      /* Number of version definitions */
-+#define       DT_VERNEED      0x6ffffffe      /* Address of table with needed
-+                                         versions */
-+#define       DT_VERNEEDNUM   0x6fffffff      /* Number of needed versions */
-+#define DT_VERSIONTAGIDX(tag) (DT_VERNEEDNUM - (tag)) /* Reverse order! */
-+#define DT_VERSIONTAGNUM 16
-+
-+/* Sun added these machine-independent extensions in the "processor-specific"
-+   range.  Be compatible.  */
-+#define DT_AUXILIARY    0x7ffffffd      /* Shared object to load before self */
-+#define DT_FILTER       0x7fffffff      /* Shared object to get values from */
-+#define DT_EXTRATAGIDX(tag)   ((Elf32_Word)-((Elf32_Sword) (tag) <<1>>1)-1)
-+#define DT_EXTRANUM   3
-+
-+/* Values of `d_un.d_val' in the DT_FLAGS entry.  */
-+#define DF_ORIGIN     0x00000001      /* Object may use DF_ORIGIN */
-+#define DF_SYMBOLIC   0x00000002      /* Symbol resolutions starts here */
-+#define DF_TEXTREL    0x00000004      /* Object contains text relocations */
-+#define DF_BIND_NOW   0x00000008      /* No lazy binding for this object */
-+#define DF_STATIC_TLS 0x00000010      /* Module uses the static TLS model */
-+
-+/* State flags selectable in the `d_un.d_val' element of the DT_FLAGS_1
-+   entry in the dynamic section.  */
-+#define DF_1_NOW      0x00000001      /* Set RTLD_NOW for this object.  */
-+#define DF_1_GLOBAL   0x00000002      /* Set RTLD_GLOBAL for this object.  */
-+#define DF_1_GROUP    0x00000004      /* Set RTLD_GROUP for this object.  */
-+#define DF_1_NODELETE 0x00000008      /* Set RTLD_NODELETE for this object.*/
-+#define DF_1_LOADFLTR 0x00000010      /* Trigger filtee loading at runtime.*/
-+#define DF_1_INITFIRST        0x00000020      /* Set RTLD_INITFIRST for this object*/
-+#define DF_1_NOOPEN   0x00000040      /* Set RTLD_NOOPEN for this object.  */
-+#define DF_1_ORIGIN   0x00000080      /* $ORIGIN must be handled.  */
-+#define DF_1_DIRECT   0x00000100      /* Direct binding enabled.  */
-+#define DF_1_TRANS    0x00000200
-+#define DF_1_INTERPOSE        0x00000400      /* Object is used to interpose.  */
-+#define DF_1_NODEFLIB 0x00000800      /* Ignore default lib search path.  */
-+#define DF_1_NODUMP   0x00001000      /* Object can't be dldump'ed.  */
-+#define DF_1_CONFALT  0x00002000      /* Configuration alternative created.*/
-+#define DF_1_ENDFILTEE        0x00004000      /* Filtee terminates filters search. */
-+#define       DF_1_DISPRELDNE 0x00008000      /* Disp reloc applied at build time. */
-+#define       DF_1_DISPRELPND 0x00010000      /* Disp reloc applied at run-time.  */
-+
-+/* Flags for the feature selection in DT_FEATURE_1.  */
-+#define DTF_1_PARINIT 0x00000001
-+#define DTF_1_CONFEXP 0x00000002
-+
-+/* Flags in the DT_POSFLAG_1 entry effecting only the next DT_* entry.  */
-+#define DF_P1_LAZYLOAD        0x00000001      /* Lazyload following object.  */
-+#define DF_P1_GROUPPERM       0x00000002      /* Symbols from next object are not
-+                                         generally available.  */
-+
-+/* Version definition sections.  */
-+
-+typedef struct
-+{
-+  Elf32_Half  vd_version;             /* Version revision */
-+  Elf32_Half  vd_flags;               /* Version information */
-+  Elf32_Half  vd_ndx;                 /* Version Index */
-+  Elf32_Half  vd_cnt;                 /* Number of associated aux entries */
-+  Elf32_Word  vd_hash;                /* Version name hash value */
-+  Elf32_Word  vd_aux;                 /* Offset in bytes to verdaux array */
-+  Elf32_Word  vd_next;                /* Offset in bytes to next verdef
-+                                         entry */
-+} Elf32_Verdef;
-+
-+typedef struct
-+{
-+  Elf64_Half  vd_version;             /* Version revision */
-+  Elf64_Half  vd_flags;               /* Version information */
-+  Elf64_Half  vd_ndx;                 /* Version Index */
-+  Elf64_Half  vd_cnt;                 /* Number of associated aux entries */
-+  Elf64_Word  vd_hash;                /* Version name hash value */
-+  Elf64_Word  vd_aux;                 /* Offset in bytes to verdaux array */
-+  Elf64_Word  vd_next;                /* Offset in bytes to next verdef
-+                                         entry */
-+} Elf64_Verdef;
-+
-+
-+/* Legal values for vd_version (version revision).  */
-+#define VER_DEF_NONE  0               /* No version */
-+#define VER_DEF_CURRENT       1               /* Current version */
-+#define VER_DEF_NUM   2               /* Given version number */
-+
-+/* Legal values for vd_flags (version information flags).  */
-+#define VER_FLG_BASE  0x1             /* Version definition of file itself */
-+#define VER_FLG_WEAK  0x2             /* Weak version identifier */
-+
-+/* Versym symbol index values.  */
-+#define       VER_NDX_LOCAL           0       /* Symbol is local.  */
-+#define       VER_NDX_GLOBAL          1       /* Symbol is global.  */
-+#define       VER_NDX_LORESERVE       0xff00  /* Beginning of reserved entries.  */
-+#define       VER_NDX_ELIMINATE       0xff01  /* Symbol is to be eliminated.  */
-+
-+/* Auxialiary version information.  */
-+
-+typedef struct
-+{
-+  Elf32_Word  vda_name;               /* Version or dependency names */
-+  Elf32_Word  vda_next;               /* Offset in bytes to next verdaux
-+                                         entry */
-+} Elf32_Verdaux;
-+
-+typedef struct
-+{
-+  Elf64_Word  vda_name;               /* Version or dependency names */
-+  Elf64_Word  vda_next;               /* Offset in bytes to next verdaux
-+                                         entry */
-+} Elf64_Verdaux;
-+
-+
-+/* Version dependency section.  */
-+
-+typedef struct
-+{
-+  Elf32_Half  vn_version;             /* Version of structure */
-+  Elf32_Half  vn_cnt;                 /* Number of associated aux entries */
-+  Elf32_Word  vn_file;                /* Offset of filename for this
-+                                         dependency */
-+  Elf32_Word  vn_aux;                 /* Offset in bytes to vernaux array */
-+  Elf32_Word  vn_next;                /* Offset in bytes to next verneed
-+                                         entry */
-+} Elf32_Verneed;
-+
-+typedef struct
-+{
-+  Elf64_Half  vn_version;             /* Version of structure */
-+  Elf64_Half  vn_cnt;                 /* Number of associated aux entries */
-+  Elf64_Word  vn_file;                /* Offset of filename for this
-+                                         dependency */
-+  Elf64_Word  vn_aux;                 /* Offset in bytes to vernaux array */
-+  Elf64_Word  vn_next;                /* Offset in bytes to next verneed
-+                                         entry */
-+} Elf64_Verneed;
-+
-+
-+/* Legal values for vn_version (version revision).  */
-+#define VER_NEED_NONE  0              /* No version */
-+#define VER_NEED_CURRENT 1            /* Current version */
-+#define VER_NEED_NUM   2              /* Given version number */
-+
-+/* Auxiliary needed version information.  */
-+
-+typedef struct
-+{
-+  Elf32_Word  vna_hash;               /* Hash value of dependency name */
-+  Elf32_Half  vna_flags;              /* Dependency specific information */
-+  Elf32_Half  vna_other;              /* Unused */
-+  Elf32_Word  vna_name;               /* Dependency name string offset */
-+  Elf32_Word  vna_next;               /* Offset in bytes to next vernaux
-+                                         entry */
-+} Elf32_Vernaux;
-+
-+typedef struct
-+{
-+  Elf64_Word  vna_hash;               /* Hash value of dependency name */
-+  Elf64_Half  vna_flags;              /* Dependency specific information */
-+  Elf64_Half  vna_other;              /* Unused */
-+  Elf64_Word  vna_name;               /* Dependency name string offset */
-+  Elf64_Word  vna_next;               /* Offset in bytes to next vernaux
-+                                         entry */
-+} Elf64_Vernaux;
-+
-+
-+/* Legal values for vna_flags.  */
-+#define VER_FLG_WEAK  0x2             /* Weak version identifier */
-+
-+
-+/* Auxiliary vector.  */
-+
-+/* This vector is normally only used by the program interpreter.  The
-+   usual definition in an ABI supplement uses the name auxv_t.  The
-+   vector is not usually defined in a standard <elf.h> file, but it
-+   can't hurt.  We rename it to avoid conflicts.  The sizes of these
-+   types are an arrangement between the exec server and the program
-+   interpreter, so we don't fully specify them here.  */
-+
-+typedef struct
-+{
-+  uint32_t a_type;            /* Entry type */
-+  union
-+    {
-+      uint32_t a_val;         /* Integer value */
-+      /* We use to have pointer elements added here.  We cannot do that,
-+       though, since it does not work when using 32-bit definitions
-+       on 64-bit platforms and vice versa.  */
-+    } a_un;
-+} Elf32_auxv_t;
-+
-+typedef struct
-+{
-+  uint64_t a_type;            /* Entry type */
-+  union
-+    {
-+      uint64_t a_val;         /* Integer value */
-+      /* We use to have pointer elements added here.  We cannot do that,
-+       though, since it does not work when using 32-bit definitions
-+       on 64-bit platforms and vice versa.  */
-+    } a_un;
-+} Elf64_auxv_t;
-+
-+/* Legal values for a_type (entry type).  */
-+
-+#define AT_NULL               0               /* End of vector */
-+#define AT_IGNORE     1               /* Entry should be ignored */
-+#define AT_EXECFD     2               /* File descriptor of program */
-+#define AT_PHDR               3               /* Program headers for program */
-+#define AT_PHENT      4               /* Size of program header entry */
-+#define AT_PHNUM      5               /* Number of program headers */
-+#define AT_PAGESZ     6               /* System page size */
-+#define AT_BASE               7               /* Base address of interpreter */
-+#define AT_FLAGS      8               /* Flags */
-+#define AT_ENTRY      9               /* Entry point of program */
-+#define AT_NOTELF     10              /* Program is not ELF */
-+#define AT_UID                11              /* Real uid */
-+#define AT_EUID               12              /* Effective uid */
-+#define AT_GID                13              /* Real gid */
-+#define AT_EGID               14              /* Effective gid */
-+#define AT_CLKTCK     17              /* Frequency of times() */
-+
-+/* Some more special a_type values describing the hardware.  */
-+#define AT_PLATFORM   15              /* String identifying platform.  */
-+#define AT_HWCAP      16              /* Machine dependent hints about
-+                                         processor capabilities.  */
-+
-+/* This entry gives some information about the FPU initialization
-+   performed by the kernel.  */
-+#define AT_FPUCW      18              /* Used FPU control word.  */
-+
-+/* Cache block sizes.  */
-+#define AT_DCACHEBSIZE        19              /* Data cache block size.  */
-+#define AT_ICACHEBSIZE        20              /* Instruction cache block size.  */
-+#define AT_UCACHEBSIZE        21              /* Unified cache block size.  */
-+
-+/* A special ignored value for PPC, used by the kernel to control the
-+   interpretation of the AUXV. Must be > 16.  */
-+#define AT_IGNOREPPC  22              /* Entry should be ignored.  */
-+
-+#define       AT_SECURE       23              /* Boolean, was exec setuid-like?  */
-+
-+#define AT_BASE_PLATFORM 24           /* String identifying real platforms.*/
-+
-+#define AT_RANDOM     25              /* Address of 16 random bytes.  */
-+
-+#define AT_EXECFN     31              /* Filename of executable.  */
-+
-+/* Pointer to the global system page used for system calls and other
-+   nice things.  */
-+#define AT_SYSINFO    32
-+#define AT_SYSINFO_EHDR       33
-+
-+/* Shapes of the caches.  Bits 0-3 contains associativity; bits 4-7 contains
-+   log2 of line size; mask those to get cache size.  */
-+#define AT_L1I_CACHESHAPE     34
-+#define AT_L1D_CACHESHAPE     35
-+#define AT_L2_CACHESHAPE      36
-+#define AT_L3_CACHESHAPE      37
-+
-+/* Note section contents.  Each entry in the note section begins with
-+   a header of a fixed form.  */
-+
-+typedef struct
-+{
-+  Elf32_Word n_namesz;                        /* Length of the note's name.  */
-+  Elf32_Word n_descsz;                        /* Length of the note's descriptor.  */
-+  Elf32_Word n_type;                  /* Type of the note.  */
-+} Elf32_Nhdr;
-+
-+typedef struct
-+{
-+  Elf64_Word n_namesz;                        /* Length of the note's name.  */
-+  Elf64_Word n_descsz;                        /* Length of the note's descriptor.  */
-+  Elf64_Word n_type;                  /* Type of the note.  */
-+} Elf64_Nhdr;
-+
-+/* Known names of notes.  */
-+
-+/* Solaris entries in the note section have this name.  */
-+#define ELF_NOTE_SOLARIS      "SUNW Solaris"
-+
-+/* Note entries for GNU systems have this name.  */
-+#define ELF_NOTE_GNU          "GNU"
-+
-+
-+/* Defined types of notes for Solaris.  */
-+
-+/* Value of descriptor (one word) is desired pagesize for the binary.  */
-+#define ELF_NOTE_PAGESIZE_HINT        1
-+
-+
-+/* Defined note types for GNU systems.  */
-+
-+/* ABI information.  The descriptor consists of words:
-+   word 0: OS descriptor
-+   word 1: major version of the ABI
-+   word 2: minor version of the ABI
-+   word 3: subminor version of the ABI
-+*/
-+#define NT_GNU_ABI_TAG        1
-+#define ELF_NOTE_ABI  NT_GNU_ABI_TAG /* Old name.  */
-+
-+/* Known OSes.  These values can appear in word 0 of an
-+   NT_GNU_ABI_TAG note section entry.  */
-+#define ELF_NOTE_OS_LINUX     0
-+#define ELF_NOTE_OS_GNU               1
-+#define ELF_NOTE_OS_SOLARIS2  2
-+#define ELF_NOTE_OS_FREEBSD   3
-+
-+/* Synthetic hwcap information.  The descriptor begins with two words:
-+   word 0: number of entries
-+   word 1: bitmask of enabled entries
-+   Then follow variable-length entries, one byte followed by a
-+   '\0'-terminated hwcap name string.  The byte gives the bit
-+   number to test if enabled, (1U << bit) & bitmask.  */
-+#define NT_GNU_HWCAP  2
-+
-+/* Build ID bits as generated by ld --build-id.
-+   The descriptor consists of any nonzero number of bytes.  */
-+#define NT_GNU_BUILD_ID       3
-+
-+/* Version note generated by GNU gold containing a version string.  */
-+#define NT_GNU_GOLD_VERSION   4
-+
-+
-+/* Move records.  */
-+typedef struct
-+{
-+  Elf32_Xword m_value;                /* Symbol value.  */
-+  Elf32_Word m_info;          /* Size and index.  */
-+  Elf32_Word m_poffset;               /* Symbol offset.  */
-+  Elf32_Half m_repeat;                /* Repeat count.  */
-+  Elf32_Half m_stride;                /* Stride info.  */
-+} Elf32_Move;
-+
-+typedef struct
-+{
-+  Elf64_Xword m_value;                /* Symbol value.  */
-+  Elf64_Xword m_info;         /* Size and index.  */
-+  Elf64_Xword m_poffset;      /* Symbol offset.  */
-+  Elf64_Half m_repeat;                /* Repeat count.  */
-+  Elf64_Half m_stride;                /* Stride info.  */
-+} Elf64_Move;
-+
-+/* Macro to construct move records.  */
-+#define ELF32_M_SYM(info)     ((info) >> 8)
-+#define ELF32_M_SIZE(info)    ((unsigned char) (info))
-+#define ELF32_M_INFO(sym, size)       (((sym) << 8) + (unsigned char) (size))
-+
-+#define ELF64_M_SYM(info)     ELF32_M_SYM (info)
-+#define ELF64_M_SIZE(info)    ELF32_M_SIZE (info)
-+#define ELF64_M_INFO(sym, size)       ELF32_M_INFO (sym, size)
-+
-+
-+/* Motorola 68k specific definitions.  */
-+
-+/* Values for Elf32_Ehdr.e_flags.  */
-+#define EF_CPU32      0x00810000
-+
-+/* m68k relocs.  */
-+
-+#define R_68K_NONE    0               /* No reloc */
-+#define R_68K_32      1               /* Direct 32 bit  */
-+#define R_68K_16      2               /* Direct 16 bit  */
-+#define R_68K_8               3               /* Direct 8 bit  */
-+#define R_68K_PC32    4               /* PC relative 32 bit */
-+#define R_68K_PC16    5               /* PC relative 16 bit */
-+#define R_68K_PC8     6               /* PC relative 8 bit */
-+#define R_68K_GOT32   7               /* 32 bit PC relative GOT entry */
-+#define R_68K_GOT16   8               /* 16 bit PC relative GOT entry */
-+#define R_68K_GOT8    9               /* 8 bit PC relative GOT entry */
-+#define R_68K_GOT32O  10              /* 32 bit GOT offset */
-+#define R_68K_GOT16O  11              /* 16 bit GOT offset */
-+#define R_68K_GOT8O   12              /* 8 bit GOT offset */
-+#define R_68K_PLT32   13              /* 32 bit PC relative PLT address */
-+#define R_68K_PLT16   14              /* 16 bit PC relative PLT address */
-+#define R_68K_PLT8    15              /* 8 bit PC relative PLT address */
-+#define R_68K_PLT32O  16              /* 32 bit PLT offset */
-+#define R_68K_PLT16O  17              /* 16 bit PLT offset */
-+#define R_68K_PLT8O   18              /* 8 bit PLT offset */
-+#define R_68K_COPY    19              /* Copy symbol at runtime */
-+#define R_68K_GLOB_DAT        20              /* Create GOT entry */
-+#define R_68K_JMP_SLOT        21              /* Create PLT entry */
-+#define R_68K_RELATIVE        22              /* Adjust by program base */
-+#define R_68K_TLS_GD32      25          /* 32 bit GOT offset for GD */
-+#define R_68K_TLS_GD16      26          /* 16 bit GOT offset for GD */
-+#define R_68K_TLS_GD8       27          /* 8 bit GOT offset for GD */
-+#define R_68K_TLS_LDM32     28          /* 32 bit GOT offset for LDM */
-+#define R_68K_TLS_LDM16     29          /* 16 bit GOT offset for LDM */
-+#define R_68K_TLS_LDM8      30          /* 8 bit GOT offset for LDM */
-+#define R_68K_TLS_LDO32     31          /* 32 bit module-relative offset */
-+#define R_68K_TLS_LDO16     32          /* 16 bit module-relative offset */
-+#define R_68K_TLS_LDO8      33          /* 8 bit module-relative offset */
-+#define R_68K_TLS_IE32      34          /* 32 bit GOT offset for IE */
-+#define R_68K_TLS_IE16      35          /* 16 bit GOT offset for IE */
-+#define R_68K_TLS_IE8       36          /* 8 bit GOT offset for IE */
-+#define R_68K_TLS_LE32      37          /* 32 bit offset relative to
-+                                         static TLS block */
-+#define R_68K_TLS_LE16      38          /* 16 bit offset relative to
-+                                         static TLS block */
-+#define R_68K_TLS_LE8       39          /* 8 bit offset relative to
-+                                         static TLS block */
-+#define R_68K_TLS_DTPMOD32  40          /* 32 bit module number */
-+#define R_68K_TLS_DTPREL32  41          /* 32 bit module-relative offset */
-+#define R_68K_TLS_TPREL32   42          /* 32 bit TP-relative offset */
-+/* Keep this the last entry.  */
-+#define R_68K_NUM     43
-+
-+/* Intel 80386 specific definitions.  */
-+
-+/* i386 relocs.  */
-+
-+#define R_386_NONE       0            /* No reloc */
-+#define R_386_32         1            /* Direct 32 bit  */
-+#define R_386_PC32       2            /* PC relative 32 bit */
-+#define R_386_GOT32      3            /* 32 bit GOT entry */
-+#define R_386_PLT32      4            /* 32 bit PLT address */
-+#define R_386_COPY       5            /* Copy symbol at runtime */
-+#define R_386_GLOB_DAT           6            /* Create GOT entry */
-+#define R_386_JMP_SLOT           7            /* Create PLT entry */
-+#define R_386_RELATIVE           8            /* Adjust by program base */
-+#define R_386_GOTOFF     9            /* 32 bit offset to GOT */
-+#define R_386_GOTPC      10           /* 32 bit PC relative offset to GOT */
-+#define R_386_32PLT      11
-+#define R_386_TLS_TPOFF          14           /* Offset in static TLS block */
-+#define R_386_TLS_IE     15           /* Address of GOT entry for static TLS
-+                                         block offset */
-+#define R_386_TLS_GOTIE          16           /* GOT entry for static TLS block
-+                                         offset */
-+#define R_386_TLS_LE     17           /* Offset relative to static TLS
-+                                         block */
-+#define R_386_TLS_GD     18           /* Direct 32 bit for GNU version of
-+                                         general dynamic thread local data */
-+#define R_386_TLS_LDM    19           /* Direct 32 bit for GNU version of
-+                                         local dynamic thread local data
-+                                         in LE code */
-+#define R_386_16         20
-+#define R_386_PC16       21
-+#define R_386_8                  22
-+#define R_386_PC8        23
-+#define R_386_TLS_GD_32          24           /* Direct 32 bit for general dynamic
-+                                         thread local data */
-+#define R_386_TLS_GD_PUSH  25         /* Tag for pushl in GD TLS code */
-+#define R_386_TLS_GD_CALL  26         /* Relocation for call to
-+                                         __tls_get_addr() */
-+#define R_386_TLS_GD_POP   27         /* Tag for popl in GD TLS code */
-+#define R_386_TLS_LDM_32   28         /* Direct 32 bit for local dynamic
-+                                         thread local data in LE code */
-+#define R_386_TLS_LDM_PUSH 29         /* Tag for pushl in LDM TLS code */
-+#define R_386_TLS_LDM_CALL 30         /* Relocation for call to
-+                                         __tls_get_addr() in LDM code */
-+#define R_386_TLS_LDM_POP  31         /* Tag for popl in LDM TLS code */
-+#define R_386_TLS_LDO_32   32         /* Offset relative to TLS block */
-+#define R_386_TLS_IE_32          33           /* GOT entry for negated static TLS
-+                                         block offset */
-+#define R_386_TLS_LE_32          34           /* Negated offset relative to static
-+                                         TLS block */
-+#define R_386_TLS_DTPMOD32 35         /* ID of module containing symbol */
-+#define R_386_TLS_DTPOFF32 36         /* Offset in TLS block */
-+#define R_386_TLS_TPOFF32  37         /* Negated offset in static TLS block */
-+/* 38? */
-+#define R_386_TLS_GOTDESC  39         /* GOT offset for TLS descriptor.  */
-+#define R_386_TLS_DESC_CALL 40                /* Marker of call through TLS
-+                                         descriptor for
-+                                         relaxation.  */
-+#define R_386_TLS_DESC     41         /* TLS descriptor containing
-+                                         pointer to code and to
-+                                         argument, returning the TLS
-+                                         offset for the symbol.  */
-+#define R_386_IRELATIVE          42           /* Adjust indirectly by program base */
-+/* Keep this the last entry.  */
-+#define R_386_NUM        43
-+
-+/* SUN SPARC specific definitions.  */
-+
-+/* Legal values for ST_TYPE subfield of st_info (symbol type).  */
-+
-+#define STT_SPARC_REGISTER    13      /* Global register reserved to app. */
-+
-+/* Values for Elf64_Ehdr.e_flags.  */
-+
-+#define EF_SPARCV9_MM         3
-+#define EF_SPARCV9_TSO                0
-+#define EF_SPARCV9_PSO                1
-+#define EF_SPARCV9_RMO                2
-+#define EF_SPARC_LEDATA               0x800000 /* little endian data */
-+#define EF_SPARC_EXT_MASK     0xFFFF00
-+#define EF_SPARC_32PLUS               0x000100 /* generic V8+ features */
-+#define EF_SPARC_SUN_US1      0x000200 /* Sun UltraSPARC1 extensions */
-+#define EF_SPARC_HAL_R1               0x000400 /* HAL R1 extensions */
-+#define EF_SPARC_SUN_US3      0x000800 /* Sun UltraSPARCIII extensions */
-+
-+/* SPARC relocs.  */
-+
-+#define R_SPARC_NONE          0       /* No reloc */
-+#define R_SPARC_8             1       /* Direct 8 bit */
-+#define R_SPARC_16            2       /* Direct 16 bit */
-+#define R_SPARC_32            3       /* Direct 32 bit */
-+#define R_SPARC_DISP8         4       /* PC relative 8 bit */
-+#define R_SPARC_DISP16                5       /* PC relative 16 bit */
-+#define R_SPARC_DISP32                6       /* PC relative 32 bit */
-+#define R_SPARC_WDISP30               7       /* PC relative 30 bit shifted */
-+#define R_SPARC_WDISP22               8       /* PC relative 22 bit shifted */
-+#define R_SPARC_HI22          9       /* High 22 bit */
-+#define R_SPARC_22            10      /* Direct 22 bit */
-+#define R_SPARC_13            11      /* Direct 13 bit */
-+#define R_SPARC_LO10          12      /* Truncated 10 bit */
-+#define R_SPARC_GOT10         13      /* Truncated 10 bit GOT entry */
-+#define R_SPARC_GOT13         14      /* 13 bit GOT entry */
-+#define R_SPARC_GOT22         15      /* 22 bit GOT entry shifted */
-+#define R_SPARC_PC10          16      /* PC relative 10 bit truncated */
-+#define R_SPARC_PC22          17      /* PC relative 22 bit shifted */
-+#define R_SPARC_WPLT30                18      /* 30 bit PC relative PLT address */
-+#define R_SPARC_COPY          19      /* Copy symbol at runtime */
-+#define R_SPARC_GLOB_DAT      20      /* Create GOT entry */
-+#define R_SPARC_JMP_SLOT      21      /* Create PLT entry */
-+#define R_SPARC_RELATIVE      22      /* Adjust by program base */
-+#define R_SPARC_UA32          23      /* Direct 32 bit unaligned */
-+
-+/* Additional Sparc64 relocs.  */
-+
-+#define R_SPARC_PLT32         24      /* Direct 32 bit ref to PLT entry */
-+#define R_SPARC_HIPLT22               25      /* High 22 bit PLT entry */
-+#define R_SPARC_LOPLT10               26      /* Truncated 10 bit PLT entry */
-+#define R_SPARC_PCPLT32               27      /* PC rel 32 bit ref to PLT entry */
-+#define R_SPARC_PCPLT22               28      /* PC rel high 22 bit PLT entry */
-+#define R_SPARC_PCPLT10               29      /* PC rel trunc 10 bit PLT entry */
-+#define R_SPARC_10            30      /* Direct 10 bit */
-+#define R_SPARC_11            31      /* Direct 11 bit */
-+#define R_SPARC_64            32      /* Direct 64 bit */
-+#define R_SPARC_OLO10         33      /* 10bit with secondary 13bit addend */
-+#define R_SPARC_HH22          34      /* Top 22 bits of direct 64 bit */
-+#define R_SPARC_HM10          35      /* High middle 10 bits of ... */
-+#define R_SPARC_LM22          36      /* Low middle 22 bits of ... */
-+#define R_SPARC_PC_HH22               37      /* Top 22 bits of pc rel 64 bit */
-+#define R_SPARC_PC_HM10               38      /* High middle 10 bit of ... */
-+#define R_SPARC_PC_LM22               39      /* Low miggle 22 bits of ... */
-+#define R_SPARC_WDISP16               40      /* PC relative 16 bit shifted */
-+#define R_SPARC_WDISP19               41      /* PC relative 19 bit shifted */
-+#define R_SPARC_GLOB_JMP      42      /* was part of v9 ABI but was removed */
-+#define R_SPARC_7             43      /* Direct 7 bit */
-+#define R_SPARC_5             44      /* Direct 5 bit */
-+#define R_SPARC_6             45      /* Direct 6 bit */
-+#define R_SPARC_DISP64                46      /* PC relative 64 bit */
-+#define R_SPARC_PLT64         47      /* Direct 64 bit ref to PLT entry */
-+#define R_SPARC_HIX22         48      /* High 22 bit complemented */
-+#define R_SPARC_LOX10         49      /* Truncated 11 bit complemented */
-+#define R_SPARC_H44           50      /* Direct high 12 of 44 bit */
-+#define R_SPARC_M44           51      /* Direct mid 22 of 44 bit */
-+#define R_SPARC_L44           52      /* Direct low 10 of 44 bit */
-+#define R_SPARC_REGISTER      53      /* Global register usage */
-+#define R_SPARC_UA64          54      /* Direct 64 bit unaligned */
-+#define R_SPARC_UA16          55      /* Direct 16 bit unaligned */
-+#define R_SPARC_TLS_GD_HI22   56
-+#define R_SPARC_TLS_GD_LO10   57
-+#define R_SPARC_TLS_GD_ADD    58
-+#define R_SPARC_TLS_GD_CALL   59
-+#define R_SPARC_TLS_LDM_HI22  60
-+#define R_SPARC_TLS_LDM_LO10  61
-+#define R_SPARC_TLS_LDM_ADD   62
-+#define R_SPARC_TLS_LDM_CALL  63
-+#define R_SPARC_TLS_LDO_HIX22 64
-+#define R_SPARC_TLS_LDO_LOX10 65
-+#define R_SPARC_TLS_LDO_ADD   66
-+#define R_SPARC_TLS_IE_HI22   67
-+#define R_SPARC_TLS_IE_LO10   68
-+#define R_SPARC_TLS_IE_LD     69
-+#define R_SPARC_TLS_IE_LDX    70
-+#define R_SPARC_TLS_IE_ADD    71
-+#define R_SPARC_TLS_LE_HIX22  72
-+#define R_SPARC_TLS_LE_LOX10  73
-+#define R_SPARC_TLS_DTPMOD32  74
-+#define R_SPARC_TLS_DTPMOD64  75
-+#define R_SPARC_TLS_DTPOFF32  76
-+#define R_SPARC_TLS_DTPOFF64  77
-+#define R_SPARC_TLS_TPOFF32   78
-+#define R_SPARC_TLS_TPOFF64   79
-+#define R_SPARC_GOTDATA_HIX22 80
-+#define R_SPARC_GOTDATA_LOX10 81
-+#define R_SPARC_GOTDATA_OP_HIX22      82
-+#define R_SPARC_GOTDATA_OP_LOX10      83
-+#define R_SPARC_GOTDATA_OP    84
-+#define R_SPARC_H34           85
-+#define R_SPARC_SIZE32                86
-+#define R_SPARC_SIZE64                87
-+#define R_SPARC_WDISP10               88
-+#define R_SPARC_JMP_IREL      248
-+#define R_SPARC_IRELATIVE     249
-+#define R_SPARC_GNU_VTINHERIT 250
-+#define R_SPARC_GNU_VTENTRY   251
-+#define R_SPARC_REV32         252
-+/* Keep this the last entry.  */
-+#define R_SPARC_NUM           253
-+
-+/* For Sparc64, legal values for d_tag of Elf64_Dyn.  */
-+
-+#define DT_SPARC_REGISTER 0x70000001
-+#define DT_SPARC_NUM  2
-+
-+/* MIPS R3000 specific definitions.  */
-+
-+/* Legal values for e_flags field of Elf32_Ehdr.  */
-+
-+#define EF_MIPS_NOREORDER   1         /* A .noreorder directive was used */
-+#define EF_MIPS_PIC       2           /* Contains PIC code */
-+#define EF_MIPS_CPIC      4           /* Uses PIC calling sequence */
-+#define EF_MIPS_XGOT      8
-+#define EF_MIPS_64BIT_WHIRL 16
-+#define EF_MIPS_ABI2      32
-+#define EF_MIPS_ABI_ON32    64
-+#define EF_MIPS_ARCH      0xf0000000  /* MIPS architecture level */
-+
-+/* Legal values for MIPS architecture level.  */
-+
-+#define EF_MIPS_ARCH_1            0x00000000  /* -mips1 code.  */
-+#define EF_MIPS_ARCH_2            0x10000000  /* -mips2 code.  */
-+#define EF_MIPS_ARCH_3            0x20000000  /* -mips3 code.  */
-+#define EF_MIPS_ARCH_4            0x30000000  /* -mips4 code.  */
-+#define EF_MIPS_ARCH_5            0x40000000  /* -mips5 code.  */
-+#define EF_MIPS_ARCH_32           0x60000000  /* MIPS32 code.  */
-+#define EF_MIPS_ARCH_64           0x70000000  /* MIPS64 code.  */
-+
-+/* The following are non-official names and should not be used.  */
-+
-+#define E_MIPS_ARCH_1   0x00000000    /* -mips1 code.  */
-+#define E_MIPS_ARCH_2   0x10000000    /* -mips2 code.  */
-+#define E_MIPS_ARCH_3   0x20000000    /* -mips3 code.  */
-+#define E_MIPS_ARCH_4   0x30000000    /* -mips4 code.  */
-+#define E_MIPS_ARCH_5   0x40000000    /* -mips5 code.  */
-+#define E_MIPS_ARCH_32          0x60000000    /* MIPS32 code.  */
-+#define E_MIPS_ARCH_64          0x70000000    /* MIPS64 code.  */
-+
-+/* Special section indices.  */
-+
-+#define SHN_MIPS_ACOMMON    0xff00    /* Allocated common symbols */
-+#define SHN_MIPS_TEXT     0xff01      /* Allocated test symbols.  */
-+#define SHN_MIPS_DATA     0xff02      /* Allocated data symbols.  */
-+#define SHN_MIPS_SCOMMON    0xff03    /* Small common symbols */
-+#define SHN_MIPS_SUNDEFINED 0xff04    /* Small undefined symbols */
-+
-+/* Legal values for sh_type field of Elf32_Shdr.  */
-+
-+#define SHT_MIPS_LIBLIST       0x70000000 /* Shared objects used in link */
-+#define SHT_MIPS_MSYM        0x70000001
-+#define SHT_MIPS_CONFLICT      0x70000002 /* Conflicting symbols */
-+#define SHT_MIPS_GPTAB               0x70000003 /* Global data area sizes */
-+#define SHT_MIPS_UCODE               0x70000004 /* Reserved for SGI/MIPS compilers */
-+#define SHT_MIPS_DEBUG               0x70000005 /* MIPS ECOFF debugging information*/
-+#define SHT_MIPS_REGINFO       0x70000006 /* Register usage information */
-+#define SHT_MIPS_PACKAGE       0x70000007
-+#define SHT_MIPS_PACKSYM       0x70000008
-+#define SHT_MIPS_RELD        0x70000009
-+#define SHT_MIPS_IFACE         0x7000000b
-+#define SHT_MIPS_CONTENT       0x7000000c
-+#define SHT_MIPS_OPTIONS       0x7000000d /* Miscellaneous options.  */
-+#define SHT_MIPS_SHDR        0x70000010
-+#define SHT_MIPS_FDESC               0x70000011
-+#define SHT_MIPS_EXTSYM              0x70000012
-+#define SHT_MIPS_DENSE               0x70000013
-+#define SHT_MIPS_PDESC               0x70000014
-+#define SHT_MIPS_LOCSYM              0x70000015
-+#define SHT_MIPS_AUXSYM              0x70000016
-+#define SHT_MIPS_OPTSYM              0x70000017
-+#define SHT_MIPS_LOCSTR              0x70000018
-+#define SHT_MIPS_LINE        0x70000019
-+#define SHT_MIPS_RFDESC              0x7000001a
-+#define SHT_MIPS_DELTASYM      0x7000001b
-+#define SHT_MIPS_DELTAINST     0x7000001c
-+#define SHT_MIPS_DELTACLASS    0x7000001d
-+#define SHT_MIPS_DWARF         0x7000001e /* DWARF debugging information.  */
-+#define SHT_MIPS_DELTADECL     0x7000001f
-+#define SHT_MIPS_SYMBOL_LIB    0x70000020
-+#define SHT_MIPS_EVENTS              0x70000021 /* Event section.  */
-+#define SHT_MIPS_TRANSLATE     0x70000022
-+#define SHT_MIPS_PIXIE               0x70000023
-+#define SHT_MIPS_XLATE               0x70000024
-+#define SHT_MIPS_XLATE_DEBUG   0x70000025
-+#define SHT_MIPS_WHIRL               0x70000026
-+#define SHT_MIPS_EH_REGION     0x70000027
-+#define SHT_MIPS_XLATE_OLD     0x70000028
-+#define SHT_MIPS_PDR_EXCEPTION 0x70000029
-+
-+/* Legal values for sh_flags field of Elf32_Shdr.  */
-+
-+#define SHF_MIPS_GPREL         0x10000000     /* Must be part of global data area */
-+#define SHF_MIPS_MERGE         0x20000000
-+#define SHF_MIPS_ADDR  0x40000000
-+#define SHF_MIPS_STRINGS 0x80000000
-+#define SHF_MIPS_NOSTRIP 0x08000000
-+#define SHF_MIPS_LOCAL         0x04000000
-+#define SHF_MIPS_NAMES         0x02000000
-+#define SHF_MIPS_NODUPE        0x01000000
-+
-+
-+/* Symbol tables.  */
-+
-+/* MIPS specific values for `st_other'.  */
-+#define STO_MIPS_DEFAULT              0x0
-+#define STO_MIPS_INTERNAL             0x1
-+#define STO_MIPS_HIDDEN                       0x2
-+#define STO_MIPS_PROTECTED            0x3
-+#define STO_MIPS_PLT                  0x8
-+#define STO_MIPS_SC_ALIGN_UNUSED      0xff
-+
-+/* MIPS specific values for `st_info'.  */
-+#define STB_MIPS_SPLIT_COMMON         13
-+
-+/* Entries found in sections of type SHT_MIPS_GPTAB.  */
-+
-+typedef union
-+{
-+  struct
-+    {
-+      Elf32_Word gt_current_g_value;  /* -G value used for compilation */
-+      Elf32_Word gt_unused;           /* Not used */
-+    } gt_header;                      /* First entry in section */
-+  struct
-+    {
-+      Elf32_Word gt_g_value;          /* If this value were used for -G */
-+      Elf32_Word gt_bytes;            /* This many bytes would be used */
-+    } gt_entry;                               /* Subsequent entries in section */
-+} Elf32_gptab;
-+
-+/* Entry found in sections of type SHT_MIPS_REGINFO.  */
-+
-+typedef struct
-+{
-+  Elf32_Word  ri_gprmask;             /* General registers used */
-+  Elf32_Word  ri_cprmask[4];          /* Coprocessor registers used */
-+  Elf32_Sword ri_gp_value;            /* $gp register value */
-+} Elf32_RegInfo;
-+
-+/* Entries found in sections of type SHT_MIPS_OPTIONS.  */
-+
-+typedef struct
-+{
-+  unsigned char kind;         /* Determines interpretation of the
-+                                 variable part of descriptor.  */
-+  unsigned char size;         /* Size of descriptor, including header.  */
-+  Elf32_Section section;      /* Section header index of section affected,
-+                                 0 for global options.  */
-+  Elf32_Word info;            /* Kind-specific information.  */
-+} Elf_Options;
-+
-+/* Values for `kind' field in Elf_Options.  */
-+
-+#define ODK_NULL      0       /* Undefined.  */
-+#define ODK_REGINFO   1       /* Register usage information.  */
-+#define ODK_EXCEPTIONS        2       /* Exception processing options.  */
-+#define ODK_PAD               3       /* Section padding options.  */
-+#define ODK_HWPATCH   4       /* Hardware workarounds performed */
-+#define ODK_FILL      5       /* record the fill value used by the linker. */
-+#define ODK_TAGS      6       /* reserve space for desktop tools to write. */
-+#define ODK_HWAND     7       /* HW workarounds.  'AND' bits when merging. */
-+#define ODK_HWOR      8       /* HW workarounds.  'OR' bits when merging.  */
-+
-+/* Values for `info' in Elf_Options for ODK_EXCEPTIONS entries.  */
-+
-+#define OEX_FPU_MIN   0x1f    /* FPE's which MUST be enabled.  */
-+#define OEX_FPU_MAX   0x1f00  /* FPE's which MAY be enabled.  */
-+#define OEX_PAGE0     0x10000 /* page zero must be mapped.  */
-+#define OEX_SMM               0x20000 /* Force sequential memory mode?  */
-+#define OEX_FPDBUG    0x40000 /* Force floating point debug mode?  */
-+#define OEX_PRECISEFP OEX_FPDBUG
-+#define OEX_DISMISS   0x80000 /* Dismiss invalid address faults?  */
-+
-+#define OEX_FPU_INVAL 0x10
-+#define OEX_FPU_DIV0  0x08
-+#define OEX_FPU_OFLO  0x04
-+#define OEX_FPU_UFLO  0x02
-+#define OEX_FPU_INEX  0x01
-+
-+/* Masks for `info' in Elf_Options for an ODK_HWPATCH entry.  */
-+
-+#define OHW_R4KEOP    0x1     /* R4000 end-of-page patch.  */
-+#define OHW_R8KPFETCH 0x2     /* may need R8000 prefetch patch.  */
-+#define OHW_R5KEOP    0x4     /* R5000 end-of-page patch.  */
-+#define OHW_R5KCVTL   0x8     /* R5000 cvt.[ds].l bug.  clean=1.  */
-+
-+#define OPAD_PREFIX   0x1
-+#define OPAD_POSTFIX  0x2
-+#define OPAD_SYMBOL   0x4
-+
-+/* Entry found in `.options' section.  */
-+
-+typedef struct
-+{
-+  Elf32_Word hwp_flags1;      /* Extra flags.  */
-+  Elf32_Word hwp_flags2;      /* Extra flags.  */
-+} Elf_Options_Hw;
-+
-+/* Masks for `info' in ElfOptions for ODK_HWAND and ODK_HWOR entries.  */
-+
-+#define OHWA0_R4KEOP_CHECKED  0x00000001
-+#define OHWA1_R4KEOP_CLEAN    0x00000002
-+
-+/* MIPS relocs.  */
-+
-+#define R_MIPS_NONE           0       /* No reloc */
-+#define R_MIPS_16             1       /* Direct 16 bit */
-+#define R_MIPS_32             2       /* Direct 32 bit */
-+#define R_MIPS_REL32          3       /* PC relative 32 bit */
-+#define R_MIPS_26             4       /* Direct 26 bit shifted */
-+#define R_MIPS_HI16           5       /* High 16 bit */
-+#define R_MIPS_LO16           6       /* Low 16 bit */
-+#define R_MIPS_GPREL16                7       /* GP relative 16 bit */
-+#define R_MIPS_LITERAL                8       /* 16 bit literal entry */
-+#define R_MIPS_GOT16          9       /* 16 bit GOT entry */
-+#define R_MIPS_PC16           10      /* PC relative 16 bit */
-+#define R_MIPS_CALL16         11      /* 16 bit GOT entry for function */
-+#define R_MIPS_GPREL32                12      /* GP relative 32 bit */
-+
-+#define R_MIPS_SHIFT5         16
-+#define R_MIPS_SHIFT6         17
-+#define R_MIPS_64             18
-+#define R_MIPS_GOT_DISP               19
-+#define R_MIPS_GOT_PAGE               20
-+#define R_MIPS_GOT_OFST               21
-+#define R_MIPS_GOT_HI16               22
-+#define R_MIPS_GOT_LO16               23
-+#define R_MIPS_SUB            24
-+#define R_MIPS_INSERT_A               25
-+#define R_MIPS_INSERT_B               26
-+#define R_MIPS_DELETE         27
-+#define R_MIPS_HIGHER         28
-+#define R_MIPS_HIGHEST                29
-+#define R_MIPS_CALL_HI16      30
-+#define R_MIPS_CALL_LO16      31
-+#define R_MIPS_SCN_DISP               32
-+#define R_MIPS_REL16          33
-+#define R_MIPS_ADD_IMMEDIATE  34
-+#define R_MIPS_PJUMP          35
-+#define R_MIPS_RELGOT         36
-+#define R_MIPS_JALR           37
-+#define R_MIPS_TLS_DTPMOD32   38      /* Module number 32 bit */
-+#define R_MIPS_TLS_DTPREL32   39      /* Module-relative offset 32 bit */
-+#define R_MIPS_TLS_DTPMOD64   40      /* Module number 64 bit */
-+#define R_MIPS_TLS_DTPREL64   41      /* Module-relative offset 64 bit */
-+#define R_MIPS_TLS_GD         42      /* 16 bit GOT offset for GD */
-+#define R_MIPS_TLS_LDM                43      /* 16 bit GOT offset for LDM */
-+#define R_MIPS_TLS_DTPREL_HI16        44      /* Module-relative offset, high 16 bits */
-+#define R_MIPS_TLS_DTPREL_LO16        45      /* Module-relative offset, low 16 bits */
-+#define R_MIPS_TLS_GOTTPREL   46      /* 16 bit GOT offset for IE */
-+#define R_MIPS_TLS_TPREL32    47      /* TP-relative offset, 32 bit */
-+#define R_MIPS_TLS_TPREL64    48      /* TP-relative offset, 64 bit */
-+#define R_MIPS_TLS_TPREL_HI16 49      /* TP-relative offset, high 16 bits */
-+#define R_MIPS_TLS_TPREL_LO16 50      /* TP-relative offset, low 16 bits */
-+#define R_MIPS_GLOB_DAT               51
-+#define R_MIPS_COPY           126
-+#define R_MIPS_JUMP_SLOT        127
-+/* Keep this the last entry.  */
-+#define R_MIPS_NUM            128
-+
-+/* Legal values for p_type field of Elf32_Phdr.  */
-+
-+#define PT_MIPS_REGINFO       0x70000000      /* Register usage information */
-+#define PT_MIPS_RTPROC  0x70000001    /* Runtime procedure table. */
-+#define PT_MIPS_OPTIONS 0x70000002
-+
-+/* Special program header types.  */
-+
-+#define PF_MIPS_LOCAL 0x10000000
-+
-+/* Legal values for d_tag field of Elf32_Dyn.  */
-+
-+#define DT_MIPS_RLD_VERSION  0x70000001       /* Runtime linker interface version */
-+#define DT_MIPS_TIME_STAMP   0x70000002       /* Timestamp */
-+#define DT_MIPS_ICHECKSUM    0x70000003       /* Checksum */
-+#define DT_MIPS_IVERSION     0x70000004       /* Version string (string tbl index) */
-+#define DT_MIPS_FLAGS      0x70000005 /* Flags */
-+#define DT_MIPS_BASE_ADDRESS 0x70000006       /* Base address */
-+#define DT_MIPS_MSYM       0x70000007
-+#define DT_MIPS_CONFLICT     0x70000008       /* Address of CONFLICT section */
-+#define DT_MIPS_LIBLIST            0x70000009 /* Address of LIBLIST section */
-+#define DT_MIPS_LOCAL_GOTNO  0x7000000a       /* Number of local GOT entries */
-+#define DT_MIPS_CONFLICTNO   0x7000000b       /* Number of CONFLICT entries */
-+#define DT_MIPS_LIBLISTNO    0x70000010       /* Number of LIBLIST entries */
-+#define DT_MIPS_SYMTABNO     0x70000011       /* Number of DYNSYM entries */
-+#define DT_MIPS_UNREFEXTNO   0x70000012       /* First external DYNSYM */
-+#define DT_MIPS_GOTSYM             0x70000013 /* First GOT entry in DYNSYM */
-+#define DT_MIPS_HIPAGENO     0x70000014       /* Number of GOT page table entries */
-+#define DT_MIPS_RLD_MAP            0x70000016 /* Address of run time loader map.  */
-+#define DT_MIPS_DELTA_CLASS  0x70000017       /* Delta C++ class definition.  */
-+#define DT_MIPS_DELTA_CLASS_NO    0x70000018 /* Number of entries in
-+                                              DT_MIPS_DELTA_CLASS.  */
-+#define DT_MIPS_DELTA_INSTANCE    0x70000019 /* Delta C++ class instances.  */
-+#define DT_MIPS_DELTA_INSTANCE_NO 0x7000001a /* Number of entries in
-+                                              DT_MIPS_DELTA_INSTANCE.  */
-+#define DT_MIPS_DELTA_RELOC  0x7000001b /* Delta relocations.  */
-+#define DT_MIPS_DELTA_RELOC_NO 0x7000001c /* Number of entries in
-+                                           DT_MIPS_DELTA_RELOC.  */
-+#define DT_MIPS_DELTA_SYM    0x7000001d /* Delta symbols that Delta
-+                                         relocations refer to.  */
-+#define DT_MIPS_DELTA_SYM_NO 0x7000001e /* Number of entries in
-+                                         DT_MIPS_DELTA_SYM.  */
-+#define DT_MIPS_DELTA_CLASSSYM 0x70000020 /* Delta symbols that hold the
-+                                           class declaration.  */
-+#define DT_MIPS_DELTA_CLASSSYM_NO 0x70000021 /* Number of entries in
-+                                              DT_MIPS_DELTA_CLASSSYM.  */
-+#define DT_MIPS_CXX_FLAGS    0x70000022 /* Flags indicating for C++ flavor.  */
-+#define DT_MIPS_PIXIE_INIT   0x70000023
-+#define DT_MIPS_SYMBOL_LIB   0x70000024
-+#define DT_MIPS_LOCALPAGE_GOTIDX 0x70000025
-+#define DT_MIPS_LOCAL_GOTIDX 0x70000026
-+#define DT_MIPS_HIDDEN_GOTIDX 0x70000027
-+#define DT_MIPS_PROTECTED_GOTIDX 0x70000028
-+#define DT_MIPS_OPTIONS            0x70000029 /* Address of .options.  */
-+#define DT_MIPS_INTERFACE    0x7000002a /* Address of .interface.  */
-+#define DT_MIPS_DYNSTR_ALIGN 0x7000002b
-+#define DT_MIPS_INTERFACE_SIZE 0x7000002c /* Size of the .interface section. */
-+#define DT_MIPS_RLD_TEXT_RESOLVE_ADDR 0x7000002d /* Address of rld_text_rsolve
-+                                                  function stored in GOT.  */
-+#define DT_MIPS_PERF_SUFFIX  0x7000002e /* Default suffix of dso to be added
-+                                         by rld on dlopen() calls.  */
-+#define DT_MIPS_COMPACT_SIZE 0x7000002f /* (O32)Size of compact rel section. */
-+#define DT_MIPS_GP_VALUE     0x70000030 /* GP value for aux GOTs.  */
-+#define DT_MIPS_AUX_DYNAMIC  0x70000031 /* Address of aux .dynamic.  */
-+/* The address of .got.plt in an executable using the new non-PIC ABI.  */
-+#define DT_MIPS_PLTGOT             0x70000032
-+/* The base of the PLT in an executable using the new non-PIC ABI if that
-+   PLT is writable.  For a non-writable PLT, this is omitted or has a zero
-+   value.  */
-+#define DT_MIPS_RWPLT        0x70000034
-+#define DT_MIPS_NUM        0x35
-+
-+/* Legal values for DT_MIPS_FLAGS Elf32_Dyn entry.  */
-+
-+#define RHF_NONE                 0            /* No flags */
-+#define RHF_QUICKSTART                   (1 << 0)     /* Use quickstart */
-+#define RHF_NOTPOT               (1 << 1)     /* Hash size not power of 2 */
-+#define RHF_NO_LIBRARY_REPLACEMENT (1 << 2)   /* Ignore LD_LIBRARY_PATH */
-+#define RHF_NO_MOVE              (1 << 3)
-+#define RHF_SGI_ONLY             (1 << 4)
-+#define RHF_GUARANTEE_INIT       (1 << 5)
-+#define RHF_DELTA_C_PLUS_PLUS    (1 << 6)
-+#define RHF_GUARANTEE_START_INIT   (1 << 7)
-+#define RHF_PIXIE                (1 << 8)
-+#define RHF_DEFAULT_DELAY_LOAD           (1 << 9)
-+#define RHF_REQUICKSTART         (1 << 10)
-+#define RHF_REQUICKSTARTED       (1 << 11)
-+#define RHF_CORD                 (1 << 12)
-+#define RHF_NO_UNRES_UNDEF       (1 << 13)
-+#define RHF_RLD_ORDER_SAFE       (1 << 14)
-+
-+/* Entries found in sections of type SHT_MIPS_LIBLIST.  */
-+
-+typedef struct
-+{
-+  Elf32_Word l_name;          /* Name (string table index) */
-+  Elf32_Word l_time_stamp;    /* Timestamp */
-+  Elf32_Word l_checksum;      /* Checksum */
-+  Elf32_Word l_version;               /* Interface version */
-+  Elf32_Word l_flags;         /* Flags */
-+} Elf32_Lib;
-+
-+typedef struct
-+{
-+  Elf64_Word l_name;          /* Name (string table index) */
-+  Elf64_Word l_time_stamp;    /* Timestamp */
-+  Elf64_Word l_checksum;      /* Checksum */
-+  Elf64_Word l_version;               /* Interface version */
-+  Elf64_Word l_flags;         /* Flags */
-+} Elf64_Lib;
-+
-+
-+/* Legal values for l_flags.  */
-+
-+#define LL_NONE                 0
-+#define LL_EXACT_MATCH          (1 << 0)      /* Require exact match */
-+#define LL_IGNORE_INT_VER (1 << 1)    /* Ignore interface version */
-+#define LL_REQUIRE_MINOR  (1 << 2)
-+#define LL_EXPORTS      (1 << 3)
-+#define LL_DELAY_LOAD   (1 << 4)
-+#define LL_DELTA        (1 << 5)
-+
-+/* Entries found in sections of type SHT_MIPS_CONFLICT.  */
-+
-+typedef Elf32_Addr Elf32_Conflict;
-+
-+
-+/* HPPA specific definitions.  */
-+
-+/* Legal values for e_flags field of Elf32_Ehdr.  */
-+
-+#define EF_PARISC_TRAPNIL     0x00010000 /* Trap nil pointer dereference.  */
-+#define EF_PARISC_EXT         0x00020000 /* Program uses arch. extensions. */
-+#define EF_PARISC_LSB         0x00040000 /* Program expects little endian. */
-+#define EF_PARISC_WIDE                0x00080000 /* Program expects wide mode.  */
-+#define EF_PARISC_NO_KABP     0x00100000 /* No kernel assisted branch
-+                                            prediction.  */
-+#define EF_PARISC_LAZYSWAP    0x00400000 /* Allow lazy swapping.  */
-+#define EF_PARISC_ARCH                0x0000ffff /* Architecture version.  */
-+
-+/* Defined values for `e_flags & EF_PARISC_ARCH' are:  */
-+
-+#define EFA_PARISC_1_0                    0x020b /* PA-RISC 1.0 big-endian.  */
-+#define EFA_PARISC_1_1                    0x0210 /* PA-RISC 1.1 big-endian.  */
-+#define EFA_PARISC_2_0                    0x0214 /* PA-RISC 2.0 big-endian.  */
-+
-+/* Additional section indeces.  */
-+
-+#define SHN_PARISC_ANSI_COMMON        0xff00     /* Section for tenatively declared
-+                                            symbols in ANSI C.  */
-+#define SHN_PARISC_HUGE_COMMON        0xff01     /* Common blocks in huge model.  */
-+
-+/* Legal values for sh_type field of Elf32_Shdr.  */
-+
-+#define SHT_PARISC_EXT                0x70000000 /* Contains product specific ext. */
-+#define SHT_PARISC_UNWIND     0x70000001 /* Unwind information.  */
-+#define SHT_PARISC_DOC                0x70000002 /* Debug info for optimized code. */
-+
-+/* Legal values for sh_flags field of Elf32_Shdr.  */
-+
-+#define SHF_PARISC_SHORT      0x20000000 /* Section with short addressing. */
-+#define SHF_PARISC_HUGE               0x40000000 /* Section far from gp.  */
-+#define SHF_PARISC_SBP                0x80000000 /* Static branch prediction code. */
-+
-+/* Legal values for ST_TYPE subfield of st_info (symbol type).  */
-+
-+#define STT_PARISC_MILLICODE  13      /* Millicode function entry point.  */
-+
-+#define STT_HP_OPAQUE         (STT_LOOS + 0x1)
-+#define STT_HP_STUB           (STT_LOOS + 0x2)
-+
-+/* HPPA relocs.  */
-+
-+#define R_PARISC_NONE         0       /* No reloc.  */
-+#define R_PARISC_DIR32                1       /* Direct 32-bit reference.  */
-+#define R_PARISC_DIR21L               2       /* Left 21 bits of eff. address.  */
-+#define R_PARISC_DIR17R               3       /* Right 17 bits of eff. address.  */
-+#define R_PARISC_DIR17F               4       /* 17 bits of eff. address.  */
-+#define R_PARISC_DIR14R               6       /* Right 14 bits of eff. address.  */
-+#define R_PARISC_PCREL32      9       /* 32-bit rel. address.  */
-+#define R_PARISC_PCREL21L     10      /* Left 21 bits of rel. address.  */
-+#define R_PARISC_PCREL17R     11      /* Right 17 bits of rel. address.  */
-+#define R_PARISC_PCREL17F     12      /* 17 bits of rel. address.  */
-+#define R_PARISC_PCREL14R     14      /* Right 14 bits of rel. address.  */
-+#define R_PARISC_DPREL21L     18      /* Left 21 bits of rel. address.  */
-+#define R_PARISC_DPREL14R     22      /* Right 14 bits of rel. address.  */
-+#define R_PARISC_GPREL21L     26      /* GP-relative, left 21 bits.  */
-+#define R_PARISC_GPREL14R     30      /* GP-relative, right 14 bits.  */
-+#define R_PARISC_LTOFF21L     34      /* LT-relative, left 21 bits.  */
-+#define R_PARISC_LTOFF14R     38      /* LT-relative, right 14 bits.  */
-+#define R_PARISC_SECREL32     41      /* 32 bits section rel. address.  */
-+#define R_PARISC_SEGBASE      48      /* No relocation, set segment base.  */
-+#define R_PARISC_SEGREL32     49      /* 32 bits segment rel. address.  */
-+#define R_PARISC_PLTOFF21L    50      /* PLT rel. address, left 21 bits.  */
-+#define R_PARISC_PLTOFF14R    54      /* PLT rel. address, right 14 bits.  */
-+#define R_PARISC_LTOFF_FPTR32 57      /* 32 bits LT-rel. function pointer. */
-+#define R_PARISC_LTOFF_FPTR21L        58      /* LT-rel. fct ptr, left 21 bits. */
-+#define R_PARISC_LTOFF_FPTR14R        62      /* LT-rel. fct ptr, right 14 bits. */
-+#define R_PARISC_FPTR64               64      /* 64 bits function address.  */
-+#define R_PARISC_PLABEL32     65      /* 32 bits function address.  */
-+#define R_PARISC_PLABEL21L    66      /* Left 21 bits of fdesc address.  */
-+#define R_PARISC_PLABEL14R    70      /* Right 14 bits of fdesc address.  */
-+#define R_PARISC_PCREL64      72      /* 64 bits PC-rel. address.  */
-+#define R_PARISC_PCREL22F     74      /* 22 bits PC-rel. address.  */
-+#define R_PARISC_PCREL14WR    75      /* PC-rel. address, right 14 bits.  */
-+#define R_PARISC_PCREL14DR    76      /* PC rel. address, right 14 bits.  */
-+#define R_PARISC_PCREL16F     77      /* 16 bits PC-rel. address.  */
-+#define R_PARISC_PCREL16WF    78      /* 16 bits PC-rel. address.  */
-+#define R_PARISC_PCREL16DF    79      /* 16 bits PC-rel. address.  */
-+#define R_PARISC_DIR64                80      /* 64 bits of eff. address.  */
-+#define R_PARISC_DIR14WR      83      /* 14 bits of eff. address.  */
-+#define R_PARISC_DIR14DR      84      /* 14 bits of eff. address.  */
-+#define R_PARISC_DIR16F               85      /* 16 bits of eff. address.  */
-+#define R_PARISC_DIR16WF      86      /* 16 bits of eff. address.  */
-+#define R_PARISC_DIR16DF      87      /* 16 bits of eff. address.  */
-+#define R_PARISC_GPREL64      88      /* 64 bits of GP-rel. address.  */
-+#define R_PARISC_GPREL14WR    91      /* GP-rel. address, right 14 bits.  */
-+#define R_PARISC_GPREL14DR    92      /* GP-rel. address, right 14 bits.  */
-+#define R_PARISC_GPREL16F     93      /* 16 bits GP-rel. address.  */
-+#define R_PARISC_GPREL16WF    94      /* 16 bits GP-rel. address.  */
-+#define R_PARISC_GPREL16DF    95      /* 16 bits GP-rel. address.  */
-+#define R_PARISC_LTOFF64      96      /* 64 bits LT-rel. address.  */
-+#define R_PARISC_LTOFF14WR    99      /* LT-rel. address, right 14 bits.  */
-+#define R_PARISC_LTOFF14DR    100     /* LT-rel. address, right 14 bits.  */
-+#define R_PARISC_LTOFF16F     101     /* 16 bits LT-rel. address.  */
-+#define R_PARISC_LTOFF16WF    102     /* 16 bits LT-rel. address.  */
-+#define R_PARISC_LTOFF16DF    103     /* 16 bits LT-rel. address.  */
-+#define R_PARISC_SECREL64     104     /* 64 bits section rel. address.  */
-+#define R_PARISC_SEGREL64     112     /* 64 bits segment rel. address.  */
-+#define R_PARISC_PLTOFF14WR   115     /* PLT-rel. address, right 14 bits.  */
-+#define R_PARISC_PLTOFF14DR   116     /* PLT-rel. address, right 14 bits.  */
-+#define R_PARISC_PLTOFF16F    117     /* 16 bits LT-rel. address.  */
-+#define R_PARISC_PLTOFF16WF   118     /* 16 bits PLT-rel. address.  */
-+#define R_PARISC_PLTOFF16DF   119     /* 16 bits PLT-rel. address.  */
-+#define R_PARISC_LTOFF_FPTR64 120     /* 64 bits LT-rel. function ptr.  */
-+#define R_PARISC_LTOFF_FPTR14WR       123     /* LT-rel. fct. ptr., right 14 bits. */
-+#define R_PARISC_LTOFF_FPTR14DR       124     /* LT-rel. fct. ptr., right 14 bits. */
-+#define R_PARISC_LTOFF_FPTR16F        125     /* 16 bits LT-rel. function ptr.  */
-+#define R_PARISC_LTOFF_FPTR16WF       126     /* 16 bits LT-rel. function ptr.  */
-+#define R_PARISC_LTOFF_FPTR16DF       127     /* 16 bits LT-rel. function ptr.  */
-+#define R_PARISC_LORESERVE    128
-+#define R_PARISC_COPY         128     /* Copy relocation.  */
-+#define R_PARISC_IPLT         129     /* Dynamic reloc, imported PLT */
-+#define R_PARISC_EPLT         130     /* Dynamic reloc, exported PLT */
-+#define R_PARISC_TPREL32      153     /* 32 bits TP-rel. address.  */
-+#define R_PARISC_TPREL21L     154     /* TP-rel. address, left 21 bits.  */
-+#define R_PARISC_TPREL14R     158     /* TP-rel. address, right 14 bits.  */
-+#define R_PARISC_LTOFF_TP21L  162     /* LT-TP-rel. address, left 21 bits. */
-+#define R_PARISC_LTOFF_TP14R  166     /* LT-TP-rel. address, right 14 bits.*/
-+#define R_PARISC_LTOFF_TP14F  167     /* 14 bits LT-TP-rel. address.  */
-+#define R_PARISC_TPREL64      216     /* 64 bits TP-rel. address.  */
-+#define R_PARISC_TPREL14WR    219     /* TP-rel. address, right 14 bits.  */
-+#define R_PARISC_TPREL14DR    220     /* TP-rel. address, right 14 bits.  */
-+#define R_PARISC_TPREL16F     221     /* 16 bits TP-rel. address.  */
-+#define R_PARISC_TPREL16WF    222     /* 16 bits TP-rel. address.  */
-+#define R_PARISC_TPREL16DF    223     /* 16 bits TP-rel. address.  */
-+#define R_PARISC_LTOFF_TP64   224     /* 64 bits LT-TP-rel. address.  */
-+#define R_PARISC_LTOFF_TP14WR 227     /* LT-TP-rel. address, right 14 bits.*/
-+#define R_PARISC_LTOFF_TP14DR 228     /* LT-TP-rel. address, right 14 bits.*/
-+#define R_PARISC_LTOFF_TP16F  229     /* 16 bits LT-TP-rel. address.  */
-+#define R_PARISC_LTOFF_TP16WF 230     /* 16 bits LT-TP-rel. address.  */
-+#define R_PARISC_LTOFF_TP16DF 231     /* 16 bits LT-TP-rel. address.  */
-+#define R_PARISC_GNU_VTENTRY  232
-+#define R_PARISC_GNU_VTINHERIT        233
-+#define R_PARISC_TLS_GD21L    234     /* GD 21-bit left.  */
-+#define R_PARISC_TLS_GD14R    235     /* GD 14-bit right.  */
-+#define R_PARISC_TLS_GDCALL   236     /* GD call to __t_g_a.  */
-+#define R_PARISC_TLS_LDM21L   237     /* LD module 21-bit left.  */
-+#define R_PARISC_TLS_LDM14R   238     /* LD module 14-bit right.  */
-+#define R_PARISC_TLS_LDMCALL  239     /* LD module call to __t_g_a.  */
-+#define R_PARISC_TLS_LDO21L   240     /* LD offset 21-bit left.  */
-+#define R_PARISC_TLS_LDO14R   241     /* LD offset 14-bit right.  */
-+#define R_PARISC_TLS_DTPMOD32 242     /* DTP module 32-bit.  */
-+#define R_PARISC_TLS_DTPMOD64 243     /* DTP module 64-bit.  */
-+#define R_PARISC_TLS_DTPOFF32 244     /* DTP offset 32-bit.  */
-+#define R_PARISC_TLS_DTPOFF64 245     /* DTP offset 32-bit.  */
-+#define R_PARISC_TLS_LE21L    R_PARISC_TPREL21L
-+#define R_PARISC_TLS_LE14R    R_PARISC_TPREL14R
-+#define R_PARISC_TLS_IE21L    R_PARISC_LTOFF_TP21L
-+#define R_PARISC_TLS_IE14R    R_PARISC_LTOFF_TP14R
-+#define R_PARISC_TLS_TPREL32  R_PARISC_TPREL32
-+#define R_PARISC_TLS_TPREL64  R_PARISC_TPREL64
-+#define R_PARISC_HIRESERVE    255
-+
-+/* Legal values for p_type field of Elf32_Phdr/Elf64_Phdr.  */
-+
-+#define PT_HP_TLS             (PT_LOOS + 0x0)
-+#define PT_HP_CORE_NONE               (PT_LOOS + 0x1)
-+#define PT_HP_CORE_VERSION    (PT_LOOS + 0x2)
-+#define PT_HP_CORE_KERNEL     (PT_LOOS + 0x3)
-+#define PT_HP_CORE_COMM               (PT_LOOS + 0x4)
-+#define PT_HP_CORE_PROC               (PT_LOOS + 0x5)
-+#define PT_HP_CORE_LOADABLE   (PT_LOOS + 0x6)
-+#define PT_HP_CORE_STACK      (PT_LOOS + 0x7)
-+#define PT_HP_CORE_SHM                (PT_LOOS + 0x8)
-+#define PT_HP_CORE_MMF                (PT_LOOS + 0x9)
-+#define PT_HP_PARALLEL                (PT_LOOS + 0x10)
-+#define PT_HP_FASTBIND                (PT_LOOS + 0x11)
-+#define PT_HP_OPT_ANNOT               (PT_LOOS + 0x12)
-+#define PT_HP_HSL_ANNOT               (PT_LOOS + 0x13)
-+#define PT_HP_STACK           (PT_LOOS + 0x14)
-+
-+#define PT_PARISC_ARCHEXT     0x70000000
-+#define PT_PARISC_UNWIND      0x70000001
-+
-+/* Legal values for p_flags field of Elf32_Phdr/Elf64_Phdr.  */
-+
-+#define PF_PARISC_SBP         0x08000000
-+
-+#define PF_HP_PAGE_SIZE               0x00100000
-+#define PF_HP_FAR_SHARED      0x00200000
-+#define PF_HP_NEAR_SHARED     0x00400000
-+#define PF_HP_CODE            0x01000000
-+#define PF_HP_MODIFY          0x02000000
-+#define PF_HP_LAZYSWAP                0x04000000
-+#define PF_HP_SBP             0x08000000
-+
-+
-+/* Alpha specific definitions.  */
-+
-+/* Legal values for e_flags field of Elf64_Ehdr.  */
-+
-+#define EF_ALPHA_32BIT                1       /* All addresses must be < 2GB.  */
-+#define EF_ALPHA_CANRELAX     2       /* Relocations for relaxing exist.  */
-+
-+/* Legal values for sh_type field of Elf64_Shdr.  */
-+
-+/* These two are primerily concerned with ECOFF debugging info.  */
-+#define SHT_ALPHA_DEBUG               0x70000001
-+#define SHT_ALPHA_REGINFO     0x70000002
-+
-+/* Legal values for sh_flags field of Elf64_Shdr.  */
-+
-+#define SHF_ALPHA_GPREL               0x10000000
-+
-+/* Legal values for st_other field of Elf64_Sym.  */
-+#define STO_ALPHA_NOPV                0x80    /* No PV required.  */
-+#define STO_ALPHA_STD_GPLOAD  0x88    /* PV only used for initial ldgp.  */
-+
-+/* Alpha relocs.  */
-+
-+#define R_ALPHA_NONE          0       /* No reloc */
-+#define R_ALPHA_REFLONG               1       /* Direct 32 bit */
-+#define R_ALPHA_REFQUAD               2       /* Direct 64 bit */
-+#define R_ALPHA_GPREL32               3       /* GP relative 32 bit */
-+#define R_ALPHA_LITERAL               4       /* GP relative 16 bit w/optimization */
-+#define R_ALPHA_LITUSE                5       /* Optimization hint for LITERAL */
-+#define R_ALPHA_GPDISP                6       /* Add displacement to GP */
-+#define R_ALPHA_BRADDR                7       /* PC+4 relative 23 bit shifted */
-+#define R_ALPHA_HINT          8       /* PC+4 relative 16 bit shifted */
-+#define R_ALPHA_SREL16                9       /* PC relative 16 bit */
-+#define R_ALPHA_SREL32                10      /* PC relative 32 bit */
-+#define R_ALPHA_SREL64                11      /* PC relative 64 bit */
-+#define R_ALPHA_GPRELHIGH     17      /* GP relative 32 bit, high 16 bits */
-+#define R_ALPHA_GPRELLOW      18      /* GP relative 32 bit, low 16 bits */
-+#define R_ALPHA_GPREL16               19      /* GP relative 16 bit */
-+#define R_ALPHA_COPY          24      /* Copy symbol at runtime */
-+#define R_ALPHA_GLOB_DAT      25      /* Create GOT entry */
-+#define R_ALPHA_JMP_SLOT      26      /* Create PLT entry */
-+#define R_ALPHA_RELATIVE      27      /* Adjust by program base */
-+#define R_ALPHA_TLS_GD_HI     28
-+#define R_ALPHA_TLSGD         29
-+#define R_ALPHA_TLS_LDM               30
-+#define R_ALPHA_DTPMOD64      31
-+#define R_ALPHA_GOTDTPREL     32
-+#define R_ALPHA_DTPREL64      33
-+#define R_ALPHA_DTPRELHI      34
-+#define R_ALPHA_DTPRELLO      35
-+#define R_ALPHA_DTPREL16      36
-+#define R_ALPHA_GOTTPREL      37
-+#define R_ALPHA_TPREL64               38
-+#define R_ALPHA_TPRELHI               39
-+#define R_ALPHA_TPRELLO               40
-+#define R_ALPHA_TPREL16               41
-+/* Keep this the last entry.  */
-+#define R_ALPHA_NUM           46
-+
-+/* Magic values of the LITUSE relocation addend.  */
-+#define LITUSE_ALPHA_ADDR     0
-+#define LITUSE_ALPHA_BASE     1
-+#define LITUSE_ALPHA_BYTOFF   2
-+#define LITUSE_ALPHA_JSR      3
-+#define LITUSE_ALPHA_TLS_GD   4
-+#define LITUSE_ALPHA_TLS_LDM  5
-+
-+/* Legal values for d_tag of Elf64_Dyn.  */
-+#define DT_ALPHA_PLTRO                (DT_LOPROC + 0)
-+#define DT_ALPHA_NUM          1
-+
-+/* PowerPC specific declarations */
-+
-+/* Values for Elf32/64_Ehdr.e_flags.  */
-+#define EF_PPC_EMB            0x80000000      /* PowerPC embedded flag */
-+
-+/* Cygnus local bits below */
-+#define EF_PPC_RELOCATABLE    0x00010000      /* PowerPC -mrelocatable flag*/
-+#define EF_PPC_RELOCATABLE_LIB        0x00008000      /* PowerPC -mrelocatable-lib
-+                                                 flag */
-+
-+/* PowerPC relocations defined by the ABIs */
-+#define R_PPC_NONE            0
-+#define R_PPC_ADDR32          1       /* 32bit absolute address */
-+#define R_PPC_ADDR24          2       /* 26bit address, 2 bits ignored.  */
-+#define R_PPC_ADDR16          3       /* 16bit absolute address */
-+#define R_PPC_ADDR16_LO               4       /* lower 16bit of absolute address */
-+#define R_PPC_ADDR16_HI               5       /* high 16bit of absolute address */
-+#define R_PPC_ADDR16_HA               6       /* adjusted high 16bit */
-+#define R_PPC_ADDR14          7       /* 16bit address, 2 bits ignored */
-+#define R_PPC_ADDR14_BRTAKEN  8
-+#define R_PPC_ADDR14_BRNTAKEN 9
-+#define R_PPC_REL24           10      /* PC relative 26 bit */
-+#define R_PPC_REL14           11      /* PC relative 16 bit */
-+#define R_PPC_REL14_BRTAKEN   12
-+#define R_PPC_REL14_BRNTAKEN  13
-+#define R_PPC_GOT16           14
-+#define R_PPC_GOT16_LO                15
-+#define R_PPC_GOT16_HI                16
-+#define R_PPC_GOT16_HA                17
-+#define R_PPC_PLTREL24                18
-+#define R_PPC_COPY            19
-+#define R_PPC_GLOB_DAT                20
-+#define R_PPC_JMP_SLOT                21
-+#define R_PPC_RELATIVE                22
-+#define R_PPC_LOCAL24PC               23
-+#define R_PPC_UADDR32         24
-+#define R_PPC_UADDR16         25
-+#define R_PPC_REL32           26
-+#define R_PPC_PLT32           27
-+#define R_PPC_PLTREL32                28
-+#define R_PPC_PLT16_LO                29
-+#define R_PPC_PLT16_HI                30
-+#define R_PPC_PLT16_HA                31
-+#define R_PPC_SDAREL16                32
-+#define R_PPC_SECTOFF         33
-+#define R_PPC_SECTOFF_LO      34
-+#define R_PPC_SECTOFF_HI      35
-+#define R_PPC_SECTOFF_HA      36
-+
-+/* PowerPC relocations defined for the TLS access ABI.  */
-+#define R_PPC_TLS             67 /* none      (sym+add)@tls */
-+#define R_PPC_DTPMOD32                68 /* word32    (sym+add)@dtpmod */
-+#define R_PPC_TPREL16         69 /* half16*   (sym+add)@tprel */
-+#define R_PPC_TPREL16_LO      70 /* half16    (sym+add)@tprel@l */
-+#define R_PPC_TPREL16_HI      71 /* half16    (sym+add)@tprel@h */
-+#define R_PPC_TPREL16_HA      72 /* half16    (sym+add)@tprel@ha */
-+#define R_PPC_TPREL32         73 /* word32    (sym+add)@tprel */
-+#define R_PPC_DTPREL16                74 /* half16*   (sym+add)@dtprel */
-+#define R_PPC_DTPREL16_LO     75 /* half16    (sym+add)@dtprel@l */
-+#define R_PPC_DTPREL16_HI     76 /* half16    (sym+add)@dtprel@h */
-+#define R_PPC_DTPREL16_HA     77 /* half16    (sym+add)@dtprel@ha */
-+#define R_PPC_DTPREL32                78 /* word32    (sym+add)@dtprel */
-+#define R_PPC_GOT_TLSGD16     79 /* half16*   (sym+add)@got@tlsgd */
-+#define R_PPC_GOT_TLSGD16_LO  80 /* half16    (sym+add)@got@tlsgd@l */
-+#define R_PPC_GOT_TLSGD16_HI  81 /* half16    (sym+add)@got@tlsgd@h */
-+#define R_PPC_GOT_TLSGD16_HA  82 /* half16    (sym+add)@got@tlsgd@ha */
-+#define R_PPC_GOT_TLSLD16     83 /* half16*   (sym+add)@got@tlsld */
-+#define R_PPC_GOT_TLSLD16_LO  84 /* half16    (sym+add)@got@tlsld@l */
-+#define R_PPC_GOT_TLSLD16_HI  85 /* half16    (sym+add)@got@tlsld@h */
-+#define R_PPC_GOT_TLSLD16_HA  86 /* half16    (sym+add)@got@tlsld@ha */
-+#define R_PPC_GOT_TPREL16     87 /* half16*   (sym+add)@got@tprel */
-+#define R_PPC_GOT_TPREL16_LO  88 /* half16    (sym+add)@got@tprel@l */
-+#define R_PPC_GOT_TPREL16_HI  89 /* half16    (sym+add)@got@tprel@h */
-+#define R_PPC_GOT_TPREL16_HA  90 /* half16    (sym+add)@got@tprel@ha */
-+#define R_PPC_GOT_DTPREL16    91 /* half16*   (sym+add)@got@dtprel */
-+#define R_PPC_GOT_DTPREL16_LO 92 /* half16*   (sym+add)@got@dtprel@l */
-+#define R_PPC_GOT_DTPREL16_HI 93 /* half16*   (sym+add)@got@dtprel@h */
-+#define R_PPC_GOT_DTPREL16_HA 94 /* half16*   (sym+add)@got@dtprel@ha */
-+
-+/* The remaining relocs are from the Embedded ELF ABI, and are not
-+   in the SVR4 ELF ABI.  */
-+#define R_PPC_EMB_NADDR32     101
-+#define R_PPC_EMB_NADDR16     102
-+#define R_PPC_EMB_NADDR16_LO  103
-+#define R_PPC_EMB_NADDR16_HI  104
-+#define R_PPC_EMB_NADDR16_HA  105
-+#define R_PPC_EMB_SDAI16      106
-+#define R_PPC_EMB_SDA2I16     107
-+#define R_PPC_EMB_SDA2REL     108
-+#define R_PPC_EMB_SDA21               109     /* 16 bit offset in SDA */
-+#define R_PPC_EMB_MRKREF      110
-+#define R_PPC_EMB_RELSEC16    111
-+#define R_PPC_EMB_RELST_LO    112
-+#define R_PPC_EMB_RELST_HI    113
-+#define R_PPC_EMB_RELST_HA    114
-+#define R_PPC_EMB_BIT_FLD     115
-+#define R_PPC_EMB_RELSDA      116     /* 16 bit relative offset in SDA */
-+
-+/* Diab tool relocations.  */
-+#define R_PPC_DIAB_SDA21_LO   180     /* like EMB_SDA21, but lower 16 bit */
-+#define R_PPC_DIAB_SDA21_HI   181     /* like EMB_SDA21, but high 16 bit */
-+#define R_PPC_DIAB_SDA21_HA   182     /* like EMB_SDA21, adjusted high 16 */
-+#define R_PPC_DIAB_RELSDA_LO  183     /* like EMB_RELSDA, but lower 16 bit */
-+#define R_PPC_DIAB_RELSDA_HI  184     /* like EMB_RELSDA, but high 16 bit */
-+#define R_PPC_DIAB_RELSDA_HA  185     /* like EMB_RELSDA, adjusted high 16 */
-+
-+/* GNU extension to support local ifunc.  */
-+#define R_PPC_IRELATIVE               248
-+
-+/* GNU relocs used in PIC code sequences.  */
-+#define R_PPC_REL16           249     /* half16   (sym+add-.) */
-+#define R_PPC_REL16_LO                250     /* half16   (sym+add-.)@l */
-+#define R_PPC_REL16_HI                251     /* half16   (sym+add-.)@h */
-+#define R_PPC_REL16_HA                252     /* half16   (sym+add-.)@ha */
-+
-+/* This is a phony reloc to handle any old fashioned TOC16 references
-+   that may still be in object files.  */
-+#define R_PPC_TOC16           255
-+
-+/* PowerPC specific values for the Dyn d_tag field.  */
-+#define DT_PPC_GOT            (DT_LOPROC + 0)
-+#define DT_PPC_NUM            1
-+
-+/* PowerPC64 relocations defined by the ABIs */
-+#define R_PPC64_NONE          R_PPC_NONE
-+#define R_PPC64_ADDR32                R_PPC_ADDR32 /* 32bit absolute address */
-+#define R_PPC64_ADDR24                R_PPC_ADDR24 /* 26bit address, word aligned */
-+#define R_PPC64_ADDR16                R_PPC_ADDR16 /* 16bit absolute address */
-+#define R_PPC64_ADDR16_LO     R_PPC_ADDR16_LO /* lower 16bits of address */
-+#define R_PPC64_ADDR16_HI     R_PPC_ADDR16_HI /* high 16bits of address. */
-+#define R_PPC64_ADDR16_HA     R_PPC_ADDR16_HA /* adjusted high 16bits.  */
-+#define R_PPC64_ADDR14                R_PPC_ADDR14 /* 16bit address, word aligned */
-+#define R_PPC64_ADDR14_BRTAKEN        R_PPC_ADDR14_BRTAKEN
-+#define R_PPC64_ADDR14_BRNTAKEN       R_PPC_ADDR14_BRNTAKEN
-+#define R_PPC64_REL24         R_PPC_REL24 /* PC-rel. 26 bit, word aligned */
-+#define R_PPC64_REL14         R_PPC_REL14 /* PC relative 16 bit */
-+#define R_PPC64_REL14_BRTAKEN R_PPC_REL14_BRTAKEN
-+#define R_PPC64_REL14_BRNTAKEN        R_PPC_REL14_BRNTAKEN
-+#define R_PPC64_GOT16         R_PPC_GOT16
-+#define R_PPC64_GOT16_LO      R_PPC_GOT16_LO
-+#define R_PPC64_GOT16_HI      R_PPC_GOT16_HI
-+#define R_PPC64_GOT16_HA      R_PPC_GOT16_HA
-+
-+#define R_PPC64_COPY          R_PPC_COPY
-+#define R_PPC64_GLOB_DAT      R_PPC_GLOB_DAT
-+#define R_PPC64_JMP_SLOT      R_PPC_JMP_SLOT
-+#define R_PPC64_RELATIVE      R_PPC_RELATIVE
-+
-+#define R_PPC64_UADDR32               R_PPC_UADDR32
-+#define R_PPC64_UADDR16               R_PPC_UADDR16
-+#define R_PPC64_REL32         R_PPC_REL32
-+#define R_PPC64_PLT32         R_PPC_PLT32
-+#define R_PPC64_PLTREL32      R_PPC_PLTREL32
-+#define R_PPC64_PLT16_LO      R_PPC_PLT16_LO
-+#define R_PPC64_PLT16_HI      R_PPC_PLT16_HI
-+#define R_PPC64_PLT16_HA      R_PPC_PLT16_HA
-+
-+#define R_PPC64_SECTOFF               R_PPC_SECTOFF
-+#define R_PPC64_SECTOFF_LO    R_PPC_SECTOFF_LO
-+#define R_PPC64_SECTOFF_HI    R_PPC_SECTOFF_HI
-+#define R_PPC64_SECTOFF_HA    R_PPC_SECTOFF_HA
-+#define R_PPC64_ADDR30                37 /* word30 (S + A - P) >> 2 */
-+#define R_PPC64_ADDR64                38 /* doubleword64 S + A */
-+#define R_PPC64_ADDR16_HIGHER 39 /* half16 #higher(S + A) */
-+#define R_PPC64_ADDR16_HIGHERA        40 /* half16 #highera(S + A) */
-+#define R_PPC64_ADDR16_HIGHEST        41 /* half16 #highest(S + A) */
-+#define R_PPC64_ADDR16_HIGHESTA       42 /* half16 #highesta(S + A) */
-+#define R_PPC64_UADDR64               43 /* doubleword64 S + A */
-+#define R_PPC64_REL64         44 /* doubleword64 S + A - P */
-+#define R_PPC64_PLT64         45 /* doubleword64 L + A */
-+#define R_PPC64_PLTREL64      46 /* doubleword64 L + A - P */
-+#define R_PPC64_TOC16         47 /* half16* S + A - .TOC */
-+#define R_PPC64_TOC16_LO      48 /* half16 #lo(S + A - .TOC.) */
-+#define R_PPC64_TOC16_HI      49 /* half16 #hi(S + A - .TOC.) */
-+#define R_PPC64_TOC16_HA      50 /* half16 #ha(S + A - .TOC.) */
-+#define R_PPC64_TOC           51 /* doubleword64 .TOC */
-+#define R_PPC64_PLTGOT16      52 /* half16* M + A */
-+#define R_PPC64_PLTGOT16_LO   53 /* half16 #lo(M + A) */
-+#define R_PPC64_PLTGOT16_HI   54 /* half16 #hi(M + A) */
-+#define R_PPC64_PLTGOT16_HA   55 /* half16 #ha(M + A) */
-+
-+#define R_PPC64_ADDR16_DS     56 /* half16ds* (S + A) >> 2 */
-+#define R_PPC64_ADDR16_LO_DS  57 /* half16ds  #lo(S + A) >> 2 */
-+#define R_PPC64_GOT16_DS      58 /* half16ds* (G + A) >> 2 */
-+#define R_PPC64_GOT16_LO_DS   59 /* half16ds  #lo(G + A) >> 2 */
-+#define R_PPC64_PLT16_LO_DS   60 /* half16ds  #lo(L + A) >> 2 */
-+#define R_PPC64_SECTOFF_DS    61 /* half16ds* (R + A) >> 2 */
-+#define R_PPC64_SECTOFF_LO_DS 62 /* half16ds  #lo(R + A) >> 2 */
-+#define R_PPC64_TOC16_DS      63 /* half16ds* (S + A - .TOC.) >> 2 */
-+#define R_PPC64_TOC16_LO_DS   64 /* half16ds  #lo(S + A - .TOC.) >> 2 */
-+#define R_PPC64_PLTGOT16_DS   65 /* half16ds* (M + A) >> 2 */
-+#define R_PPC64_PLTGOT16_LO_DS        66 /* half16ds  #lo(M + A) >> 2 */
-+
-+/* PowerPC64 relocations defined for the TLS access ABI.  */
-+#define R_PPC64_TLS           67 /* none      (sym+add)@tls */
-+#define R_PPC64_DTPMOD64      68 /* doubleword64 (sym+add)@dtpmod */
-+#define R_PPC64_TPREL16               69 /* half16*   (sym+add)@tprel */
-+#define R_PPC64_TPREL16_LO    70 /* half16    (sym+add)@tprel@l */
-+#define R_PPC64_TPREL16_HI    71 /* half16    (sym+add)@tprel@h */
-+#define R_PPC64_TPREL16_HA    72 /* half16    (sym+add)@tprel@ha */
-+#define R_PPC64_TPREL64               73 /* doubleword64 (sym+add)@tprel */
-+#define R_PPC64_DTPREL16      74 /* half16*   (sym+add)@dtprel */
-+#define R_PPC64_DTPREL16_LO   75 /* half16    (sym+add)@dtprel@l */
-+#define R_PPC64_DTPREL16_HI   76 /* half16    (sym+add)@dtprel@h */
-+#define R_PPC64_DTPREL16_HA   77 /* half16    (sym+add)@dtprel@ha */
-+#define R_PPC64_DTPREL64      78 /* doubleword64 (sym+add)@dtprel */
-+#define R_PPC64_GOT_TLSGD16   79 /* half16*   (sym+add)@got@tlsgd */
-+#define R_PPC64_GOT_TLSGD16_LO        80 /* half16    (sym+add)@got@tlsgd@l */
-+#define R_PPC64_GOT_TLSGD16_HI        81 /* half16    (sym+add)@got@tlsgd@h */
-+#define R_PPC64_GOT_TLSGD16_HA        82 /* half16    (sym+add)@got@tlsgd@ha */
-+#define R_PPC64_GOT_TLSLD16   83 /* half16*   (sym+add)@got@tlsld */
-+#define R_PPC64_GOT_TLSLD16_LO        84 /* half16    (sym+add)@got@tlsld@l */
-+#define R_PPC64_GOT_TLSLD16_HI        85 /* half16    (sym+add)@got@tlsld@h */
-+#define R_PPC64_GOT_TLSLD16_HA        86 /* half16    (sym+add)@got@tlsld@ha */
-+#define R_PPC64_GOT_TPREL16_DS        87 /* half16ds* (sym+add)@got@tprel */
-+#define R_PPC64_GOT_TPREL16_LO_DS 88 /* half16ds (sym+add)@got@tprel@l */
-+#define R_PPC64_GOT_TPREL16_HI        89 /* half16    (sym+add)@got@tprel@h */
-+#define R_PPC64_GOT_TPREL16_HA        90 /* half16    (sym+add)@got@tprel@ha */
-+#define R_PPC64_GOT_DTPREL16_DS       91 /* half16ds* (sym+add)@got@dtprel */
-+#define R_PPC64_GOT_DTPREL16_LO_DS 92 /* half16ds (sym+add)@got@dtprel@l */
-+#define R_PPC64_GOT_DTPREL16_HI       93 /* half16    (sym+add)@got@dtprel@h */
-+#define R_PPC64_GOT_DTPREL16_HA       94 /* half16    (sym+add)@got@dtprel@ha */
-+#define R_PPC64_TPREL16_DS    95 /* half16ds* (sym+add)@tprel */
-+#define R_PPC64_TPREL16_LO_DS 96 /* half16ds  (sym+add)@tprel@l */
-+#define R_PPC64_TPREL16_HIGHER        97 /* half16    (sym+add)@tprel@higher */
-+#define R_PPC64_TPREL16_HIGHERA       98 /* half16    (sym+add)@tprel@highera */
-+#define R_PPC64_TPREL16_HIGHEST       99 /* half16    (sym+add)@tprel@highest */
-+#define R_PPC64_TPREL16_HIGHESTA 100 /* half16        (sym+add)@tprel@highesta */
-+#define R_PPC64_DTPREL16_DS   101 /* half16ds* (sym+add)@dtprel */
-+#define R_PPC64_DTPREL16_LO_DS        102 /* half16ds (sym+add)@dtprel@l */
-+#define R_PPC64_DTPREL16_HIGHER       103 /* half16   (sym+add)@dtprel@higher */
-+#define R_PPC64_DTPREL16_HIGHERA 104 /* half16        (sym+add)@dtprel@highera */
-+#define R_PPC64_DTPREL16_HIGHEST 105 /* half16        (sym+add)@dtprel@highest */
-+#define R_PPC64_DTPREL16_HIGHESTA 106 /* half16       (sym+add)@dtprel@highesta */
-+
-+/* GNU extension to support local ifunc.  */
-+#define R_PPC64_JMP_IREL      247
-+#define R_PPC64_IRELATIVE     248
-+#define R_PPC64_REL16         249     /* half16   (sym+add-.) */
-+#define R_PPC64_REL16_LO      250     /* half16   (sym+add-.)@l */
-+#define R_PPC64_REL16_HI      251     /* half16   (sym+add-.)@h */
-+#define R_PPC64_REL16_HA      252     /* half16   (sym+add-.)@ha */
-+
-+/* PowerPC64 specific values for the Dyn d_tag field.  */
-+#define DT_PPC64_GLINK  (DT_LOPROC + 0)
-+#define DT_PPC64_OPD  (DT_LOPROC + 1)
-+#define DT_PPC64_OPDSZ        (DT_LOPROC + 2)
-+#define DT_PPC64_NUM    3
-+
-+
-+/* ARM specific declarations */
-+
-+/* Processor specific flags for the ELF header e_flags field.  */
-+#define EF_ARM_RELEXEC                0x01
-+#define EF_ARM_HASENTRY               0x02
-+#define EF_ARM_INTERWORK      0x04
-+#define EF_ARM_APCS_26                0x08
-+#define EF_ARM_APCS_FLOAT     0x10
-+#define EF_ARM_PIC            0x20
-+#define EF_ARM_ALIGN8         0x40 /* 8-bit structure alignment is in use */
-+#define EF_ARM_NEW_ABI                0x80
-+#define EF_ARM_OLD_ABI                0x100
-+#define EF_ARM_SOFT_FLOAT     0x200
-+#define EF_ARM_VFP_FLOAT      0x400
-+#define EF_ARM_MAVERICK_FLOAT 0x800
-+
-+
-+/* Other constants defined in the ARM ELF spec. version B-01.  */
-+/* NB. These conflict with values defined above.  */
-+#define EF_ARM_SYMSARESORTED  0x04
-+#define EF_ARM_DYNSYMSUSESEGIDX       0x08
-+#define EF_ARM_MAPSYMSFIRST   0x10
-+#define EF_ARM_EABIMASK               0XFF000000
-+
-+/* Constants defined in AAELF.  */
-+#define EF_ARM_BE8        0x00800000
-+#define EF_ARM_LE8        0x00400000
-+
-+#define EF_ARM_EABI_VERSION(flags)    ((flags) & EF_ARM_EABIMASK)
-+#define EF_ARM_EABI_UNKNOWN   0x00000000
-+#define EF_ARM_EABI_VER1      0x01000000
-+#define EF_ARM_EABI_VER2      0x02000000
-+#define EF_ARM_EABI_VER3      0x03000000
-+#define EF_ARM_EABI_VER4      0x04000000
-+#define EF_ARM_EABI_VER5      0x05000000
-+
-+/* Additional symbol types for Thumb.  */
-+#define STT_ARM_TFUNC         STT_LOPROC /* A Thumb function.  */
-+#define STT_ARM_16BIT         STT_HIPROC /* A Thumb label.  */
-+
-+/* ARM-specific values for sh_flags */
-+#define SHF_ARM_ENTRYSECT     0x10000000 /* Section contains an entry point */
-+#define SHF_ARM_COMDEF                0x80000000 /* Section may be multiply defined
-+                                            in the input to a link step.  */
-+
-+/* ARM-specific program header flags */
-+#define PF_ARM_SB             0x10000000 /* Segment contains the location
-+                                            addressed by the static base. */
-+#define PF_ARM_PI             0x20000000 /* Position-independent segment.  */
-+#define PF_ARM_ABS            0x40000000 /* Absolute segment.  */
-+
-+/* Processor specific values for the Phdr p_type field.  */
-+#define PT_ARM_EXIDX          (PT_LOPROC + 1) /* ARM unwind segment.  */
-+
-+/* Processor specific values for the Shdr sh_type field.  */
-+#define SHT_ARM_EXIDX         (SHT_LOPROC + 1) /* ARM unwind section.  */
-+#define SHT_ARM_PREEMPTMAP    (SHT_LOPROC + 2) /* Preemption details.  */
-+#define SHT_ARM_ATTRIBUTES    (SHT_LOPROC + 3) /* ARM attributes section.  */
-+
-+
-+/* ARM relocs.  */
-+
-+#define R_ARM_NONE            0       /* No reloc */
-+#define R_ARM_PC24            1       /* PC relative 26 bit branch */
-+#define R_ARM_ABS32           2       /* Direct 32 bit  */
-+#define R_ARM_REL32           3       /* PC relative 32 bit */
-+#define R_ARM_PC13            4
-+#define R_ARM_ABS16           5       /* Direct 16 bit */
-+#define R_ARM_ABS12           6       /* Direct 12 bit */
-+#define R_ARM_THM_ABS5                7
-+#define R_ARM_ABS8            8       /* Direct 8 bit */
-+#define R_ARM_SBREL32         9
-+#define R_ARM_THM_PC22                10
-+#define R_ARM_THM_PC8         11
-+#define R_ARM_AMP_VCALL9      12
-+#define R_ARM_SWI24           13      /* Obsolete static relocation.  */
-+#define R_ARM_TLS_DESC                13      /* Dynamic relocation.  */
-+#define R_ARM_THM_SWI8                14
-+#define R_ARM_XPC25           15
-+#define R_ARM_THM_XPC22               16
-+#define R_ARM_TLS_DTPMOD32    17      /* ID of module containing symbol */
-+#define R_ARM_TLS_DTPOFF32    18      /* Offset in TLS block */
-+#define R_ARM_TLS_TPOFF32     19      /* Offset in static TLS block */
-+#define R_ARM_COPY            20      /* Copy symbol at runtime */
-+#define R_ARM_GLOB_DAT                21      /* Create GOT entry */
-+#define R_ARM_JUMP_SLOT               22      /* Create PLT entry */
-+#define R_ARM_RELATIVE                23      /* Adjust by program base */
-+#define R_ARM_GOTOFF          24      /* 32 bit offset to GOT */
-+#define R_ARM_GOTPC           25      /* 32 bit PC relative offset to GOT */
-+#define R_ARM_GOT32           26      /* 32 bit GOT entry */
-+#define R_ARM_PLT32           27      /* 32 bit PLT address */
-+#define R_ARM_ALU_PCREL_7_0   32
-+#define R_ARM_ALU_PCREL_15_8  33
-+#define R_ARM_ALU_PCREL_23_15 34
-+#define R_ARM_LDR_SBREL_11_0  35
-+#define R_ARM_ALU_SBREL_19_12 36
-+#define R_ARM_ALU_SBREL_27_20 37
-+#define R_ARM_TLS_GOTDESC     90
-+#define R_ARM_TLS_CALL                91
-+#define R_ARM_TLS_DESCSEQ     92
-+#define R_ARM_THM_TLS_CALL    93
-+#define R_ARM_GNU_VTENTRY     100
-+#define R_ARM_GNU_VTINHERIT   101
-+#define R_ARM_THM_PC11                102     /* thumb unconditional branch */
-+#define R_ARM_THM_PC9         103     /* thumb conditional branch */
-+#define R_ARM_TLS_GD32                104     /* PC-rel 32 bit for global dynamic
-+                                         thread local data */
-+#define R_ARM_TLS_LDM32               105     /* PC-rel 32 bit for local dynamic
-+                                         thread local data */
-+#define R_ARM_TLS_LDO32               106     /* 32 bit offset relative to TLS
-+                                         block */
-+#define R_ARM_TLS_IE32                107     /* PC-rel 32 bit for GOT entry of
-+                                         static TLS block offset */
-+#define R_ARM_TLS_LE32                108     /* 32 bit offset relative to static
-+                                         TLS block */
-+#define       R_ARM_THM_TLS_DESCSEQ   129
-+#define R_ARM_IRELATIVE               160
-+#define R_ARM_RXPC25          249
-+#define R_ARM_RSBREL32                250
-+#define R_ARM_THM_RPC22               251
-+#define R_ARM_RREL32          252
-+#define R_ARM_RABS22          253
-+#define R_ARM_RPC24           254
-+#define R_ARM_RBASE           255
-+/* Keep this the last entry.  */
-+#define R_ARM_NUM             256
-+
-+/* IA-64 specific declarations.  */
-+
-+/* Processor specific flags for the Ehdr e_flags field.  */
-+#define EF_IA_64_MASKOS               0x0000000f      /* os-specific flags */
-+#define EF_IA_64_ABI64                0x00000010      /* 64-bit ABI */
-+#define EF_IA_64_ARCH         0xff000000      /* arch. version mask */
-+
-+/* Processor specific values for the Phdr p_type field.  */
-+#define PT_IA_64_ARCHEXT      (PT_LOPROC + 0) /* arch extension bits */
-+#define PT_IA_64_UNWIND               (PT_LOPROC + 1) /* ia64 unwind bits */
-+#define PT_IA_64_HP_OPT_ANOT  (PT_LOOS + 0x12)
-+#define PT_IA_64_HP_HSL_ANOT  (PT_LOOS + 0x13)
-+#define PT_IA_64_HP_STACK     (PT_LOOS + 0x14)
-+
-+/* Processor specific flags for the Phdr p_flags field.  */
-+#define PF_IA_64_NORECOV      0x80000000      /* spec insns w/o recovery */
-+
-+/* Processor specific values for the Shdr sh_type field.  */
-+#define SHT_IA_64_EXT         (SHT_LOPROC + 0) /* extension bits */
-+#define SHT_IA_64_UNWIND      (SHT_LOPROC + 1) /* unwind bits */
-+
-+/* Processor specific flags for the Shdr sh_flags field.  */
-+#define SHF_IA_64_SHORT               0x10000000      /* section near gp */
-+#define SHF_IA_64_NORECOV     0x20000000      /* spec insns w/o recovery */
-+
-+/* Processor specific values for the Dyn d_tag field.  */
-+#define DT_IA_64_PLT_RESERVE  (DT_LOPROC + 0)
-+#define DT_IA_64_NUM          1
-+
-+/* IA-64 relocations.  */
-+#define R_IA64_NONE           0x00    /* none */
-+#define R_IA64_IMM14          0x21    /* symbol + addend, add imm14 */
-+#define R_IA64_IMM22          0x22    /* symbol + addend, add imm22 */
-+#define R_IA64_IMM64          0x23    /* symbol + addend, mov imm64 */
-+#define R_IA64_DIR32MSB               0x24    /* symbol + addend, data4 MSB */
-+#define R_IA64_DIR32LSB               0x25    /* symbol + addend, data4 LSB */
-+#define R_IA64_DIR64MSB               0x26    /* symbol + addend, data8 MSB */
-+#define R_IA64_DIR64LSB               0x27    /* symbol + addend, data8 LSB */
-+#define R_IA64_GPREL22                0x2a    /* @gprel(sym + add), add imm22 */
-+#define R_IA64_GPREL64I               0x2b    /* @gprel(sym + add), mov imm64 */
-+#define R_IA64_GPREL32MSB     0x2c    /* @gprel(sym + add), data4 MSB */
-+#define R_IA64_GPREL32LSB     0x2d    /* @gprel(sym + add), data4 LSB */
-+#define R_IA64_GPREL64MSB     0x2e    /* @gprel(sym + add), data8 MSB */
-+#define R_IA64_GPREL64LSB     0x2f    /* @gprel(sym + add), data8 LSB */
-+#define R_IA64_LTOFF22                0x32    /* @ltoff(sym + add), add imm22 */
-+#define R_IA64_LTOFF64I               0x33    /* @ltoff(sym + add), mov imm64 */
-+#define R_IA64_PLTOFF22               0x3a    /* @pltoff(sym + add), add imm22 */
-+#define R_IA64_PLTOFF64I      0x3b    /* @pltoff(sym + add), mov imm64 */
-+#define R_IA64_PLTOFF64MSB    0x3e    /* @pltoff(sym + add), data8 MSB */
-+#define R_IA64_PLTOFF64LSB    0x3f    /* @pltoff(sym + add), data8 LSB */
-+#define R_IA64_FPTR64I                0x43    /* @fptr(sym + add), mov imm64 */
-+#define R_IA64_FPTR32MSB      0x44    /* @fptr(sym + add), data4 MSB */
-+#define R_IA64_FPTR32LSB      0x45    /* @fptr(sym + add), data4 LSB */
-+#define R_IA64_FPTR64MSB      0x46    /* @fptr(sym + add), data8 MSB */
-+#define R_IA64_FPTR64LSB      0x47    /* @fptr(sym + add), data8 LSB */
-+#define R_IA64_PCREL60B               0x48    /* @pcrel(sym + add), brl */
-+#define R_IA64_PCREL21B               0x49    /* @pcrel(sym + add), ptb, call */
-+#define R_IA64_PCREL21M               0x4a    /* @pcrel(sym + add), chk.s */
-+#define R_IA64_PCREL21F               0x4b    /* @pcrel(sym + add), fchkf */
-+#define R_IA64_PCREL32MSB     0x4c    /* @pcrel(sym + add), data4 MSB */
-+#define R_IA64_PCREL32LSB     0x4d    /* @pcrel(sym + add), data4 LSB */
-+#define R_IA64_PCREL64MSB     0x4e    /* @pcrel(sym + add), data8 MSB */
-+#define R_IA64_PCREL64LSB     0x4f    /* @pcrel(sym + add), data8 LSB */
-+#define R_IA64_LTOFF_FPTR22   0x52    /* @ltoff(@fptr(s+a)), imm22 */
-+#define R_IA64_LTOFF_FPTR64I  0x53    /* @ltoff(@fptr(s+a)), imm64 */
-+#define R_IA64_LTOFF_FPTR32MSB        0x54    /* @ltoff(@fptr(s+a)), data4 MSB */
-+#define R_IA64_LTOFF_FPTR32LSB        0x55    /* @ltoff(@fptr(s+a)), data4 LSB */
-+#define R_IA64_LTOFF_FPTR64MSB        0x56    /* @ltoff(@fptr(s+a)), data8 MSB */
-+#define R_IA64_LTOFF_FPTR64LSB        0x57    /* @ltoff(@fptr(s+a)), data8 LSB */
-+#define R_IA64_SEGREL32MSB    0x5c    /* @segrel(sym + add), data4 MSB */
-+#define R_IA64_SEGREL32LSB    0x5d    /* @segrel(sym + add), data4 LSB */
-+#define R_IA64_SEGREL64MSB    0x5e    /* @segrel(sym + add), data8 MSB */
-+#define R_IA64_SEGREL64LSB    0x5f    /* @segrel(sym + add), data8 LSB */
-+#define R_IA64_SECREL32MSB    0x64    /* @secrel(sym + add), data4 MSB */
-+#define R_IA64_SECREL32LSB    0x65    /* @secrel(sym + add), data4 LSB */
-+#define R_IA64_SECREL64MSB    0x66    /* @secrel(sym + add), data8 MSB */
-+#define R_IA64_SECREL64LSB    0x67    /* @secrel(sym + add), data8 LSB */
-+#define R_IA64_REL32MSB               0x6c    /* data 4 + REL */
-+#define R_IA64_REL32LSB               0x6d    /* data 4 + REL */
-+#define R_IA64_REL64MSB               0x6e    /* data 8 + REL */
-+#define R_IA64_REL64LSB               0x6f    /* data 8 + REL */
-+#define R_IA64_LTV32MSB               0x74    /* symbol + addend, data4 MSB */
-+#define R_IA64_LTV32LSB               0x75    /* symbol + addend, data4 LSB */
-+#define R_IA64_LTV64MSB               0x76    /* symbol + addend, data8 MSB */
-+#define R_IA64_LTV64LSB               0x77    /* symbol + addend, data8 LSB */
-+#define R_IA64_PCREL21BI      0x79    /* @pcrel(sym + add), 21bit inst */
-+#define R_IA64_PCREL22                0x7a    /* @pcrel(sym + add), 22bit inst */
-+#define R_IA64_PCREL64I               0x7b    /* @pcrel(sym + add), 64bit inst */
-+#define R_IA64_IPLTMSB                0x80    /* dynamic reloc, imported PLT, MSB */
-+#define R_IA64_IPLTLSB                0x81    /* dynamic reloc, imported PLT, LSB */
-+#define R_IA64_COPY           0x84    /* copy relocation */
-+#define R_IA64_SUB            0x85    /* Addend and symbol difference */
-+#define R_IA64_LTOFF22X               0x86    /* LTOFF22, relaxable.  */
-+#define R_IA64_LDXMOV         0x87    /* Use of LTOFF22X.  */
-+#define R_IA64_TPREL14                0x91    /* @tprel(sym + add), imm14 */
-+#define R_IA64_TPREL22                0x92    /* @tprel(sym + add), imm22 */
-+#define R_IA64_TPREL64I               0x93    /* @tprel(sym + add), imm64 */
-+#define R_IA64_TPREL64MSB     0x96    /* @tprel(sym + add), data8 MSB */
-+#define R_IA64_TPREL64LSB     0x97    /* @tprel(sym + add), data8 LSB */
-+#define R_IA64_LTOFF_TPREL22  0x9a    /* @ltoff(@tprel(s+a)), imm2 */
-+#define R_IA64_DTPMOD64MSB    0xa6    /* @dtpmod(sym + add), data8 MSB */
-+#define R_IA64_DTPMOD64LSB    0xa7    /* @dtpmod(sym + add), data8 LSB */
-+#define R_IA64_LTOFF_DTPMOD22 0xaa    /* @ltoff(@dtpmod(sym + add)), imm22 */
-+#define R_IA64_DTPREL14               0xb1    /* @dtprel(sym + add), imm14 */
-+#define R_IA64_DTPREL22               0xb2    /* @dtprel(sym + add), imm22 */
-+#define R_IA64_DTPREL64I      0xb3    /* @dtprel(sym + add), imm64 */
-+#define R_IA64_DTPREL32MSB    0xb4    /* @dtprel(sym + add), data4 MSB */
-+#define R_IA64_DTPREL32LSB    0xb5    /* @dtprel(sym + add), data4 LSB */
-+#define R_IA64_DTPREL64MSB    0xb6    /* @dtprel(sym + add), data8 MSB */
-+#define R_IA64_DTPREL64LSB    0xb7    /* @dtprel(sym + add), data8 LSB */
-+#define R_IA64_LTOFF_DTPREL22 0xba    /* @ltoff(@dtprel(s+a)), imm22 */
-+
-+/* SH specific declarations */
-+
-+/* Processor specific flags for the ELF header e_flags field.  */
-+#define EF_SH_MACH_MASK               0x1f
-+#define EF_SH_UNKNOWN         0x0
-+#define EF_SH1                        0x1
-+#define EF_SH2                        0x2
-+#define EF_SH3                        0x3
-+#define EF_SH_DSP             0x4
-+#define EF_SH3_DSP            0x5
-+#define EF_SH4AL_DSP          0x6
-+#define EF_SH3E                       0x8
-+#define EF_SH4                        0x9
-+#define EF_SH2E                       0xb
-+#define EF_SH4A                       0xc
-+#define EF_SH2A                       0xd
-+#define EF_SH4_NOFPU          0x10
-+#define EF_SH4A_NOFPU         0x11
-+#define EF_SH4_NOMMU_NOFPU    0x12
-+#define EF_SH2A_NOFPU         0x13
-+#define EF_SH3_NOMMU          0x14
-+#define EF_SH2A_SH4_NOFPU     0x15
-+#define EF_SH2A_SH3_NOFPU     0x16
-+#define EF_SH2A_SH4           0x17
-+#define EF_SH2A_SH3E          0x18
-+
-+/* SH relocs.  */
-+#define       R_SH_NONE               0
-+#define       R_SH_DIR32              1
-+#define       R_SH_REL32              2
-+#define       R_SH_DIR8WPN            3
-+#define       R_SH_IND12W             4
-+#define       R_SH_DIR8WPL            5
-+#define       R_SH_DIR8WPZ            6
-+#define       R_SH_DIR8BP             7
-+#define       R_SH_DIR8W              8
-+#define       R_SH_DIR8L              9
-+#define       R_SH_SWITCH16           25
-+#define       R_SH_SWITCH32           26
-+#define       R_SH_USES               27
-+#define       R_SH_COUNT              28
-+#define       R_SH_ALIGN              29
-+#define       R_SH_CODE               30
-+#define       R_SH_DATA               31
-+#define       R_SH_LABEL              32
-+#define       R_SH_SWITCH8            33
-+#define       R_SH_GNU_VTINHERIT      34
-+#define       R_SH_GNU_VTENTRY        35
-+#define       R_SH_TLS_GD_32          144
-+#define       R_SH_TLS_LD_32          145
-+#define       R_SH_TLS_LDO_32         146
-+#define       R_SH_TLS_IE_32          147
-+#define       R_SH_TLS_LE_32          148
-+#define       R_SH_TLS_DTPMOD32       149
-+#define       R_SH_TLS_DTPOFF32       150
-+#define       R_SH_TLS_TPOFF32        151
-+#define       R_SH_GOT32              160
-+#define       R_SH_PLT32              161
-+#define       R_SH_COPY               162
-+#define       R_SH_GLOB_DAT           163
-+#define       R_SH_JMP_SLOT           164
-+#define       R_SH_RELATIVE           165
-+#define       R_SH_GOTOFF             166
-+#define       R_SH_GOTPC              167
-+/* Keep this the last entry.  */
-+#define       R_SH_NUM                256
-+
-+/* S/390 specific definitions.  */
-+
-+/* Valid values for the e_flags field.  */
-+
-+#define EF_S390_HIGH_GPRS    0x00000001  /* High GPRs kernel facility needed.  */
-+
-+/* Additional s390 relocs */
-+
-+#define R_390_NONE            0       /* No reloc.  */
-+#define R_390_8                       1       /* Direct 8 bit.  */
-+#define R_390_12              2       /* Direct 12 bit.  */
-+#define R_390_16              3       /* Direct 16 bit.  */
-+#define R_390_32              4       /* Direct 32 bit.  */
-+#define R_390_PC32            5       /* PC relative 32 bit.  */
-+#define R_390_GOT12           6       /* 12 bit GOT offset.  */
-+#define R_390_GOT32           7       /* 32 bit GOT offset.  */
-+#define R_390_PLT32           8       /* 32 bit PC relative PLT address.  */
-+#define R_390_COPY            9       /* Copy symbol at runtime.  */
-+#define R_390_GLOB_DAT                10      /* Create GOT entry.  */
-+#define R_390_JMP_SLOT                11      /* Create PLT entry.  */
-+#define R_390_RELATIVE                12      /* Adjust by program base.  */
-+#define R_390_GOTOFF32                13      /* 32 bit offset to GOT.         */
-+#define R_390_GOTPC           14      /* 32 bit PC relative offset to GOT.  */
-+#define R_390_GOT16           15      /* 16 bit GOT offset.  */
-+#define R_390_PC16            16      /* PC relative 16 bit.  */
-+#define R_390_PC16DBL         17      /* PC relative 16 bit shifted by 1.  */
-+#define R_390_PLT16DBL                18      /* 16 bit PC rel. PLT shifted by 1.  */
-+#define R_390_PC32DBL         19      /* PC relative 32 bit shifted by 1.  */
-+#define R_390_PLT32DBL                20      /* 32 bit PC rel. PLT shifted by 1.  */
-+#define R_390_GOTPCDBL                21      /* 32 bit PC rel. GOT shifted by 1.  */
-+#define R_390_64              22      /* Direct 64 bit.  */
-+#define R_390_PC64            23      /* PC relative 64 bit.  */
-+#define R_390_GOT64           24      /* 64 bit GOT offset.  */
-+#define R_390_PLT64           25      /* 64 bit PC relative PLT address.  */
-+#define R_390_GOTENT          26      /* 32 bit PC rel. to GOT entry >> 1. */
-+#define R_390_GOTOFF16                27      /* 16 bit offset to GOT. */
-+#define R_390_GOTOFF64                28      /* 64 bit offset to GOT. */
-+#define R_390_GOTPLT12                29      /* 12 bit offset to jump slot.  */
-+#define R_390_GOTPLT16                30      /* 16 bit offset to jump slot.  */
-+#define R_390_GOTPLT32                31      /* 32 bit offset to jump slot.  */
-+#define R_390_GOTPLT64                32      /* 64 bit offset to jump slot.  */
-+#define R_390_GOTPLTENT               33      /* 32 bit rel. offset to jump slot.  */
-+#define R_390_PLTOFF16                34      /* 16 bit offset from GOT to PLT. */
-+#define R_390_PLTOFF32                35      /* 32 bit offset from GOT to PLT. */
-+#define R_390_PLTOFF64                36      /* 16 bit offset from GOT to PLT. */
-+#define R_390_TLS_LOAD                37      /* Tag for load insn in TLS code.  */
-+#define R_390_TLS_GDCALL      38      /* Tag for function call in general
-+                                         dynamic TLS code. */
-+#define R_390_TLS_LDCALL      39      /* Tag for function call in local
-+                                         dynamic TLS code. */
-+#define R_390_TLS_GD32                40      /* Direct 32 bit for general dynamic
-+                                         thread local data.  */
-+#define R_390_TLS_GD64                41      /* Direct 64 bit for general dynamic
-+                                        thread local data.  */
-+#define R_390_TLS_GOTIE12     42      /* 12 bit GOT offset for static TLS
-+                                         block offset.  */
-+#define R_390_TLS_GOTIE32     43      /* 32 bit GOT offset for static TLS
-+                                         block offset.  */
-+#define R_390_TLS_GOTIE64     44      /* 64 bit GOT offset for static TLS
-+                                         block offset. */
-+#define R_390_TLS_LDM32               45      /* Direct 32 bit for local dynamic
-+                                         thread local data in LE code.  */
-+#define R_390_TLS_LDM64               46      /* Direct 64 bit for local dynamic
-+                                         thread local data in LE code.  */
-+#define R_390_TLS_IE32                47      /* 32 bit address of GOT entry for
-+                                         negated static TLS block offset.  */
-+#define R_390_TLS_IE64                48      /* 64 bit address of GOT entry for
-+                                         negated static TLS block offset.  */
-+#define R_390_TLS_IEENT               49      /* 32 bit rel. offset to GOT entry for
-+                                         negated static TLS block offset.  */
-+#define R_390_TLS_LE32                50      /* 32 bit negated offset relative to
-+                                         static TLS block.  */
-+#define R_390_TLS_LE64                51      /* 64 bit negated offset relative to
-+                                         static TLS block.  */
-+#define R_390_TLS_LDO32               52      /* 32 bit offset relative to TLS
-+                                         block.  */
-+#define R_390_TLS_LDO64               53      /* 64 bit offset relative to TLS
-+                                         block.  */
-+#define R_390_TLS_DTPMOD      54      /* ID of module containing symbol.  */
-+#define R_390_TLS_DTPOFF      55      /* Offset in TLS block.  */
-+#define R_390_TLS_TPOFF               56      /* Negated offset in static TLS
-+                                         block.  */
-+#define R_390_20              57      /* Direct 20 bit.  */
-+#define R_390_GOT20           58      /* 20 bit GOT offset.  */
-+#define R_390_GOTPLT20                59      /* 20 bit offset to jump slot.  */
-+#define R_390_TLS_GOTIE20     60      /* 20 bit GOT offset for static TLS
-+                                         block offset.  */
-+#define R_390_IRELATIVE         61      /* STT_GNU_IFUNC relocation.  */
-+/* Keep this the last entry.  */
-+#define R_390_NUM             62
-+
-+
-+/* CRIS relocations.  */
-+#define R_CRIS_NONE           0
-+#define R_CRIS_8              1
-+#define R_CRIS_16             2
-+#define R_CRIS_32             3
-+#define R_CRIS_8_PCREL                4
-+#define R_CRIS_16_PCREL               5
-+#define R_CRIS_32_PCREL               6
-+#define R_CRIS_GNU_VTINHERIT  7
-+#define R_CRIS_GNU_VTENTRY    8
-+#define R_CRIS_COPY           9
-+#define R_CRIS_GLOB_DAT               10
-+#define R_CRIS_JUMP_SLOT      11
-+#define R_CRIS_RELATIVE               12
-+#define R_CRIS_16_GOT         13
-+#define R_CRIS_32_GOT         14
-+#define R_CRIS_16_GOTPLT      15
-+#define R_CRIS_32_GOTPLT      16
-+#define R_CRIS_32_GOTREL      17
-+#define R_CRIS_32_PLT_GOTREL  18
-+#define R_CRIS_32_PLT_PCREL   19
-+
-+#define R_CRIS_NUM            20
-+
-+
-+/* AMD x86-64 relocations.  */
-+#define R_X86_64_NONE         0       /* No reloc */
-+#define R_X86_64_64           1       /* Direct 64 bit  */
-+#define R_X86_64_PC32         2       /* PC relative 32 bit signed */
-+#define R_X86_64_GOT32                3       /* 32 bit GOT entry */
-+#define R_X86_64_PLT32                4       /* 32 bit PLT address */
-+#define R_X86_64_COPY         5       /* Copy symbol at runtime */
-+#define R_X86_64_GLOB_DAT     6       /* Create GOT entry */
-+#define R_X86_64_JUMP_SLOT    7       /* Create PLT entry */
-+#define R_X86_64_RELATIVE     8       /* Adjust by program base */
-+#define R_X86_64_GOTPCREL     9       /* 32 bit signed PC relative
-+                                         offset to GOT */
-+#define R_X86_64_32           10      /* Direct 32 bit zero extended */
-+#define R_X86_64_32S          11      /* Direct 32 bit sign extended */
-+#define R_X86_64_16           12      /* Direct 16 bit zero extended */
-+#define R_X86_64_PC16         13      /* 16 bit sign extended pc relative */
-+#define R_X86_64_8            14      /* Direct 8 bit sign extended  */
-+#define R_X86_64_PC8          15      /* 8 bit sign extended pc relative */
-+#define R_X86_64_DTPMOD64     16      /* ID of module containing symbol */
-+#define R_X86_64_DTPOFF64     17      /* Offset in module's TLS block */
-+#define R_X86_64_TPOFF64      18      /* Offset in initial TLS block */
-+#define R_X86_64_TLSGD                19      /* 32 bit signed PC relative offset
-+                                         to two GOT entries for GD symbol */
-+#define R_X86_64_TLSLD                20      /* 32 bit signed PC relative offset
-+                                         to two GOT entries for LD symbol */
-+#define R_X86_64_DTPOFF32     21      /* Offset in TLS block */
-+#define R_X86_64_GOTTPOFF     22      /* 32 bit signed PC relative offset
-+                                         to GOT entry for IE symbol */
-+#define R_X86_64_TPOFF32      23      /* Offset in initial TLS block */
-+#define R_X86_64_PC64         24      /* PC relative 64 bit */
-+#define R_X86_64_GOTOFF64     25      /* 64 bit offset to GOT */
-+#define R_X86_64_GOTPC32      26      /* 32 bit signed pc relative
-+                                         offset to GOT */
-+#define R_X86_64_GOT64                27      /* 64-bit GOT entry offset */
-+#define R_X86_64_GOTPCREL64   28      /* 64-bit PC relative offset
-+                                         to GOT entry */
-+#define R_X86_64_GOTPC64      29      /* 64-bit PC relative offset to GOT */
-+#define R_X86_64_GOTPLT64     30      /* like GOT64, says PLT entry needed */
-+#define R_X86_64_PLTOFF64     31      /* 64-bit GOT relative offset
-+                                         to PLT entry */
-+#define R_X86_64_SIZE32               32      /* Size of symbol plus 32-bit addend */
-+#define R_X86_64_SIZE64               33      /* Size of symbol plus 64-bit addend */
-+#define R_X86_64_GOTPC32_TLSDESC 34   /* GOT offset for TLS descriptor.  */
-+#define R_X86_64_TLSDESC_CALL   35    /* Marker for call through TLS
-+                                         descriptor.  */
-+#define R_X86_64_TLSDESC        36    /* TLS descriptor.  */
-+#define R_X86_64_IRELATIVE    37      /* Adjust indirectly by program base */
-+#define R_X86_64_RELATIVE64   38      /* 64-bit adjust by program base */
-+
-+#define R_X86_64_NUM          39
-+
-+
-+/* AM33 relocations.  */
-+#define R_MN10300_NONE                0       /* No reloc.  */
-+#define R_MN10300_32          1       /* Direct 32 bit.  */
-+#define R_MN10300_16          2       /* Direct 16 bit.  */
-+#define R_MN10300_8           3       /* Direct 8 bit.  */
-+#define R_MN10300_PCREL32     4       /* PC-relative 32-bit.  */
-+#define R_MN10300_PCREL16     5       /* PC-relative 16-bit signed.  */
-+#define R_MN10300_PCREL8      6       /* PC-relative 8-bit signed.  */
-+#define R_MN10300_GNU_VTINHERIT       7       /* Ancient C++ vtable garbage... */
-+#define R_MN10300_GNU_VTENTRY 8       /* ... collection annotation.  */
-+#define R_MN10300_24          9       /* Direct 24 bit.  */
-+#define R_MN10300_GOTPC32     10      /* 32-bit PCrel offset to GOT.  */
-+#define R_MN10300_GOTPC16     11      /* 16-bit PCrel offset to GOT.  */
-+#define R_MN10300_GOTOFF32    12      /* 32-bit offset from GOT.  */
-+#define R_MN10300_GOTOFF24    13      /* 24-bit offset from GOT.  */
-+#define R_MN10300_GOTOFF16    14      /* 16-bit offset from GOT.  */
-+#define R_MN10300_PLT32               15      /* 32-bit PCrel to PLT entry.  */
-+#define R_MN10300_PLT16               16      /* 16-bit PCrel to PLT entry.  */
-+#define R_MN10300_GOT32               17      /* 32-bit offset to GOT entry.  */
-+#define R_MN10300_GOT24               18      /* 24-bit offset to GOT entry.  */
-+#define R_MN10300_GOT16               19      /* 16-bit offset to GOT entry.  */
-+#define R_MN10300_COPY                20      /* Copy symbol at runtime.  */
-+#define R_MN10300_GLOB_DAT    21      /* Create GOT entry.  */
-+#define R_MN10300_JMP_SLOT    22      /* Create PLT entry.  */
-+#define R_MN10300_RELATIVE    23      /* Adjust by program base.  */
-+
-+#define R_MN10300_NUM         24
-+
-+
-+/* M32R relocs.  */
-+#define R_M32R_NONE           0       /* No reloc. */
-+#define R_M32R_16             1       /* Direct 16 bit. */
-+#define R_M32R_32             2       /* Direct 32 bit. */
-+#define R_M32R_24             3       /* Direct 24 bit. */
-+#define R_M32R_10_PCREL               4       /* PC relative 10 bit shifted. */
-+#define R_M32R_18_PCREL               5       /* PC relative 18 bit shifted. */
-+#define R_M32R_26_PCREL               6       /* PC relative 26 bit shifted. */
-+#define R_M32R_HI16_ULO               7       /* High 16 bit with unsigned low. */
-+#define R_M32R_HI16_SLO               8       /* High 16 bit with signed low. */
-+#define R_M32R_LO16           9       /* Low 16 bit. */
-+#define R_M32R_SDA16          10      /* 16 bit offset in SDA. */
-+#define R_M32R_GNU_VTINHERIT  11
-+#define R_M32R_GNU_VTENTRY    12
-+/* M32R relocs use SHT_RELA.  */
-+#define R_M32R_16_RELA                33      /* Direct 16 bit. */
-+#define R_M32R_32_RELA                34      /* Direct 32 bit. */
-+#define R_M32R_24_RELA                35      /* Direct 24 bit. */
-+#define R_M32R_10_PCREL_RELA  36      /* PC relative 10 bit shifted. */
-+#define R_M32R_18_PCREL_RELA  37      /* PC relative 18 bit shifted. */
-+#define R_M32R_26_PCREL_RELA  38      /* PC relative 26 bit shifted. */
-+#define R_M32R_HI16_ULO_RELA  39      /* High 16 bit with unsigned low */
-+#define R_M32R_HI16_SLO_RELA  40      /* High 16 bit with signed low */
-+#define R_M32R_LO16_RELA      41      /* Low 16 bit */
-+#define R_M32R_SDA16_RELA     42      /* 16 bit offset in SDA */
-+#define R_M32R_RELA_GNU_VTINHERIT     43
-+#define R_M32R_RELA_GNU_VTENTRY       44
-+#define R_M32R_REL32          45      /* PC relative 32 bit.  */
-+
-+#define R_M32R_GOT24          48      /* 24 bit GOT entry */
-+#define R_M32R_26_PLTREL      49      /* 26 bit PC relative to PLT shifted */
-+#define R_M32R_COPY           50      /* Copy symbol at runtime */
-+#define R_M32R_GLOB_DAT               51      /* Create GOT entry */
-+#define R_M32R_JMP_SLOT               52      /* Create PLT entry */
-+#define R_M32R_RELATIVE               53      /* Adjust by program base */
-+#define R_M32R_GOTOFF         54      /* 24 bit offset to GOT */
-+#define R_M32R_GOTPC24                55      /* 24 bit PC relative offset to GOT */
-+#define R_M32R_GOT16_HI_ULO   56      /* High 16 bit GOT entry with unsigned
-+                                         low */
-+#define R_M32R_GOT16_HI_SLO   57      /* High 16 bit GOT entry with signed
-+                                         low */
-+#define R_M32R_GOT16_LO               58      /* Low 16 bit GOT entry */
-+#define R_M32R_GOTPC_HI_ULO   59      /* High 16 bit PC relative offset to
-+                                         GOT with unsigned low */
-+#define R_M32R_GOTPC_HI_SLO   60      /* High 16 bit PC relative offset to
-+                                         GOT with signed low */
-+#define R_M32R_GOTPC_LO               61      /* Low 16 bit PC relative offset to
-+                                         GOT */
-+#define R_M32R_GOTOFF_HI_ULO  62      /* High 16 bit offset to GOT
-+                                         with unsigned low */
-+#define R_M32R_GOTOFF_HI_SLO  63      /* High 16 bit offset to GOT
-+                                         with signed low */
-+#define R_M32R_GOTOFF_LO      64      /* Low 16 bit offset to GOT */
-+#define R_M32R_NUM            256     /* Keep this the last entry. */
-+
-+
-+/* TILEPro relocations.  */
-+#define R_TILEPRO_NONE                0       /* No reloc */
-+#define R_TILEPRO_32          1       /* Direct 32 bit */
-+#define R_TILEPRO_16          2       /* Direct 16 bit */
-+#define R_TILEPRO_8           3       /* Direct 8 bit */
-+#define R_TILEPRO_32_PCREL    4       /* PC relative 32 bit */
-+#define R_TILEPRO_16_PCREL    5       /* PC relative 16 bit */
-+#define R_TILEPRO_8_PCREL     6       /* PC relative 8 bit */
-+#define R_TILEPRO_LO16                7       /* Low 16 bit */
-+#define R_TILEPRO_HI16                8       /* High 16 bit */
-+#define R_TILEPRO_HA16                9       /* High 16 bit, adjusted */
-+#define R_TILEPRO_COPY                10      /* Copy relocation */
-+#define R_TILEPRO_GLOB_DAT    11      /* Create GOT entry */
-+#define R_TILEPRO_JMP_SLOT    12      /* Create PLT entry */
-+#define R_TILEPRO_RELATIVE    13      /* Adjust by program base */
-+#define R_TILEPRO_BROFF_X1    14      /* X1 pipe branch offset */
-+#define R_TILEPRO_JOFFLONG_X1 15      /* X1 pipe jump offset */
-+#define R_TILEPRO_JOFFLONG_X1_PLT 16  /* X1 pipe jump offset to PLT */
-+#define R_TILEPRO_IMM8_X0     17      /* X0 pipe 8-bit */
-+#define R_TILEPRO_IMM8_Y0     18      /* Y0 pipe 8-bit */
-+#define R_TILEPRO_IMM8_X1     19      /* X1 pipe 8-bit */
-+#define R_TILEPRO_IMM8_Y1     20      /* Y1 pipe 8-bit */
-+#define R_TILEPRO_MT_IMM15_X1 21      /* X1 pipe mtspr */
-+#define R_TILEPRO_MF_IMM15_X1 22      /* X1 pipe mfspr */
-+#define R_TILEPRO_IMM16_X0    23      /* X0 pipe 16-bit */
-+#define R_TILEPRO_IMM16_X1    24      /* X1 pipe 16-bit */
-+#define R_TILEPRO_IMM16_X0_LO 25      /* X0 pipe low 16-bit */
-+#define R_TILEPRO_IMM16_X1_LO 26      /* X1 pipe low 16-bit */
-+#define R_TILEPRO_IMM16_X0_HI 27      /* X0 pipe high 16-bit */
-+#define R_TILEPRO_IMM16_X1_HI 28      /* X1 pipe high 16-bit */
-+#define R_TILEPRO_IMM16_X0_HA 29      /* X0 pipe high 16-bit, adjusted */
-+#define R_TILEPRO_IMM16_X1_HA 30      /* X1 pipe high 16-bit, adjusted */
-+#define R_TILEPRO_IMM16_X0_PCREL 31   /* X0 pipe PC relative 16 bit */
-+#define R_TILEPRO_IMM16_X1_PCREL 32   /* X1 pipe PC relative 16 bit */
-+#define R_TILEPRO_IMM16_X0_LO_PCREL 33        /* X0 pipe PC relative low 16 bit */
-+#define R_TILEPRO_IMM16_X1_LO_PCREL 34        /* X1 pipe PC relative low 16 bit */
-+#define R_TILEPRO_IMM16_X0_HI_PCREL 35        /* X0 pipe PC relative high 16 bit */
-+#define R_TILEPRO_IMM16_X1_HI_PCREL 36        /* X1 pipe PC relative high 16 bit */
-+#define R_TILEPRO_IMM16_X0_HA_PCREL 37        /* X0 pipe PC relative ha() 16 bit */
-+#define R_TILEPRO_IMM16_X1_HA_PCREL 38        /* X1 pipe PC relative ha() 16 bit */
-+#define R_TILEPRO_IMM16_X0_GOT        39      /* X0 pipe 16-bit GOT offset */
-+#define R_TILEPRO_IMM16_X1_GOT        40      /* X1 pipe 16-bit GOT offset */
-+#define R_TILEPRO_IMM16_X0_GOT_LO 41  /* X0 pipe low 16-bit GOT offset */
-+#define R_TILEPRO_IMM16_X1_GOT_LO 42  /* X1 pipe low 16-bit GOT offset */
-+#define R_TILEPRO_IMM16_X0_GOT_HI 43  /* X0 pipe high 16-bit GOT offset */
-+#define R_TILEPRO_IMM16_X1_GOT_HI 44  /* X1 pipe high 16-bit GOT offset */
-+#define R_TILEPRO_IMM16_X0_GOT_HA 45  /* X0 pipe ha() 16-bit GOT offset */
-+#define R_TILEPRO_IMM16_X1_GOT_HA 46  /* X1 pipe ha() 16-bit GOT offset */
-+#define R_TILEPRO_MMSTART_X0  47      /* X0 pipe mm "start" */
-+#define R_TILEPRO_MMEND_X0    48      /* X0 pipe mm "end" */
-+#define R_TILEPRO_MMSTART_X1  49      /* X1 pipe mm "start" */
-+#define R_TILEPRO_MMEND_X1    50      /* X1 pipe mm "end" */
-+#define R_TILEPRO_SHAMT_X0    51      /* X0 pipe shift amount */
-+#define R_TILEPRO_SHAMT_X1    52      /* X1 pipe shift amount */
-+#define R_TILEPRO_SHAMT_Y0    53      /* Y0 pipe shift amount */
-+#define R_TILEPRO_SHAMT_Y1    54      /* Y1 pipe shift amount */
-+#define R_TILEPRO_DEST_IMM8_X1        55      /* X1 pipe destination 8-bit */
-+/* Relocs 56-59 are currently not defined.  */
-+#define R_TILEPRO_TLS_GD_CALL 60      /* "jal" for TLS GD */
-+#define R_TILEPRO_IMM8_X0_TLS_GD_ADD 61       /* X0 pipe "addi" for TLS GD */
-+#define R_TILEPRO_IMM8_X1_TLS_GD_ADD 62       /* X1 pipe "addi" for TLS GD */
-+#define R_TILEPRO_IMM8_Y0_TLS_GD_ADD 63       /* Y0 pipe "addi" for TLS GD */
-+#define R_TILEPRO_IMM8_Y1_TLS_GD_ADD 64       /* Y1 pipe "addi" for TLS GD */
-+#define R_TILEPRO_TLS_IE_LOAD 65      /* "lw_tls" for TLS IE */
-+#define R_TILEPRO_IMM16_X0_TLS_GD 66  /* X0 pipe 16-bit TLS GD offset */
-+#define R_TILEPRO_IMM16_X1_TLS_GD 67  /* X1 pipe 16-bit TLS GD offset */
-+#define R_TILEPRO_IMM16_X0_TLS_GD_LO 68       /* X0 pipe low 16-bit TLS GD offset */
-+#define R_TILEPRO_IMM16_X1_TLS_GD_LO 69       /* X1 pipe low 16-bit TLS GD offset */
-+#define R_TILEPRO_IMM16_X0_TLS_GD_HI 70       /* X0 pipe high 16-bit TLS GD offset */
-+#define R_TILEPRO_IMM16_X1_TLS_GD_HI 71       /* X1 pipe high 16-bit TLS GD offset */
-+#define R_TILEPRO_IMM16_X0_TLS_GD_HA 72       /* X0 pipe ha() 16-bit TLS GD offset */
-+#define R_TILEPRO_IMM16_X1_TLS_GD_HA 73       /* X1 pipe ha() 16-bit TLS GD offset */
-+#define R_TILEPRO_IMM16_X0_TLS_IE 74  /* X0 pipe 16-bit TLS IE offset */
-+#define R_TILEPRO_IMM16_X1_TLS_IE 75  /* X1 pipe 16-bit TLS IE offset */
-+#define R_TILEPRO_IMM16_X0_TLS_IE_LO 76       /* X0 pipe low 16-bit TLS IE offset */
-+#define R_TILEPRO_IMM16_X1_TLS_IE_LO 77       /* X1 pipe low 16-bit TLS IE offset */
-+#define R_TILEPRO_IMM16_X0_TLS_IE_HI 78       /* X0 pipe high 16-bit TLS IE offset */
-+#define R_TILEPRO_IMM16_X1_TLS_IE_HI 79       /* X1 pipe high 16-bit TLS IE offset */
-+#define R_TILEPRO_IMM16_X0_TLS_IE_HA 80       /* X0 pipe ha() 16-bit TLS IE offset */
-+#define R_TILEPRO_IMM16_X1_TLS_IE_HA 81       /* X1 pipe ha() 16-bit TLS IE offset */
-+#define R_TILEPRO_TLS_DTPMOD32        82      /* ID of module containing symbol */
-+#define R_TILEPRO_TLS_DTPOFF32        83      /* Offset in TLS block */
-+#define R_TILEPRO_TLS_TPOFF32 84      /* Offset in static TLS block */
-+#define R_TILEPRO_IMM16_X0_TLS_LE 85  /* X0 pipe 16-bit TLS LE offset */
-+#define R_TILEPRO_IMM16_X1_TLS_LE 86  /* X1 pipe 16-bit TLS LE offset */
-+#define R_TILEPRO_IMM16_X0_TLS_LE_LO 87       /* X0 pipe low 16-bit TLS LE offset */
-+#define R_TILEPRO_IMM16_X1_TLS_LE_LO 88       /* X1 pipe low 16-bit TLS LE offset */
-+#define R_TILEPRO_IMM16_X0_TLS_LE_HI 89       /* X0 pipe high 16-bit TLS LE offset */
-+#define R_TILEPRO_IMM16_X1_TLS_LE_HI 90       /* X1 pipe high 16-bit TLS LE offset */
-+#define R_TILEPRO_IMM16_X0_TLS_LE_HA 91       /* X0 pipe ha() 16-bit TLS LE offset */
-+#define R_TILEPRO_IMM16_X1_TLS_LE_HA 92       /* X1 pipe ha() 16-bit TLS LE offset */
-+
-+#define R_TILEPRO_GNU_VTINHERIT       128     /* GNU C++ vtable hierarchy */
-+#define R_TILEPRO_GNU_VTENTRY 129     /* GNU C++ vtable member usage */
-+
-+#define R_TILEPRO_NUM         130
-+
-+
-+/* TILE-Gx relocations.  */
-+#define R_TILEGX_NONE         0       /* No reloc */
-+#define R_TILEGX_64           1       /* Direct 64 bit */
-+#define R_TILEGX_32           2       /* Direct 32 bit */
-+#define R_TILEGX_16           3       /* Direct 16 bit */
-+#define R_TILEGX_8            4       /* Direct 8 bit */
-+#define R_TILEGX_64_PCREL     5       /* PC relative 64 bit */
-+#define R_TILEGX_32_PCREL     6       /* PC relative 32 bit */
-+#define R_TILEGX_16_PCREL     7       /* PC relative 16 bit */
-+#define R_TILEGX_8_PCREL      8       /* PC relative 8 bit */
-+#define R_TILEGX_HW0          9       /* hword 0 16-bit */
-+#define R_TILEGX_HW1          10      /* hword 1 16-bit */
-+#define R_TILEGX_HW2          11      /* hword 2 16-bit */
-+#define R_TILEGX_HW3          12      /* hword 3 16-bit */
-+#define R_TILEGX_HW0_LAST     13      /* last hword 0 16-bit */
-+#define R_TILEGX_HW1_LAST     14      /* last hword 1 16-bit */
-+#define R_TILEGX_HW2_LAST     15      /* last hword 2 16-bit */
-+#define R_TILEGX_COPY         16      /* Copy relocation */
-+#define R_TILEGX_GLOB_DAT     17      /* Create GOT entry */
-+#define R_TILEGX_JMP_SLOT     18      /* Create PLT entry */
-+#define R_TILEGX_RELATIVE     19      /* Adjust by program base */
-+#define R_TILEGX_BROFF_X1     20      /* X1 pipe branch offset */
-+#define R_TILEGX_JUMPOFF_X1   21      /* X1 pipe jump offset */
-+#define R_TILEGX_JUMPOFF_X1_PLT       22      /* X1 pipe jump offset to PLT */
-+#define R_TILEGX_IMM8_X0      23      /* X0 pipe 8-bit */
-+#define R_TILEGX_IMM8_Y0      24      /* Y0 pipe 8-bit */
-+#define R_TILEGX_IMM8_X1      25      /* X1 pipe 8-bit */
-+#define R_TILEGX_IMM8_Y1      26      /* Y1 pipe 8-bit */
-+#define R_TILEGX_DEST_IMM8_X1 27      /* X1 pipe destination 8-bit */
-+#define R_TILEGX_MT_IMM14_X1  28      /* X1 pipe mtspr */
-+#define R_TILEGX_MF_IMM14_X1  29      /* X1 pipe mfspr */
-+#define R_TILEGX_MMSTART_X0   30      /* X0 pipe mm "start" */
-+#define R_TILEGX_MMEND_X0     31      /* X0 pipe mm "end" */
-+#define R_TILEGX_SHAMT_X0     32      /* X0 pipe shift amount */
-+#define R_TILEGX_SHAMT_X1     33      /* X1 pipe shift amount */
-+#define R_TILEGX_SHAMT_Y0     34      /* Y0 pipe shift amount */
-+#define R_TILEGX_SHAMT_Y1     35      /* Y1 pipe shift amount */
-+#define R_TILEGX_IMM16_X0_HW0 36      /* X0 pipe hword 0 */
-+#define R_TILEGX_IMM16_X1_HW0 37      /* X1 pipe hword 0 */
-+#define R_TILEGX_IMM16_X0_HW1 38      /* X0 pipe hword 1 */
-+#define R_TILEGX_IMM16_X1_HW1 39      /* X1 pipe hword 1 */
-+#define R_TILEGX_IMM16_X0_HW2 40      /* X0 pipe hword 2 */
-+#define R_TILEGX_IMM16_X1_HW2 41      /* X1 pipe hword 2 */
-+#define R_TILEGX_IMM16_X0_HW3 42      /* X0 pipe hword 3 */
-+#define R_TILEGX_IMM16_X1_HW3 43      /* X1 pipe hword 3 */
-+#define R_TILEGX_IMM16_X0_HW0_LAST 44 /* X0 pipe last hword 0 */
-+#define R_TILEGX_IMM16_X1_HW0_LAST 45 /* X1 pipe last hword 0 */
-+#define R_TILEGX_IMM16_X0_HW1_LAST 46 /* X0 pipe last hword 1 */
-+#define R_TILEGX_IMM16_X1_HW1_LAST 47 /* X1 pipe last hword 1 */
-+#define R_TILEGX_IMM16_X0_HW2_LAST 48 /* X0 pipe last hword 2 */
-+#define R_TILEGX_IMM16_X1_HW2_LAST 49 /* X1 pipe last hword 2 */
-+#define R_TILEGX_IMM16_X0_HW0_PCREL 50        /* X0 pipe PC relative hword 0 */
-+#define R_TILEGX_IMM16_X1_HW0_PCREL 51        /* X1 pipe PC relative hword 0 */
-+#define R_TILEGX_IMM16_X0_HW1_PCREL 52        /* X0 pipe PC relative hword 1 */
-+#define R_TILEGX_IMM16_X1_HW1_PCREL 53        /* X1 pipe PC relative hword 1 */
-+#define R_TILEGX_IMM16_X0_HW2_PCREL 54        /* X0 pipe PC relative hword 2 */
-+#define R_TILEGX_IMM16_X1_HW2_PCREL 55        /* X1 pipe PC relative hword 2 */
-+#define R_TILEGX_IMM16_X0_HW3_PCREL 56        /* X0 pipe PC relative hword 3 */
-+#define R_TILEGX_IMM16_X1_HW3_PCREL 57        /* X1 pipe PC relative hword 3 */
-+#define R_TILEGX_IMM16_X0_HW0_LAST_PCREL 58 /* X0 pipe PC-rel last hword 0 */
-+#define R_TILEGX_IMM16_X1_HW0_LAST_PCREL 59 /* X1 pipe PC-rel last hword 0 */
-+#define R_TILEGX_IMM16_X0_HW1_LAST_PCREL 60 /* X0 pipe PC-rel last hword 1 */
-+#define R_TILEGX_IMM16_X1_HW1_LAST_PCREL 61 /* X1 pipe PC-rel last hword 1 */
-+#define R_TILEGX_IMM16_X0_HW2_LAST_PCREL 62 /* X0 pipe PC-rel last hword 2 */
-+#define R_TILEGX_IMM16_X1_HW2_LAST_PCREL 63 /* X1 pipe PC-rel last hword 2 */
-+#define R_TILEGX_IMM16_X0_HW0_GOT 64  /* X0 pipe hword 0 GOT offset */
-+#define R_TILEGX_IMM16_X1_HW0_GOT 65  /* X1 pipe hword 0 GOT offset */
-+/* Relocs 66-71 are currently not defined.  */
-+#define R_TILEGX_IMM16_X0_HW0_LAST_GOT 72 /* X0 pipe last hword 0 GOT offset */
-+#define R_TILEGX_IMM16_X1_HW0_LAST_GOT 73 /* X1 pipe last hword 0 GOT offset */
-+#define R_TILEGX_IMM16_X0_HW1_LAST_GOT 74 /* X0 pipe last hword 1 GOT offset */
-+#define R_TILEGX_IMM16_X1_HW1_LAST_GOT 75 /* X1 pipe last hword 1 GOT offset */
-+/* Relocs 76-77 are currently not defined.  */
-+#define R_TILEGX_IMM16_X0_HW0_TLS_GD 78       /* X0 pipe hword 0 TLS GD offset */
-+#define R_TILEGX_IMM16_X1_HW0_TLS_GD 79       /* X1 pipe hword 0 TLS GD offset */
-+#define R_TILEGX_IMM16_X0_HW0_TLS_LE 80       /* X0 pipe hword 0 TLS LE offset */
-+#define R_TILEGX_IMM16_X1_HW0_TLS_LE 81       /* X1 pipe hword 0 TLS LE offset */
-+#define R_TILEGX_IMM16_X0_HW0_LAST_TLS_LE 82 /* X0 pipe last hword 0 LE off */
-+#define R_TILEGX_IMM16_X1_HW0_LAST_TLS_LE 83 /* X1 pipe last hword 0 LE off */
-+#define R_TILEGX_IMM16_X0_HW1_LAST_TLS_LE 84 /* X0 pipe last hword 1 LE off */
-+#define R_TILEGX_IMM16_X1_HW1_LAST_TLS_LE 85 /* X1 pipe last hword 1 LE off */
-+#define R_TILEGX_IMM16_X0_HW0_LAST_TLS_GD 86 /* X0 pipe last hword 0 GD off */
-+#define R_TILEGX_IMM16_X1_HW0_LAST_TLS_GD 87 /* X1 pipe last hword 0 GD off */
-+#define R_TILEGX_IMM16_X0_HW1_LAST_TLS_GD 88 /* X0 pipe last hword 1 GD off */
-+#define R_TILEGX_IMM16_X1_HW1_LAST_TLS_GD 89 /* X1 pipe last hword 1 GD off */
-+/* Relocs 90-91 are currently not defined.  */
-+#define R_TILEGX_IMM16_X0_HW0_TLS_IE 92       /* X0 pipe hword 0 TLS IE offset */
-+#define R_TILEGX_IMM16_X1_HW0_TLS_IE 93       /* X1 pipe hword 0 TLS IE offset */
-+/* Relocs 94-99 are currently not defined.  */
-+#define R_TILEGX_IMM16_X0_HW0_LAST_TLS_IE 100 /* X0 pipe last hword 0 IE off */
-+#define R_TILEGX_IMM16_X1_HW0_LAST_TLS_IE 101 /* X1 pipe last hword 0 IE off */
-+#define R_TILEGX_IMM16_X0_HW1_LAST_TLS_IE 102 /* X0 pipe last hword 1 IE off */
-+#define R_TILEGX_IMM16_X1_HW1_LAST_TLS_IE 103 /* X1 pipe last hword 1 IE off */
-+/* Relocs 104-105 are currently not defined.  */
-+#define R_TILEGX_TLS_DTPMOD64 106     /* 64-bit ID of symbol's module */
-+#define R_TILEGX_TLS_DTPOFF64 107     /* 64-bit offset in TLS block */
-+#define R_TILEGX_TLS_TPOFF64  108     /* 64-bit offset in static TLS block */
-+#define R_TILEGX_TLS_DTPMOD32 109     /* 32-bit ID of symbol's module */
-+#define R_TILEGX_TLS_DTPOFF32 110     /* 32-bit offset in TLS block */
-+#define R_TILEGX_TLS_TPOFF32  111     /* 32-bit offset in static TLS block */
-+#define R_TILEGX_TLS_GD_CALL  112     /* "jal" for TLS GD */
-+#define R_TILEGX_IMM8_X0_TLS_GD_ADD 113       /* X0 pipe "addi" for TLS GD */
-+#define R_TILEGX_IMM8_X1_TLS_GD_ADD 114       /* X1 pipe "addi" for TLS GD */
-+#define R_TILEGX_IMM8_Y0_TLS_GD_ADD 115       /* Y0 pipe "addi" for TLS GD */
-+#define R_TILEGX_IMM8_Y1_TLS_GD_ADD 116       /* Y1 pipe "addi" for TLS GD */
-+#define R_TILEGX_TLS_IE_LOAD  117     /* "ld_tls" for TLS IE */
-+#define R_TILEGX_IMM8_X0_TLS_ADD 118  /* X0 pipe "addi" for TLS GD/IE */
-+#define R_TILEGX_IMM8_X1_TLS_ADD 119  /* X1 pipe "addi" for TLS GD/IE */
-+#define R_TILEGX_IMM8_Y0_TLS_ADD 120  /* Y0 pipe "addi" for TLS GD/IE */
-+#define R_TILEGX_IMM8_Y1_TLS_ADD 121  /* Y1 pipe "addi" for TLS GD/IE */
-+
-+#define R_TILEGX_GNU_VTINHERIT        128     /* GNU C++ vtable hierarchy */
-+#define R_TILEGX_GNU_VTENTRY  129     /* GNU C++ vtable member usage */
-+
-+#define R_TILEGX_NUM          130
-+
-+#endif        /* elf.h */
---- a/scripts/mod/mk_elfconfig.c
-+++ b/scripts/mod/mk_elfconfig.c
-@@ -2,7 +2,11 @@
- #include <stdio.h>
- #include <stdlib.h>
- #include <string.h>
-+#ifndef __APPLE__
- #include <elf.h>
-+#else
-+#include "elf.h"
-+#endif
- int
- main(int argc, char **argv)
---- a/scripts/mod/modpost.h
-+++ b/scripts/mod/modpost.h
-@@ -8,7 +8,11 @@
- #include <sys/mman.h>
- #include <fcntl.h>
- #include <unistd.h>
-+#if !(defined(__APPLE__) || defined(__CYGWIN__))
- #include <elf.h>
-+#else
-+#include "elf.h"
-+#endif
- #include "elfconfig.h"
diff --git a/target/linux/generic/hack-5.15/211-darwin-uuid-typedef-clash.patch b/target/linux/generic/hack-5.15/211-darwin-uuid-typedef-clash.patch
deleted file mode 100644 (file)
index 50a6227..0000000
+++ /dev/null
@@ -1,22 +0,0 @@
-From e44fc2af1ddc452b6659d08c16973d65c73b7d0a Mon Sep 17 00:00:00 2001
-From: Kevin Darbyshire-Bryant <[email protected]>
-Date: Wed, 5 Feb 2020 18:36:43 +0000
-Subject: [PATCH] file2alias: build on macos
-
-Signed-off-by: Kevin Darbyshire-Bryant <[email protected]>
----
- scripts/mod/file2alias.c | 3 +++
- 1 file changed, 3 insertions(+)
-
---- a/scripts/mod/file2alias.c
-+++ b/scripts/mod/file2alias.c
-@@ -38,6 +38,9 @@ typedef struct {
-       __u8 b[16];
- } guid_t;
-+#ifdef __APPLE__
-+#define uuid_t compat_uuid_t
-+#endif
- /* backwards compatibility, don't use in new code */
- typedef struct {
-       __u8 b[16];
diff --git a/target/linux/generic/hack-5.15/212-tools_portability.patch b/target/linux/generic/hack-5.15/212-tools_portability.patch
deleted file mode 100644 (file)
index b488155..0000000
+++ /dev/null
@@ -1,110 +0,0 @@
-From 48232d3d931c95953ce2ddfe7da7bb164aef6a73 Mon Sep 17 00:00:00 2001
-From: Felix Fietkau <[email protected]>
-Date: Fri, 7 Jul 2017 17:03:16 +0200
-Subject: fix portability of some includes files in tools/ used on the host
-
-Signed-off-by: Felix Fietkau <[email protected]>
----
- tools/include/tools/be_byteshift.h |  4 ++++
- tools/include/tools/le_byteshift.h |  4 ++++
- tools/include/tools/linux_types.h  | 22 ++++++++++++++++++++++
- 3 files changed, 30 insertions(+)
- create mode 100644 tools/include/tools/linux_types.h
-
---- a/tools/include/tools/be_byteshift.h
-+++ b/tools/include/tools/be_byteshift.h
-@@ -2,6 +2,10 @@
- #ifndef _TOOLS_BE_BYTESHIFT_H
- #define _TOOLS_BE_BYTESHIFT_H
-+#ifndef __linux__
-+#include "linux_types.h"
-+#endif
-+
- #include <stdint.h>
- static inline uint16_t __get_unaligned_be16(const uint8_t *p)
---- a/tools/include/tools/le_byteshift.h
-+++ b/tools/include/tools/le_byteshift.h
-@@ -2,6 +2,10 @@
- #ifndef _TOOLS_LE_BYTESHIFT_H
- #define _TOOLS_LE_BYTESHIFT_H
-+#ifndef __linux__
-+#include "linux_types.h"
-+#endif
-+
- #include <stdint.h>
- static inline uint16_t __get_unaligned_le16(const uint8_t *p)
---- /dev/null
-+++ b/tools/include/tools/linux_types.h
-@@ -0,0 +1,26 @@
-+#ifndef __LINUX_TYPES_H
-+#define __LINUX_TYPES_H
-+
-+#include <stdint.h>
-+
-+typedef int8_t __s8;
-+typedef uint8_t __u8;
-+typedef uint8_t __be8;
-+typedef uint8_t __le8;
-+
-+typedef int16_t __s16;
-+typedef uint16_t __u16;
-+typedef uint16_t __be16;
-+typedef uint16_t __le16;
-+
-+typedef int32_t __s32;
-+typedef uint32_t __u32;
-+typedef uint32_t __be32;
-+typedef uint32_t __le32;
-+
-+typedef int64_t __s64;
-+typedef uint64_t __u64;
-+typedef uint64_t __be64;
-+typedef uint64_t __le64;
-+
-+#endif
---- a/tools/include/linux/types.h
-+++ b/tools/include/linux/types.h
-@@ -10,8 +10,12 @@
- #define __SANE_USERSPACE_TYPES__      /* For PPC64, to get LL64 types */
- #endif
-+#ifndef __linux__
-+#include <tools/linux_types.h>
-+#else
- #include <asm/types.h>
- #include <asm/posix_types.h>
-+#endif
- struct page;
- struct kmem_cache;
---- a/tools/perf/pmu-events/jevents.c
-+++ b/tools/perf/pmu-events/jevents.c
-@@ -1,4 +1,6 @@
-+#ifdef __linux__
- #define  _XOPEN_SOURCE 500    /* needed for nftw() */
-+#endif
- #define  _GNU_SOURCE          /* needed for asprintf() */
- /* Parse event JSON files */
-@@ -35,6 +37,7 @@
- #include <stdlib.h>
- #include <errno.h>
- #include <string.h>
-+#include <strings.h>
- #include <ctype.h>
- #include <unistd.h>
- #include <stdarg.h>
---- a/tools/perf/pmu-events/json.c
-+++ b/tools/perf/pmu-events/json.c
-@@ -38,7 +38,6 @@
- #include <unistd.h>
- #include "jsmn.h"
- #include "json.h"
--#include <linux/kernel.h>
- static char *mapfile(const char *fn, size_t *size)
diff --git a/target/linux/generic/hack-5.15/214-spidev_h_portability.patch b/target/linux/generic/hack-5.15/214-spidev_h_portability.patch
deleted file mode 100644 (file)
index db754a2..0000000
+++ /dev/null
@@ -1,24 +0,0 @@
-From be9be95ff10e16a5b4ad36f903978d0cc5747024 Mon Sep 17 00:00:00 2001
-From: Felix Fietkau <[email protected]>
-Date: Fri, 7 Jul 2017 17:04:08 +0200
-Subject: kernel: fix linux/spi/spidev.h portability issues with musl
-
-Felix will try to get this define included into musl
-
-lede-commit: 795e7cf60de19e7a076a46874fab7bb88b43bbff
-Signed-off-by: Felix Fietkau <[email protected]>
----
- include/uapi/linux/spi/spidev.h | 2 +-
- 1 file changed, 1 insertion(+), 1 deletion(-)
-
---- a/include/uapi/linux/spi/spidev.h
-+++ b/include/uapi/linux/spi/spidev.h
-@@ -93,7 +93,7 @@ struct spi_ioc_transfer {
- /* not all platforms use <asm-generic/ioctl.h> or _IOC_TYPECHECK() ... */
- #define SPI_MSGSIZE(N) \
--      ((((N)*(sizeof (struct spi_ioc_transfer))) < (1 << _IOC_SIZEBITS)) \
-+      ((((N)*(sizeof (struct spi_ioc_transfer))) < (1 << 13)) \
-               ? ((N)*(sizeof (struct spi_ioc_transfer))) : 0)
- #define SPI_IOC_MESSAGE(N) _IOW(SPI_IOC_MAGIC, 0, char[SPI_MSGSIZE(N)])
diff --git a/target/linux/generic/hack-5.15/220-arm-gc_sections.patch b/target/linux/generic/hack-5.15/220-arm-gc_sections.patch
deleted file mode 100644 (file)
index dd6507c..0000000
+++ /dev/null
@@ -1,123 +0,0 @@
-From e3d8676f5722b7622685581e06e8f53e6138e3ab Mon Sep 17 00:00:00 2001
-From: Felix Fietkau <[email protected]>
-Date: Sat, 15 Jul 2017 23:42:36 +0200
-Subject: use -ffunction-sections, -fdata-sections and --gc-sections
-
-In combination with kernel symbol export stripping this significantly reduces
-the kernel image size. Used on both ARM and MIPS architectures.
-
-Signed-off-by: Felix Fietkau <[email protected]>
-Signed-off-by: Jonas Gorski <[email protected]>
-Signed-off-by: Gabor Juhos <[email protected]>
----
---- a/arch/arm/Kconfig
-+++ b/arch/arm/Kconfig
-@@ -118,6 +118,7 @@ config ARM
-       select HAVE_UID16
-       select HAVE_VIRT_CPU_ACCOUNTING_GEN
-       select IRQ_FORCED_THREADING
-+      select HAVE_LD_DEAD_CODE_DATA_ELIMINATION
-       select MODULES_USE_ELF_REL
-       select NEED_DMA_MAP_STATE
-       select OF_EARLY_FLATTREE if OF
---- a/arch/arm/boot/compressed/Makefile
-+++ b/arch/arm/boot/compressed/Makefile
-@@ -92,6 +92,7 @@ endif
- ifeq ($(CONFIG_USE_OF),y)
- OBJS  += $(libfdt_objs) fdt_check_mem_start.o
- endif
-+KBUILD_CFLAGS_KERNEL := $(patsubst -f%-sections,,$(KBUILD_CFLAGS_KERNEL))
- # -fstack-protector-strong triggers protection checks in this code,
- # but it is being used too early to link to meaningful stack_chk logic.
---- a/arch/arm/kernel/vmlinux.lds.S
-+++ b/arch/arm/kernel/vmlinux.lds.S
-@@ -75,7 +75,7 @@ SECTIONS
-       . = ALIGN(4);
-       __ex_table : AT(ADDR(__ex_table) - LOAD_OFFSET) {
-               __start___ex_table = .;
--              ARM_MMU_KEEP(*(__ex_table))
-+              KEEP(*(__ex_table))
-               __stop___ex_table = .;
-       }
-@@ -100,24 +100,24 @@ SECTIONS
-       }
-       .init.arch.info : {
-               __arch_info_begin = .;
--              *(.arch.info.init)
-+              KEEP(*(.arch.info.init))
-               __arch_info_end = .;
-       }
-       .init.tagtable : {
-               __tagtable_begin = .;
--              *(.taglist.init)
-+              KEEP(*(.taglist.init))
-               __tagtable_end = .;
-       }
- #ifdef CONFIG_SMP_ON_UP
-       .init.smpalt : {
-               __smpalt_begin = .;
--              *(.alt.smp.init)
-+              KEEP(*(.alt.smp.init))
-               __smpalt_end = .;
-       }
- #endif
-       .init.pv_table : {
-               __pv_table_begin = .;
--              *(.pv_table)
-+              KEEP(*(.pv_table))
-               __pv_table_end = .;
-       }
---- a/arch/arm/include/asm/vmlinux.lds.h
-+++ b/arch/arm/include/asm/vmlinux.lds.h
-@@ -42,13 +42,13 @@
- #define PROC_INFO                                                     \
-               . = ALIGN(4);                                           \
-               __proc_info_begin = .;                                  \
--              *(.proc.info.init)                                      \
-+              KEEP(*(.proc.info.init))                                \
-               __proc_info_end = .;
- #define IDMAP_TEXT                                                    \
-               ALIGN_FUNCTION();                                       \
-               __idmap_text_start = .;                                 \
--              *(.idmap.text)                                          \
-+              KEEP(*(.idmap.text))                                    \
-               __idmap_text_end = .;                                   \
- #define ARM_DISCARD                                                   \
-@@ -109,12 +109,12 @@
-       . = ALIGN(8);                                                   \
-       .ARM.unwind_idx : {                                             \
-               __start_unwind_idx = .;                                 \
--              *(.ARM.exidx*)                                          \
-+              KEEP(*(.ARM.exidx*))                                    \
-               __stop_unwind_idx = .;                                  \
-       }                                                               \
-       .ARM.unwind_tab : {                                             \
-               __start_unwind_tab = .;                                 \
--              *(.ARM.extab*)                                          \
-+              KEEP(*(.ARM.extab*))                                    \
-               __stop_unwind_tab = .;                                  \
-       }
-@@ -126,7 +126,7 @@
-       __vectors_lma = .;                                              \
-       OVERLAY 0xffff0000 : NOCROSSREFS AT(__vectors_lma) {            \
-               .vectors {                                              \
--                      *(.vectors)                                     \
-+                      KEEP(*(.vectors))                               \
-               }                                                       \
-               .vectors.bhb.loop8 {                                    \
-                       *(.vectors.bhb.loop8)                           \
-@@ -144,7 +144,7 @@
-                                                                       \
-       __stubs_lma = .;                                                \
-       .stubs ADDR(.vectors) + 0x1000 : AT(__stubs_lma) {              \
--              *(.stubs)                                               \
-+              KEEP(*(.stubs))                                         \
-       }                                                               \
-       ARM_LMA(__stubs, .stubs);                                       \
-       . = __stubs_lma + SIZEOF(.stubs);                               \
diff --git a/target/linux/generic/hack-5.15/221-module_exports.patch b/target/linux/generic/hack-5.15/221-module_exports.patch
deleted file mode 100644 (file)
index 8db0f7d..0000000
+++ /dev/null
@@ -1,126 +0,0 @@
-From b14784e7883390c20ed3ff904892255404a5914b Mon Sep 17 00:00:00 2001
-From: Felix Fietkau <[email protected]>
-Date: Fri, 7 Jul 2017 17:05:53 +0200
-Subject: add an optional config option for stripping all unnecessary symbol exports from the kernel image
-
-lede-commit: bb5a40c64b7c4f4848509fa0a6625055fc9e66cc
-Signed-off-by: Felix Fietkau <[email protected]>
----
- include/asm-generic/vmlinux.lds.h | 18 +++++++++++++++---
- include/linux/export.h            |  9 ++++++++-
- scripts/Makefile.build            |  2 +-
- 3 files changed, 24 insertions(+), 5 deletions(-)
-
---- a/include/asm-generic/vmlinux.lds.h
-+++ b/include/asm-generic/vmlinux.lds.h
-@@ -81,6 +81,16 @@
- #define RO_EXCEPTION_TABLE
- #endif
-+#ifndef SYMTAB_KEEP
-+#define SYMTAB_KEEP KEEP(*(SORT(___ksymtab+*)))
-+#define SYMTAB_KEEP_GPL KEEP(*(SORT(___ksymtab_gpl+*)))
-+#endif
-+
-+#ifndef SYMTAB_DISCARD
-+#define SYMTAB_DISCARD
-+#define SYMTAB_DISCARD_GPL
-+#endif
-+
- /* Align . function alignment. */
- #define ALIGN_FUNCTION()  . = ALIGN(CONFIG_FUNCTION_ALIGNMENT)
-@@ -485,14 +495,14 @@
-       /* Kernel symbol table: Normal symbols */                       \
-       __ksymtab         : AT(ADDR(__ksymtab) - LOAD_OFFSET) {         \
-               __start___ksymtab = .;                                  \
--              KEEP(*(SORT(___ksymtab+*)))                             \
-+              SYMTAB_KEEP                                             \
-               __stop___ksymtab = .;                                   \
-       }                                                               \
-                                                                       \
-       /* Kernel symbol table: GPL-only symbols */                     \
-       __ksymtab_gpl     : AT(ADDR(__ksymtab_gpl) - LOAD_OFFSET) {     \
-               __start___ksymtab_gpl = .;                              \
--              KEEP(*(SORT(___ksymtab_gpl+*)))                         \
-+              SYMTAB_KEEP_GPL                                         \
-               __stop___ksymtab_gpl = .;                               \
-       }                                                               \
-                                                                       \
-@@ -512,7 +522,7 @@
-                                                                       \
-       /* Kernel symbol table: strings */                              \
-         __ksymtab_strings : AT(ADDR(__ksymtab_strings) - LOAD_OFFSET) {       \
--              *(__ksymtab_strings)                                    \
-+              *(__ksymtab_strings+*)                                  \
-       }                                                               \
-                                                                       \
-       /* __*init sections */                                          \
-@@ -1022,6 +1032,8 @@
- #define COMMON_DISCARDS                                                       \
-       SANITIZER_DISCARDS                                              \
-+      SYMTAB_DISCARD                                                  \
-+      SYMTAB_DISCARD_GPL                                              \
-       *(.discard)                                                     \
-       *(.discard.*)                                                   \
-       *(.modinfo)                                                     \
---- a/include/linux/export.h
-+++ b/include/linux/export.h
-@@ -84,6 +84,12 @@ struct kernel_symbol {
- #else
-+#ifdef MODULE
-+#define __EXPORT_SUFFIX(sym)
-+#else
-+#define __EXPORT_SUFFIX(sym) "+" #sym
-+#endif
-+
- /*
-  * For every exported symbol, do the following:
-  *
-@@ -101,7 +107,7 @@ struct kernel_symbol {
-       extern const char __kstrtab_##sym[];                                    \
-       extern const char __kstrtabns_##sym[];                                  \
-       __CRC_SYMBOL(sym, sec);                                                 \
--      asm("   .section \"__ksymtab_strings\",\"aMS\",%progbits,1      \n"     \
-+      asm("   .section \"__ksymtab_strings" __EXPORT_SUFFIX(sym) "\",\"aMS\",%progbits,1      \n"     \
-           "__kstrtab_" #sym ":                                        \n"     \
-           "   .asciz  \"" #sym "\"                                    \n"     \
-           "__kstrtabns_" #sym ":                                      \n"     \
---- a/include/asm-generic/export.h
-+++ b/include/asm-generic/export.h
-@@ -26,6 +26,12 @@
- #endif
- .endm
-+#ifdef MODULE
-+#define __EXPORT_SUFFIX(name)
-+#else
-+#define __EXPORT_SUFFIX(name) + #name
-+#endif
-+
- /*
-  * note on .section use: we specify progbits since usage of the "M" (SHF_MERGE)
-  * section flag requires it. Use '%progbits' instead of '@progbits' since the
-@@ -39,7 +45,7 @@
- __ksymtab_\name:
-       __put \val, __kstrtab_\name
-       .previous
--      .section __ksymtab_strings,"aMS",%progbits,1
-+      .section __ksymtab_strings __EXPORT_SUFFIX(name),"aMS",%progbits,1
- __kstrtab_\name:
-       .asciz "\name"
-       .previous
---- a/scripts/Makefile.build
-+++ b/scripts/Makefile.build
-@@ -397,7 +397,7 @@ targets += $(real-dtb-y) $(lib-y) $(alwa
- # Linker scripts preprocessor (.lds.S -> .lds)
- # ---------------------------------------------------------------------------
- quiet_cmd_cpp_lds_S = LDS     $@
--      cmd_cpp_lds_S = $(CPP) $(cpp_flags) -P -U$(ARCH) \
-+      cmd_cpp_lds_S = $(CPP) $(EXTRA_LDSFLAGS) $(cpp_flags) -P -U$(ARCH) \
-                            -D__ASSEMBLY__ -DLINKER_SCRIPT -o $@ $<
- $(obj)/%.lds: $(src)/%.lds.S FORCE
diff --git a/target/linux/generic/hack-5.15/230-openwrt_lzma_options.patch b/target/linux/generic/hack-5.15/230-openwrt_lzma_options.patch
deleted file mode 100644 (file)
index f9361b0..0000000
+++ /dev/null
@@ -1,34 +0,0 @@
-From b3d00b452467f621317953d9e4c6f9ae8dcfd271 Mon Sep 17 00:00:00 2001
-From: Imre Kaloz <[email protected]>
-Date: Fri, 7 Jul 2017 17:06:55 +0200
-Subject: use the openwrt lzma options for now
-
-lede-commit: 548de949f392049420a6a1feeef118b30ab8ea8c
-Signed-off-by: Imre Kaloz <[email protected]>
----
- lib/decompress.c              |  1 +
- scripts/Makefile.lib          |  2 +-
- usr/gen_initramfs_list.sh | 10 +++++-----
- 3 files changed, 7 insertions(+), 6 deletions(-)
-
---- a/lib/decompress.c
-+++ b/lib/decompress.c
-@@ -53,6 +53,7 @@ static const struct compress_format comp
-       { {0x1f, 0x9e}, "gzip", gunzip },
-       { {0x42, 0x5a}, "bzip2", bunzip2 },
-       { {0x5d, 0x00}, "lzma", unlzma },
-+      { {0x6d, 0x00}, "lzma-openwrt", unlzma },
-       { {0xfd, 0x37}, "xz", unxz },
-       { {0x89, 0x4c}, "lzo", unlzo },
-       { {0x02, 0x21}, "lz4", unlz4 },
---- a/scripts/Makefile.lib
-+++ b/scripts/Makefile.lib
-@@ -402,7 +402,7 @@ quiet_cmd_bzip2 = BZIP2   $@
- # ---------------------------------------------------------------------------
- quiet_cmd_lzma = LZMA    $@
--      cmd_lzma = { cat $(real-prereqs) | $(LZMA) -9; $(size_append); } > $@
-+      cmd_lzma = { cat $(real-prereqs) | $(LZMA) e -d20 -lc1 -lp2 -pb2 -eos -si -so; $(size_append); } > $@
- quiet_cmd_lzo = LZO     $@
-       cmd_lzo = { cat $(real-prereqs) | $(KLZOP) -9; $(size_append); } > $@
diff --git a/target/linux/generic/hack-5.15/250-netfilter_depends.patch b/target/linux/generic/hack-5.15/250-netfilter_depends.patch
deleted file mode 100644 (file)
index 1f8af6d..0000000
+++ /dev/null
@@ -1,27 +0,0 @@
-From: Felix Fietkau <[email protected]>
-Subject: hack: net: remove bogus netfilter dependencies
-
-lede-commit: 589d2a377dee27d206fc3725325309cf649e4df6
-Signed-off-by: Felix Fietkau <[email protected]>
----
- net/netfilter/Kconfig | 2 --
- 1 file changed, 2 deletions(-)
-
---- a/net/netfilter/Kconfig
-+++ b/net/netfilter/Kconfig
-@@ -242,7 +242,6 @@ config NF_CONNTRACK_FTP
- config NF_CONNTRACK_H323
-       tristate "H.323 protocol support"
--      depends on IPV6 || IPV6=n
-       depends on NETFILTER_ADVANCED
-       help
-         H.323 is a VoIP signalling protocol from ITU-T. As one of the most
-@@ -1114,7 +1113,6 @@ config NETFILTER_XT_TARGET_SECMARK
- config NETFILTER_XT_TARGET_TCPMSS
-       tristate '"TCPMSS" target support'
--      depends on IPV6 || IPV6=n
-       default m if NETFILTER_ADVANCED=n
-       help
-         This option adds a `TCPMSS' target, which allows you to alter the
diff --git a/target/linux/generic/hack-5.15/251-kconfig.patch b/target/linux/generic/hack-5.15/251-kconfig.patch
deleted file mode 100644 (file)
index 00c23db..0000000
+++ /dev/null
@@ -1,157 +0,0 @@
-From da3c50704f14132f4adf80d48e9a4cd5d46e54c9 Mon Sep 17 00:00:00 2001
-From: John Crispin <[email protected]>
-Date: Fri, 7 Jul 2017 17:09:21 +0200
-Subject: kconfig: owrt specifc dependencies
-
-Signed-off-by: John Crispin <[email protected]>
----
- crypto/Kconfig        | 10 +++++-----
- drivers/bcma/Kconfig  |  1 +
- drivers/ssb/Kconfig   |  3 ++-
- lib/Kconfig           |  8 ++++----
- net/netfilter/Kconfig |  2 +-
- net/wireless/Kconfig  | 17 ++++++++++-------
- sound/core/Kconfig    |  4 ++--
- 7 files changed, 25 insertions(+), 20 deletions(-)
-
---- a/crypto/Kconfig
-+++ b/crypto/Kconfig
-@@ -34,7 +34,7 @@ config CRYPTO_FIPS
-         this is.
- config CRYPTO_ALGAPI
--      tristate
-+      tristate "ALGAPI"
-       select CRYPTO_ALGAPI2
-       help
-         This option provides the API for cryptographic algorithms.
-@@ -43,7 +43,7 @@ config CRYPTO_ALGAPI2
-       tristate
- config CRYPTO_AEAD
--      tristate
-+      tristate "AEAD"
-       select CRYPTO_AEAD2
-       select CRYPTO_ALGAPI
-@@ -54,7 +54,7 @@ config CRYPTO_AEAD2
-       select CRYPTO_RNG2
- config CRYPTO_SKCIPHER
--      tristate
-+      tristate "SKCIPHER"
-       select CRYPTO_SKCIPHER2
-       select CRYPTO_ALGAPI
-@@ -64,7 +64,7 @@ config CRYPTO_SKCIPHER2
-       select CRYPTO_RNG2
- config CRYPTO_HASH
--      tristate
-+      tristate "HASH"
-       select CRYPTO_HASH2
-       select CRYPTO_ALGAPI
-@@ -73,7 +73,7 @@ config CRYPTO_HASH2
-       select CRYPTO_ALGAPI2
- config CRYPTO_RNG
--      tristate
-+      tristate "RNG"
-       select CRYPTO_RNG2
-       select CRYPTO_ALGAPI
---- a/drivers/bcma/Kconfig
-+++ b/drivers/bcma/Kconfig
-@@ -16,6 +16,7 @@ if BCMA
- # Support for Block-I/O. SELECT this from the driver that needs it.
- config BCMA_BLOCKIO
-       bool
-+      default y
- config BCMA_HOST_PCI_POSSIBLE
-       bool
---- a/drivers/ssb/Kconfig
-+++ b/drivers/ssb/Kconfig
-@@ -29,6 +29,7 @@ config SSB_SPROM
- config SSB_BLOCKIO
-       bool
-       depends on SSB
-+      default y
- config SSB_PCIHOST_POSSIBLE
-       bool
-@@ -49,7 +50,7 @@ config SSB_PCIHOST
- config SSB_B43_PCI_BRIDGE
-       bool
-       depends on SSB_PCIHOST
--      default n
-+      default y
- config SSB_PCMCIAHOST_POSSIBLE
-       bool
---- a/lib/Kconfig
-+++ b/lib/Kconfig
-@@ -443,16 +443,16 @@ config BCH_CONST_T
- # Textsearch support is select'ed if needed
- #
- config TEXTSEARCH
--      bool
-+      bool "Textsearch support"
- config TEXTSEARCH_KMP
--      tristate
-+      tristate "Textsearch KMP"
- config TEXTSEARCH_BM
--      tristate
-+      tristate "Textsearch BM"
- config TEXTSEARCH_FSM
--      tristate
-+      tristate "Textsearch FSM"
- config BTREE
-       bool
---- a/net/netfilter/Kconfig
-+++ b/net/netfilter/Kconfig
-@@ -11,7 +11,7 @@ config NETFILTER_INGRESS
-         infrastructure.
- config NETFILTER_NETLINK
--      tristate
-+      tristate "Netfilter NFNETLINK interface"
- config NETFILTER_FAMILY_BRIDGE
-       bool
---- a/sound/core/Kconfig
-+++ b/sound/core/Kconfig
-@@ -17,7 +17,7 @@ config SND_DMAENGINE_PCM
-       tristate
- config SND_HWDEP
--      tristate
-+      tristate "Sound hardware support"
- config SND_SEQ_DEVICE
-       tristate
-@@ -27,7 +27,7 @@ config SND_RAWMIDI
-       select SND_SEQ_DEVICE if SND_SEQUENCER != n
- config SND_COMPRESS_OFFLOAD
--      tristate
-+      tristate "Compression offloading support"
- config SND_JACK
-       bool
---- a/net/Kconfig
-+++ b/net/Kconfig
-@@ -430,7 +430,7 @@ config NET_DEVLINK
-       default n
- config PAGE_POOL
--      bool
-+      bool "Page pool support"
- config PAGE_POOL_STATS
-       default n
diff --git a/target/linux/generic/hack-5.15/253-ksmbd-config.patch b/target/linux/generic/hack-5.15/253-ksmbd-config.patch
deleted file mode 100644 (file)
index b8cb94f..0000000
+++ /dev/null
@@ -1,32 +0,0 @@
-From dcd966fa7ca63f38cf7147e1184d13d66e2ca340 Mon Sep 17 00:00:00 2001
-From: OpenWrt community <[email protected]>
-Date: Wed, 13 Jul 2022 13:33:30 +0200
-Subject: [PATCH] Kconfig: add tristate for OID and ASNI string
-
----
- init/Kconfig | 2 +-
- lib/Kconfig  | 2 +-
- 2 files changed, 2 insertions(+), 2 deletions(-)
-
---- a/init/Kconfig
-+++ b/init/Kconfig
-@@ -2388,7 +2388,7 @@ config PADATA
-       bool
- config ASN1
--      tristate
-+      tristate "ASN1"
-       help
-         Build a simple ASN.1 grammar compiler that produces a bytecode output
-         that can be interpreted by the ASN.1 stream decoder and used to
---- a/lib/Kconfig
-+++ b/lib/Kconfig
-@@ -614,7 +614,7 @@ config LIBFDT
-       bool
- config OID_REGISTRY
--      tristate
-+      tristate "OID"
-       help
-         Enable fast lookup object identifier registry.
diff --git a/target/linux/generic/hack-5.15/259-regmap_dynamic.patch b/target/linux/generic/hack-5.15/259-regmap_dynamic.patch
deleted file mode 100644 (file)
index ea06821..0000000
+++ /dev/null
@@ -1,144 +0,0 @@
-From 811d9e2268a62b830cfe93cd8bc929afcb8b198b Mon Sep 17 00:00:00 2001
-From: Felix Fietkau <[email protected]>
-Date: Sat, 15 Jul 2017 21:12:38 +0200
-Subject: kernel: move regmap bloat out of the kernel image if it is only being used in modules
-
-lede-commit: 96f39119815028073583e4fca3a9c5fe9141e998
-Signed-off-by: Felix Fietkau <[email protected]>
----
- drivers/base/regmap/Kconfig  | 15 ++++++++++-----
- drivers/base/regmap/Makefile | 12 ++++++++----
- drivers/base/regmap/regmap.c |  3 +++
- include/linux/regmap.h       |  2 +-
- 4 files changed, 22 insertions(+), 10 deletions(-)
-
---- a/drivers/base/regmap/Kconfig
-+++ b/drivers/base/regmap/Kconfig
-@@ -4,10 +4,9 @@
- # subsystems should select the appropriate symbols.
- config REGMAP
--      default y if (REGMAP_I2C || REGMAP_SPI || REGMAP_SPMI || REGMAP_W1 || REGMAP_AC97 || REGMAP_MMIO || REGMAP_IRQ || REGMAP_SOUNDWIRE || REGMAP_SOUNDWIRE_MBQ || REGMAP_SCCB || REGMAP_I3C || REGMAP_SPI_AVMM || REGMAP_MDIO)
-       select IRQ_DOMAIN if REGMAP_IRQ
-       select MDIO_BUS if REGMAP_MDIO
--      bool
-+      tristate
- config REGCACHE_COMPRESSED
-       select LZO_COMPRESS
-@@ -15,53 +14,67 @@ config REGCACHE_COMPRESSED
-       bool
- config REGMAP_AC97
-+      select REGMAP
-       tristate
- config REGMAP_I2C
-+      select REGMAP
-       tristate
-       depends on I2C
- config REGMAP_SLIMBUS
-+      select REGMAP
-       tristate
-       depends on SLIMBUS
- config REGMAP_SPI
-+      select REGMAP
-       tristate
-       depends on SPI
- config REGMAP_SPMI
-+      select REGMAP
-       tristate
-       depends on SPMI
- config REGMAP_W1
-+      select REGMAP
-       tristate
-       depends on W1
- config REGMAP_MDIO
-+      select REGMAP
-       tristate
- config REGMAP_MMIO
-+      select REGMAP
-       tristate
- config REGMAP_IRQ
-+      select REGMAP
-       bool
- config REGMAP_SOUNDWIRE
-+      select REGMAP
-       tristate
-       depends on SOUNDWIRE
- config REGMAP_SOUNDWIRE_MBQ
-+      select REGMAP
-       tristate
-       depends on SOUNDWIRE
- config REGMAP_SCCB
-+      select REGMAP
-       tristate
-       depends on I2C
- config REGMAP_I3C
-+      select REGMAP
-       tristate
-       depends on I3C
- config REGMAP_SPI_AVMM
-+      select REGMAP
-       tristate
-       depends on SPI
---- a/drivers/base/regmap/Makefile
-+++ b/drivers/base/regmap/Makefile
-@@ -2,10 +2,14 @@
- # For include/trace/define_trace.h to include trace.h
- CFLAGS_regmap.o := -I$(src)
--obj-$(CONFIG_REGMAP) += regmap.o regcache.o
--obj-$(CONFIG_REGMAP) += regcache-rbtree.o regcache-flat.o
--obj-$(CONFIG_REGCACHE_COMPRESSED) += regcache-lzo.o
--obj-$(CONFIG_DEBUG_FS) += regmap-debugfs.o
-+regmap-core-objs = regmap.o regcache.o regcache-rbtree.o regcache-flat.o
-+ifdef CONFIG_DEBUG_FS
-+regmap-core-objs += regmap-debugfs.o
-+endif
-+ifdef CONFIG_REGCACHE_COMPRESSED
-+regmap-core-objs += regcache-lzo.o
-+endif
-+obj-$(CONFIG_REGMAP) += regmap-core.o
- obj-$(CONFIG_REGMAP_AC97) += regmap-ac97.o
- obj-$(CONFIG_REGMAP_I2C) += regmap-i2c.o
- obj-$(CONFIG_REGMAP_SLIMBUS) += regmap-slimbus.o
---- a/drivers/base/regmap/regmap.c
-+++ b/drivers/base/regmap/regmap.c
-@@ -9,6 +9,7 @@
- #include <linux/device.h>
- #include <linux/slab.h>
- #include <linux/export.h>
-+#include <linux/module.h>
- #include <linux/mutex.h>
- #include <linux/err.h>
- #include <linux/property.h>
-@@ -3364,3 +3365,5 @@ static int __init regmap_initcall(void)
-       return 0;
- }
- postcore_initcall(regmap_initcall);
-+
-+MODULE_LICENSE("GPL");
---- a/include/linux/regmap.h
-+++ b/include/linux/regmap.h
-@@ -180,7 +180,7 @@ struct reg_sequence {
-       __ret ?: __tmp; \
- })
--#ifdef CONFIG_REGMAP
-+#if IS_REACHABLE(CONFIG_REGMAP)
- enum regmap_endian {
-       /* Unspecified -> 0 -> Backwards compatible default */
diff --git a/target/linux/generic/hack-5.15/260-crypto_test_dependencies.patch b/target/linux/generic/hack-5.15/260-crypto_test_dependencies.patch
deleted file mode 100644 (file)
index 64daa82..0000000
+++ /dev/null
@@ -1,52 +0,0 @@
-From fd1799b0bf5efa46dd3e6dfbbf3955564807e508 Mon Sep 17 00:00:00 2001
-From: Felix Fietkau <[email protected]>
-Date: Fri, 7 Jul 2017 17:12:51 +0200
-Subject: kernel: prevent cryptomgr from pulling in useless extra dependencies for tests that are not run
-
-Reduces kernel size after LZMA by about 5k on MIPS
-
-lede-commit: 044c316167e076479a344c59905e5b435b84a77f
-Signed-off-by: Felix Fietkau <[email protected]>
----
- crypto/Kconfig   | 13 ++++++-------
- crypto/algboss.c |  4 ++++
- 2 files changed, 10 insertions(+), 7 deletions(-)
-
---- a/crypto/Kconfig
-+++ b/crypto/Kconfig
-@@ -121,13 +121,13 @@ config CRYPTO_MANAGER
-         cbc(aes).
- config CRYPTO_MANAGER2
--      def_tristate CRYPTO_MANAGER || (CRYPTO_MANAGER!=n && CRYPTO_ALGAPI=y)
--      select CRYPTO_AEAD2
--      select CRYPTO_HASH2
--      select CRYPTO_SKCIPHER2
--      select CRYPTO_AKCIPHER2
--      select CRYPTO_KPP2
--      select CRYPTO_ACOMP2
-+      def_tristate CRYPTO_MANAGER || (CRYPTO_MANAGER!=n && CRYPTO_ALGAPI=y && !CRYPTO_MANAGER_DISABLE_TESTS)
-+      select CRYPTO_AEAD2 if !CRYPTO_MANAGER_DISABLE_TESTS
-+      select CRYPTO_HASH2 if !CRYPTO_MANAGER_DISABLE_TESTS
-+      select CRYPTO_SKCIPHER2 if !CRYPTO_MANAGER_DISABLE_TESTS
-+      select CRYPTO_AKCIPHER2 if !CRYPTO_MANAGER_DISABLE_TESTS
-+      select CRYPTO_KPP2 if !CRYPTO_MANAGER_DISABLE_TESTS
-+      select CRYPTO_ACOMP2 if !CRYPTO_MANAGER_DISABLE_TESTS
- config CRYPTO_USER
-       tristate "Userspace cryptographic algorithm configuration"
---- a/crypto/algboss.c
-+++ b/crypto/algboss.c
-@@ -211,8 +211,12 @@ static int cryptomgr_schedule_test(struc
-       type = alg->cra_flags;
-       /* Do not test internal algorithms. */
-+#ifdef CONFIG_CRYPTO_MANAGER_DISABLE_TESTS
-+      type |= CRYPTO_ALG_TESTED;
-+#else
-       if (type & CRYPTO_ALG_INTERNAL)
-               type |= CRYPTO_ALG_TESTED;
-+#endif
-       param->type = type;
diff --git a/target/linux/generic/hack-5.15/261-lib-arc4-unhide.patch b/target/linux/generic/hack-5.15/261-lib-arc4-unhide.patch
deleted file mode 100644 (file)
index ee923c7..0000000
+++ /dev/null
@@ -1,24 +0,0 @@
-From 241e5d3f7b0dd3c01f8c7fa83cbc9a3882286d53 Mon Sep 17 00:00:00 2001
-From: OpenWrt community <[email protected]>
-Date: Wed, 13 Jul 2022 13:35:18 +0200
-Subject: [PATCH] lib/crypto: add tristate string for ARC4
-
-This makes it possible to select CONFIG_CRYPTO_LIB_ARC4 directly. We 
-need this to be able to compile this into the kernel and make use of it 
-from backports.
-
----
- lib/crypto/Kconfig | 2 +-
- 1 file changed, 1 insertion(+), 1 deletion(-)
-
---- a/lib/crypto/Kconfig
-+++ b/lib/crypto/Kconfig
-@@ -6,7 +6,7 @@ config CRYPTO_LIB_AES
-       tristate
- config CRYPTO_LIB_ARC4
--      tristate
-+      tristate "ARC4 cipher library"
- config CRYPTO_ARCH_HAVE_LIB_BLAKE2S
-       bool
diff --git a/target/linux/generic/hack-5.15/280-rfkill-stubs.patch b/target/linux/generic/hack-5.15/280-rfkill-stubs.patch
deleted file mode 100644 (file)
index ff6638f..0000000
+++ /dev/null
@@ -1,84 +0,0 @@
-From 236c1acdfef5958010ac9814a9872e0a46fd78ee Mon Sep 17 00:00:00 2001
-From: John Crispin <[email protected]>
-Date: Fri, 7 Jul 2017 17:13:44 +0200
-Subject: rfkill: add fake rfkill support
-
-allow building of modules depending on RFKILL even if RFKILL is not enabled.
-
-Signed-off-by: John Crispin <[email protected]>
----
- include/linux/rfkill.h |  2 +-
- net/Makefile           |  2 +-
- net/rfkill/Kconfig     | 14 +++++++++-----
- net/rfkill/Makefile    |  2 +-
- 4 files changed, 12 insertions(+), 8 deletions(-)
-
---- a/include/linux/rfkill.h
-+++ b/include/linux/rfkill.h
-@@ -64,7 +64,7 @@ struct rfkill_ops {
-       int     (*set_block)(void *data, bool blocked);
- };
--#if defined(CONFIG_RFKILL) || defined(CONFIG_RFKILL_MODULE)
-+#if defined(CONFIG_RFKILL_FULL) || defined(CONFIG_RFKILL_FULL_MODULE)
- /**
-  * rfkill_alloc - Allocate rfkill structure
-  * @name: name of the struct -- the string is not copied internally
---- a/net/Makefile
-+++ b/net/Makefile
-@@ -51,7 +51,7 @@ obj-$(CONFIG_TIPC)           += tipc/
- obj-$(CONFIG_NETLABEL)                += netlabel/
- obj-$(CONFIG_IUCV)            += iucv/
- obj-$(CONFIG_SMC)             += smc/
--obj-$(CONFIG_RFKILL)          += rfkill/
-+obj-$(CONFIG_RFKILL_FULL)     += rfkill/
- obj-$(CONFIG_NET_9P)          += 9p/
- obj-$(CONFIG_CAIF)            += caif/
- obj-$(CONFIG_DCB)             += dcb/
---- a/net/rfkill/Kconfig
-+++ b/net/rfkill/Kconfig
-@@ -2,7 +2,11 @@
- #
- # RF switch subsystem configuration
- #
--menuconfig RFKILL
-+config RFKILL
-+      bool
-+      default y
-+
-+menuconfig RFKILL_FULL
-       tristate "RF switch subsystem support"
-       help
-         Say Y here if you want to have control over RF switches
-@@ -14,19 +18,19 @@ menuconfig RFKILL
- # LED trigger support
- config RFKILL_LEDS
-       bool
--      depends on RFKILL
-+      depends on RFKILL_FULL
-       depends on LEDS_TRIGGERS = y || RFKILL = LEDS_TRIGGERS
-       default y
- config RFKILL_INPUT
-       bool "RF switch input support" if EXPERT
--      depends on RFKILL
-+      depends on RFKILL_FULL
-       depends on INPUT = y || RFKILL = INPUT
-       default y if !EXPERT
- config RFKILL_GPIO
-       tristate "GPIO RFKILL driver"
--      depends on RFKILL
-+      depends on RFKILL_FULL
-       depends on GPIOLIB || COMPILE_TEST
-       default n
-       help
---- a/net/rfkill/Makefile
-+++ b/net/rfkill/Makefile
-@@ -5,5 +5,5 @@
- rfkill-y                      += core.o
- rfkill-$(CONFIG_RFKILL_INPUT) += input.o
--obj-$(CONFIG_RFKILL)          += rfkill.o
-+obj-$(CONFIG_RFKILL_FULL)     += rfkill.o
- obj-$(CONFIG_RFKILL_GPIO)     += rfkill-gpio.o
diff --git a/target/linux/generic/hack-5.15/300-MIPS-r4k_cache-use-more-efficient-cache-blast.patch b/target/linux/generic/hack-5.15/300-MIPS-r4k_cache-use-more-efficient-cache-blast.patch
deleted file mode 100644 (file)
index f21f200..0000000
+++ /dev/null
@@ -1,64 +0,0 @@
-From: Ben Menchaca <[email protected]>
-Date: Fri, 7 Jun 2013 18:35:22 -0500
-Subject: MIPS: r4k_cache: use more efficient cache blast
-
-Optimize the compiler output for larger cache blast cases that are
-common for DMA-based networking.
-
-Signed-off-by: Ben Menchaca <[email protected]>
-Signed-off-by: Felix Fietkau <[email protected]>
----
---- a/arch/mips/include/asm/r4kcache.h
-+++ b/arch/mips/include/asm/r4kcache.h
-@@ -286,14 +286,46 @@ static inline void prot##extra##blast_##
-                                                   unsigned long end)  \
- {                                                                     \
-       unsigned long lsize = cpu_##desc##_line_size();                 \
-+      unsigned long lsize_2 = lsize * 2;                              \
-+      unsigned long lsize_3 = lsize * 3;                              \
-+      unsigned long lsize_4 = lsize * 4;                              \
-+      unsigned long lsize_5 = lsize * 5;                              \
-+      unsigned long lsize_6 = lsize * 6;                              \
-+      unsigned long lsize_7 = lsize * 7;                              \
-+      unsigned long lsize_8 = lsize * 8;                              \
-       unsigned long addr = start & ~(lsize - 1);                      \
--      unsigned long aend = (end - 1) & ~(lsize - 1);                  \
-+      unsigned long aend = (end + lsize - 1) & ~(lsize - 1);          \
-+      int lines = (aend - addr) / lsize;                              \
-                                                                       \
--      while (1) {                                                     \
-+      while (lines >= 8) {                                            \
-+              prot##cache_op(hitop, addr);                            \
-+              prot##cache_op(hitop, addr + lsize);                    \
-+              prot##cache_op(hitop, addr + lsize_2);                  \
-+              prot##cache_op(hitop, addr + lsize_3);                  \
-+              prot##cache_op(hitop, addr + lsize_4);                  \
-+              prot##cache_op(hitop, addr + lsize_5);                  \
-+              prot##cache_op(hitop, addr + lsize_6);                  \
-+              prot##cache_op(hitop, addr + lsize_7);                  \
-+              addr += lsize_8;                                        \
-+              lines -= 8;                                             \
-+      }                                                               \
-+                                                                      \
-+      if (lines & 0x4) {                                              \
-+              prot##cache_op(hitop, addr);                            \
-+              prot##cache_op(hitop, addr + lsize);                    \
-+              prot##cache_op(hitop, addr + lsize_2);                  \
-+              prot##cache_op(hitop, addr + lsize_3);                  \
-+              addr += lsize_4;                                        \
-+      }                                                               \
-+                                                                      \
-+      if (lines & 0x2) {                                              \
-+              prot##cache_op(hitop, addr);                            \
-+              prot##cache_op(hitop, addr + lsize);                    \
-+              addr += lsize_2;                                        \
-+      }                                                               \
-+                                                                      \
-+      if (lines & 0x1) {                                              \
-               prot##cache_op(hitop, addr);                            \
--              if (addr == aend)                                       \
--                      break;                                          \
--              addr += lsize;                                          \
-       }                                                               \
- }
diff --git a/target/linux/generic/hack-5.15/402-mtd-blktrans-call-add-disks-after-mtd-device.patch b/target/linux/generic/hack-5.15/402-mtd-blktrans-call-add-disks-after-mtd-device.patch
deleted file mode 100644 (file)
index 8aac97c..0000000
+++ /dev/null
@@ -1,98 +0,0 @@
-From 0bccc3722bdd88e8ae995e77ef9f7b77ee4cbdee Mon Sep 17 00:00:00 2001
-From: Daniel Golle <[email protected]>
-Date: Wed, 7 Apr 2021 22:45:54 +0100
-Subject: [PATCH 2/2] mtd: blktrans: call add disks after mtd device
-Cc: Vignesh Raghavendra <[email protected]>,
-    Richard Weinberger <[email protected]>,
-    Miquel Raynal <[email protected]>,
-    David Woodhouse <[email protected]>
-
-Calling device_add_disk while holding mtd_table_mutex leads
-to deadlock in case part_bits!=0 as block partition parsers
-will try to open the newly created disks, trying to acquire
-mutex once again.
-Move device_add_disk to additional function called after
-add partitions of an MTD device have been added and locks
-have been released.
-
-Signed-off-by: Daniel Golle <[email protected]>
----
- drivers/mtd/mtd_blkdevs.c    | 33 ++++++++++++++++++++++++++-------
- drivers/mtd/mtdcore.c        |  3 +++
- include/linux/mtd/blktrans.h |  1 +
- 3 files changed, 30 insertions(+), 7 deletions(-)
-
---- a/drivers/mtd/mtd_blkdevs.c
-+++ b/drivers/mtd/mtd_blkdevs.c
-@@ -384,13 +384,6 @@ int add_mtd_blktrans_dev(struct mtd_blkt
-       if (new->readonly)
-               set_disk_ro(gd, 1);
--      device_add_disk(&new->mtd->dev, gd, NULL);
--
--      if (new->disk_attributes) {
--              ret = sysfs_create_group(&disk_to_dev(gd)->kobj,
--                                      new->disk_attributes);
--              WARN_ON(ret);
--      }
-       return 0;
- out_free_tag_set:
-@@ -402,6 +395,27 @@ out_list_del:
-       return ret;
- }
-+void register_mtd_blktrans_devs(void)
-+{
-+      struct mtd_blktrans_ops *tr;
-+      struct mtd_blktrans_dev *dev, *next;
-+      int ret;
-+
-+      list_for_each_entry(tr, &blktrans_majors, list) {
-+              list_for_each_entry_safe(dev, next, &tr->devs, list) {
-+                      if (disk_live(dev->disk))
-+                              continue;
-+
-+                      device_add_disk(&dev->mtd->dev, dev->disk, NULL);
-+                      if (dev->disk_attributes) {
-+                              ret = sysfs_create_group(&disk_to_dev(dev->disk)->kobj,
-+                                                      dev->disk_attributes);
-+                              WARN_ON(ret);
-+                      }
-+              }
-+      }
-+}
-+
- int del_mtd_blktrans_dev(struct mtd_blktrans_dev *old)
- {
-       unsigned long flags;
---- a/drivers/mtd/mtdcore.c
-+++ b/drivers/mtd/mtdcore.c
-@@ -32,6 +32,7 @@
- #include <linux/mtd/mtd.h>
- #include <linux/mtd/partitions.h>
-+#include <linux/mtd/blktrans.h>
- #include "mtdcore.h"
-@@ -1108,6 +1109,8 @@ int mtd_device_parse_register(struct mtd
-               register_reboot_notifier(&mtd->reboot_notifier);
-       }
-+      register_mtd_blktrans_devs();
-+
- out:
-       if (ret) {
-               nvmem_unregister(mtd->otp_user_nvmem);
---- a/include/linux/mtd/blktrans.h
-+++ b/include/linux/mtd/blktrans.h
-@@ -76,6 +76,7 @@ extern int deregister_mtd_blktrans(struc
- extern int add_mtd_blktrans_dev(struct mtd_blktrans_dev *dev);
- extern int del_mtd_blktrans_dev(struct mtd_blktrans_dev *dev);
- extern int mtd_blktrans_cease_background(struct mtd_blktrans_dev *dev);
-+extern void register_mtd_blktrans_devs(void);
- /**
-  * module_mtd_blktrans() - Helper macro for registering a mtd blktrans driver
diff --git a/target/linux/generic/hack-5.15/420-mtd-support-OpenWrt-s-MTD_ROOTFS_ROOT_DEV.patch b/target/linux/generic/hack-5.15/420-mtd-support-OpenWrt-s-MTD_ROOTFS_ROOT_DEV.patch
deleted file mode 100644 (file)
index ed46301..0000000
+++ /dev/null
@@ -1,24 +0,0 @@
-From: =?UTF-8?q?Rafa=C5=82=20Mi=C5=82ecki?= <[email protected]>
-Date: Mon, 7 Nov 2022 23:48:24 +0100
-Subject: [PATCH] mtd: support OpenWrt's MTD_ROOTFS_ROOT_DEV
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-This allows setting ROOT_DEV to MTD partition named "rootfs".
-
-Signed-off-by: Rafał Miłecki <[email protected]>
----
-
---- a/drivers/mtd/mtdcore.c
-+++ b/drivers/mtd/mtdcore.c
-@@ -784,7 +784,8 @@ int add_mtd_device(struct mtd_info *mtd)
-       mutex_unlock(&mtd_table_mutex);
--      if (of_find_property(mtd_get_of_node(mtd), "linux,rootfs", NULL)) {
-+      if (of_find_property(mtd_get_of_node(mtd), "linux,rootfs", NULL) ||
-+          (IS_ENABLED(CONFIG_MTD_ROOTFS_ROOT_DEV) && !strcmp(mtd->name, "rootfs") && ROOT_DEV == 0)) {
-               if (IS_BUILTIN(CONFIG_MTD)) {
-                       pr_info("mtd: setting mtd%d (%s) as root device\n", mtd->index, mtd->name);
-                       ROOT_DEV = MKDEV(MTD_BLOCK_MAJOR, mtd->index);
diff --git a/target/linux/generic/hack-5.15/421-drivers-mtd-parsers-add-nvmem-support-to-cmdlinepart.patch b/target/linux/generic/hack-5.15/421-drivers-mtd-parsers-add-nvmem-support-to-cmdlinepart.patch
deleted file mode 100644 (file)
index 965a331..0000000
+++ /dev/null
@@ -1,120 +0,0 @@
-From 6fa9e3678eb002246df1280322b6a024853950a5 Mon Sep 17 00:00:00 2001
-From: Ansuel Smith <[email protected]>
-Date: Mon, 11 Oct 2021 00:53:14 +0200
-Subject: [PATCH] drivers: mtd: parsers: add nvmem support to cmdlinepart
-
-Assuming cmdlinepart is only one level deep partition scheme and that
-static partition are also defined in DTS, we can assign an of_node for
-partition declared from bootargs. cmdlinepart have priority than
-fiexed-partition parser so in this specific case the parser doesn't
-assign an of_node. Fix this by searching a defined of_node using a
-similar fixed_partition parser and if a partition is found with the same
-label, check that it has the same offset and size and return the DT
-of_node to correctly use NVMEM cells.
-
-Signed-off-by: Ansuel Smith <[email protected]>
----
- drivers/mtd/parsers/cmdlinepart.c | 71 +++++++++++++++++++++++++++++++
- 1 file changed, 71 insertions(+)
-
---- a/drivers/mtd/parsers/cmdlinepart.c
-+++ b/drivers/mtd/parsers/cmdlinepart.c
-@@ -43,6 +43,7 @@
- #include <linux/mtd/partitions.h>
- #include <linux/module.h>
- #include <linux/err.h>
-+#include <linux/of.h>
- /* debug macro */
- #if 0
-@@ -323,6 +324,68 @@ static int mtdpart_setup_real(char *s)
-       return 0;
- }
-+static int search_fixed_partition(struct mtd_info *master,
-+                                struct mtd_partition *target_part,
-+                                struct mtd_partition *fixed_part)
-+{
-+      struct device_node *mtd_node;
-+      struct device_node *ofpart_node;
-+      struct device_node *pp;
-+      struct mtd_partition part;
-+      const char *partname;
-+
-+      mtd_node = mtd_get_of_node(master);
-+      if (!mtd_node)
-+              return -EINVAL;
-+
-+      ofpart_node = of_get_child_by_name(mtd_node, "partitions");
-+
-+      for_each_child_of_node(ofpart_node,  pp) {
-+              const __be32 *reg;
-+              int len;
-+              int a_cells, s_cells;
-+
-+              reg = of_get_property(pp, "reg", &len);
-+              if (!reg) {
-+                      pr_debug("%s: ofpart partition %pOF (%pOF) missing reg property.\n",
-+                               master->name, pp,
-+                               mtd_node);
-+                      continue;
-+              }
-+
-+              a_cells = of_n_addr_cells(pp);
-+              s_cells = of_n_size_cells(pp);
-+              if (len / 4 != a_cells + s_cells) {
-+                      pr_debug("%s: ofpart partition %pOF (%pOF) error parsing reg property.\n",
-+                               master->name, pp,
-+                               mtd_node);
-+                      continue;
-+              }
-+
-+              part.offset = of_read_number(reg, a_cells);
-+              part.size = of_read_number(reg + a_cells, s_cells);
-+              part.of_node = pp;
-+
-+              partname = of_get_property(pp, "label", &len);
-+              if (!partname)
-+                      partname = of_get_property(pp, "name", &len);
-+              part.name = partname;
-+
-+              if (!strncmp(target_part->name, part.name, len)) {
-+                      if (part.offset != target_part->offset)
-+                              return -EINVAL;
-+
-+                      if (part.size != target_part->size)
-+                              return -EINVAL;
-+
-+                      memcpy(fixed_part, &part, sizeof(struct mtd_partition));
-+                      return 0;
-+              }
-+      }
-+
-+      return -EINVAL;
-+}
-+
- /*
-  * Main function to be called from the MTD mapping driver/device to
-  * obtain the partitioning information. At this point the command line
-@@ -338,6 +401,7 @@ static int parse_cmdline_partitions(stru
-       int i, err;
-       struct cmdline_mtd_partition *part;
-       const char *mtd_id = master->name;
-+      struct mtd_partition fixed_part;
-       /* parse command line */
-       if (!cmdline_parsed) {
-@@ -382,6 +446,13 @@ static int parse_cmdline_partitions(stru
-                               sizeof(*part->parts) * (part->num_parts - i));
-                       i--;
-               }
-+
-+              err = search_fixed_partition(master, &part->parts[i], &fixed_part);
-+              if (!err) {
-+                      part->parts[i].of_node = fixed_part.of_node;
-+                      pr_info("Found partition defined in DT for %s. Assigning OF node to support nvmem.",
-+                              part->parts[i].name);
-+              }
-       }
-       *pparts = kmemdup(part->parts, sizeof(*part->parts) * part->num_parts,
diff --git a/target/linux/generic/hack-5.15/430-mtk-bmt-support.patch b/target/linux/generic/hack-5.15/430-mtk-bmt-support.patch
deleted file mode 100644 (file)
index 2a83f46..0000000
+++ /dev/null
@@ -1,33 +0,0 @@
-From ac84397efb3b3868c71c10ad7521161773228a17 Mon Sep 17 00:00:00 2001
-From: OpenWrt community <[email protected]>
-Date: Wed, 13 Jul 2022 13:41:44 +0200
-Subject: [PATCH] mtd/nand: add MediaTek NAND bad block managment table
-
----
- drivers/mtd/nand/Kconfig  | 4 ++++
- drivers/mtd/nand/Makefile | 1 +
- 2 files changed, 5 insertions(+)
-
---- a/drivers/mtd/nand/Kconfig
-+++ b/drivers/mtd/nand/Kconfig
-@@ -46,6 +46,10 @@ config MTD_NAND_ECC_SW_BCH
-         ECC codes. They are used with NAND devices requiring more than 1 bit
-         of error correction.
-+config MTD_NAND_MTK_BMT
-+      bool "Support MediaTek NAND Bad-block Management Table"
-+      default n
-+
- endmenu
- endmenu
---- a/drivers/mtd/nand/Makefile
-+++ b/drivers/mtd/nand/Makefile
-@@ -2,6 +2,7 @@
- nandcore-objs := core.o bbt.o
- obj-$(CONFIG_MTD_NAND_CORE) += nandcore.o
-+obj-$(CONFIG_MTD_NAND_MTK_BMT)        += mtk_bmt.o mtk_bmt_v2.o mtk_bmt_bbt.o mtk_bmt_nmbm.o
- obj-y += onenand/
- obj-y += raw/
diff --git a/target/linux/generic/hack-5.15/645-netfilter-connmark-introduce-set-dscpmark.patch b/target/linux/generic/hack-5.15/645-netfilter-connmark-introduce-set-dscpmark.patch
deleted file mode 100644 (file)
index c368c4a..0000000
+++ /dev/null
@@ -1,214 +0,0 @@
-From eda40b8c8c82e0f2789d6bc8bf63846dce2e8f32 Mon Sep 17 00:00:00 2001
-From: Kevin Darbyshire-Bryant <[email protected]>
-Date: Sat, 23 Mar 2019 09:29:49 +0000
-Subject: [PATCH] netfilter: connmark: introduce set-dscpmark
-
-set-dscpmark is a method of storing the DSCP of an ip packet into
-conntrack mark.  In combination with a suitable tc filter action
-(act_ctinfo) DSCP values are able to be stored in the mark on egress and
-restored on ingress across links that otherwise alter or bleach DSCP.
-
-This is useful for qdiscs such as CAKE which are able to shape according
-to policies based on DSCP.
-
-Ingress classification is traditionally a challenging task since
-iptables rules haven't yet run and tc filter/eBPF programs are pre-NAT
-lookups, hence are unable to see internal IPv4 addresses as used on the
-typical home masquerading gateway.
-
-x_tables CONNMARK set-dscpmark target solves the problem of storing the
-DSCP to the conntrack mark in a way suitable for the new act_ctinfo tc
-action to restore.
-
-The set-dscpmark option accepts 2 parameters, a 32bit 'dscpmask' and a
-32bit 'statemask'.  The dscp mask must be 6 contiguous bits and
-represents the area where the DSCP will be stored in the connmark.  The
-state mask is a minimum 1 bit length mask that must not overlap with the
-dscpmask.  It represents a flag which is set when the DSCP has been
-stored in the conntrack mark. This is useful to implement a 'one shot'
-iptables based classification where the 'complicated' iptables rules are
-only run once to classify the connection on initial (egress) packet and
-subsequent packets are all marked/restored with the same DSCP.  A state
-mask of zero disables the setting of a status bit/s.
-
-example syntax with a suitably modified iptables user space application:
-
-iptables -A QOS_MARK_eth0 -t mangle -j CONNMARK --set-dscpmark 0xfc000000/0x01000000
-
-Would store the DSCP in the top 6 bits of the 32bit mark field, and use
-the LSB of the top byte as the 'DSCP has been stored' marker.
-
-|----0xFC----conntrack mark----000000---|
-| Bits 31-26 | bit 25 | bit24 |~~~ Bit 0|
-| DSCP       | unused | flag  |unused   |
-|-----------------------0x01---000000---|
-      ^                   ^
-      |                   |
-      ---|             Conditional flag
-         |             set this when dscp
-|-ip diffserv-|        stored in mark
-| 6 bits      |
-|-------------|
-
-an identically configured tc action to restore looks like:
-
-tc filter show dev eth0 ingress
-filter parent ffff: protocol all pref 10 u32 chain 0
-filter parent ffff: protocol all pref 10 u32 chain 0 fh 800: ht divisor 1
-filter parent ffff: protocol all pref 10 u32 chain 0 fh 800::800 order 2048 key ht 800 bkt 0 flowid 1: not_in_hw
-  match 00000000/00000000 at 0
-       action order 1: ctinfo zone 0 pipe
-        index 2 ref 1 bind 1 dscp 0xfc000000/0x1000000
-
-       action order 2: mirred (Egress Redirect to device ifb4eth0) stolen
-       index 1 ref 1 bind 1
-
-|----0xFC----conntrack mark----000000---|
-| Bits 31-26 | bit 25 | bit24 |~~~ Bit 0|
-| DSCP       | unused | flag  |unused   |
-|-----------------------0x01---000000---|
-      |                   |
-      |                   |
-      ---|             Conditional flag
-         v             only restore if set
-|-ip diffserv-|
-| 6 bits      |
-|-------------|
-
-Signed-off-by: Kevin Darbyshire-Bryant <[email protected]>
----
- include/uapi/linux/netfilter/xt_connmark.h | 10 ++++
- net/netfilter/xt_connmark.c                | 55 ++++++++++++++++++----
- 2 files changed, 57 insertions(+), 8 deletions(-)
-
---- a/include/uapi/linux/netfilter/xt_connmark.h
-+++ b/include/uapi/linux/netfilter/xt_connmark.h
-@@ -20,6 +20,11 @@ enum {
- };
- enum {
-+      XT_CONNMARK_VALUE =     (1 << 0),
-+      XT_CONNMARK_DSCP =      (1 << 1)
-+};
-+
-+enum {
-       D_SHIFT_LEFT = 0,
-       D_SHIFT_RIGHT,
- };
-@@ -34,6 +39,11 @@ struct xt_connmark_tginfo2 {
-       __u8 shift_dir, shift_bits, mode;
- };
-+struct xt_connmark_tginfo3 {
-+      __u32 ctmark, ctmask, nfmask;
-+      __u8 shift_dir, shift_bits, mode, func;
-+};
-+
- struct xt_connmark_mtinfo1 {
-       __u32 mark, mask;
-       __u8 invert;
---- a/net/netfilter/xt_connmark.c
-+++ b/net/netfilter/xt_connmark.c
-@@ -24,13 +24,13 @@ MODULE_ALIAS("ipt_connmark");
- MODULE_ALIAS("ip6t_connmark");
- static unsigned int
--connmark_tg_shift(struct sk_buff *skb, const struct xt_connmark_tginfo2 *info)
-+connmark_tg_shift(struct sk_buff *skb, const struct xt_connmark_tginfo3 *info)
- {
-       enum ip_conntrack_info ctinfo;
-       u_int32_t new_targetmark;
-       struct nf_conn *ct;
-       u_int32_t newmark;
--      u_int32_t oldmark;
-+      u_int8_t dscp;
-       ct = nf_ct_get(skb, &ctinfo);
-       if (ct == NULL)
-@@ -38,13 +38,24 @@ connmark_tg_shift(struct sk_buff *skb, c
-       switch (info->mode) {
-       case XT_CONNMARK_SET:
--              oldmark = READ_ONCE(ct->mark);
--              newmark = (oldmark & ~info->ctmask) ^ info->ctmark;
--              if (info->shift_dir == D_SHIFT_RIGHT)
--                      newmark >>= info->shift_bits;
--              else
--                      newmark <<= info->shift_bits;
-+              newmark = READ_ONCE(ct->mark);
-+              if (info->func & XT_CONNMARK_VALUE) {
-+                      newmark = (newmark & ~info->ctmask) ^ info->ctmark;
-+                      if (info->shift_dir == D_SHIFT_RIGHT)
-+                              newmark >>= info->shift_bits;
-+                      else
-+                              newmark <<= info->shift_bits;
-+              } else if (info->func & XT_CONNMARK_DSCP) {
-+                      if (skb->protocol == htons(ETH_P_IP))
-+                              dscp = ipv4_get_dsfield(ip_hdr(skb)) >> 2;
-+                      else if (skb->protocol == htons(ETH_P_IPV6))
-+                              dscp = ipv6_get_dsfield(ipv6_hdr(skb)) >> 2;
-+                      else    /* protocol doesn't have diffserv */
-+                              break;
-+                      newmark = (newmark & ~info->ctmark) |
-+                                (info->ctmask | (dscp << info->shift_bits));
-+              }
-               if (READ_ONCE(ct->mark) != newmark) {
-                       WRITE_ONCE(ct->mark, newmark);
-                       nf_conntrack_event_cache(IPCT_MARK, ct);
-@@ -83,20 +94,36 @@ static unsigned int
- connmark_tg(struct sk_buff *skb, const struct xt_action_param *par)
- {
-       const struct xt_connmark_tginfo1 *info = par->targinfo;
--      const struct xt_connmark_tginfo2 info2 = {
-+      const struct xt_connmark_tginfo3 info3 = {
-               .ctmark = info->ctmark,
-               .ctmask = info->ctmask,
-               .nfmask = info->nfmask,
-               .mode   = info->mode,
-+              .func   = XT_CONNMARK_VALUE
-       };
--      return connmark_tg_shift(skb, &info2);
-+      return connmark_tg_shift(skb, &info3);
- }
- static unsigned int
- connmark_tg_v2(struct sk_buff *skb, const struct xt_action_param *par)
- {
-       const struct xt_connmark_tginfo2 *info = par->targinfo;
-+      const struct xt_connmark_tginfo3 info3 = {
-+              .ctmark = info->ctmark,
-+              .ctmask = info->ctmask,
-+              .nfmask = info->nfmask,
-+              .mode   = info->mode,
-+              .func   = XT_CONNMARK_VALUE
-+      };
-+
-+      return connmark_tg_shift(skb, &info3);
-+}
-+
-+static unsigned int
-+connmark_tg_v3(struct sk_buff *skb, const struct xt_action_param *par)
-+{
-+      const struct xt_connmark_tginfo3 *info = par->targinfo;
-       return connmark_tg_shift(skb, info);
- }
-@@ -167,6 +194,16 @@ static struct xt_target connmark_tg_reg[
-               .targetsize     = sizeof(struct xt_connmark_tginfo2),
-               .destroy        = connmark_tg_destroy,
-               .me             = THIS_MODULE,
-+      },
-+      {
-+              .name           = "CONNMARK",
-+              .revision       = 3,
-+              .family         = NFPROTO_UNSPEC,
-+              .checkentry     = connmark_tg_check,
-+              .target         = connmark_tg_v3,
-+              .targetsize     = sizeof(struct xt_connmark_tginfo3),
-+              .destroy        = connmark_tg_destroy,
-+              .me             = THIS_MODULE,
-       }
- };
diff --git a/target/linux/generic/hack-5.15/650-netfilter-add-xt_FLOWOFFLOAD-target.patch b/target/linux/generic/hack-5.15/650-netfilter-add-xt_FLOWOFFLOAD-target.patch
deleted file mode 100644 (file)
index d22b9f9..0000000
+++ /dev/null
@@ -1,865 +0,0 @@
-From: Felix Fietkau <[email protected]>
-Date: Tue, 20 Feb 2018 15:56:02 +0100
-Subject: [PATCH] netfilter: add xt_FLOWOFFLOAD target
-
-Signed-off-by: Felix Fietkau <[email protected]>
----
- create mode 100644 net/netfilter/xt_OFFLOAD.c
-
---- a/net/ipv4/netfilter/Kconfig
-+++ b/net/ipv4/netfilter/Kconfig
-@@ -56,8 +56,6 @@ config NF_TABLES_ARP
-       help
-         This option enables the ARP support for nf_tables.
--endif # NF_TABLES
--
- config NF_FLOW_TABLE_IPV4
-       tristate "Netfilter flow table IPv4 module"
-       depends on NF_FLOW_TABLE
-@@ -66,6 +64,8 @@ config NF_FLOW_TABLE_IPV4
-         To compile it as a module, choose M here.
-+endif # NF_TABLES
-+
- config NF_DUP_IPV4
-       tristate "Netfilter IPv4 packet duplication to alternate destination"
-       depends on !NF_CONNTRACK || NF_CONNTRACK
---- a/net/ipv6/netfilter/Kconfig
-+++ b/net/ipv6/netfilter/Kconfig
-@@ -45,7 +45,6 @@ config NFT_FIB_IPV6
-         multicast or blackhole.
- endif # NF_TABLES_IPV6
--endif # NF_TABLES
- config NF_FLOW_TABLE_IPV6
-       tristate "Netfilter flow table IPv6 module"
-@@ -55,6 +54,8 @@ config NF_FLOW_TABLE_IPV6
-         To compile it as a module, choose M here.
-+endif # NF_TABLES
-+
- config NF_DUP_IPV6
-       tristate "Netfilter IPv6 packet duplication to alternate destination"
-       depends on !NF_CONNTRACK || NF_CONNTRACK
---- a/net/netfilter/Kconfig
-+++ b/net/netfilter/Kconfig
-@@ -707,8 +707,6 @@ config NFT_REJECT_NETDEV
- endif # NF_TABLES_NETDEV
--endif # NF_TABLES
--
- config NF_FLOW_TABLE_INET
-       tristate "Netfilter flow table mixed IPv4/IPv6 module"
-       depends on NF_FLOW_TABLE
-@@ -717,11 +715,12 @@ config NF_FLOW_TABLE_INET
-         To compile it as a module, choose M here.
-+endif # NF_TABLES
-+
- config NF_FLOW_TABLE
-       tristate "Netfilter flow table module"
-       depends on NETFILTER_INGRESS
-       depends on NF_CONNTRACK
--      depends on NF_TABLES
-       help
-         This option adds the flow table core infrastructure.
-@@ -1019,6 +1018,15 @@ config NETFILTER_XT_TARGET_NOTRACK
-       depends on NETFILTER_ADVANCED
-       select NETFILTER_XT_TARGET_CT
-+config NETFILTER_XT_TARGET_FLOWOFFLOAD
-+      tristate '"FLOWOFFLOAD" target support'
-+      depends on NF_FLOW_TABLE
-+      depends on NETFILTER_INGRESS
-+      help
-+        This option adds a `FLOWOFFLOAD' target, which uses the nf_flow_offload
-+        module to speed up processing of packets by bypassing the usual
-+        netfilter chains
-+
- config NETFILTER_XT_TARGET_RATEEST
-       tristate '"RATEEST" target support'
-       depends on NETFILTER_ADVANCED
---- a/net/netfilter/Makefile
-+++ b/net/netfilter/Makefile
-@@ -144,6 +144,7 @@ obj-$(CONFIG_NETFILTER_XT_TARGET_CLASSIF
- obj-$(CONFIG_NETFILTER_XT_TARGET_CONNSECMARK) += xt_CONNSECMARK.o
- obj-$(CONFIG_NETFILTER_XT_TARGET_CT) += xt_CT.o
- obj-$(CONFIG_NETFILTER_XT_TARGET_DSCP) += xt_DSCP.o
-+obj-$(CONFIG_NETFILTER_XT_TARGET_FLOWOFFLOAD) += xt_FLOWOFFLOAD.o
- obj-$(CONFIG_NETFILTER_XT_TARGET_HL) += xt_HL.o
- obj-$(CONFIG_NETFILTER_XT_TARGET_HMARK) += xt_HMARK.o
- obj-$(CONFIG_NETFILTER_XT_TARGET_LED) += xt_LED.o
---- /dev/null
-+++ b/net/netfilter/xt_FLOWOFFLOAD.c
-@@ -0,0 +1,702 @@
-+/*
-+ * Copyright (C) 2018-2021 Felix Fietkau <[email protected]>
-+ *
-+ * This program is free software; you can redistribute it and/or modify
-+ * it under the terms of the GNU General Public License version 2 as
-+ * published by the Free Software Foundation.
-+ */
-+#include <linux/module.h>
-+#include <linux/init.h>
-+#include <linux/netfilter.h>
-+#include <linux/netfilter/xt_FLOWOFFLOAD.h>
-+#include <linux/if_vlan.h>
-+#include <net/ip.h>
-+#include <net/netfilter/nf_conntrack.h>
-+#include <net/netfilter/nf_conntrack_extend.h>
-+#include <net/netfilter/nf_conntrack_helper.h>
-+#include <net/netfilter/nf_flow_table.h>
-+
-+struct xt_flowoffload_hook {
-+      struct hlist_node list;
-+      struct nf_hook_ops ops;
-+      struct net *net;
-+      bool registered;
-+      bool used;
-+};
-+
-+struct xt_flowoffload_table {
-+      struct nf_flowtable ft;
-+      struct hlist_head hooks;
-+      struct delayed_work work;
-+};
-+
-+struct nf_forward_info {
-+      const struct net_device *indev;
-+      const struct net_device *outdev;
-+      const struct net_device *hw_outdev;
-+      struct id {
-+              __u16   id;
-+              __be16  proto;
-+      } encap[NF_FLOW_TABLE_ENCAP_MAX];
-+      u8 num_encaps;
-+      u8 ingress_vlans;
-+      u8 h_source[ETH_ALEN];
-+      u8 h_dest[ETH_ALEN];
-+      enum flow_offload_xmit_type xmit_type;
-+};
-+
-+static DEFINE_SPINLOCK(hooks_lock);
-+
-+struct xt_flowoffload_table flowtable[2];
-+
-+static unsigned int
-+xt_flowoffload_net_hook(void *priv, struct sk_buff *skb,
-+                      const struct nf_hook_state *state)
-+{
-+      struct vlan_ethhdr *veth;
-+      __be16 proto;
-+
-+      switch (skb->protocol) {
-+      case htons(ETH_P_8021Q):
-+              veth = (struct vlan_ethhdr *)skb_mac_header(skb);
-+              proto = veth->h_vlan_encapsulated_proto;
-+              break;
-+      case htons(ETH_P_PPP_SES):
-+              if (!nf_flow_pppoe_proto(skb, &proto))
-+                      return NF_ACCEPT;
-+              break;
-+      default:
-+              proto = skb->protocol;
-+              break;
-+      }
-+
-+      switch (proto) {
-+      case htons(ETH_P_IP):
-+              return nf_flow_offload_ip_hook(priv, skb, state);
-+      case htons(ETH_P_IPV6):
-+              return nf_flow_offload_ipv6_hook(priv, skb, state);
-+      }
-+
-+      return NF_ACCEPT;
-+}
-+
-+static int
-+xt_flowoffload_create_hook(struct xt_flowoffload_table *table,
-+                         struct net_device *dev)
-+{
-+      struct xt_flowoffload_hook *hook;
-+      struct nf_hook_ops *ops;
-+
-+      hook = kzalloc(sizeof(*hook), GFP_ATOMIC);
-+      if (!hook)
-+              return -ENOMEM;
-+
-+      ops = &hook->ops;
-+      ops->pf = NFPROTO_NETDEV;
-+      ops->hooknum = NF_NETDEV_INGRESS;
-+      ops->priority = 10;
-+      ops->priv = &table->ft;
-+      ops->hook = xt_flowoffload_net_hook;
-+      ops->dev = dev;
-+
-+      hlist_add_head(&hook->list, &table->hooks);
-+      mod_delayed_work(system_power_efficient_wq, &table->work, 0);
-+
-+      return 0;
-+}
-+
-+static struct xt_flowoffload_hook *
-+flow_offload_lookup_hook(struct xt_flowoffload_table *table,
-+                       struct net_device *dev)
-+{
-+      struct xt_flowoffload_hook *hook;
-+
-+      hlist_for_each_entry(hook, &table->hooks, list) {
-+              if (hook->ops.dev == dev)
-+                      return hook;
-+      }
-+
-+      return NULL;
-+}
-+
-+static void
-+xt_flowoffload_check_device(struct xt_flowoffload_table *table,
-+                          struct net_device *dev)
-+{
-+      struct xt_flowoffload_hook *hook;
-+
-+      if (!dev)
-+              return;
-+
-+      spin_lock_bh(&hooks_lock);
-+      hook = flow_offload_lookup_hook(table, dev);
-+      if (hook)
-+              hook->used = true;
-+      else
-+              xt_flowoffload_create_hook(table, dev);
-+      spin_unlock_bh(&hooks_lock);
-+}
-+
-+static void
-+xt_flowoffload_register_hooks(struct xt_flowoffload_table *table)
-+{
-+      struct xt_flowoffload_hook *hook;
-+
-+restart:
-+      hlist_for_each_entry(hook, &table->hooks, list) {
-+              if (hook->registered)
-+                      continue;
-+
-+              hook->registered = true;
-+              hook->net = dev_net(hook->ops.dev);
-+              spin_unlock_bh(&hooks_lock);
-+              nf_register_net_hook(hook->net, &hook->ops);
-+              if (table->ft.flags & NF_FLOWTABLE_HW_OFFLOAD)
-+                      table->ft.type->setup(&table->ft, hook->ops.dev,
-+                                            FLOW_BLOCK_BIND);
-+              spin_lock_bh(&hooks_lock);
-+              goto restart;
-+      }
-+
-+}
-+
-+static bool
-+xt_flowoffload_cleanup_hooks(struct xt_flowoffload_table *table)
-+{
-+      struct xt_flowoffload_hook *hook;
-+      bool active = false;
-+
-+restart:
-+      spin_lock_bh(&hooks_lock);
-+      hlist_for_each_entry(hook, &table->hooks, list) {
-+              if (hook->used || !hook->registered) {
-+                      active = true;
-+                      continue;
-+              }
-+
-+              hlist_del(&hook->list);
-+              spin_unlock_bh(&hooks_lock);
-+              if (table->ft.flags & NF_FLOWTABLE_HW_OFFLOAD)
-+                      table->ft.type->setup(&table->ft, hook->ops.dev,
-+                                            FLOW_BLOCK_UNBIND);
-+              nf_unregister_net_hook(hook->net, &hook->ops);
-+              kfree(hook);
-+              goto restart;
-+      }
-+      spin_unlock_bh(&hooks_lock);
-+
-+      return active;
-+}
-+
-+static void
-+xt_flowoffload_check_hook(struct nf_flowtable *flowtable,
-+                        struct flow_offload *flow, void *data)
-+{
-+      struct xt_flowoffload_table *table;
-+      struct flow_offload_tuple *tuple0 = &flow->tuplehash[0].tuple;
-+      struct flow_offload_tuple *tuple1 = &flow->tuplehash[1].tuple;
-+      struct xt_flowoffload_hook *hook;
-+
-+      table = container_of(flowtable, struct xt_flowoffload_table, ft);
-+
-+      spin_lock_bh(&hooks_lock);
-+      hlist_for_each_entry(hook, &table->hooks, list) {
-+              if (hook->ops.dev->ifindex != tuple0->iifidx &&
-+                  hook->ops.dev->ifindex != tuple1->iifidx)
-+                      continue;
-+
-+              hook->used = true;
-+      }
-+      spin_unlock_bh(&hooks_lock);
-+}
-+
-+static void
-+xt_flowoffload_hook_work(struct work_struct *work)
-+{
-+      struct xt_flowoffload_table *table;
-+      struct xt_flowoffload_hook *hook;
-+      int err;
-+
-+      table = container_of(work, struct xt_flowoffload_table, work.work);
-+
-+      spin_lock_bh(&hooks_lock);
-+      xt_flowoffload_register_hooks(table);
-+      hlist_for_each_entry(hook, &table->hooks, list)
-+              hook->used = false;
-+      spin_unlock_bh(&hooks_lock);
-+
-+      err = nf_flow_table_iterate(&table->ft, xt_flowoffload_check_hook,
-+                                  NULL);
-+      if (err && err != -EAGAIN)
-+              goto out;
-+
-+      if (!xt_flowoffload_cleanup_hooks(table))
-+              return;
-+
-+out:
-+      queue_delayed_work(system_power_efficient_wq, &table->work, HZ);
-+}
-+
-+static bool
-+xt_flowoffload_skip(struct sk_buff *skb, int family)
-+{
-+      if (skb_sec_path(skb))
-+              return true;
-+
-+      if (family == NFPROTO_IPV4) {
-+              const struct ip_options *opt = &(IPCB(skb)->opt);
-+
-+              if (unlikely(opt->optlen))
-+                      return true;
-+      }
-+
-+      return false;
-+}
-+
-+static enum flow_offload_xmit_type nf_xmit_type(struct dst_entry *dst)
-+{
-+      if (dst_xfrm(dst))
-+              return FLOW_OFFLOAD_XMIT_XFRM;
-+
-+      return FLOW_OFFLOAD_XMIT_NEIGH;
-+}
-+
-+static void nf_default_forward_path(struct nf_flow_route *route,
-+                                  struct dst_entry *dst_cache,
-+                                  enum ip_conntrack_dir dir,
-+                                  struct net_device **dev)
-+{
-+      dev[!dir] = dst_cache->dev;
-+      route->tuple[!dir].in.ifindex   = dst_cache->dev->ifindex;
-+      route->tuple[dir].dst           = dst_cache;
-+      route->tuple[dir].xmit_type     = nf_xmit_type(dst_cache);
-+}
-+
-+static bool nf_is_valid_ether_device(const struct net_device *dev)
-+{
-+      if (!dev || (dev->flags & IFF_LOOPBACK) || dev->type != ARPHRD_ETHER ||
-+          dev->addr_len != ETH_ALEN || !is_valid_ether_addr(dev->dev_addr))
-+              return false;
-+
-+      return true;
-+}
-+
-+static void nf_dev_path_info(const struct net_device_path_stack *stack,
-+                           struct nf_forward_info *info,
-+                           unsigned char *ha)
-+{
-+      const struct net_device_path *path;
-+      int i;
-+
-+      memcpy(info->h_dest, ha, ETH_ALEN);
-+
-+      for (i = 0; i < stack->num_paths; i++) {
-+              path = &stack->path[i];
-+              switch (path->type) {
-+              case DEV_PATH_ETHERNET:
-+              case DEV_PATH_DSA:
-+              case DEV_PATH_VLAN:
-+              case DEV_PATH_PPPOE:
-+                      info->indev = path->dev;
-+                      if (is_zero_ether_addr(info->h_source))
-+                              memcpy(info->h_source, path->dev->dev_addr, ETH_ALEN);
-+
-+                      if (path->type == DEV_PATH_ETHERNET)
-+                              break;
-+                      if (path->type == DEV_PATH_DSA) {
-+                              i = stack->num_paths;
-+                              break;
-+                      }
-+
-+                      /* DEV_PATH_VLAN and DEV_PATH_PPPOE */
-+                      if (info->num_encaps >= NF_FLOW_TABLE_ENCAP_MAX) {
-+                              info->indev = NULL;
-+                              break;
-+                      }
-+                      if (!info->outdev)
-+                              info->outdev = path->dev;
-+                      info->encap[info->num_encaps].id = path->encap.id;
-+                      info->encap[info->num_encaps].proto = path->encap.proto;
-+                      info->num_encaps++;
-+                      if (path->type == DEV_PATH_PPPOE)
-+                              memcpy(info->h_dest, path->encap.h_dest, ETH_ALEN);
-+                      break;
-+              case DEV_PATH_BRIDGE:
-+                      if (is_zero_ether_addr(info->h_source))
-+                              memcpy(info->h_source, path->dev->dev_addr, ETH_ALEN);
-+
-+                      switch (path->bridge.vlan_mode) {
-+                      case DEV_PATH_BR_VLAN_UNTAG_HW:
-+                              info->ingress_vlans |= BIT(info->num_encaps - 1);
-+                              break;
-+                      case DEV_PATH_BR_VLAN_TAG:
-+                              info->encap[info->num_encaps].id = path->bridge.vlan_id;
-+                              info->encap[info->num_encaps].proto = path->bridge.vlan_proto;
-+                              info->num_encaps++;
-+                              break;
-+                      case DEV_PATH_BR_VLAN_UNTAG:
-+                              info->num_encaps--;
-+                              break;
-+                      case DEV_PATH_BR_VLAN_KEEP:
-+                              break;
-+                      }
-+                      break;
-+              default:
-+                      info->indev = NULL;
-+                      break;
-+              }
-+      }
-+      if (!info->outdev)
-+              info->outdev = info->indev;
-+
-+      info->hw_outdev = info->indev;
-+
-+      if (nf_is_valid_ether_device(info->indev))
-+              info->xmit_type = FLOW_OFFLOAD_XMIT_DIRECT;
-+}
-+
-+static int nf_dev_fill_forward_path(const struct nf_flow_route *route,
-+                                   const struct dst_entry *dst_cache,
-+                                   const struct nf_conn *ct,
-+                                   enum ip_conntrack_dir dir, u8 *ha,
-+                                   struct net_device_path_stack *stack)
-+{
-+      const void *daddr = &ct->tuplehash[!dir].tuple.src.u3;
-+      struct net_device *dev = dst_cache->dev;
-+      struct neighbour *n;
-+      u8 nud_state;
-+
-+      if (!nf_is_valid_ether_device(dev))
-+              goto out;
-+
-+      n = dst_neigh_lookup(dst_cache, daddr);
-+      if (!n)
-+              return -1;
-+
-+      read_lock_bh(&n->lock);
-+      nud_state = n->nud_state;
-+      ether_addr_copy(ha, n->ha);
-+      read_unlock_bh(&n->lock);
-+      neigh_release(n);
-+
-+      if (!(nud_state & NUD_VALID))
-+              return -1;
-+
-+out:
-+      return dev_fill_forward_path(dev, ha, stack);
-+}
-+
-+static void nf_dev_forward_path(struct nf_flow_route *route,
-+                              const struct nf_conn *ct,
-+                              enum ip_conntrack_dir dir,
-+                              struct net_device **devs)
-+{
-+      const struct dst_entry *dst = route->tuple[dir].dst;
-+      struct net_device_path_stack stack;
-+      struct nf_forward_info info = {};
-+      unsigned char ha[ETH_ALEN];
-+      int i;
-+
-+      if (nf_dev_fill_forward_path(route, dst, ct, dir, ha, &stack) >= 0)
-+              nf_dev_path_info(&stack, &info, ha);
-+
-+      devs[!dir] = (struct net_device *)info.indev;
-+      if (!info.indev)
-+              return;
-+
-+      route->tuple[!dir].in.ifindex = info.indev->ifindex;
-+      for (i = 0; i < info.num_encaps; i++) {
-+              route->tuple[!dir].in.encap[i].id = info.encap[i].id;
-+              route->tuple[!dir].in.encap[i].proto = info.encap[i].proto;
-+      }
-+      route->tuple[!dir].in.num_encaps = info.num_encaps;
-+      route->tuple[!dir].in.ingress_vlans = info.ingress_vlans;
-+
-+      if (info.xmit_type == FLOW_OFFLOAD_XMIT_DIRECT) {
-+              memcpy(route->tuple[dir].out.h_source, info.h_source, ETH_ALEN);
-+              memcpy(route->tuple[dir].out.h_dest, info.h_dest, ETH_ALEN);
-+              route->tuple[dir].out.ifindex = info.outdev->ifindex;
-+              route->tuple[dir].out.hw_ifindex = info.hw_outdev->ifindex;
-+              route->tuple[dir].xmit_type = info.xmit_type;
-+      }
-+}
-+
-+static int
-+xt_flowoffload_route(struct sk_buff *skb, const struct nf_conn *ct,
-+                   const struct xt_action_param *par,
-+                   struct nf_flow_route *route, enum ip_conntrack_dir dir,
-+                   struct net_device **devs)
-+{
-+      struct dst_entry *this_dst = skb_dst(skb);
-+      struct dst_entry *other_dst = NULL;
-+      struct flowi fl;
-+
-+      memset(&fl, 0, sizeof(fl));
-+      switch (xt_family(par)) {
-+      case NFPROTO_IPV4:
-+              fl.u.ip4.daddr = ct->tuplehash[dir].tuple.src.u3.ip;
-+              fl.u.ip4.flowi4_oif = xt_in(par)->ifindex;
-+              break;
-+      case NFPROTO_IPV6:
-+              fl.u.ip6.saddr = ct->tuplehash[!dir].tuple.dst.u3.in6;
-+              fl.u.ip6.daddr = ct->tuplehash[dir].tuple.src.u3.in6;
-+              fl.u.ip6.flowi6_oif = xt_in(par)->ifindex;
-+              break;
-+      }
-+
-+      if (!dst_hold_safe(this_dst))
-+              return -ENOENT;
-+
-+      nf_route(xt_net(par), &other_dst, &fl, false, xt_family(par));
-+      if (!other_dst) {
-+              dst_release(this_dst);
-+              return -ENOENT;
-+      }
-+
-+      nf_default_forward_path(route, this_dst, dir, devs);
-+      nf_default_forward_path(route, other_dst, !dir, devs);
-+
-+      if (route->tuple[dir].xmit_type == FLOW_OFFLOAD_XMIT_NEIGH &&
-+          route->tuple[!dir].xmit_type == FLOW_OFFLOAD_XMIT_NEIGH) {
-+              nf_dev_forward_path(route, ct, dir, devs);
-+              nf_dev_forward_path(route, ct, !dir, devs);
-+      }
-+
-+      return 0;
-+}
-+
-+static unsigned int
-+flowoffload_tg(struct sk_buff *skb, const struct xt_action_param *par)
-+{
-+      struct xt_flowoffload_table *table;
-+      const struct xt_flowoffload_target_info *info = par->targinfo;
-+      struct tcphdr _tcph, *tcph = NULL;
-+      enum ip_conntrack_info ctinfo;
-+      enum ip_conntrack_dir dir;
-+      struct nf_flow_route route = {};
-+      struct flow_offload *flow = NULL;
-+      struct net_device *devs[2] = {};
-+      struct nf_conn *ct;
-+      struct net *net;
-+
-+      if (xt_flowoffload_skip(skb, xt_family(par)))
-+              return XT_CONTINUE;
-+
-+      ct = nf_ct_get(skb, &ctinfo);
-+      if (ct == NULL)
-+              return XT_CONTINUE;
-+
-+      switch (ct->tuplehash[IP_CT_DIR_ORIGINAL].tuple.dst.protonum) {
-+      case IPPROTO_TCP:
-+              if (ct->proto.tcp.state != TCP_CONNTRACK_ESTABLISHED)
-+                      return XT_CONTINUE;
-+
-+              tcph = skb_header_pointer(skb, par->thoff,
-+                                        sizeof(_tcph), &_tcph);
-+              if (unlikely(!tcph || tcph->fin || tcph->rst))
-+                      return XT_CONTINUE;
-+              break;
-+      case IPPROTO_UDP:
-+              break;
-+      default:
-+              return XT_CONTINUE;
-+      }
-+
-+      if (nf_ct_ext_exist(ct, NF_CT_EXT_HELPER) ||
-+          ct->status & (IPS_SEQ_ADJUST | IPS_NAT_CLASH))
-+              return XT_CONTINUE;
-+
-+      if (!nf_ct_is_confirmed(ct))
-+              return XT_CONTINUE;
-+
-+      dir = CTINFO2DIR(ctinfo);
-+
-+      devs[dir] = xt_out(par);
-+      devs[!dir] = xt_in(par);
-+
-+      if (!devs[dir] || !devs[!dir])
-+              return XT_CONTINUE;
-+
-+      if (test_and_set_bit(IPS_OFFLOAD_BIT, &ct->status))
-+              return XT_CONTINUE;
-+
-+      if (xt_flowoffload_route(skb, ct, par, &route, dir, devs) < 0)
-+              goto err_flow_route;
-+
-+      flow = flow_offload_alloc(ct);
-+      if (!flow)
-+              goto err_flow_alloc;
-+
-+      flow_offload_route_init(flow, &route);
-+
-+      if (tcph) {
-+              ct->proto.tcp.seen[0].flags |= IP_CT_TCP_FLAG_BE_LIBERAL;
-+              ct->proto.tcp.seen[1].flags |= IP_CT_TCP_FLAG_BE_LIBERAL;
-+      }
-+
-+      table = &flowtable[!!(info->flags & XT_FLOWOFFLOAD_HW)];
-+
-+      net = read_pnet(&table->ft.net);
-+      if (!net)
-+              write_pnet(&table->ft.net, xt_net(par));
-+
-+      if (flow_offload_add(&table->ft, flow) < 0)
-+              goto err_flow_add;
-+
-+      xt_flowoffload_check_device(table, devs[0]);
-+      xt_flowoffload_check_device(table, devs[1]);
-+
-+      return XT_CONTINUE;
-+
-+err_flow_add:
-+      flow_offload_free(flow);
-+err_flow_alloc:
-+      dst_release(route.tuple[dir].dst);
-+      dst_release(route.tuple[!dir].dst);
-+err_flow_route:
-+      clear_bit(IPS_OFFLOAD_BIT, &ct->status);
-+
-+      return XT_CONTINUE;
-+}
-+
-+static int flowoffload_chk(const struct xt_tgchk_param *par)
-+{
-+      struct xt_flowoffload_target_info *info = par->targinfo;
-+
-+      if (info->flags & ~XT_FLOWOFFLOAD_MASK)
-+              return -EINVAL;
-+
-+      return 0;
-+}
-+
-+static struct xt_target offload_tg_reg __read_mostly = {
-+      .family         = NFPROTO_UNSPEC,
-+      .name           = "FLOWOFFLOAD",
-+      .revision       = 0,
-+      .targetsize     = sizeof(struct xt_flowoffload_target_info),
-+      .usersize       = sizeof(struct xt_flowoffload_target_info),
-+      .checkentry     = flowoffload_chk,
-+      .target         = flowoffload_tg,
-+      .me             = THIS_MODULE,
-+};
-+
-+static int flow_offload_netdev_event(struct notifier_block *this,
-+                                   unsigned long event, void *ptr)
-+{
-+      struct xt_flowoffload_hook *hook0, *hook1;
-+      struct net_device *dev = netdev_notifier_info_to_dev(ptr);
-+
-+      if (event != NETDEV_UNREGISTER)
-+              return NOTIFY_DONE;
-+
-+      spin_lock_bh(&hooks_lock);
-+      hook0 = flow_offload_lookup_hook(&flowtable[0], dev);
-+      if (hook0)
-+              hlist_del(&hook0->list);
-+
-+      hook1 = flow_offload_lookup_hook(&flowtable[1], dev);
-+      if (hook1)
-+              hlist_del(&hook1->list);
-+      spin_unlock_bh(&hooks_lock);
-+
-+      if (hook0) {
-+              nf_unregister_net_hook(hook0->net, &hook0->ops);
-+              kfree(hook0);
-+      }
-+
-+      if (hook1) {
-+              nf_unregister_net_hook(hook1->net, &hook1->ops);
-+              kfree(hook1);
-+      }
-+
-+      nf_flow_table_cleanup(dev);
-+
-+      return NOTIFY_DONE;
-+}
-+
-+static struct notifier_block flow_offload_netdev_notifier = {
-+      .notifier_call  = flow_offload_netdev_event,
-+};
-+
-+static int nf_flow_rule_route_inet(struct net *net,
-+                                 const struct flow_offload *flow,
-+                                 enum flow_offload_tuple_dir dir,
-+                                 struct nf_flow_rule *flow_rule)
-+{
-+      const struct flow_offload_tuple *flow_tuple = &flow->tuplehash[dir].tuple;
-+      int err;
-+
-+      switch (flow_tuple->l3proto) {
-+      case NFPROTO_IPV4:
-+              err = nf_flow_rule_route_ipv4(net, flow, dir, flow_rule);
-+              break;
-+      case NFPROTO_IPV6:
-+              err = nf_flow_rule_route_ipv6(net, flow, dir, flow_rule);
-+              break;
-+      default:
-+              err = -1;
-+              break;
-+      }
-+
-+      return err;
-+}
-+
-+static struct nf_flowtable_type flowtable_inet = {
-+      .family         = NFPROTO_INET,
-+      .init           = nf_flow_table_init,
-+      .setup          = nf_flow_table_offload_setup,
-+      .action         = nf_flow_rule_route_inet,
-+      .free           = nf_flow_table_free,
-+      .hook           = xt_flowoffload_net_hook,
-+      .owner          = THIS_MODULE,
-+};
-+
-+static int init_flowtable(struct xt_flowoffload_table *tbl)
-+{
-+      INIT_DELAYED_WORK(&tbl->work, xt_flowoffload_hook_work);
-+      tbl->ft.type = &flowtable_inet;
-+      tbl->ft.flags = NF_FLOWTABLE_COUNTER;
-+
-+      return nf_flow_table_init(&tbl->ft);
-+}
-+
-+static int __init xt_flowoffload_tg_init(void)
-+{
-+      int ret;
-+
-+      register_netdevice_notifier(&flow_offload_netdev_notifier);
-+
-+      ret = init_flowtable(&flowtable[0]);
-+      if (ret)
-+              return ret;
-+
-+      ret = init_flowtable(&flowtable[1]);
-+      if (ret)
-+              goto cleanup;
-+
-+      flowtable[1].ft.flags |= NF_FLOWTABLE_HW_OFFLOAD;
-+
-+      ret = xt_register_target(&offload_tg_reg);
-+      if (ret)
-+              goto cleanup2;
-+
-+      return 0;
-+
-+cleanup2:
-+      nf_flow_table_free(&flowtable[1].ft);
-+cleanup:
-+      nf_flow_table_free(&flowtable[0].ft);
-+      return ret;
-+}
-+
-+static void __exit xt_flowoffload_tg_exit(void)
-+{
-+      xt_unregister_target(&offload_tg_reg);
-+      unregister_netdevice_notifier(&flow_offload_netdev_notifier);
-+      nf_flow_table_free(&flowtable[0].ft);
-+      nf_flow_table_free(&flowtable[1].ft);
-+}
-+
-+MODULE_LICENSE("GPL");
-+module_init(xt_flowoffload_tg_init);
-+module_exit(xt_flowoffload_tg_exit);
---- a/net/netfilter/nf_flow_table_core.c
-+++ b/net/netfilter/nf_flow_table_core.c
-@@ -7,7 +7,6 @@
- #include <linux/netdevice.h>
- #include <net/ip.h>
- #include <net/ip6_route.h>
--#include <net/netfilter/nf_tables.h>
- #include <net/netfilter/nf_flow_table.h>
- #include <net/netfilter/nf_conntrack.h>
- #include <net/netfilter/nf_conntrack_core.h>
-@@ -373,8 +372,7 @@ flow_offload_lookup(struct nf_flowtable
- }
- EXPORT_SYMBOL_GPL(flow_offload_lookup);
--static int
--nf_flow_table_iterate(struct nf_flowtable *flow_table,
-+int nf_flow_table_iterate(struct nf_flowtable *flow_table,
-                     void (*iter)(struct nf_flowtable *flowtable,
-                                  struct flow_offload *flow, void *data),
-                     void *data)
-@@ -428,6 +426,7 @@ static void nf_flow_offload_gc_step(stru
-               nf_flow_offload_stats(flow_table, flow);
-       }
- }
-+EXPORT_SYMBOL_GPL(nf_flow_table_iterate);
- void nf_flow_table_gc_run(struct nf_flowtable *flow_table)
- {
---- /dev/null
-+++ b/include/uapi/linux/netfilter/xt_FLOWOFFLOAD.h
-@@ -0,0 +1,17 @@
-+/* SPDX-License-Identifier: GPL-2.0 WITH Linux-syscall-note */
-+#ifndef _XT_FLOWOFFLOAD_H
-+#define _XT_FLOWOFFLOAD_H
-+
-+#include <linux/types.h>
-+
-+enum {
-+      XT_FLOWOFFLOAD_HW       = 1 << 0,
-+
-+      XT_FLOWOFFLOAD_MASK     = XT_FLOWOFFLOAD_HW
-+};
-+
-+struct xt_flowoffload_target_info {
-+      __u32 flags;
-+};
-+
-+#endif /* _XT_FLOWOFFLOAD_H */
---- a/include/net/netfilter/nf_flow_table.h
-+++ b/include/net/netfilter/nf_flow_table.h
-@@ -276,6 +276,11 @@ void nf_flow_table_free(struct nf_flowta
- void flow_offload_teardown(struct flow_offload *flow);
-+int nf_flow_table_iterate(struct nf_flowtable *flow_table,
-+                      void (*iter)(struct nf_flowtable *flowtable,
-+                                   struct flow_offload *flow, void *data),
-+                      void *data);
-+
- void nf_flow_snat_port(const struct flow_offload *flow,
-                      struct sk_buff *skb, unsigned int thoff,
-                      u8 protocol, enum flow_offload_tuple_dir dir);
diff --git a/target/linux/generic/hack-5.15/651-wireless_mesh_header.patch b/target/linux/generic/hack-5.15/651-wireless_mesh_header.patch
deleted file mode 100644 (file)
index 12a031e..0000000
+++ /dev/null
@@ -1,24 +0,0 @@
-From 6d3bc769657b0ee7c7506dad9911111c4226a7ea Mon Sep 17 00:00:00 2001
-From: Imre Kaloz <[email protected]>
-Date: Fri, 7 Jul 2017 17:21:05 +0200
-Subject: mac80211: increase wireless mesh header size
-
-lede-commit 3d4466cfd8f75f717efdb1f96fdde3c70d865fc1
-Signed-off-by: Imre Kaloz <[email protected]>
----
- include/linux/netdevice.h | 4 ++--
- 1 file changed, 2 insertions(+), 2 deletions(-)
-
---- a/include/linux/netdevice.h
-+++ b/include/linux/netdevice.h
-@@ -145,8 +145,8 @@ static inline bool dev_xmit_complete(int
- #if defined(CONFIG_HYPERV_NET)
- # define LL_MAX_HEADER 128
--#elif defined(CONFIG_WLAN) || IS_ENABLED(CONFIG_AX25)
--# if defined(CONFIG_MAC80211_MESH)
-+#elif defined(CONFIG_WLAN) || IS_ENABLED(CONFIG_AX25) || 1
-+# if defined(CONFIG_MAC80211_MESH) || 1
- #  define LL_MAX_HEADER 128
- # else
- #  define LL_MAX_HEADER 96
diff --git a/target/linux/generic/hack-5.15/660-fq_codel_defaults.patch b/target/linux/generic/hack-5.15/660-fq_codel_defaults.patch
deleted file mode 100644 (file)
index a57a045..0000000
+++ /dev/null
@@ -1,27 +0,0 @@
-From a6ccb238939b25851474a279b20367fd24a0e816 Mon Sep 17 00:00:00 2001
-From: Felix Fietkau <[email protected]>
-Date: Fri, 7 Jul 2017 17:21:53 +0200
-Subject:  hack: net: fq_codel: tune defaults for small devices
-
-Assume that x86_64 devices always have a big memory and do not need this 
-optimization compared to devices with only 32 MB or 64 MB RAM.
-
-Signed-off-by: Felix Fietkau <[email protected]>
----
- net/sched/sch_fq_codel.c | 2 +-
- 1 file changed, 1 insertion(+), 1 deletion(-)
-
---- a/net/sched/sch_fq_codel.c
-+++ b/net/sched/sch_fq_codel.c
-@@ -467,7 +467,11 @@ static int fq_codel_init(struct Qdisc *s
-       sch->limit = 10*1024;
-       q->flows_cnt = 1024;
-+#ifdef CONFIG_X86_64
-       q->memory_limit = 32 << 20; /* 32 MBytes */
-+#else
-+      q->memory_limit = 4 << 20; /* 4 MBytes */
-+#endif
-       q->drop_batch_size = 64;
-       q->quantum = psched_mtu(qdisc_dev(sch));
-       INIT_LIST_HEAD(&q->new_flows);
diff --git a/target/linux/generic/hack-5.15/661-kernel-ct-size-the-hashtable-more-adequately.patch b/target/linux/generic/hack-5.15/661-kernel-ct-size-the-hashtable-more-adequately.patch
deleted file mode 100644 (file)
index 89074d0..0000000
+++ /dev/null
@@ -1,25 +0,0 @@
-From 804fbb3f2ec9283f7b778e057a68bfff440a0be6 Mon Sep 17 00:00:00 2001
-From: Rui Salvaterra <[email protected]>
-Date: Wed, 30 Mar 2022 22:51:55 +0100
-Subject: [PATCH] kernel: ct: size the hashtable more adequately
-
-To set the default size of the connection tracking hash table, a divider of
-16384 becomes inadequate for a router handling lots of connections. Divide by
-2048 instead, making the default size scale better with the available RAM.
-
-Signed-off-by: Rui Salvaterra <[email protected]>
----
- net/netfilter/nf_conntrack_core.c | 2 +-
- 1 file changed, 1 insertion(+), 1 deletion(-)
-
---- a/net/netfilter/nf_conntrack_core.c
-+++ b/net/netfilter/nf_conntrack_core.c
-@@ -2737,7 +2737,7 @@ int nf_conntrack_init_start(void)
-       if (!nf_conntrack_htable_size) {
-               nf_conntrack_htable_size
--                      = (((nr_pages << PAGE_SHIFT) / 16384)
-+                      = (((nr_pages << PAGE_SHIFT) / 2048)
-                          / sizeof(struct hlist_head));
-               if (BITS_PER_LONG >= 64 &&
-                   nr_pages > (4 * (1024 * 1024 * 1024 / PAGE_SIZE)))
diff --git a/target/linux/generic/hack-5.15/700-swconfig_switch_drivers.patch b/target/linux/generic/hack-5.15/700-swconfig_switch_drivers.patch
deleted file mode 100644 (file)
index 9d77efa..0000000
+++ /dev/null
@@ -1,131 +0,0 @@
-From 36e516290611e613aa92996cb4339561452695b4 Mon Sep 17 00:00:00 2001
-From: Felix Fietkau <[email protected]>
-Date: Fri, 7 Jul 2017 17:24:23 +0200
-Subject: net: swconfig: adds openwrt switch layer
-
-Signed-off-by: Felix Fietkau <[email protected]>
----
- drivers/net/phy/Kconfig   | 83 +++++++++++++++++++++++++++++++++++++++++++++++
- drivers/net/phy/Makefile  | 15 +++++++++
- include/uapi/linux/Kbuild |  1 +
- 3 files changed, 99 insertions(+)
-
---- a/drivers/net/phy/Kconfig
-+++ b/drivers/net/phy/Kconfig
-@@ -62,6 +62,80 @@ config SFP
-       depends on HWMON || HWMON=n
-       select MDIO_I2C
-+comment "Switch configuration API + drivers"
-+
-+config SWCONFIG
-+      tristate "Switch configuration API"
-+      help
-+        Switch configuration API using netlink. This allows
-+        you to configure the VLAN features of certain switches.
-+
-+config SWCONFIG_LEDS
-+      bool "Switch LED trigger support"
-+      depends on (SWCONFIG && LEDS_TRIGGERS)
-+
-+config ADM6996_PHY
-+      tristate "Driver for ADM6996 switches"
-+      select SWCONFIG
-+      help
-+        Currently supports the ADM6996FC and ADM6996M switches.
-+        Support for FC is very limited.
-+
-+config AR8216_PHY
-+      tristate "Driver for Atheros AR8216/8327 switches"
-+      select SWCONFIG
-+      select ETHERNET_PACKET_MANGLE
-+
-+config AR8216_PHY_LEDS
-+      bool "Atheros AR8216 switch LED support"
-+      depends on (AR8216_PHY && LEDS_CLASS)
-+
-+source "drivers/net/phy/b53/Kconfig"
-+
-+config IP17XX_PHY
-+      tristate "Driver for IC+ IP17xx switches"
-+      select SWCONFIG
-+
-+config PSB6970_PHY
-+      tristate "Lantiq XWAY Tantos (PSB6970) Ethernet switch"
-+      select SWCONFIG
-+
-+config RTL8306_PHY
-+      tristate "Driver for Realtek RTL8306S switches"
-+      select SWCONFIG
-+
-+config RTL8366_SMI
-+      tristate "Driver for the RTL8366 SMI interface"
-+      depends on GPIOLIB
-+      help
-+        This module implements the SMI interface protocol which is used
-+        by some RTL8366 ethernet switch devices via the generic GPIO API.
-+
-+if RTL8366_SMI
-+
-+config RTL8366_SMI_DEBUG_FS
-+      bool "RTL8366 SMI interface debugfs support"
-+        depends on DEBUG_FS
-+        default n
-+
-+config RTL8366S_PHY
-+      tristate "Driver for the Realtek RTL8366S switch"
-+      select SWCONFIG
-+
-+config RTL8366RB_PHY
-+      tristate "Driver for the Realtek RTL8366RB switch"
-+      select SWCONFIG
-+
-+config RTL8367_PHY
-+      tristate "Driver for the Realtek RTL8367R/M switches"
-+      select SWCONFIG
-+
-+config RTL8367B_PHY
-+      tristate "Driver fot the Realtek RTL8367R-VB switch"
-+      select SWCONFIG
-+
-+endif # RTL8366_SMI
-+
- comment "MII PHY device drivers"
- config AMD_PHY
---- a/drivers/net/phy/Makefile
-+++ b/drivers/net/phy/Makefile
-@@ -24,6 +24,21 @@ libphy-$(CONFIG_LED_TRIGGER_PHY)    += phy_
- obj-$(CONFIG_PHYLINK)         += phylink.o
- obj-$(CONFIG_PHYLIB)          += libphy.o
-+obj-$(CONFIG_SWCONFIG)                += swconfig.o
-+obj-$(CONFIG_ADM6996_PHY)     += adm6996.o
-+obj-$(CONFIG_AR8216_PHY)      += ar8xxx.o
-+ar8xxx-y                      += ar8216.o
-+ar8xxx-y                      += ar8327.o
-+obj-$(CONFIG_SWCONFIG_B53)    += b53/
-+obj-$(CONFIG_IP17XX_PHY)      += ip17xx.o
-+obj-$(CONFIG_PSB6970_PHY)     += psb6970.o
-+obj-$(CONFIG_RTL8306_PHY)     += rtl8306.o
-+obj-$(CONFIG_RTL8366_SMI)     += rtl8366_smi.o
-+obj-$(CONFIG_RTL8366S_PHY)    += rtl8366s.o
-+obj-$(CONFIG_RTL8366RB_PHY)   += rtl8366rb.o
-+obj-$(CONFIG_RTL8367_PHY)     += rtl8367.o
-+obj-$(CONFIG_RTL8367B_PHY)    += rtl8367b.o
-+
- obj-$(CONFIG_NETWORK_PHY_TIMESTAMPING) += mii_timestamper.o
- obj-$(CONFIG_SFP)             += sfp.o
---- a/include/linux/platform_data/b53.h
-+++ b/include/linux/platform_data/b53.h
-@@ -29,6 +29,9 @@ struct b53_platform_data {
-       u32 chip_id;
-       u16 enabled_ports;
-+      /* allow to specify an ethX alias */
-+      const char *alias;
-+
-       /* only used by MMAP'd driver */
-       unsigned big_endian:1;
-       void __iomem *regs;
diff --git a/target/linux/generic/hack-5.15/711-net-dsa-mv88e6xxx-disable-ATU-violation.patch b/target/linux/generic/hack-5.15/711-net-dsa-mv88e6xxx-disable-ATU-violation.patch
deleted file mode 100644 (file)
index 526cfdb..0000000
+++ /dev/null
@@ -1,21 +0,0 @@
-From ebd924d773223593142d417c41d4ee6fa16f1805 Mon Sep 17 00:00:00 2001
-From: OpenWrt community <[email protected]>
-Date: Wed, 13 Jul 2022 13:45:56 +0200
-Subject: [PATCH] net/dsa/mv88e6xxx: disable ATU violation
-
----
- drivers/net/dsa/mv88e6xxx/chip.c | 3 +++
- 1 file changed, 3 insertions(+)
-
---- a/drivers/net/dsa/mv88e6xxx/chip.c
-+++ b/drivers/net/dsa/mv88e6xxx/chip.c
-@@ -3027,6 +3027,9 @@ static int mv88e6xxx_setup_port(struct m
-       else
-               reg = 1 << port;
-+      /* Disable ATU member violation interrupt */
-+      reg |= MV88E6XXX_PORT_ASSOC_VECTOR_IGNORE_WRONG;
-+
-       err = mv88e6xxx_port_write(chip, port, MV88E6XXX_PORT_ASSOC_VECTOR,
-                                  reg);
-       if (err)
diff --git a/target/linux/generic/hack-5.15/721-net-add-packet-mangeling.patch b/target/linux/generic/hack-5.15/721-net-add-packet-mangeling.patch
deleted file mode 100644 (file)
index 70a0a1e..0000000
+++ /dev/null
@@ -1,178 +0,0 @@
-From ffe387740bbe88dd88bbe04d6375902708003d6e Mon Sep 17 00:00:00 2001
-From: Felix Fietkau <[email protected]>
-Date: Fri, 7 Jul 2017 17:25:00 +0200
-Subject: net: add packet mangeling
-
-ar8216 switches have a hardware bug, which renders normal 802.1q support
-unusable. Packet mangling is required to fix up the vlan for incoming
-packets.
-
-Signed-off-by: Felix Fietkau <[email protected]>
----
- include/linux/netdevice.h | 11 +++++++++++
- include/linux/skbuff.h    | 14 ++++----------
- net/Kconfig               |  6 ++++++
- net/core/dev.c            | 20 +++++++++++++++-----
- net/core/skbuff.c         | 17 +++++++++++++++++
- net/ethernet/eth.c        |  6 ++++++
- 6 files changed, 59 insertions(+), 15 deletions(-)
-
---- a/include/linux/netdevice.h
-+++ b/include/linux/netdevice.h
-@@ -1682,6 +1682,10 @@ enum netdev_priv_flags {
-       IFF_TX_SKB_NO_LINEAR            = BIT_ULL(31),
- };
-+enum netdev_extra_priv_flags {
-+      IFF_NO_IP_ALIGN                 = 1<<0,
-+};
-+
- #define IFF_802_1Q_VLAN                       IFF_802_1Q_VLAN
- #define IFF_EBRIDGE                   IFF_EBRIDGE
- #define IFF_BONDING                   IFF_BONDING
-@@ -1713,6 +1717,7 @@ enum netdev_priv_flags {
- #define IFF_FAILOVER_SLAVE            IFF_FAILOVER_SLAVE
- #define IFF_L3MDEV_RX_HANDLER         IFF_L3MDEV_RX_HANDLER
- #define IFF_TX_SKB_NO_LINEAR          IFF_TX_SKB_NO_LINEAR
-+#define IFF_NO_IP_ALIGN                       IFF_NO_IP_ALIGN
- /* Specifies the type of the struct net_device::ml_priv pointer */
- enum netdev_ml_priv_type {
-@@ -2013,6 +2018,7 @@ struct net_device {
-       /* Read-mostly cache-line for fast-path access */
-       unsigned int            flags;
-       unsigned int            priv_flags;
-+      unsigned int            extra_priv_flags;
-       const struct net_device_ops *netdev_ops;
-       int                     ifindex;
-       unsigned short          gflags;
-@@ -2073,6 +2079,11 @@ struct net_device {
-       const struct tlsdev_ops *tlsdev_ops;
- #endif
-+#ifdef CONFIG_ETHERNET_PACKET_MANGLE
-+      void (*eth_mangle_rx)(struct net_device *dev, struct sk_buff *skb);
-+      struct sk_buff *(*eth_mangle_tx)(struct net_device *dev, struct sk_buff *skb);
-+#endif
-+
-       const struct header_ops *header_ops;
-       unsigned char           operstate;
-@@ -2144,6 +2155,10 @@ struct net_device {
-       struct mctp_dev __rcu   *mctp_ptr;
- #endif
-+#ifdef CONFIG_ETHERNET_PACKET_MANGLE
-+      void                    *phy_ptr; /* PHY device specific data */
-+#endif
-+
- /*
-  * Cache lines mostly used on receive path (including eth_type_trans())
-  */
---- a/include/linux/skbuff.h
-+++ b/include/linux/skbuff.h
-@@ -2870,6 +2870,10 @@ static inline int pskb_trim(struct sk_bu
-       return (len < skb->len) ? __pskb_trim(skb, len) : 0;
- }
-+extern struct sk_buff *__netdev_alloc_skb_ip_align(struct net_device *dev,
-+              unsigned int length, gfp_t gfp);
-+
-+
- /**
-  *    pskb_trim_unique - remove end from a paged unique (not cloned) buffer
-  *    @skb: buffer to alter
-@@ -3020,16 +3024,6 @@ static inline struct sk_buff *dev_alloc_
- }
--static inline struct sk_buff *__netdev_alloc_skb_ip_align(struct net_device *dev,
--              unsigned int length, gfp_t gfp)
--{
--      struct sk_buff *skb = __netdev_alloc_skb(dev, length + NET_IP_ALIGN, gfp);
--
--      if (NET_IP_ALIGN && skb)
--              skb_reserve(skb, NET_IP_ALIGN);
--      return skb;
--}
--
- static inline struct sk_buff *netdev_alloc_skb_ip_align(struct net_device *dev,
-               unsigned int length)
- {
---- a/net/Kconfig
-+++ b/net/Kconfig
-@@ -26,6 +26,12 @@ menuconfig NET
- if NET
-+config ETHERNET_PACKET_MANGLE
-+      bool
-+      help
-+        This option can be selected by phy drivers that need to mangle
-+        packets going in or out of an ethernet device.
-+
- config WANT_COMPAT_NETLINK_MESSAGES
-       bool
-       help
---- a/net/core/dev.c
-+++ b/net/core/dev.c
-@@ -3600,6 +3600,11 @@ static int xmit_one(struct sk_buff *skb,
-       if (dev_nit_active(dev))
-               dev_queue_xmit_nit(skb, dev);
-+#ifdef CONFIG_ETHERNET_PACKET_MANGLE
-+      if (dev->eth_mangle_tx && !(skb = dev->eth_mangle_tx(dev, skb)))
-+              return NETDEV_TX_OK;
-+#endif
-+
-       len = skb->len;
-       PRANDOM_ADD_NOISE(skb, dev, txq, len + jiffies);
-       trace_net_dev_start_xmit(skb, dev);
---- a/net/core/skbuff.c
-+++ b/net/core/skbuff.c
-@@ -61,6 +61,7 @@
- #include <linux/if_vlan.h>
- #include <linux/mpls.h>
- #include <linux/kcov.h>
-+#include <linux/if.h>
- #include <net/protocol.h>
- #include <net/dst.h>
-@@ -602,6 +603,22 @@ skb_fail:
- }
- EXPORT_SYMBOL(__napi_alloc_skb);
-+struct sk_buff *__netdev_alloc_skb_ip_align(struct net_device *dev,
-+              unsigned int length, gfp_t gfp)
-+{
-+      struct sk_buff *skb = __netdev_alloc_skb(dev, length + NET_IP_ALIGN, gfp);
-+
-+#ifdef CONFIG_ETHERNET_PACKET_MANGLE
-+      if (dev && (dev->extra_priv_flags & IFF_NO_IP_ALIGN))
-+              return skb;
-+#endif
-+
-+      if (NET_IP_ALIGN && skb)
-+              skb_reserve(skb, NET_IP_ALIGN);
-+      return skb;
-+}
-+EXPORT_SYMBOL(__netdev_alloc_skb_ip_align);
-+
- void skb_add_rx_frag(struct sk_buff *skb, int i, struct page *page, int off,
-                    int size, unsigned int truesize)
- {
---- a/net/ethernet/eth.c
-+++ b/net/ethernet/eth.c
-@@ -170,6 +170,12 @@ __be16 eth_type_trans(struct sk_buff *sk
-       const struct ethhdr *eth;
-       skb->dev = dev;
-+
-+#ifdef CONFIG_ETHERNET_PACKET_MANGLE
-+      if (dev->eth_mangle_rx)
-+              dev->eth_mangle_rx(dev, skb);
-+#endif
-+
-       skb_reset_mac_header(skb);
-       eth = (struct ethhdr *)skb->data;
diff --git a/target/linux/generic/hack-5.15/722-net-phy-aquantia-enable-AQR112-and-AQR412.patch b/target/linux/generic/hack-5.15/722-net-phy-aquantia-enable-AQR112-and-AQR412.patch
deleted file mode 100644 (file)
index d003291..0000000
+++ /dev/null
@@ -1,148 +0,0 @@
-From 5f62951fba63a9f9cfff564209426bdea5fcc371 Mon Sep 17 00:00:00 2001
-From: Alex Marginean <[email protected]>
-Date: Tue, 27 Aug 2019 15:16:56 +0300
-Subject: [PATCH] drivers: net: phy: aquantia: enable AQR112 and AQR412
-
-Adds support for AQR112 and AQR412 which is mostly based on existing code
-with the addition of code configuring the protocol on system side.
-This allows changing the system side protocol without having to deploy a
-different firmware on the PHY.
-
-Signed-off-by: Alex Marginean <[email protected]>
----
- drivers/net/phy/aquantia/aquantia_main.c | 88 +++++++++++++++++++++++++++++++++++++++++
- 1 file changed, 88 insertions(+)
-
---- a/drivers/net/phy/aquantia/aquantia_main.c
-+++ b/drivers/net/phy/aquantia/aquantia_main.c
-@@ -27,6 +27,8 @@
- #define PHY_ID_AQR113 0x31c31c40
- #define PHY_ID_AQR113C        0x31c31c12
- #define PHY_ID_AQR813 0x31c31cb2
-+#define PHY_ID_AQR112 0x03a1b662
-+#define PHY_ID_AQR412 0x03a1b712
- #define MDIO_PHYXS_VEND_IF_STATUS             0xe812
- #define MDIO_PHYXS_VEND_IF_STATUS_TYPE_MASK   GENMASK(7, 3)
-@@ -99,6 +101,29 @@
- #define AQR107_OP_IN_PROG_SLEEP               1000
- #define AQR107_OP_IN_PROG_TIMEOUT     100000
-+/* registers in MDIO_MMD_VEND1 region */
-+#define AQUANTIA_VND1_GLOBAL_SC                       0x000
-+#define  AQUANTIA_VND1_GLOBAL_SC_LP           BIT(0xb)
-+
-+/* global start rate, the protocol associated with this speed is used by default
-+ * on SI.
-+ */
-+#define AQUANTIA_VND1_GSTART_RATE             0x31a
-+#define  AQUANTIA_VND1_GSTART_RATE_OFF                0
-+#define  AQUANTIA_VND1_GSTART_RATE_100M               1
-+#define  AQUANTIA_VND1_GSTART_RATE_1G         2
-+#define  AQUANTIA_VND1_GSTART_RATE_10G                3
-+#define  AQUANTIA_VND1_GSTART_RATE_2_5G               4
-+#define  AQUANTIA_VND1_GSTART_RATE_5G         5
-+
-+/* SYSCFG registers for 100M, 1G, 2.5G, 5G, 10G */
-+#define AQUANTIA_VND1_GSYSCFG_BASE            0x31b
-+#define AQUANTIA_VND1_GSYSCFG_100M            0
-+#define AQUANTIA_VND1_GSYSCFG_1G              1
-+#define AQUANTIA_VND1_GSYSCFG_2_5G            2
-+#define AQUANTIA_VND1_GSYSCFG_5G              3
-+#define AQUANTIA_VND1_GSYSCFG_10G             4
-+
- struct aqr107_hw_stat {
-       const char *name;
-       int reg;
-@@ -230,6 +255,51 @@ static int aqr_config_aneg(struct phy_de
-       return genphy_c45_check_and_restart_aneg(phydev, changed);
- }
-+static struct {
-+      u16 syscfg;
-+      int cnt;
-+      u16 start_rate;
-+} aquantia_syscfg[PHY_INTERFACE_MODE_MAX] = {
-+      [PHY_INTERFACE_MODE_SGMII] =      {0x04b, AQUANTIA_VND1_GSYSCFG_1G,
-+                                         AQUANTIA_VND1_GSTART_RATE_1G},
-+      [PHY_INTERFACE_MODE_2500BASEX] = {0x144, AQUANTIA_VND1_GSYSCFG_2_5G,
-+                                         AQUANTIA_VND1_GSTART_RATE_2_5G},
-+      [PHY_INTERFACE_MODE_XGMII] =      {0x100, AQUANTIA_VND1_GSYSCFG_10G,
-+                                         AQUANTIA_VND1_GSTART_RATE_10G},
-+      [PHY_INTERFACE_MODE_USXGMII] =    {0x080, AQUANTIA_VND1_GSYSCFG_10G,
-+                                         AQUANTIA_VND1_GSTART_RATE_10G},
-+};
-+
-+/* Sets up protocol on system side before calling aqr_config_aneg */
-+static int aqr_config_aneg_set_prot(struct phy_device *phydev)
-+{
-+      int if_type = phydev->interface;
-+      int i;
-+
-+      if (!aquantia_syscfg[if_type].cnt)
-+              return 0;
-+
-+      /* set PHY in low power mode so we can configure protocols */
-+      phy_write_mmd(phydev, MDIO_MMD_VEND1, AQUANTIA_VND1_GLOBAL_SC,
-+                    AQUANTIA_VND1_GLOBAL_SC_LP);
-+      mdelay(10);
-+
-+      /* set the default rate to enable the SI link */
-+      phy_write_mmd(phydev, MDIO_MMD_VEND1, AQUANTIA_VND1_GSTART_RATE,
-+                    aquantia_syscfg[if_type].start_rate);
-+
-+      for (i = 0; i <= aquantia_syscfg[if_type].cnt; i++)
-+              phy_write_mmd(phydev, MDIO_MMD_VEND1,
-+                            AQUANTIA_VND1_GSYSCFG_BASE + i,
-+                            aquantia_syscfg[if_type].syscfg);
-+
-+      /* wake PHY back up */
-+      phy_write_mmd(phydev, MDIO_MMD_VEND1, AQUANTIA_VND1_GLOBAL_SC, 0);
-+      mdelay(10);
-+
-+      return aqr_config_aneg(phydev);
-+}
-+
- static int aqr_config_intr(struct phy_device *phydev)
- {
-       bool en = phydev->interrupts == PHY_INTERRUPT_ENABLED;
-@@ -858,6 +928,30 @@ static struct phy_driver aqr_driver[] =
-       .get_stats      = aqr107_get_stats,
-       .link_change_notify = aqr107_link_change_notify,
- },
-+{
-+      PHY_ID_MATCH_MODEL(PHY_ID_AQR112),
-+      .name           = "Aquantia AQR112",
-+      .probe          = aqr107_probe,
-+      .config_aneg    = aqr_config_aneg_set_prot,
-+      .config_intr    = aqr_config_intr,
-+      .handle_interrupt = aqr_handle_interrupt,
-+      .read_status    = aqr107_read_status,
-+      .get_sset_count = aqr107_get_sset_count,
-+      .get_strings    = aqr107_get_strings,
-+      .get_stats      = aqr107_get_stats,
-+},
-+{
-+      PHY_ID_MATCH_MODEL(PHY_ID_AQR412),
-+      .name           = "Aquantia AQR412",
-+      .probe          = aqr107_probe,
-+      .config_aneg    = aqr_config_aneg_set_prot,
-+      .config_intr    = aqr_config_intr,
-+      .handle_interrupt = aqr_handle_interrupt,
-+      .read_status    = aqr107_read_status,
-+      .get_sset_count = aqr107_get_sset_count,
-+      .get_strings    = aqr107_get_strings,
-+      .get_stats      = aqr107_get_stats,
-+},
- };
- module_phy_driver(aqr_driver);
-@@ -875,6 +969,8 @@ static struct mdio_device_id __maybe_unu
-       { PHY_ID_MATCH_MODEL(PHY_ID_AQR113) },
-       { PHY_ID_MATCH_MODEL(PHY_ID_AQR113C) },
-       { PHY_ID_MATCH_MODEL(PHY_ID_AQR813) },
-+      { PHY_ID_MATCH_MODEL(PHY_ID_AQR112) },
-+      { PHY_ID_MATCH_MODEL(PHY_ID_AQR412) },
-       { }
- };
diff --git a/target/linux/generic/hack-5.15/723-net-phy-aquantia-fix-system-side-protocol-mi.patch b/target/linux/generic/hack-5.15/723-net-phy-aquantia-fix-system-side-protocol-mi.patch
deleted file mode 100644 (file)
index 72a70eb..0000000
+++ /dev/null
@@ -1,34 +0,0 @@
-From 5f008cb22f60da4e10375f22266c1a4e20b1252e Mon Sep 17 00:00:00 2001
-From: Alex Marginean <[email protected]>
-Date: Fri, 20 Sep 2019 18:22:52 +0300
-Subject: [PATCH] drivers: net: phy: aquantia: fix system side protocol
- misconfiguration
-
-Do not set up protocols for speeds that are not supported by FW.  Enabling
-these protocols leads to link issues on system side.
-
-Signed-off-by: Alex Marginean <[email protected]>
----
- drivers/net/phy/aquantia/aquantia_main.c | 8 +++++++-
- 1 file changed, 7 insertions(+), 1 deletion(-)
-
---- a/drivers/net/phy/aquantia/aquantia_main.c
-+++ b/drivers/net/phy/aquantia/aquantia_main.c
-@@ -288,10 +288,16 @@ static int aqr_config_aneg_set_prot(stru
-       phy_write_mmd(phydev, MDIO_MMD_VEND1, AQUANTIA_VND1_GSTART_RATE,
-                     aquantia_syscfg[if_type].start_rate);
--      for (i = 0; i <= aquantia_syscfg[if_type].cnt; i++)
-+      for (i = 0; i <= aquantia_syscfg[if_type].cnt; i++) {
-+              u16 reg = phy_read_mmd(phydev, MDIO_MMD_VEND1,
-+                                     AQUANTIA_VND1_GSYSCFG_BASE + i);
-+              if (!reg)
-+                      continue;
-+
-               phy_write_mmd(phydev, MDIO_MMD_VEND1,
-                             AQUANTIA_VND1_GSYSCFG_BASE + i,
-                             aquantia_syscfg[if_type].syscfg);
-+      }
-       /* wake PHY back up */
-       phy_write_mmd(phydev, MDIO_MMD_VEND1, AQUANTIA_VND1_GLOBAL_SC, 0);
diff --git a/target/linux/generic/hack-5.15/725-net-phy-aquantia-add-PHY_IDs-for-AQR112-variants.patch b/target/linux/generic/hack-5.15/725-net-phy-aquantia-add-PHY_IDs-for-AQR112-variants.patch
deleted file mode 100644 (file)
index 2193844..0000000
+++ /dev/null
@@ -1,63 +0,0 @@
-From 3b92ee7b7899b6beffb2b484c58326e36612a873 Mon Sep 17 00:00:00 2001
-From: Daniel Golle <[email protected]>
-Date: Thu, 23 Dec 2021 14:52:56 +0000
-Subject: [PATCH] net: phy: aquantia: add PHY_ID for AQR112R
-
-As advised by Ian Chang this PHY is used in Puzzle devices.
-
-Signed-off-by: Daniel Golle <[email protected]>
----
- drivers/net/phy/aquantia/aquantia_main.c | 10 ++++++++++
- 1 file changed, 10 insertions(+)
-
---- a/drivers/net/phy/aquantia/aquantia_main.c
-+++ b/drivers/net/phy/aquantia/aquantia_main.c
-@@ -29,6 +29,8 @@
- #define PHY_ID_AQR813 0x31c31cb2
- #define PHY_ID_AQR112 0x03a1b662
- #define PHY_ID_AQR412 0x03a1b712
-+#define PHY_ID_AQR112C        0x03a1b790
-+#define PHY_ID_AQR112R        0x31c31d12
- #define MDIO_PHYXS_VEND_IF_STATUS             0xe812
- #define MDIO_PHYXS_VEND_IF_STATUS_TYPE_MASK   GENMASK(7, 3)
-@@ -880,6 +882,30 @@ static struct phy_driver aqr_driver[] =
-       .read_status    = aqr_read_status,
- },
- {
-+      PHY_ID_MATCH_MODEL(PHY_ID_AQR112C),
-+      .name           = "Aquantia AQR112C",
-+      .probe          = aqr107_probe,
-+      .config_aneg    = aqr_config_aneg_set_prot,
-+      .config_intr    = aqr_config_intr,
-+      .handle_interrupt = aqr_handle_interrupt,
-+      .read_status    = aqr107_read_status,
-+      .get_sset_count = aqr107_get_sset_count,
-+      .get_strings    = aqr107_get_strings,
-+      .get_stats      = aqr107_get_stats,
-+},
-+{
-+      PHY_ID_MATCH_MODEL(PHY_ID_AQR112R),
-+      .name           = "Aquantia AQR112R",
-+      .probe          = aqr107_probe,
-+      .config_aneg    = aqr_config_aneg_set_prot,
-+      .config_intr    = aqr_config_intr,
-+      .handle_interrupt = aqr_handle_interrupt,
-+      .read_status    = aqr107_read_status,
-+      .get_sset_count = aqr107_get_sset_count,
-+      .get_strings    = aqr107_get_strings,
-+      .get_stats      = aqr107_get_stats,
-+},
-+{
-       PHY_ID_MATCH_MODEL(PHY_ID_AQR113),
-       .name           = "Aquantia AQR113",
-       .probe          = aqr107_probe,
-@@ -977,6 +1003,8 @@ static struct mdio_device_id __maybe_unu
-       { PHY_ID_MATCH_MODEL(PHY_ID_AQR813) },
-       { PHY_ID_MATCH_MODEL(PHY_ID_AQR112) },
-       { PHY_ID_MATCH_MODEL(PHY_ID_AQR412) },
-+      { PHY_ID_MATCH_MODEL(PHY_ID_AQR112C) },
-+      { PHY_ID_MATCH_MODEL(PHY_ID_AQR112R) },
-       { }
- };
diff --git a/target/linux/generic/hack-5.15/750-net-pcs-mtk-lynxi-workaround-2500BaseX-no-an.patch b/target/linux/generic/hack-5.15/750-net-pcs-mtk-lynxi-workaround-2500BaseX-no-an.patch
deleted file mode 100644 (file)
index 8b7f2f0..0000000
+++ /dev/null
@@ -1,53 +0,0 @@
-From 880d1311335120f64447ca9d11933872d734e19a Mon Sep 17 00:00:00 2001
-From: Daniel Golle <[email protected]>
-Date: Mon, 27 Mar 2023 18:41:54 +0100
-Subject: [PATCH] generic: pcs-mtk-lynxi: add hack to use 2500Base-X without AN
-
-Using 2500Base-T SFP modules e.g. on the BananaPi R3 requires manually
-disabling auto-negotiation, e.g. using ethtool. While a proper fix
-using SFP quirks is being discussed upstream, bring a work-around to
-restore user experience to what it was before the switch to the
-dedicated SGMII PCS driver.
-
-Signed-off-by: Daniel Golle <[email protected]>
-
---- a/drivers/net/pcs/pcs-mtk-lynxi.c
-+++ b/drivers/net/pcs/pcs-mtk-lynxi.c
-@@ -92,14 +92,23 @@ static void mtk_pcs_lynxi_get_state(stru
-                                   struct phylink_link_state *state)
- {
-       struct mtk_pcs_lynxi *mpcs = pcs_to_mtk_pcs_lynxi(pcs);
--      unsigned int bm, adv;
-+      unsigned int bm, bmsr, adv;
-       /* Read the BMSR and LPA */
-       regmap_read(mpcs->regmap, SGMSYS_PCS_CONTROL_1, &bm);
--      regmap_read(mpcs->regmap, SGMSYS_PCS_ADVERTISE, &adv);
-+      bmsr = FIELD_GET(SGMII_BMSR, bm);
-+
-+      if (state->interface == PHY_INTERFACE_MODE_2500BASEX) {
-+              state->link = !!(bmsr & BMSR_LSTATUS);
-+              state->an_complete = !!(bmsr & BMSR_ANEGCOMPLETE);
-+              state->speed = SPEED_2500;
-+              state->duplex = DUPLEX_FULL;
--      phylink_mii_c22_pcs_decode_state(state, FIELD_GET(SGMII_BMSR, bm),
--                                       FIELD_GET(SGMII_LPA, adv));
-+              return;
-+      }
-+
-+      regmap_read(mpcs->regmap, SGMSYS_PCS_ADVERTISE, &adv);
-+      phylink_mii_c22_pcs_decode_state(state, bmsr, FIELD_GET(SGMII_LPA, adv));
- }
- static int mtk_pcs_lynxi_config(struct phylink_pcs *pcs, unsigned int mode,
-@@ -134,7 +143,8 @@ static int mtk_pcs_lynxi_config(struct p
-               /* 1000base-X or 2500base-X autoneg */
-               sgm_mode = SGMII_REMOTE_FAULT_DIS;
-               use_an = linkmode_test_bit(ETHTOOL_LINK_MODE_Autoneg_BIT,
--                                         advertising);
-+                                         advertising) &&
-+                       !(interface == PHY_INTERFACE_MODE_2500BASEX);
-       } else {
-               /* 1000base-X or 2500base-X without autoneg */
-               sgm_mode = 0;
diff --git a/target/linux/generic/hack-5.15/760-net-usb-r8152-add-LED-configuration-from-OF.patch b/target/linux/generic/hack-5.15/760-net-usb-r8152-add-LED-configuration-from-OF.patch
deleted file mode 100644 (file)
index 5c5bd99..0000000
+++ /dev/null
@@ -1,74 +0,0 @@
-From 82985725e071f2a5735052f18e109a32aeac3a0b Mon Sep 17 00:00:00 2001
-From: David Bauer <[email protected]>
-Date: Sun, 26 Jul 2020 02:38:31 +0200
-Subject: [PATCH] net: usb: r8152: add LED configuration from OF
-
-This adds the ability to configure the LED configuration register using
-OF. This way, the correct value for board specific LED configuration can
-be determined.
-
-Signed-off-by: David Bauer <[email protected]>
----
- drivers/net/usb/r8152.c | 23 +++++++++++++++++++++++
- 1 file changed, 23 insertions(+)
-
---- a/drivers/net/usb/r8152.c
-+++ b/drivers/net/usb/r8152.c
-@@ -11,6 +11,7 @@
- #include <linux/mii.h>
- #include <linux/ethtool.h>
- #include <linux/usb.h>
-+#include <linux/of.h>
- #include <linux/crc32.h>
- #include <linux/if_vlan.h>
- #include <linux/uaccess.h>
-@@ -6994,6 +6995,22 @@ static void rtl_tally_reset(struct r8152
-       ocp_write_word(tp, MCU_TYPE_PLA, PLA_RSTTALLY, ocp_data);
- }
-+static int r8152_led_configuration(struct r8152 *tp)
-+{
-+      u32 led_data;
-+      int ret;
-+
-+      ret = of_property_read_u32(tp->udev->dev.of_node, "realtek,led-data",
-+                                                              &led_data);
-+
-+      if (ret)
-+              return ret;
-+      
-+      ocp_write_word(tp, MCU_TYPE_PLA, PLA_LEDSEL, led_data);
-+
-+      return 0;
-+}
-+
- static void r8152b_init(struct r8152 *tp)
- {
-       u32 ocp_data;
-@@ -7035,6 +7052,8 @@ static void r8152b_init(struct r8152 *tp
-       ocp_data = ocp_read_word(tp, MCU_TYPE_USB, USB_USB_CTRL);
-       ocp_data &= ~(RX_AGG_DISABLE | RX_ZERO_EN);
-       ocp_write_word(tp, MCU_TYPE_USB, USB_USB_CTRL, ocp_data);
-+
-+      r8152_led_configuration(tp);
- }
- static void r8153_init(struct r8152 *tp)
-@@ -7175,6 +7194,8 @@ static void r8153_init(struct r8152 *tp)
-               tp->coalesce = COALESCE_SLOW;
-               break;
-       }
-+
-+      r8152_led_configuration(tp);
- }
- static void r8153b_init(struct r8152 *tp)
-@@ -7257,6 +7278,8 @@ static void r8153b_init(struct r8152 *tp
-       rtl_tally_reset(tp);
-       tp->coalesce = 15000;   /* 15 us */
-+
-+      r8152_led_configuration(tp);
- }
- static void r8153c_init(struct r8152 *tp)
diff --git a/target/linux/generic/hack-5.15/761-dt-bindings-net-add-RTL8152-binding-documentation.patch b/target/linux/generic/hack-5.15/761-dt-bindings-net-add-RTL8152-binding-documentation.patch
deleted file mode 100644 (file)
index be262b9..0000000
+++ /dev/null
@@ -1,54 +0,0 @@
-From 3ee05f4aa64fc86af3be5bc176ba5808de9260a7 Mon Sep 17 00:00:00 2001
-From: David Bauer <[email protected]>
-Date: Sun, 26 Jul 2020 15:30:33 +0200
-Subject: [PATCH] dt-bindings: net: add RTL8152 binding documentation
-
-Add binding documentation for the Realtek RTL8152 / RTL8153 USB ethernet
-adapters.
-
-Signed-off-by: David Bauer <[email protected]>
----
- .../bindings/net/realtek,rtl8152.yaml         | 36 +++++++++++++++++++
- 1 file changed, 36 insertions(+)
- create mode 100644 Documentation/devicetree/bindings/net/realtek,rtl8152.yaml
-
---- /dev/null
-+++ b/Documentation/devicetree/bindings/net/realtek,rtl8152.yaml
-@@ -0,0 +1,36 @@
-+# SPDX-License-Identifier: GPL-2.0
-+%YAML 1.2
-+---
-+$id: http://devicetree.org/schemas/net/realtek,rtl8152.yaml#
-+$schema: http://devicetree.org/meta-schemas/core.yaml#
-+
-+title: Realtek RTL8152/RTL8153 series USB ethernet
-+
-+maintainers:
-+  - David Bauer <[email protected]>
-+
-+properties:
-+  compatible:
-+    oneOf:
-+      - items:
-+          - enum:
-+              - realtek,rtl8152
-+              - realtek,rtl8153
-+
-+  reg:
-+    description: The device number on the USB bus
-+
-+  realtek,led-data:
-+    description: Value to be written to the LED configuration register.
-+
-+required:
-+  - compatible
-+  - reg
-+
-+examples:
-+  - |
-+    usb-eth@2 {
-+      compatible = "realtek,rtl8153";
-+      reg = <2>;
-+      realtek,led-data = <0x87>;
-+    };
-\ No newline at end of file
diff --git a/target/linux/generic/hack-5.15/765-mxl-gpy-control-LED-reg-from-DT.patch b/target/linux/generic/hack-5.15/765-mxl-gpy-control-LED-reg-from-DT.patch
deleted file mode 100644 (file)
index 95e9749..0000000
+++ /dev/null
@@ -1,105 +0,0 @@
-From 94b90966095f3fa625897e8f53d215882f6e19b3 Mon Sep 17 00:00:00 2001
-From: David Bauer <[email protected]>
-Date: Sat, 11 Mar 2023 17:00:01 +0100
-Subject: [PATCH] mxl-gpy: control LED reg from DT
-
-Add dynamic configuration for the LED control registers on MXL PHYs.
-
-This patch has been tested with MaxLinear GPY211C. It is unlikely to be
-accepted upstream, as upstream plans on integrating their own framework
-for handling these LEDs.
-
-For the time being, use this hack to configure PHY driven device-LEDs to
-show the correct state.
-
-A possible alternative might be to expose the LEDs using the kernel LED
-framework and bind it to the netdevice. This might also be upstreamable,
-although it is a considerable extra amount of work.
-
-Signed-off-by: David Bauer <[email protected]>
----
- drivers/net/phy/mxl-gpy.c | 37 ++++++++++++++++++++++++++++++++++++-
- 1 file changed, 36 insertions(+), 1 deletion(-)
-
---- a/drivers/net/phy/mxl-gpy.c
-+++ b/drivers/net/phy/mxl-gpy.c
-@@ -8,6 +8,7 @@
- #include <linux/module.h>
- #include <linux/bitfield.h>
-+#include <linux/of.h>
- #include <linux/phy.h>
- #include <linux/netdevice.h>
-@@ -30,6 +31,7 @@
- #define PHY_MIISTAT           0x18    /* MII state */
- #define PHY_IMASK             0x19    /* interrupt mask */
- #define PHY_ISTAT             0x1A    /* interrupt status */
-+#define PHY_LED                       0x1B    /* LED control */
- #define PHY_FWV                       0x1E    /* firmware version */
- #define PHY_MIISTAT_SPD_MASK  GENMASK(2, 0)
-@@ -53,10 +55,15 @@
-                                PHY_IMASK_ADSC | \
-                                PHY_IMASK_ANC)
-+#define PHY_LED_NUM_LEDS      4
-+
- #define PHY_FWV_REL_MASK      BIT(15)
- #define PHY_FWV_TYPE_MASK     GENMASK(11, 8)
- #define PHY_FWV_MINOR_MASK    GENMASK(7, 0)
-+/* LED */
-+#define VSPEC1_LED(x)         (0x1 + x)
-+
- /* SGMII */
- #define VSPEC1_SGMII_CTRL     0x08
- #define VSPEC1_SGMII_CTRL_ANEN        BIT(12)         /* Aneg enable */
-@@ -80,6 +87,35 @@ static const struct {
-       {9, 0x73},
- };
-+static int gpy_led_write(struct phy_device *phydev)
-+{
-+      struct device_node *node = phydev->mdio.dev.of_node;
-+      u32 led_regs[PHY_LED_NUM_LEDS];
-+      int i, ret;
-+      u16 val = 0xff00;
-+
-+      if (!IS_ENABLED(CONFIG_OF_MDIO))
-+              return 0;
-+
-+      if (of_property_read_u32_array(node, "mxl,led-config", led_regs, PHY_LED_NUM_LEDS))
-+              return 0;
-+
-+      if (of_property_read_bool(node, "mxl,led-drive-vdd"))
-+              val &= 0x0fff;
-+
-+      /* Enable LED function handling on all ports*/
-+      phy_write(phydev, PHY_LED, val);
-+
-+      /* Write LED register values */
-+      for (i = 0; i < PHY_LED_NUM_LEDS; i++) {
-+              ret = phy_write_mmd(phydev, MDIO_MMD_VEND1, VSPEC1_LED(i), (u16)led_regs[i]);
-+              if (ret < 0)
-+                      return ret;
-+      }
-+
-+      return 0;
-+}
-+
- static int gpy_config_init(struct phy_device *phydev)
- {
-       int ret;
-@@ -91,7 +127,10 @@ static int gpy_config_init(struct phy_de
-       /* Clear all pending interrupts */
-       ret = phy_read(phydev, PHY_ISTAT);
--      return ret < 0 ? ret : 0;
-+      if (ret < 0)
-+              return ret;
-+
-+      return gpy_led_write(phydev);
- }
- static int gpy_probe(struct phy_device *phydev)
diff --git a/target/linux/generic/hack-5.15/766-net-phy-mediatek-ge-add-LED-configuration-interface.patch b/target/linux/generic/hack-5.15/766-net-phy-mediatek-ge-add-LED-configuration-interface.patch
deleted file mode 100644 (file)
index 3405d5c..0000000
+++ /dev/null
@@ -1,72 +0,0 @@
-From cc225d163b5a4f7a0d1968298bf7927306646a47 Mon Sep 17 00:00:00 2001
-From: David Bauer <[email protected]>
-Date: Fri, 28 Apr 2023 01:53:01 +0200
-Subject: [PATCH] net: phy: mediatek-ge: add LED configuration interface
-
-This adds a small hack similar to the one used for ar8xxx switches to
-read a reg:value map for configuring the LED configuration registers.
-
-This allows OpenWrt to write device-specific LED action as well as blink
-configurations. It is unlikely to be accepted upstream, as upstream
-plans on integrating their own framework for handling these LEDs.
-
-Signed-off-by: David Bauer <[email protected]>
----
- drivers/net/phy/mediatek-ge.c | 33 +++++++++++++++++++++++++++++++++
- 1 file changed, 33 insertions(+)
-
---- a/drivers/net/phy/mediatek-ge.c
-+++ b/drivers/net/phy/mediatek-ge.c
-@@ -1,4 +1,5 @@
- // SPDX-License-Identifier: GPL-2.0+
-+#include <linux/of.h>
- #include <linux/bitfield.h>
- #include <linux/module.h>
- #include <linux/phy.h>
-@@ -53,6 +54,36 @@ static int mt7530_phy_config_init(struct
-       return 0;
- }
-+static int mt7530_led_config_of(struct phy_device *phydev)
-+{
-+      struct device_node *np = phydev->mdio.dev.of_node;
-+      const __be32 *paddr;
-+      int len;
-+      int i;
-+
-+      paddr = of_get_property(np, "mediatek,led-config", &len);
-+      if (!paddr)
-+              return 0;
-+
-+      if (len < (2 * sizeof(*paddr)))
-+              return -EINVAL;
-+
-+      len /= sizeof(*paddr);
-+
-+      phydev_warn(phydev, "Configure LED registers (num=%d)\n", len);
-+      for (i = 0; i < len - 1; i += 2) {
-+              u32 reg;
-+              u32 val;
-+
-+              reg = be32_to_cpup(paddr + i);
-+              val = be32_to_cpup(paddr + i + 1);
-+
-+              phy_write_mmd(phydev, MDIO_MMD_VEND2, reg, val);
-+      }
-+
-+      return 0;
-+}
-+
- static int mt7531_phy_config_init(struct phy_device *phydev)
- {
-       mtk_gephy_config_init(phydev);
-@@ -65,6 +96,9 @@ static int mt7531_phy_config_init(struct
-       phy_write_mmd(phydev, MDIO_MMD_VEND1, 0x13, 0x404);
-       phy_write_mmd(phydev, MDIO_MMD_VEND1, 0x14, 0x404);
-+      /* LED Config*/
-+      mt7530_led_config_of(phydev);
-+
-       return 0;
- }
diff --git a/target/linux/generic/hack-5.15/773-bgmac-add-srab-switch.patch b/target/linux/generic/hack-5.15/773-bgmac-add-srab-switch.patch
deleted file mode 100644 (file)
index 7127aa1..0000000
+++ /dev/null
@@ -1,98 +0,0 @@
-From 3cb240533ab787899dc7f17aa7d6c5b4810e2e58 Mon Sep 17 00:00:00 2001
-From: Hauke Mehrtens <[email protected]>
-Date: Fri, 7 Jul 2017 17:26:01 +0200
-Subject: bcm53xx: bgmac: use srab switch driver
-
-use the srab switch driver on these SoCs.
-
-Signed-off-by: Hauke Mehrtens <[email protected]>
----
- drivers/net/ethernet/broadcom/bgmac-bcma.c |  1 +
- drivers/net/ethernet/broadcom/bgmac.c      | 24 ++++++++++++++++++++++++
- drivers/net/ethernet/broadcom/bgmac.h      |  4 ++++
- 3 files changed, 29 insertions(+)
-
---- a/drivers/net/ethernet/broadcom/bgmac-bcma.c
-+++ b/drivers/net/ethernet/broadcom/bgmac-bcma.c
-@@ -280,6 +280,7 @@ static int bgmac_probe(struct bcma_devic
-               bgmac->feature_flags |= BGMAC_FEAT_CLKCTLST;
-               bgmac->feature_flags |= BGMAC_FEAT_NO_RESET;
-               bgmac->feature_flags |= BGMAC_FEAT_FORCE_SPEED_2500;
-+              bgmac->feature_flags |= BGMAC_FEAT_SRAB;
-               break;
-       default:
-               bgmac->feature_flags |= BGMAC_FEAT_CLKCTLST;
---- a/drivers/net/ethernet/broadcom/bgmac.c
-+++ b/drivers/net/ethernet/broadcom/bgmac.c
-@@ -12,6 +12,7 @@
- #include <linux/bcma/bcma.h>
- #include <linux/etherdevice.h>
- #include <linux/interrupt.h>
-+#include <linux/platform_data/b53.h>
- #include <linux/bcm47xx_nvram.h>
- #include <linux/phy.h>
- #include <linux/phy_fixed.h>
-@@ -1408,6 +1409,17 @@ static const struct ethtool_ops bgmac_et
-       .set_link_ksettings     = phy_ethtool_set_link_ksettings,
- };
-+static struct b53_platform_data bgmac_b53_pdata = {
-+};
-+
-+static struct platform_device bgmac_b53_dev = {
-+      .name           = "b53-srab-switch",
-+      .id             = -1,
-+      .dev            = {
-+              .platform_data = &bgmac_b53_pdata,
-+      },
-+};
-+
- /**************************************************
-  * MII
-  **************************************************/
-@@ -1546,6 +1558,14 @@ int bgmac_enet_probe(struct bgmac *bgmac
-       bgmac->in_init = false;
-+      if ((bgmac->feature_flags & BGMAC_FEAT_SRAB) && !bgmac_b53_pdata.regs) {
-+              bgmac_b53_pdata.regs = ioremap(0x18007000, 0x1000);
-+
-+              err = platform_device_register(&bgmac_b53_dev);
-+              if (!err)
-+                      bgmac->b53_device = &bgmac_b53_dev;
-+      }
-+
-       err = register_netdev(bgmac->net_dev);
-       if (err) {
-               dev_err(bgmac->dev, "Cannot register net device\n");
-@@ -1568,6 +1588,10 @@ EXPORT_SYMBOL_GPL(bgmac_enet_probe);
- void bgmac_enet_remove(struct bgmac *bgmac)
- {
-+      if (bgmac->b53_device)
-+              platform_device_unregister(&bgmac_b53_dev);
-+      bgmac->b53_device = NULL;
-+
-       unregister_netdev(bgmac->net_dev);
-       phy_disconnect(bgmac->net_dev->phydev);
-       netif_napi_del(&bgmac->napi);
---- a/drivers/net/ethernet/broadcom/bgmac.h
-+++ b/drivers/net/ethernet/broadcom/bgmac.h
-@@ -390,6 +390,7 @@
- #define BGMAC_FEAT_CC4_IF_SW_TYPE_RGMII       BIT(18)
- #define BGMAC_FEAT_CC7_IF_TYPE_RGMII  BIT(19)
- #define BGMAC_FEAT_IDM_MASK           BIT(20)
-+#define BGMAC_FEAT_SRAB                       BIT(21)
- struct bgmac_slot_info {
-       union {
-@@ -497,6 +498,9 @@ struct bgmac {
-       void (*cmn_maskset32)(struct bgmac *bgmac, u16 offset, u32 mask,
-                             u32 set);
-       int (*phy_connect)(struct bgmac *bgmac);
-+
-+      /* platform device for associated switch */
-+      struct platform_device *b53_device;
- };
- struct bgmac *bgmac_alloc(struct device *dev);
diff --git a/target/linux/generic/hack-5.15/780-usb-net-MeigLink_modem_support.patch b/target/linux/generic/hack-5.15/780-usb-net-MeigLink_modem_support.patch
deleted file mode 100644 (file)
index b4ed6c9..0000000
+++ /dev/null
@@ -1,69 +0,0 @@
-From f81700b6bb2eda3756247bce472d8eaf6f466f61 Mon Sep 17 00:00:00 2001
-From: OpenWrt community <[email protected]>
-Date: Wed, 13 Jul 2022 13:49:26 +0200
-Subject: [PATCH] net/usb/qmi_wwan: add MeigLink modem support
-
----
- drivers/net/usb/qmi_wwan.c  | 1 +
- drivers/usb/serial/option.c | 7 +++++++
- 2 files changed, 8 insertions(+)
-
---- a/drivers/net/usb/qmi_wwan.c
-+++ b/drivers/net/usb/qmi_wwan.c
-@@ -1080,12 +1080,18 @@ static const struct usb_device_id produc
-               USB_DEVICE_AND_INTERFACE_INFO(0x03f0, 0x581d, USB_CLASS_VENDOR_SPEC, 1, 7),
-               .driver_info = (unsigned long)&qmi_wwan_info,
-       },
-+      {       /* Meiglink SGM828 */
-+              USB_DEVICE_AND_INTERFACE_INFO(0x2dee, 0x4d49, USB_CLASS_VENDOR_SPEC, 0x10, 0x05),
-+              .driver_info = (unsigned long)&qmi_wwan_info,
-+      },
-+
-       {QMI_MATCH_FF_FF_FF(0x2c7c, 0x0125)},   /* Quectel EC25, EC20 R2.0  Mini PCIe */
-       {QMI_MATCH_FF_FF_FF(0x2c7c, 0x0306)},   /* Quectel EP06/EG06/EM06 */
-       {QMI_MATCH_FF_FF_FF(0x2c7c, 0x0512)},   /* Quectel EG12/EM12 */
-       {QMI_MATCH_FF_FF_FF(0x2c7c, 0x0620)},   /* Quectel EM160R-GL */
-       {QMI_MATCH_FF_FF_FF(0x2c7c, 0x0800)},   /* Quectel RM500Q-GL */
-       {QMI_MATCH_FF_FF_FF(0x2c7c, 0x0801)},   /* Quectel RM520N */
-+      {QMI_MATCH_FF_FF_FF(0x05c6, 0xf601)},   /* MeigLink SLM750 */
-       /* 3. Combined interface devices matching on interface number */
-       {QMI_FIXED_INTF(0x0408, 0xea42, 4)},    /* Yota / Megafon M100-1 */
---- a/drivers/usb/serial/option.c
-+++ b/drivers/usb/serial/option.c
-@@ -247,6 +247,11 @@ static void option_instat_callback(struc
- #define UBLOX_PRODUCT_R410M                   0x90b2
- /* These Yuga products use Qualcomm's vendor ID */
- #define YUGA_PRODUCT_CLM920_NC5                       0x9625
-+/* These MeigLink products use Qualcomm's vendor ID */
-+#define MEIGLINK_PRODUCT_SLM750                       0xf601
-+
-+#define MEIGLINK_VENDOR_ID                    0x2dee
-+#define MEIGLINK_PRODUCT_SLM828                       0x4d49
- #define QUECTEL_VENDOR_ID                     0x2c7c
- /* These Quectel products use Quectel's vendor ID */
-@@ -1156,6 +1161,11 @@ static const struct usb_device_id option
-       { USB_DEVICE(QUALCOMM_VENDOR_ID, 0x0023)}, /* ONYX 3G device */
-       { USB_DEVICE(QUALCOMM_VENDOR_ID, 0x9000), /* SIMCom SIM5218 */
-         .driver_info = NCTRL(0) | NCTRL(1) | NCTRL(2) | NCTRL(3) | RSVD(4) },
-+      /* MeiG */
-+      { USB_DEVICE_AND_INTERFACE_INFO(MEIGLINK_VENDOR_ID, MEIGLINK_PRODUCT_SLM828, USB_CLASS_VENDOR_SPEC, 0x10, 0x01) },
-+      { USB_DEVICE_AND_INTERFACE_INFO(MEIGLINK_VENDOR_ID, MEIGLINK_PRODUCT_SLM828, USB_CLASS_VENDOR_SPEC, 0x10, 0x02) },
-+      { USB_DEVICE_AND_INTERFACE_INFO(MEIGLINK_VENDOR_ID, MEIGLINK_PRODUCT_SLM828, USB_CLASS_VENDOR_SPEC, 0x10, 0x03) },
-+      { USB_DEVICE_AND_INTERFACE_INFO(MEIGLINK_VENDOR_ID, MEIGLINK_PRODUCT_SLM828, USB_CLASS_VENDOR_SPEC, 0x10, 0x04) },
-       /* Quectel products using Qualcomm vendor ID */
-       { USB_DEVICE(QUALCOMM_VENDOR_ID, QUECTEL_PRODUCT_UC15)},
-       { USB_DEVICE(QUALCOMM_VENDOR_ID, QUECTEL_PRODUCT_UC20),
-@@ -1197,6 +1207,11 @@ static const struct usb_device_id option
-         .driver_info = ZLP },
-       { USB_DEVICE(QUECTEL_VENDOR_ID, QUECTEL_PRODUCT_BG96),
-         .driver_info = RSVD(4) },
-+      /* Meiglink products using Qualcomm vendor ID */
-+      // Works OK. In case of some issues check macros that are used by Quectel Products
-+      { USB_DEVICE_AND_INTERFACE_INFO(QUALCOMM_VENDOR_ID, MEIGLINK_PRODUCT_SLM750, 0xff, 0xff, 0xff),
-+        .driver_info = NUMEP2 },
-+      { USB_DEVICE_AND_INTERFACE_INFO(QUALCOMM_VENDOR_ID, MEIGLINK_PRODUCT_SLM750, 0xff, 0, 0) },
-       { USB_DEVICE_AND_INTERFACE_INFO(QUECTEL_VENDOR_ID, QUECTEL_PRODUCT_EP06, 0xff, 0xff, 0xff),
-         .driver_info = RSVD(1) | RSVD(2) | RSVD(3) | RSVD(4) | NUMEP2 },
-       { USB_DEVICE_AND_INTERFACE_INFO(QUECTEL_VENDOR_ID, QUECTEL_PRODUCT_EP06, 0xff, 0, 0) },
diff --git a/target/linux/generic/hack-5.15/781-usb-net-rndis-support-asr.patch b/target/linux/generic/hack-5.15/781-usb-net-rndis-support-asr.patch
deleted file mode 100644 (file)
index 47339b6..0000000
+++ /dev/null
@@ -1,69 +0,0 @@
-From 9fabf60187f1fa19e6f6bb5441587d485bd534b0 Mon Sep 17 00:00:00 2001
-From: Daniel Golle <[email protected]>
-Date: Tue, 9 Apr 2024 17:06:38 +0100
-Subject: [PATCH] rndis_host: add a bunch of USB IDs
-
-Add a bunch of USB IDs found in various places online to the
-RNDIS USB network driver.
-
-Signed-off-by: Daniel Golle <[email protected]>
----
- drivers/net/usb/rndis_host.c | 40 ++++++++++++++++++++++
- 1 file changed, 40 insertions(+)
-
---- a/drivers/net/usb/rndis_host.c
-+++ b/drivers/net/usb/rndis_host.c
-@@ -630,6 +630,16 @@ static const struct driver_info   zte_rndi
-       .tx_fixup =     rndis_tx_fixup,
- };
-+static const struct driver_info asr_rndis_info = {
-+      .description =  "Asr RNDIS device",
-+      .flags =        FLAG_WWAN | FLAG_POINTTOPOINT | FLAG_FRAMING_RN | FLAG_NO_SETINT | FLAG_NOARP,
-+      .bind =         rndis_bind,
-+      .unbind =       rndis_unbind,
-+      .status =       rndis_status,
-+      .rx_fixup =     rndis_rx_fixup,
-+      .tx_fixup =     rndis_tx_fixup,
-+};
-+
- /*-------------------------------------------------------------------------*/
- static const struct usb_device_id     products [] = {
-@@ -666,6 +676,36 @@ static const struct usb_device_id produc
-       USB_INTERFACE_INFO(USB_CLASS_WIRELESS_CONTROLLER, 1, 3),
-       .driver_info = (unsigned long) &rndis_info,
- }, {
-+      /* Quectel EG060V rndis device */
-+      USB_DEVICE_AND_INTERFACE_INFO(0x2c7c, 0x6004,
-+                                    USB_CLASS_WIRELESS_CONTROLLER, 1, 3),
-+      .driver_info = (unsigned long) &asr_rndis_info,
-+}, {
-+      /* Quectel EC200A rndis device */
-+      USB_DEVICE_AND_INTERFACE_INFO(0x2c7c, 0x6005,
-+                                    USB_CLASS_WIRELESS_CONTROLLER, 1, 3),
-+      .driver_info = (unsigned long) &asr_rndis_info,
-+}, {
-+      /* Quectel EC200T rndis device */
-+      USB_DEVICE_AND_INTERFACE_INFO(0x2c7c, 0x6026,
-+                                    USB_CLASS_WIRELESS_CONTROLLER, 1, 3),
-+      .driver_info = (unsigned long) &asr_rndis_info,
-+}, {
-+      /* Simcom A7906E rndis device */
-+      USB_DEVICE_AND_INTERFACE_INFO(0x1e0e, 0x9011,
-+                                    USB_CLASS_WIRELESS_CONTROLLER, 1, 3),
-+      .driver_info = (unsigned long) &asr_rndis_info,
-+}, {
-+      /* Meig SLM770A */
-+      USB_DEVICE_AND_INTERFACE_INFO(0x2dee, 0x4d57,
-+                                    USB_CLASS_WIRELESS_CONTROLLER, 1, 3),
-+      .driver_info = (unsigned long) &asr_rndis_info,
-+}, {
-+      /* Meig SLM828 */
-+      USB_DEVICE_AND_INTERFACE_INFO(0x2dee, 0x4d49,
-+                                    USB_CLASS_WIRELESS_CONTROLLER, 1, 3),
-+      .driver_info = (unsigned long) &asr_rndis_info,
-+}, {
-       /* Novatel Verizon USB730L */
-       USB_INTERFACE_INFO(USB_CLASS_MISC, 4, 1),
-       .driver_info = (unsigned long) &rndis_info,
diff --git a/target/linux/generic/hack-5.15/790-SFP-GE-T-ignore-TX_FAULT.patch b/target/linux/generic/hack-5.15/790-SFP-GE-T-ignore-TX_FAULT.patch
deleted file mode 100644 (file)
index e7372b3..0000000
+++ /dev/null
@@ -1,65 +0,0 @@
-From 7cc39a6bedbd85f3ff7e16845f310e4ce8d9833f Mon Sep 17 00:00:00 2001
-From: Daniel Golle <[email protected]>
-Date: Tue, 6 Sep 2022 00:31:19 +0100
-Subject: [PATCH] net: sfp: add quirk for ATS SFP-GE-T 1000Base-TX module
-    Russell King <[email protected]>,
-    Andrew Lunn <[email protected]>,
-    Heiner Kallweit <[email protected]>
-Cc: David S. Miller <[email protected]>,
-    Eric Dumazet <[email protected]>,
-    Jakub Kicinski <[email protected]>,
-    Paolo Abeni <[email protected]>,
-    Josef Schlehofer <[email protected]>
-
-This copper module comes with broken TX_FAULT indicator which must be
-ignored for it to work. Implement ignoring TX_FAULT state bit also
-during reset/insertion and mute the warning telling the user that the
-module indicates TX_FAULT.
-
-Co-authored-by: Josef Schlehofer <[email protected]>
-Signed-off-by: Daniel Golle <[email protected]>
----
- drivers/net/phy/sfp.c | 14 +++++++++++---
- 1 file changed, 11 insertions(+), 3 deletions(-)
-
---- a/drivers/net/phy/sfp.c
-+++ b/drivers/net/phy/sfp.c
-@@ -390,6 +390,11 @@ static const struct sfp_quirk sfp_quirks
-               .modes = sfp_quirk_2500basex,
-               .fixup = sfp_fixup_ignore_tx_fault,
-       }, {
-+              // OEM SFP-GE-T is 1000Base-T module
-+              .vendor = "OEM",
-+              .part = "SFP-GE-T",
-+              .fixup = sfp_fixup_ignore_tx_fault,
-+      }, {
-               // Lantech 8330-262D-E can operate at 2500base-X, but
-               // incorrectly report 2500MBd NRZ in their EEPROM
-               .vendor = "Lantech",
-@@ -2319,7 +2324,8 @@ static void sfp_sm_main(struct sfp *sfp,
-                        * or t_start_up, so assume there is a fault.
-                        */
-                       sfp_sm_fault(sfp, SFP_S_INIT_TX_FAULT,
--                                   sfp->sm_fault_retries == N_FAULT_INIT);
-+                                   !sfp->tx_fault_ignore &&
-+                                   (sfp->sm_fault_retries == N_FAULT_INIT));
-               } else if (event == SFP_E_TIMEOUT || event == SFP_E_TX_CLEAR) {
-       init_done:
-                       sfp->sm_phy_retries = R_PHY_RETRY;
-@@ -2542,10 +2548,12 @@ static void sfp_check_state(struct sfp *
-       mutex_lock(&sfp->st_mutex);
-       state = sfp_get_state(sfp);
-       changed = state ^ sfp->state;
--      if (sfp->tx_fault_ignore)
-+      if (sfp->tx_fault_ignore) {
-               changed &= SFP_F_PRESENT | SFP_F_LOS;
--      else
-+              state &= ~SFP_F_TX_FAULT;
-+      } else {
-               changed &= SFP_F_PRESENT | SFP_F_LOS | SFP_F_TX_FAULT;
-+      }
-       for (i = 0; i < GPIO_MAX; i++)
-               if (changed & BIT(i))
diff --git a/target/linux/generic/hack-5.15/795-backport-phylink_pcs-helpers.patch b/target/linux/generic/hack-5.15/795-backport-phylink_pcs-helpers.patch
deleted file mode 100644 (file)
index f93d84c..0000000
+++ /dev/null
@@ -1,167 +0,0 @@
-From 027586ae8ecacff49757ed854c020f35d24a599c Mon Sep 17 00:00:00 2001
-From: Daniel Golle <[email protected]>
-Date: Sat, 11 Mar 2023 03:44:41 +0000
-Subject: [PATCH] generic: backport some phylink helper functions
-
-It isn't feasible to literally backport all upstream phylink_pcs changes
-down to Linux 5.15: It's just too many patches, and many downstream
-drivers and hacks are likely to break. We are too close to branching off
-to risk this, and it's also just too much work.
-Instead just add helper functions used by modern PCS drivers while keeping
-the original functions instact as well. While this may add a kilobyte or
-two of extra kernel size, it has the advantage that we get the best of both
-worlds: None of the existing codepaths are touched, but yet we have the
-option to backport singular improvements to Ethernet drivers where needed.
-
-Signed-off-by: Daniel Golle <[email protected]>
-
---- a/include/linux/phylink.h
-+++ b/include/linux/phylink.h
-@@ -600,10 +600,37 @@ int phylink_speed_up(struct phylink *pl)
- #define phylink_test(bm, mode)        __phylink_do_bit(test_bit, bm, mode)
- void phylink_set_port_modes(unsigned long *bits);
-+
-+/**
-+ * phylink_get_link_timer_ns - return the PCS link timer value
-+ * @interface: link &typedef phy_interface_t mode
-+ *
-+ * Return the PCS link timer setting in nanoseconds for the PHY @interface
-+ * mode, or -EINVAL if not appropriate.
-+ */
-+static inline int phylink_get_link_timer_ns(phy_interface_t interface)
-+{
-+      switch (interface) {
-+      case PHY_INTERFACE_MODE_SGMII:
-+              return 1600000;
-+
-+      case PHY_INTERFACE_MODE_1000BASEX:
-+      case PHY_INTERFACE_MODE_2500BASEX:
-+              return 10000000;
-+
-+      default:
-+              return -EINVAL;
-+      }
-+}
-+
- void phylink_helper_basex_speed(struct phylink_link_state *state);
-+void phylink_mii_c22_pcs_decode_state(struct phylink_link_state *state,
-+                                    u16 bmsr, u16 lpa);
- void phylink_mii_c22_pcs_get_state(struct mdio_device *pcs,
-                                  struct phylink_link_state *state);
-+int phylink_mii_c22_pcs_encode_advertisement(phy_interface_t interface,
-+                                           const unsigned long *advertising);
- int phylink_mii_c22_pcs_set_advertisement(struct mdio_device *pcs,
-                                         phy_interface_t interface,
-                                         const unsigned long *advertising);
---- a/drivers/net/phy/phylink.c
-+++ b/drivers/net/phy/phylink.c
-@@ -934,7 +934,6 @@ static int phylink_change_inband_advert(
-       return 0;
- }
--
- static void phylink_mac_pcs_get_state(struct phylink *pl,
-                                     struct phylink_link_state *state)
- {
-@@ -3019,6 +3018,52 @@ void phylink_mii_c22_pcs_get_state(struc
- EXPORT_SYMBOL_GPL(phylink_mii_c22_pcs_get_state);
- /**
-+ * phylink_mii_c22_pcs_decode_state() - Decode MAC PCS state from MII registers
-+ * @state: a pointer to a &struct phylink_link_state.
-+ * @bmsr: The value of the %MII_BMSR register
-+ * @lpa: The value of the %MII_LPA register
-+ *
-+ * Helper for MAC PCS supporting the 802.3 clause 22 register set for
-+ * clause 37 negotiation and/or SGMII control.
-+ *
-+ * Parse the Clause 37 or Cisco SGMII link partner negotiation word into
-+ * the phylink @state structure. This is suitable to be used for implementing
-+ * the mac_pcs_get_state() member of the struct phylink_mac_ops structure if
-+ * accessing @bmsr and @lpa cannot be done with MDIO directly.
-+ */
-+void phylink_mii_c22_pcs_decode_state(struct phylink_link_state *state,
-+                                    u16 bmsr, u16 lpa)
-+{
-+      state->link = !!(bmsr & BMSR_LSTATUS);
-+      state->an_complete = !!(bmsr & BMSR_ANEGCOMPLETE);
-+      /* If there is no link or autonegotiation is disabled, the LP advertisement
-+       * data is not meaningful, so don't go any further.
-+       */
-+      if (!state->link || !state->an_enabled)
-+              return;
-+
-+      switch (state->interface) {
-+      case PHY_INTERFACE_MODE_1000BASEX:
-+              phylink_decode_c37_word(state, lpa, SPEED_1000);
-+              break;
-+
-+      case PHY_INTERFACE_MODE_2500BASEX:
-+              phylink_decode_c37_word(state, lpa, SPEED_2500);
-+              break;
-+
-+      case PHY_INTERFACE_MODE_SGMII:
-+      case PHY_INTERFACE_MODE_QSGMII:
-+              phylink_decode_sgmii_word(state, lpa);
-+              break;
-+
-+      default:
-+              state->link = false;
-+              break;
-+      }
-+}
-+EXPORT_SYMBOL_GPL(phylink_mii_c22_pcs_decode_state);
-+
-+/**
-  * phylink_mii_c22_pcs_set_advertisement() - configure the clause 37 PCS
-  *    advertisement
-  * @pcs: a pointer to a &struct mdio_device.
-@@ -3090,6 +3135,46 @@ int phylink_mii_c22_pcs_set_advertisemen
- EXPORT_SYMBOL_GPL(phylink_mii_c22_pcs_set_advertisement);
- /**
-+ * phylink_mii_c22_pcs_encode_advertisement() - configure the clause 37 PCS
-+ *    advertisement
-+ * @interface: the PHY interface mode being configured
-+ * @advertising: the ethtool advertisement mask
-+ *
-+ * Helper for MAC PCS supporting the 802.3 clause 22 register set for
-+ * clause 37 negotiation and/or SGMII control.
-+ *
-+ * Encode the clause 37 PCS advertisement as specified by @interface and
-+ * @advertising.
-+ *
-+ * Return: The new value for @adv, or ``-EINVAL`` if it should not be changed.
-+ */
-+int phylink_mii_c22_pcs_encode_advertisement(phy_interface_t interface,
-+                                           const unsigned long *advertising)
-+{
-+      u16 adv;
-+
-+      switch (interface) {
-+      case PHY_INTERFACE_MODE_1000BASEX:
-+      case PHY_INTERFACE_MODE_2500BASEX:
-+              adv = ADVERTISE_1000XFULL;
-+              if (linkmode_test_bit(ETHTOOL_LINK_MODE_Pause_BIT,
-+                                    advertising))
-+                      adv |= ADVERTISE_1000XPAUSE;
-+              if (linkmode_test_bit(ETHTOOL_LINK_MODE_Asym_Pause_BIT,
-+                                    advertising))
-+                      adv |= ADVERTISE_1000XPSE_ASYM;
-+              return adv;
-+      case PHY_INTERFACE_MODE_SGMII:
-+      case PHY_INTERFACE_MODE_QSGMII:
-+              return 0x0001;
-+      default:
-+              /* Nothing to do for other modes */
-+              return -EINVAL;
-+      }
-+}
-+EXPORT_SYMBOL_GPL(phylink_mii_c22_pcs_encode_advertisement);
-+
-+/**
-  * phylink_mii_c22_pcs_config() - configure clause 22 PCS
-  * @pcs: a pointer to a &struct mdio_device.
-  * @mode: link autonegotiation mode
diff --git a/target/linux/generic/hack-5.15/800-GPIO-add-named-gpio-exports.patch b/target/linux/generic/hack-5.15/800-GPIO-add-named-gpio-exports.patch
deleted file mode 100644 (file)
index 258a5fb..0000000
+++ /dev/null
@@ -1,190 +0,0 @@
-From cc809a441d8f2924f785eb863dfa6aef47a25b0b Mon Sep 17 00:00:00 2001
-From: John Crispin <[email protected]>
-Date: Tue, 12 Aug 2014 20:49:27 +0200
-Subject: [PATCH 30/36] GPIO: add named gpio exports
-
-Signed-off-by: John Crispin <[email protected]>
---- a/drivers/gpio/gpiolib-of.c
-+++ b/drivers/gpio/gpiolib-of.c
-@@ -19,6 +19,8 @@
- #include <linux/pinctrl/pinctrl.h>
- #include <linux/slab.h>
- #include <linux/gpio/machine.h>
-+#include <linux/init.h>
-+#include <linux/platform_device.h>
- #include "gpiolib.h"
- #include "gpiolib-of.h"
-@@ -1059,3 +1061,100 @@ void of_gpio_dev_init(struct gpio_chip *
-       else
-               gc->of_node = gdev->dev.of_node;
- }
-+
-+#ifdef CONFIG_GPIO_SYSFS
-+
-+static struct of_device_id gpio_export_ids[] = {
-+      { .compatible = "gpio-export" },
-+      { /* sentinel */ }
-+};
-+
-+static int of_gpio_export_probe(struct platform_device *pdev)
-+{
-+      struct device_node *np = pdev->dev.of_node;
-+      struct device_node *cnp;
-+      u32 val;
-+      int nb = 0;
-+
-+      for_each_child_of_node(np, cnp) {
-+              const char *name = NULL;
-+              int gpio;
-+              bool dmc;
-+              int max_gpio = 1;
-+              int i;
-+
-+              of_property_read_string(cnp, "gpio-export,name", &name);
-+
-+              if (!name)
-+                      max_gpio = of_gpio_count(cnp);
-+
-+              for (i = 0; i < max_gpio; i++) {
-+                      struct gpio_desc *desc;
-+                      unsigned flags = 0;
-+                      enum of_gpio_flags of_flags;
-+
-+                      gpio = of_get_gpio_flags(cnp, i, &of_flags);
-+                      if (!gpio_is_valid(gpio))
-+                              return gpio;
-+
-+                      if (of_flags & OF_GPIO_ACTIVE_LOW)
-+                              flags |= GPIOF_ACTIVE_LOW;
-+
-+                      if (!of_property_read_u32(cnp, "gpio-export,output", &val)) {
-+                              if (of_flags & OF_GPIO_SINGLE_ENDED) {
-+                                      /*
-+                                       * As gpiod_direction_output_raw() is used, we
-+                                       * need to emulate open drain or open source here.
-+                                       */
-+                                      if (of_flags & OF_GPIO_OPEN_DRAIN) {
-+                                              flags |= GPIOF_OPEN_DRAIN;
-+                                              flags |= val ? GPIOF_IN : GPIOF_OUT_INIT_LOW;
-+                                      } else {
-+                                              flags |= GPIOF_OPEN_SOURCE;
-+                                              flags |= val ? GPIOF_OUT_INIT_HIGH : GPIOF_IN;
-+                                      }
-+                              } else {
-+                                      flags |= val ? GPIOF_OUT_INIT_HIGH : GPIOF_OUT_INIT_LOW;
-+                              }
-+                      } else {
-+                              flags |= GPIOF_IN;
-+                      }
-+
-+                      if (devm_gpio_request_one(&pdev->dev, gpio, flags, name ? name : of_node_full_name(np)))
-+                              continue;
-+
-+                      /*
-+                       * When emulating open-source or open-drain functionalities by not
-+                       * actively driving the line (setting mode to input) we still need to
-+                       * set the IS_OUT flag or otherwise we won't be able to set the line
-+                       * value anymore.
-+                       */
-+                      if ((flags & GPIOF_IN) &&
-+                          ((flags & GPIOF_OPEN_DRAIN) || (flags & GPIOF_OPEN_SOURCE))) {
-+                              desc = gpio_to_desc(gpio);
-+                              set_bit(FLAG_IS_OUT, &desc->flags);
-+                      }
-+
-+                      dmc = of_property_read_bool(cnp, "gpio-export,direction_may_change");
-+                      gpio_export_with_name(gpio, dmc, name);
-+                      nb++;
-+              }
-+      }
-+
-+      dev_info(&pdev->dev, "%d gpio(s) exported\n", nb);
-+
-+      return 0;
-+}
-+
-+static struct platform_driver gpio_export_driver = {
-+      .driver         = {
-+              .name           = "gpio-export",
-+              .owner  = THIS_MODULE,
-+              .of_match_table = of_match_ptr(gpio_export_ids),
-+      },
-+      .probe          = of_gpio_export_probe,
-+};
-+
-+module_platform_driver(gpio_export_driver);
-+
-+#endif
---- a/include/asm-generic/gpio.h
-+++ b/include/asm-generic/gpio.h
-@@ -125,6 +125,12 @@ static inline int gpio_export(unsigned g
-       return gpiod_export(gpio_to_desc(gpio), direction_may_change);
- }
-+int __gpiod_export(struct gpio_desc *desc, bool direction_may_change, const char *name);
-+static inline int gpio_export_with_name(unsigned gpio, bool direction_may_change, const char *name)
-+{
-+      return __gpiod_export(gpio_to_desc(gpio), direction_may_change, name);
-+}
-+
- static inline int gpio_export_link(struct device *dev, const char *name,
-                                  unsigned gpio)
- {
---- a/include/linux/gpio/consumer.h
-+++ b/include/linux/gpio/consumer.h
-@@ -712,6 +712,7 @@ static inline void devm_acpi_dev_remove_
- #if IS_ENABLED(CONFIG_GPIOLIB) && IS_ENABLED(CONFIG_GPIO_SYSFS)
-+int _gpiod_export(struct gpio_desc *desc, bool direction_may_change, const char *name);
- int gpiod_export(struct gpio_desc *desc, bool direction_may_change);
- int gpiod_export_link(struct device *dev, const char *name,
-                     struct gpio_desc *desc);
-@@ -719,6 +720,13 @@ void gpiod_unexport(struct gpio_desc *de
- #else  /* CONFIG_GPIOLIB && CONFIG_GPIO_SYSFS */
-+static inline int _gpiod_export(struct gpio_desc *desc,
-+                             bool direction_may_change,
-+                             const char *name)
-+{
-+      return -ENOSYS;
-+}
-+
- static inline int gpiod_export(struct gpio_desc *desc,
-                              bool direction_may_change)
- {
---- a/drivers/gpio/gpiolib-sysfs.c
-+++ b/drivers/gpio/gpiolib-sysfs.c
-@@ -564,7 +564,7 @@ static struct class gpio_class = {
-  *
-  * Returns zero on success, else an error.
-  */
--int gpiod_export(struct gpio_desc *desc, bool direction_may_change)
-+int __gpiod_export(struct gpio_desc *desc, bool direction_may_change, const char *name)
- {
-       struct gpio_chip        *chip;
-       struct gpio_device      *gdev;
-@@ -626,6 +626,8 @@ int gpiod_export(struct gpio_desc *desc,
-       offset = gpio_chip_hwgpio(desc);
-       if (chip->names && chip->names[offset])
-               ioname = chip->names[offset];
-+      if (name)
-+              ioname = name;
-       dev = device_create_with_groups(&gpio_class, &gdev->dev,
-                                       MKDEV(0, 0), data, gpio_groups,
-@@ -647,6 +649,12 @@ err_unlock:
-       gpiod_dbg(desc, "%s: status %d\n", __func__, status);
-       return status;
- }
-+EXPORT_SYMBOL_GPL(__gpiod_export);
-+
-+int gpiod_export(struct gpio_desc *desc, bool direction_may_change)
-+{
-+      return __gpiod_export(desc, direction_may_change, NULL);
-+}
- EXPORT_SYMBOL_GPL(gpiod_export);
- static int match_export(struct device *dev, const void *desc)
diff --git a/target/linux/generic/hack-5.15/810-bcma-ssb-fallback-sprom.patch b/target/linux/generic/hack-5.15/810-bcma-ssb-fallback-sprom.patch
deleted file mode 100644 (file)
index c581a51..0000000
+++ /dev/null
@@ -1,187 +0,0 @@
-From e4d708702e6c98f2111e33201a264d6788564cb2 Mon Sep 17 00:00:00 2001
-From: OpenWrt community <[email protected]>
-Date: Fri, 12 May 2023 11:08:43 +0200
-Subject: [PATCH] ssb_sprom: add generic kernel support for Broadcom  Fallback SPROMs
-
----
- drivers/bcma/Kconfig        |  4 ++++
- drivers/bcma/Makefile       |  1 +
- drivers/bcma/bcma_private.h |  4 ++++
- drivers/bcma/main.c         |  8 ++++++++
- drivers/bcma/sprom.c        | 23 ++++++++++++++---------
- drivers/ssb/Kconfig         |  5 +++++
- drivers/ssb/Makefile        |  1 +
- drivers/ssb/main.c          |  8 ++++++++
- drivers/ssb/sprom.c         | 12 +++++++++++-
- drivers/ssb/ssb_private.h   |  4 ++++
- 10 files changed, 60 insertions(+), 10 deletions(-)
-
---- a/drivers/bcma/Kconfig
-+++ b/drivers/bcma/Kconfig
-@@ -18,6 +18,10 @@ config BCMA_BLOCKIO
-       bool
-       default y
-+config BCMA_FALLBACK_SPROM
-+      bool
-+      default y
-+
- config BCMA_HOST_PCI_POSSIBLE
-       bool
-       depends on PCI = y
---- a/drivers/bcma/Makefile
-+++ b/drivers/bcma/Makefile
-@@ -11,6 +11,7 @@ bcma-$(CONFIG_BCMA_DRIVER_PCI_HOSTMODE)
- bcma-$(CONFIG_BCMA_DRIVER_MIPS)               += driver_mips.o
- bcma-$(CONFIG_BCMA_DRIVER_GMAC_CMN)   += driver_gmac_cmn.o
- bcma-$(CONFIG_BCMA_DRIVER_GPIO)               += driver_gpio.o
-+bcma-$(CONFIG_BCMA_FALLBACK_SPROM)    += fallback-sprom.o
- bcma-$(CONFIG_BCMA_HOST_PCI)          += host_pci.o
- bcma-$(CONFIG_BCMA_HOST_SOC)          += host_soc.o
- obj-$(CONFIG_BCMA)                    += bcma.o
---- a/drivers/bcma/bcma_private.h
-+++ b/drivers/bcma/bcma_private.h
-@@ -38,6 +38,10 @@ int bcma_bus_resume(struct bcma_bus *bus
- void bcma_detect_chip(struct bcma_bus *bus);
- int bcma_bus_scan(struct bcma_bus *bus);
-+/* fallback-sprom.c */
-+int __init bcma_fbs_register(void);
-+int bcma_get_fallback_sprom(struct bcma_bus *dev, struct ssb_sprom *out);
-+
- /* sprom.c */
- int bcma_sprom_get(struct bcma_bus *bus);
---- a/drivers/bcma/main.c
-+++ b/drivers/bcma/main.c
-@@ -668,6 +668,14 @@ static int __init bcma_modinit(void)
- {
-       int err;
-+#ifdef CONFIG_BCMA_FALLBACK_SPROM
-+      err = bcma_fbs_register();
-+      if (err) {
-+              pr_err("Fallback SPROM initialization failed\n");
-+              err = 0;
-+      }
-+#endif /* CONFIG_BCMA_FALLBACK_SPROM */
-+
-       err = bcma_init_bus_register();
-       if (err)
-               return err;
---- a/drivers/bcma/sprom.c
-+++ b/drivers/bcma/sprom.c
-@@ -51,21 +51,26 @@ static int bcma_fill_sprom_with_fallback
- {
-       int err;
--      if (!get_fallback_sprom) {
-+      if (get_fallback_sprom)
-+              err = get_fallback_sprom(bus, out);
-+
-+#ifdef CONFIG_BCMA_FALLBACK_SPROM
-+      if (!get_fallback_sprom || err)
-+              err = bcma_get_fallback_sprom(bus, out);
-+#else
-+      if (!get_fallback_sprom)
-               err = -ENOENT;
--              goto fail;
--      }
-+#endif /* CONFIG_BCMA_FALLBACK_SPROM */
--      err = get_fallback_sprom(bus, out);
--      if (err)
--              goto fail;
-+      if (err) {
-+              bcma_warn(bus, "Using fallback SPROM failed (err %d)\n", err);
-+              return err;
-+      }
-       bcma_debug(bus, "Using SPROM revision %d provided by platform.\n",
-                  bus->sprom.revision);
-+
-       return 0;
--fail:
--      bcma_warn(bus, "Using fallback SPROM failed (err %d)\n", err);
--      return err;
- }
- /**************************************************
---- a/drivers/ssb/Kconfig
-+++ b/drivers/ssb/Kconfig
-@@ -25,6 +25,11 @@ if SSB
- config SSB_SPROM
-       bool
-+config SSB_FALLBACK_SPROM
-+      bool
-+      depends on SSB_PCIHOST
-+      default y
-+
- # Support for Block-I/O. SELECT this from the driver that needs it.
- config SSB_BLOCKIO
-       bool
---- a/drivers/ssb/Makefile
-+++ b/drivers/ssb/Makefile
-@@ -2,6 +2,7 @@
- # core
- ssb-y                                 += main.o scan.o
- ssb-$(CONFIG_SSB_EMBEDDED)            += embedded.o
-+ssb-$(CONFIG_SSB_FALLBACK_SPROM)      += fallback-sprom.o
- ssb-$(CONFIG_SSB_SPROM)                       += sprom.o
- # host support
---- a/drivers/ssb/main.c
-+++ b/drivers/ssb/main.c
-@@ -1287,6 +1287,14 @@ static int __init ssb_modinit(void)
- {
-       int err;
-+#ifdef CONFIG_SSB_FALLBACK_SPROM
-+      err = ssb_fbs_register();
-+      if (err) {
-+              pr_err("Fallback SPROM initialization failed\n");
-+              err = 0;
-+      }
-+#endif /* CONFIG_SSB_FALLBACK_SPROM */
-+
-       /* See the comment at the ssb_is_early_boot definition */
-       ssb_is_early_boot = 0;
-       err = bus_register(&ssb_bustype);
---- a/drivers/ssb/sprom.c
-+++ b/drivers/ssb/sprom.c
-@@ -180,10 +180,20 @@ int ssb_arch_register_fallback_sprom(int
- int ssb_fill_sprom_with_fallback(struct ssb_bus *bus, struct ssb_sprom *out)
- {
-+      int err;
-+
-+      if (get_fallback_sprom)
-+              err = get_fallback_sprom(bus, out);
-+
-+#ifdef CONFIG_SSB_FALLBACK_SPROM
-+      if (!get_fallback_sprom || err)
-+              err = ssb_get_fallback_sprom(bus, out);
-+#else
-       if (!get_fallback_sprom)
-               return -ENOENT;
-+#endif /* CONFIG_SSB_FALLBACK_SPROM */
--      return get_fallback_sprom(bus, out);
-+      return err;
- }
- /* https://bcm-v4.sipsolutions.net/802.11/IsSpromAvailable */
---- a/drivers/ssb/ssb_private.h
-+++ b/drivers/ssb/ssb_private.h
-@@ -143,6 +143,10 @@ extern int ssb_bus_scan(struct ssb_bus *
- extern void ssb_iounmap(struct ssb_bus *ssb);
-+/* fallback-sprom.c */
-+int __init ssb_fbs_register(void);
-+int ssb_get_fallback_sprom(struct ssb_bus *dev, struct ssb_sprom *out);
-+
- /* sprom.c */
- extern
- ssize_t ssb_attr_sprom_show(struct ssb_bus *bus, char *buf,
diff --git a/target/linux/generic/hack-5.15/901-debloat_sock_diag.patch b/target/linux/generic/hack-5.15/901-debloat_sock_diag.patch
deleted file mode 100644 (file)
index cf8ddea..0000000
+++ /dev/null
@@ -1,172 +0,0 @@
-From 3b6115d6b57a263bdc8c9b1df273bd4a7955eead Mon Sep 17 00:00:00 2001
-From: Felix Fietkau <[email protected]>
-Date: Sat, 8 Jul 2017 08:16:31 +0200
-Subject: debloat: add some debloat patches, strip down procfs and make O_DIRECT support optional, saves ~15K after lzma on MIPS
-
-Signed-off-by: Felix Fietkau <[email protected]>
----
- net/Kconfig         | 3 +++
- net/core/Makefile   | 3 ++-
- net/core/sock.c     | 2 ++
- net/ipv4/Kconfig    | 1 +
- net/netlink/Kconfig | 1 +
- net/packet/Kconfig  | 1 +
- net/unix/Kconfig    | 1 +
- 7 files changed, 11 insertions(+), 1 deletion(-)
-
---- a/net/Kconfig
-+++ b/net/Kconfig
-@@ -104,6 +104,9 @@ source "net/mptcp/Kconfig"
- endif # if INET
-+config SOCK_DIAG
-+      bool
-+
- config NETWORK_SECMARK
-       bool "Security Marking"
-       help
---- a/net/core/Makefile
-+++ b/net/core/Makefile
-@@ -10,9 +10,10 @@ obj-$(CONFIG_SYSCTL) += sysctl_net_core.
- obj-y              += dev.o dev_addr_lists.o dst.o netevent.o \
-                       neighbour.o rtnetlink.o utils.o link_watch.o filter.o \
--                      sock_diag.o dev_ioctl.o tso.o sock_reuseport.o \
-+                      dev_ioctl.o tso.o sock_reuseport.o \
-                       fib_notifier.o xdp.o flow_offload.o
-+obj-$(CONFIG_SOCK_DIAG) += sock_diag.o
- obj-y += net-sysfs.o
- obj-$(CONFIG_PAGE_POOL) += page_pool.o
- obj-$(CONFIG_PROC_FS) += net-procfs.o
---- a/net/core/sock.c
-+++ b/net/core/sock.c
-@@ -114,6 +114,7 @@
- #include <linux/memcontrol.h>
- #include <linux/prefetch.h>
- #include <linux/compat.h>
-+#include <linux/cookie.h>
- #include <linux/uaccess.h>
-@@ -143,6 +144,7 @@
- static DEFINE_MUTEX(proto_list_mutex);
- static LIST_HEAD(proto_list);
-+DEFINE_COOKIE(sock_cookie);
- static void sock_inuse_add(struct net *net, int val);
-@@ -545,6 +547,18 @@ discard_and_relse:
- }
- EXPORT_SYMBOL(__sk_receive_skb);
-+u64 __sock_gen_cookie(struct sock *sk)
-+{
-+      while (1) {
-+              u64 res = atomic64_read(&sk->sk_cookie);
-+
-+              if (res)
-+                      return res;
-+              res = gen_cookie_next(&sock_cookie);
-+              atomic64_cmpxchg(&sk->sk_cookie, 0, res);
-+      }
-+}
-+
- INDIRECT_CALLABLE_DECLARE(struct dst_entry *ip6_dst_check(struct dst_entry *,
-                                                         u32));
- INDIRECT_CALLABLE_DECLARE(struct dst_entry *ipv4_dst_check(struct dst_entry *,
-@@ -2005,9 +2019,11 @@ static void __sk_free(struct sock *sk)
-       if (likely(sk->sk_net_refcnt))
-               sock_inuse_add(sock_net(sk), -1);
-+#ifdef CONFIG_SOCK_DIAG
-       if (unlikely(sk->sk_net_refcnt && sock_diag_has_destroy_listeners(sk)))
-               sock_diag_broadcast_destroy(sk);
-       else
-+#endif
-               sk_destruct(sk);
- }
---- a/net/core/sock_diag.c
-+++ b/net/core/sock_diag.c
-@@ -11,7 +11,6 @@
- #include <linux/tcp.h>
- #include <linux/workqueue.h>
- #include <linux/nospec.h>
--#include <linux/cookie.h>
- #include <linux/inet_diag.h>
- #include <linux/sock_diag.h>
-@@ -20,20 +19,6 @@ static int (*inet_rcv_compat)(struct sk_
- static DEFINE_MUTEX(sock_diag_table_mutex);
- static struct workqueue_struct *broadcast_wq;
--DEFINE_COOKIE(sock_cookie);
--
--u64 __sock_gen_cookie(struct sock *sk)
--{
--      while (1) {
--              u64 res = atomic64_read(&sk->sk_cookie);
--
--              if (res)
--                      return res;
--              res = gen_cookie_next(&sock_cookie);
--              atomic64_cmpxchg(&sk->sk_cookie, 0, res);
--      }
--}
--
- int sock_diag_check_cookie(struct sock *sk, const __u32 *cookie)
- {
-       u64 res;
---- a/net/ipv4/Kconfig
-+++ b/net/ipv4/Kconfig
-@@ -424,6 +424,7 @@ config INET_TUNNEL
- config INET_DIAG
-       tristate "INET: socket monitoring interface"
-+      select SOCK_DIAG
-       default y
-       help
-         Support for INET (TCP, DCCP, etc) socket monitoring interface used by
---- a/net/netlink/Kconfig
-+++ b/net/netlink/Kconfig
-@@ -5,6 +5,7 @@
- config NETLINK_DIAG
-       tristate "NETLINK: socket monitoring interface"
-+      select SOCK_DIAG
-       default n
-       help
-         Support for NETLINK socket monitoring interface used by the ss tool.
---- a/net/packet/Kconfig
-+++ b/net/packet/Kconfig
-@@ -19,6 +19,7 @@ config PACKET
- config PACKET_DIAG
-       tristate "Packet: sockets monitoring interface"
-       depends on PACKET
-+      select SOCK_DIAG
-       default n
-       help
-         Support for PF_PACKET sockets monitoring interface used by the ss tool.
---- a/net/unix/Kconfig
-+++ b/net/unix/Kconfig
-@@ -33,6 +33,7 @@ config       AF_UNIX_OOB
- config UNIX_DIAG
-       tristate "UNIX: socket monitoring interface"
-       depends on UNIX
-+      select SOCK_DIAG
-       default n
-       help
-         Support for UNIX socket monitoring interface used by the ss tool.
---- a/net/xdp/Kconfig
-+++ b/net/xdp/Kconfig
-@@ -10,6 +10,7 @@ config XDP_SOCKETS
- config XDP_SOCKETS_DIAG
-       tristate "XDP sockets: monitoring interface"
-       depends on XDP_SOCKETS
-+      select SOCK_DIAG
-       default n
-       help
-         Support for PF_XDP sockets monitoring interface used by the ss tool.
diff --git a/target/linux/generic/hack-5.15/902-debloat_proc.patch b/target/linux/generic/hack-5.15/902-debloat_proc.patch
deleted file mode 100644 (file)
index 4404d34..0000000
+++ /dev/null
@@ -1,408 +0,0 @@
-From 9e3f1d0805b2d919904dd9a4ff0d956314cc3cba Mon Sep 17 00:00:00 2001
-From: Felix Fietkau <[email protected]>
-Date: Sat, 8 Jul 2017 08:20:09 +0200
-Subject: debloat: procfs
-
-Signed-off-by: Felix Fietkau <[email protected]>
----
- fs/locks.c               |  2 ++
- fs/proc/Kconfig          |  5 +++++
- fs/proc/consoles.c       |  3 +++
- fs/proc/proc_tty.c       | 11 ++++++++++-
- include/net/snmp.h       | 18 +++++++++++++++++-
- ipc/msg.c                |  3 +++
- ipc/sem.c                |  2 ++
- ipc/shm.c                |  2 ++
- ipc/util.c               |  3 +++
- kernel/exec_domain.c     |  2 ++
- kernel/irq/proc.c        |  9 +++++++++
- kernel/time/timer_list.c |  2 ++
- mm/vmalloc.c             |  2 ++
- mm/vmstat.c              |  8 +++++---
- net/8021q/vlanproc.c     |  6 ++++++
- net/core/net-procfs.c    | 18 ++++++++++++------
- net/core/sock.c          |  2 ++
- net/ipv4/fib_trie.c      | 18 ++++++++++++------
- net/ipv4/proc.c          |  3 +++
- net/ipv4/route.c         |  3 +++
- 20 files changed, 105 insertions(+), 17 deletions(-)
-
---- a/fs/locks.c
-+++ b/fs/locks.c
-@@ -3008,6 +3008,8 @@ static const struct seq_operations locks
- static int __init proc_locks_init(void)
- {
-+      if (IS_ENABLED(CONFIG_PROC_STRIPPED))
-+              return 0;
-       proc_create_seq_private("locks", 0, NULL, &locks_seq_operations,
-                       sizeof(struct locks_iterator), NULL);
-       return 0;
---- a/fs/proc/Kconfig
-+++ b/fs/proc/Kconfig
-@@ -100,6 +100,11 @@ config PROC_CHILDREN
-         Say Y if you are running any user-space software which takes benefit from
-         this interface. For example, rkt is such a piece of software.
-+config PROC_STRIPPED
-+      default n
-+      depends on EXPERT
-+      bool "Strip non-essential /proc functionality to reduce code size"
-+
- config PROC_PID_ARCH_STATUS
-       def_bool n
-       depends on PROC_FS
---- a/fs/proc/consoles.c
-+++ b/fs/proc/consoles.c
-@@ -92,6 +92,9 @@ static const struct seq_operations conso
- static int __init proc_consoles_init(void)
- {
-+      if (IS_ENABLED(CONFIG_PROC_STRIPPED))
-+              return 0;
-+
-       proc_create_seq("consoles", 0, NULL, &consoles_op);
-       return 0;
- }
---- a/fs/proc/proc_tty.c
-+++ b/fs/proc/proc_tty.c
-@@ -133,7 +133,10 @@ static const struct seq_operations tty_d
- void proc_tty_register_driver(struct tty_driver *driver)
- {
-       struct proc_dir_entry *ent;
--              
-+
-+      if (IS_ENABLED(CONFIG_PROC_STRIPPED))
-+              return;
-+
-       if (!driver->driver_name || driver->proc_entry ||
-           !driver->ops->proc_show)
-               return;
-@@ -150,6 +153,9 @@ void proc_tty_unregister_driver(struct t
- {
-       struct proc_dir_entry *ent;
-+      if (IS_ENABLED(CONFIG_PROC_STRIPPED))
-+              return;
-+
-       ent = driver->proc_entry;
-       if (!ent)
-               return;
-@@ -164,6 +170,9 @@ void proc_tty_unregister_driver(struct t
-  */
- void __init proc_tty_init(void)
- {
-+      if (IS_ENABLED(CONFIG_PROC_STRIPPED))
-+              return;
-+
-       if (!proc_mkdir("tty", NULL))
-               return;
-       proc_mkdir("tty/ldisc", NULL);  /* Preserved: it's userspace visible */
---- a/include/net/snmp.h
-+++ b/include/net/snmp.h
-@@ -124,6 +124,21 @@ struct linux_tls_mib {
- #define DECLARE_SNMP_STAT(type, name) \
-       extern __typeof__(type) __percpu *name
-+#ifdef CONFIG_PROC_STRIPPED
-+#define __SNMP_STATS_DUMMY(mib)       \
-+      do { (void) mib->mibs[0]; } while(0)
-+
-+#define __SNMP_INC_STATS(mib, field) __SNMP_STATS_DUMMY(mib)
-+#define SNMP_INC_STATS_ATOMIC_LONG(mib, field) __SNMP_STATS_DUMMY(mib)
-+#define SNMP_INC_STATS(mib, field) __SNMP_STATS_DUMMY(mib)
-+#define SNMP_DEC_STATS(mib, field) __SNMP_STATS_DUMMY(mib)
-+#define __SNMP_ADD_STATS(mib, field, addend) __SNMP_STATS_DUMMY(mib)
-+#define SNMP_ADD_STATS(mib, field, addend) __SNMP_STATS_DUMMY(mib)
-+#define SNMP_UPD_PO_STATS(mib, basefield, addend) __SNMP_STATS_DUMMY(mib)
-+#define __SNMP_UPD_PO_STATS(mib, basefield, addend) __SNMP_STATS_DUMMY(mib)
-+
-+#else
-+
- #define __SNMP_INC_STATS(mib, field)  \
-                       __this_cpu_inc(mib->mibs[field])
-@@ -154,8 +169,9 @@ struct linux_tls_mib {
-               __this_cpu_add(ptr[basefield##OCTETS], addend); \
-       } while (0)
-+#endif
--#if BITS_PER_LONG==32
-+#if (BITS_PER_LONG==32) && !defined(CONFIG_PROC_STRIPPED)
- #define __SNMP_ADD_STATS64(mib, field, addend)                                \
-       do {                                                            \
---- a/ipc/msg.c
-+++ b/ipc/msg.c
-@@ -1350,6 +1350,9 @@ void __init msg_init(void)
- {
-       msg_init_ns(&init_ipc_ns);
-+      if (IS_ENABLED(CONFIG_PROC_STRIPPED))
-+              return;
-+
-       ipc_init_proc_interface("sysvipc/msg",
-                               "       key      msqid perms      cbytes       qnum lspid lrpid   uid   gid  cuid  cgid      stime      rtime      ctime\n",
-                               IPC_MSG_IDS, sysvipc_msg_proc_show);
---- a/ipc/sem.c
-+++ b/ipc/sem.c
-@@ -268,6 +268,8 @@ void sem_exit_ns(struct ipc_namespace *n
- void __init sem_init(void)
- {
-       sem_init_ns(&init_ipc_ns);
-+      if (IS_ENABLED(CONFIG_PROC_STRIPPED))
-+              return;
-       ipc_init_proc_interface("sysvipc/sem",
-                               "       key      semid perms      nsems   uid   gid  cuid  cgid      otime      ctime\n",
-                               IPC_SEM_IDS, sysvipc_sem_proc_show);
---- a/ipc/shm.c
-+++ b/ipc/shm.c
-@@ -154,6 +154,8 @@ pure_initcall(ipc_ns_init);
- void __init shm_init(void)
- {
-+      if (IS_ENABLED(CONFIG_PROC_STRIPPED))
-+              return;
-       ipc_init_proc_interface("sysvipc/shm",
- #if BITS_PER_LONG <= 32
-                               "       key      shmid perms       size  cpid  lpid nattch   uid   gid  cuid  cgid      atime      dtime      ctime        rss       swap\n",
---- a/ipc/util.c
-+++ b/ipc/util.c
-@@ -141,6 +141,9 @@ void __init ipc_init_proc_interface(cons
-       struct proc_dir_entry *pde;
-       struct ipc_proc_iface *iface;
-+      if (IS_ENABLED(CONFIG_PROC_STRIPPED))
-+              return;
-+
-       iface = kmalloc(sizeof(*iface), GFP_KERNEL);
-       if (!iface)
-               return;
---- a/kernel/exec_domain.c
-+++ b/kernel/exec_domain.c
-@@ -29,6 +29,8 @@ static int execdomains_proc_show(struct
- static int __init proc_execdomains_init(void)
- {
-+      if (IS_ENABLED(CONFIG_PROC_STRIPPED))
-+              return 0;
-       proc_create_single("execdomains", 0, NULL, execdomains_proc_show);
-       return 0;
- }
---- a/kernel/irq/proc.c
-+++ b/kernel/irq/proc.c
-@@ -341,6 +341,9 @@ void register_irq_proc(unsigned int irq,
-       void __maybe_unused *irqp = (void *)(unsigned long) irq;
-       char name [MAX_NAMELEN];
-+      if (IS_ENABLED(CONFIG_PROC_STRIPPED) && !IS_ENABLED(CONFIG_SMP))
-+              return;
-+
-       if (!root_irq_dir || (desc->irq_data.chip == &no_irq_chip))
-               return;
-@@ -394,6 +397,9 @@ void unregister_irq_proc(unsigned int ir
- {
-       char name [MAX_NAMELEN];
-+      if (IS_ENABLED(CONFIG_PROC_STRIPPED) && !IS_ENABLED(CONFIG_SMP))
-+              return;
-+
-       if (!root_irq_dir || !desc->dir)
-               return;
- #ifdef CONFIG_SMP
-@@ -432,6 +438,9 @@ void init_irq_proc(void)
-       unsigned int irq;
-       struct irq_desc *desc;
-+      if (IS_ENABLED(CONFIG_PROC_STRIPPED) && !IS_ENABLED(CONFIG_SMP))
-+              return;
-+
-       /* create /proc/irq */
-       root_irq_dir = proc_mkdir("irq", NULL);
-       if (!root_irq_dir)
---- a/kernel/time/timer_list.c
-+++ b/kernel/time/timer_list.c
-@@ -350,6 +350,8 @@ static int __init init_timer_list_procfs
- {
-       struct proc_dir_entry *pe;
-+      if (IS_ENABLED(CONFIG_PROC_STRIPPED))
-+              return 0;
-       pe = proc_create_seq_private("timer_list", 0400, NULL, &timer_list_sops,
-                       sizeof(struct timer_list_iter), NULL);
-       if (!pe)
---- a/mm/vmalloc.c
-+++ b/mm/vmalloc.c
-@@ -3986,6 +3986,8 @@ static const struct seq_operations vmall
- static int __init proc_vmalloc_init(void)
- {
-+      if (IS_ENABLED(CONFIG_PROC_STRIPPED))
-+              return 0;
-       if (IS_ENABLED(CONFIG_NUMA))
-               proc_create_seq_private("vmallocinfo", 0400, NULL,
-                               &vmalloc_op,
---- a/mm/vmstat.c
-+++ b/mm/vmstat.c
-@@ -2083,10 +2083,12 @@ void __init init_mm_internals(void)
-       start_shepherd_timer();
- #endif
- #ifdef CONFIG_PROC_FS
--      proc_create_seq("buddyinfo", 0444, NULL, &fragmentation_op);
--      proc_create_seq("pagetypeinfo", 0400, NULL, &pagetypeinfo_op);
-+      if (!IS_ENABLED(CONFIG_PROC_STRIPPED)) {
-+              proc_create_seq("buddyinfo", 0444, NULL, &fragmentation_op);
-+              proc_create_seq("pagetypeinfo", 0400, NULL, &pagetypeinfo_op);
-+              proc_create_seq("zoneinfo", 0444, NULL, &zoneinfo_op);
-+      }
-       proc_create_seq("vmstat", 0444, NULL, &vmstat_op);
--      proc_create_seq("zoneinfo", 0444, NULL, &zoneinfo_op);
- #endif
- }
---- a/net/8021q/vlanproc.c
-+++ b/net/8021q/vlanproc.c
-@@ -93,6 +93,9 @@ void vlan_proc_cleanup(struct net *net)
- {
-       struct vlan_net *vn = net_generic(net, vlan_net_id);
-+      if (IS_ENABLED(CONFIG_PROC_STRIPPED))
-+              return;
-+
-       if (vn->proc_vlan_conf)
-               remove_proc_entry(name_conf, vn->proc_vlan_dir);
-@@ -112,6 +115,9 @@ int __net_init vlan_proc_init(struct net
- {
-       struct vlan_net *vn = net_generic(net, vlan_net_id);
-+      if (IS_ENABLED(CONFIG_PROC_STRIPPED))
-+              return 0;
-+
-       vn->proc_vlan_dir = proc_net_mkdir(net, name_root, net->proc_net);
-       if (!vn->proc_vlan_dir)
-               goto err;
---- a/net/core/net-procfs.c
-+++ b/net/core/net-procfs.c
-@@ -317,10 +317,12 @@ static int __net_init dev_proc_net_init(
-       if (!proc_create_net("dev", 0444, net->proc_net, &dev_seq_ops,
-                       sizeof(struct seq_net_private)))
-               goto out;
--      if (!proc_create_seq("softnet_stat", 0444, net->proc_net,
-+      if (!IS_ENABLED(CONFIG_PROC_STRIPPED) &&
-+                      !proc_create_seq("softnet_stat", 0444, net->proc_net,
-                        &softnet_seq_ops))
-               goto out_dev;
--      if (!proc_create_net("ptype", 0444, net->proc_net, &ptype_seq_ops,
-+      if (!IS_ENABLED(CONFIG_PROC_STRIPPED) &&
-+                      !proc_create_net("ptype", 0444, net->proc_net, &ptype_seq_ops,
-                       sizeof(struct seq_net_private)))
-               goto out_softnet;
-@@ -330,9 +332,11 @@ static int __net_init dev_proc_net_init(
- out:
-       return rc;
- out_ptype:
--      remove_proc_entry("ptype", net->proc_net);
-+      if (!IS_ENABLED(CONFIG_PROC_STRIPPED))
-+              remove_proc_entry("ptype", net->proc_net);
- out_softnet:
--      remove_proc_entry("softnet_stat", net->proc_net);
-+      if (!IS_ENABLED(CONFIG_PROC_STRIPPED))
-+              remove_proc_entry("softnet_stat", net->proc_net);
- out_dev:
-       remove_proc_entry("dev", net->proc_net);
-       goto out;
-@@ -342,8 +346,10 @@ static void __net_exit dev_proc_net_exit
- {
-       wext_proc_exit(net);
--      remove_proc_entry("ptype", net->proc_net);
--      remove_proc_entry("softnet_stat", net->proc_net);
-+      if (!IS_ENABLED(CONFIG_PROC_STRIPPED)) {
-+              remove_proc_entry("ptype", net->proc_net);
-+              remove_proc_entry("softnet_stat", net->proc_net);
-+      }
-       remove_proc_entry("dev", net->proc_net);
- }
---- a/net/core/sock.c
-+++ b/net/core/sock.c
-@@ -3900,6 +3900,8 @@ static __net_initdata struct pernet_oper
- static int __init proto_init(void)
- {
-+      if (IS_ENABLED(CONFIG_PROC_STRIPPED))
-+              return 0;
-       return register_pernet_subsys(&proto_net_ops);
- }
---- a/net/ipv4/fib_trie.c
-+++ b/net/ipv4/fib_trie.c
-@@ -3029,11 +3029,13 @@ static const struct seq_operations fib_r
- int __net_init fib_proc_init(struct net *net)
- {
--      if (!proc_create_net("fib_trie", 0444, net->proc_net, &fib_trie_seq_ops,
-+      if (!IS_ENABLED(CONFIG_PROC_STRIPPED) &&
-+                      !proc_create_net("fib_trie", 0444, net->proc_net, &fib_trie_seq_ops,
-                       sizeof(struct fib_trie_iter)))
-               goto out1;
--      if (!proc_create_net_single("fib_triestat", 0444, net->proc_net,
-+      if (!IS_ENABLED(CONFIG_PROC_STRIPPED) &&
-+                      !proc_create_net_single("fib_triestat", 0444, net->proc_net,
-                       fib_triestat_seq_show, NULL))
-               goto out2;
-@@ -3044,17 +3046,21 @@ int __net_init fib_proc_init(struct net
-       return 0;
- out3:
--      remove_proc_entry("fib_triestat", net->proc_net);
-+      if (!IS_ENABLED(CONFIG_PROC_STRIPPED))
-+              remove_proc_entry("fib_triestat", net->proc_net);
- out2:
--      remove_proc_entry("fib_trie", net->proc_net);
-+      if (!IS_ENABLED(CONFIG_PROC_STRIPPED))
-+              remove_proc_entry("fib_trie", net->proc_net);
- out1:
-       return -ENOMEM;
- }
- void __net_exit fib_proc_exit(struct net *net)
- {
--      remove_proc_entry("fib_trie", net->proc_net);
--      remove_proc_entry("fib_triestat", net->proc_net);
-+      if (!IS_ENABLED(CONFIG_PROC_STRIPPED)) {
-+              remove_proc_entry("fib_trie", net->proc_net);
-+              remove_proc_entry("fib_triestat", net->proc_net);
-+      }
-       remove_proc_entry("route", net->proc_net);
- }
---- a/net/ipv4/proc.c
-+++ b/net/ipv4/proc.c
-@@ -553,5 +553,8 @@ static __net_initdata struct pernet_oper
- int __init ip_misc_proc_init(void)
- {
-+      if (IS_ENABLED(CONFIG_PROC_STRIPPED))
-+              return 0;
-+
-       return register_pernet_subsys(&ip_proc_ops);
- }
---- a/net/ipv4/route.c
-+++ b/net/ipv4/route.c
-@@ -388,6 +388,9 @@ static struct pernet_operations ip_rt_pr
- static int __init ip_rt_proc_init(void)
- {
-+      if (IS_ENABLED(CONFIG_PROC_STRIPPED))
-+              return 0;
-+
-       return register_pernet_subsys(&ip_rt_proc_ops);
- }
diff --git a/target/linux/generic/hack-5.15/904-debloat_dma_buf.patch b/target/linux/generic/hack-5.15/904-debloat_dma_buf.patch
deleted file mode 100644 (file)
index 71546bf..0000000
+++ /dev/null
@@ -1,92 +0,0 @@
-From e3692cb2fcd5ba1244512a0f43b8118f65f1c375 Mon Sep 17 00:00:00 2001
-From: Felix Fietkau <[email protected]>
-Date: Sat, 8 Jul 2017 08:20:43 +0200
-Subject: debloat: dmabuf
-
-Signed-off-by: Felix Fietkau <[email protected]>
----
- drivers/base/Kconfig      |  2 +-
- drivers/dma-buf/Makefile  | 10 +++++++---
- drivers/dma-buf/dma-buf.c |  4 +++-
- kernel/sched/core.c       |  1 +
- 4 files changed, 12 insertions(+), 5 deletions(-)
-
---- a/drivers/base/Kconfig
-+++ b/drivers/base/Kconfig
-@@ -187,7 +187,7 @@ config SOC_BUS
- source "drivers/base/regmap/Kconfig"
- config DMA_SHARED_BUFFER
--      bool
-+      tristate
-       default n
-       select IRQ_WORK
-       help
---- a/drivers/dma-buf/heaps/Makefile
-+++ b/drivers/dma-buf/heaps/Makefile
-@@ -1,3 +1,3 @@
- # SPDX-License-Identifier: GPL-2.0
--obj-$(CONFIG_DMABUF_HEAPS_SYSTEM)     += system_heap.o
--obj-$(CONFIG_DMABUF_HEAPS_CMA)                += cma_heap.o
-+dma-buf-objs-$(CONFIG_DMABUF_HEAPS_SYSTEM)    += system_heap.o
-+dma-buf-objs-$(CONFIG_DMABUF_HEAPS_CMA)               += cma_heap.o
---- a/drivers/dma-buf/Makefile
-+++ b/drivers/dma-buf/Makefile
-@@ -1,16 +1,20 @@
- # SPDX-License-Identifier: GPL-2.0-only
--obj-y := dma-buf.o dma-fence.o dma-fence-array.o dma-fence-chain.o \
-+obj-$(CONFIG_DMA_SHARED_BUFFER) := dma-shared-buffer.o
-+
-+dma-buf-objs-y := dma-buf.o dma-fence.o dma-fence-array.o dma-fence-chain.o \
-        dma-resv.o seqno-fence.o
--obj-$(CONFIG_DMABUF_HEAPS)    += dma-heap.o
--obj-$(CONFIG_DMABUF_HEAPS)    += heaps/
--obj-$(CONFIG_SYNC_FILE)               += sync_file.o
--obj-$(CONFIG_SW_SYNC)         += sw_sync.o sync_debug.o
--obj-$(CONFIG_UDMABUF)         += udmabuf.o
--obj-$(CONFIG_DMABUF_SYSFS_STATS) += dma-buf-sysfs-stats.o
-+dma-buf-objs-$(CONFIG_DMABUF_HEAPS)   += dma-heap.o
-+obj-$(CONFIG_DMABUF_HEAPS)            += heaps/
-+dma-buf-objs-$(CONFIG_SYNC_FILE)      += sync_file.o
-+dma-buf-objs-$(CONFIG_SW_SYNC)                += sw_sync.o sync_debug.o
-+dma-buf-objs-$(CONFIG_UDMABUF)                += udmabuf.o
-+dma-buf-objs-$(CONFIG_DMABUF_SYSFS_STATS) += udmabuf.o
- dmabuf_selftests-y := \
-       selftest.o \
-       st-dma-fence.o \
-       st-dma-fence-chain.o
--obj-$(CONFIG_DMABUF_SELFTESTS)        += dmabuf_selftests.o
-+dma-buf-objs-$(CONFIG_DMABUF_SELFTESTS)       += dmabuf_selftests.o
-+
-+dma-shared-buffer-objs :=  $(dma-buf-objs-y)
---- a/drivers/dma-buf/dma-buf.c
-+++ b/drivers/dma-buf/dma-buf.c
-@@ -1513,4 +1513,5 @@ static void __exit dma_buf_deinit(void)
-       kern_unmount(dma_buf_mnt);
-       dma_buf_uninit_sysfs_statistics();
- }
--__exitcall(dma_buf_deinit);
-+module_exit(dma_buf_deinit);
-+MODULE_LICENSE("GPL");
---- a/kernel/sched/core.c
-+++ b/kernel/sched/core.c
-@@ -4220,6 +4220,7 @@ int wake_up_state(struct task_struct *p,
- {
-       return try_to_wake_up(p, state, 0);
- }
-+EXPORT_SYMBOL_GPL(wake_up_state);
- /*
-  * Perform scheduler related setup for a newly forked process p.
---- a/fs/d_path.c
-+++ b/fs/d_path.c
-@@ -316,6 +316,7 @@ char *dynamic_dname(struct dentry *dentr
-       buffer += buflen - sz;
-       return memcpy(buffer, temp, sz);
- }
-+EXPORT_SYMBOL_GPL(dynamic_dname);
- char *simple_dname(struct dentry *dentry, char *buffer, int buflen)
- {
diff --git a/target/linux/generic/hack-5.15/910-kobject_uevent.patch b/target/linux/generic/hack-5.15/910-kobject_uevent.patch
deleted file mode 100644 (file)
index c4c41ca..0000000
+++ /dev/null
@@ -1,32 +0,0 @@
-From 0d37e6edc09c99e683dd91ca0e83bbc0df8477b3 Mon Sep 17 00:00:00 2001
-From: Felix Fietkau <[email protected]>
-Date: Sun, 16 Jul 2017 16:56:10 +0200
-Subject: lib: add uevent_next_seqnum()
-
-Signed-off-by: Felix Fietkau <[email protected]>
----
- include/linux/kobject.h |  5 +++++
- lib/kobject_uevent.c    | 37 +++++++++++++++++++++++++++++++++++++
- 2 files changed, 42 insertions(+)
-
---- a/lib/kobject_uevent.c
-+++ b/lib/kobject_uevent.c
-@@ -179,6 +179,18 @@ out:
-       return r;
- }
-+u64 uevent_next_seqnum(void)
-+{
-+      u64 seq;
-+
-+      mutex_lock(&uevent_sock_mutex);
-+      seq = ++uevent_seqnum;
-+      mutex_unlock(&uevent_sock_mutex);
-+
-+      return seq;
-+}
-+EXPORT_SYMBOL_GPL(uevent_next_seqnum);
-+
- /**
-  * kobject_synth_uevent - send synthetic uevent with arguments
-  *
diff --git a/target/linux/generic/hack-5.15/911-kobject_add_broadcast_uevent.patch b/target/linux/generic/hack-5.15/911-kobject_add_broadcast_uevent.patch
deleted file mode 100644 (file)
index dd93e0b..0000000
+++ /dev/null
@@ -1,76 +0,0 @@
-From 0d37e6edc09c99e683dd91ca0e83bbc0df8477b3 Mon Sep 17 00:00:00 2001
-From: Felix Fietkau <[email protected]>
-Date: Sun, 16 Jul 2017 16:56:10 +0200
-Subject: lib: add broadcast_uevent()
-
-Signed-off-by: Felix Fietkau <[email protected]>
----
- include/linux/kobject.h |  5 +++++
- lib/kobject_uevent.c    | 37 +++++++++++++++++++++++++++++++++++++
- 2 files changed, 42 insertions(+)
-
---- a/include/linux/kobject.h
-+++ b/include/linux/kobject.h
-@@ -32,6 +32,8 @@
- #define UEVENT_NUM_ENVP                       64      /* number of env pointers */
- #define UEVENT_BUFFER_SIZE            2048    /* buffer for the variables */
-+struct sk_buff;
-+
- #ifdef CONFIG_UEVENT_HELPER
- /* path to the userspace helper executed on an event */
- extern char uevent_helper[];
-@@ -244,4 +246,7 @@ int kobject_synth_uevent(struct kobject
- __printf(2, 3)
- int add_uevent_var(struct kobj_uevent_env *env, const char *format, ...);
-+int broadcast_uevent(struct sk_buff *skb, __u32 pid, __u32 group,
-+                   gfp_t allocation);
-+
- #endif /* _KOBJECT_H_ */
---- a/lib/kobject_uevent.c
-+++ b/lib/kobject_uevent.c
-@@ -691,6 +691,43 @@ int add_uevent_var(struct kobj_uevent_en
- EXPORT_SYMBOL_GPL(add_uevent_var);
- #if defined(CONFIG_NET)
-+int broadcast_uevent(struct sk_buff *skb, __u32 pid, __u32 group,
-+                   gfp_t allocation)
-+{
-+      struct uevent_sock *ue_sk;
-+      int err = 0;
-+
-+      /* send netlink message */
-+      mutex_lock(&uevent_sock_mutex);
-+      list_for_each_entry(ue_sk, &uevent_sock_list, list) {
-+              struct sock *uevent_sock = ue_sk->sk;
-+              struct sk_buff *skb2;
-+
-+              skb2 = skb_clone(skb, allocation);
-+              if (!skb2)
-+                      break;
-+
-+              err = netlink_broadcast(uevent_sock, skb2, pid, group,
-+                                      allocation);
-+              if (err)
-+                      break;
-+      }
-+      mutex_unlock(&uevent_sock_mutex);
-+
-+      kfree_skb(skb);
-+      return err;
-+}
-+#else
-+int broadcast_uevent(struct sk_buff *skb, __u32 pid, __u32 group,
-+                   gfp_t allocation)
-+{
-+      kfree_skb(skb);
-+      return 0;
-+}
-+#endif
-+EXPORT_SYMBOL_GPL(broadcast_uevent);
-+
-+#if defined(CONFIG_NET)
- static int uevent_net_broadcast(struct sock *usk, struct sk_buff *skb,
-                               struct netlink_ext_ack *extack)
- {
diff --git a/target/linux/generic/hack-5.15/920-device_tree_cmdline.patch b/target/linux/generic/hack-5.15/920-device_tree_cmdline.patch
deleted file mode 100644 (file)
index d1f36e7..0000000
+++ /dev/null
@@ -1,21 +0,0 @@
-From e08bcbbaa52fcc41f02743fd2e62a33255ce52da Mon Sep 17 00:00:00 2001
-From: OpenWrt community <[email protected]>
-Date: Wed, 13 Jul 2022 13:52:28 +0200
-Subject: [PATCH] of/ftd: add device tree cmdline
-
----
- drivers/of/fdt.c | 3 +++
- 1 file changed, 3 insertions(+)
-
---- a/drivers/of/fdt.c
-+++ b/drivers/of/fdt.c
-@@ -1158,6 +1158,9 @@ int __init early_init_dt_scan_chosen(uns
-       p = of_get_flat_dt_prop(node, "bootargs", &l);
-       if (p != NULL && l > 0)
-               strlcpy(data, p, min(l, COMMAND_LINE_SIZE));
-+      p = of_get_flat_dt_prop(node, "bootargs-append", &l);
-+      if (p != NULL && l > 0)
-+              strlcat(data, p, min_t(int, strlen(data) + (int)l, COMMAND_LINE_SIZE));
-       /*
-        * CONFIG_CMDLINE is meant to be a default in case nothing else
diff --git a/target/linux/generic/hack-5.15/930-Revert-Revert-Revert-driver-core-Set-fw_devlink-on-b.patch b/target/linux/generic/hack-5.15/930-Revert-Revert-Revert-driver-core-Set-fw_devlink-on-b.patch
deleted file mode 100644 (file)
index b4339e8..0000000
+++ /dev/null
@@ -1,30 +0,0 @@
-From: =?UTF-8?q?Rafa=C5=82=20Mi=C5=82ecki?= <[email protected]>
-Date: Tue, 19 Jul 2022 06:17:48 +0200
-Subject: [PATCH] Revert "Revert "Revert "driver core: Set fw_devlink=on by
- default"""
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-This reverts commit ea718c699055c8566eb64432388a04974c43b2ea.
-
-With of_platform_populate() called for MTD partitions that commit breaks
-probing devices which reference MTD in device tree.
-
-Link: https://lore.kernel.org/all/[email protected]/T/#u
-Signed-off-by: Rafał Miłecki <[email protected]>
----
- drivers/base/core.c | 2 +-
- 1 file changed, 1 insertion(+), 1 deletion(-)
-
---- a/drivers/base/core.c
-+++ b/drivers/base/core.c
-@@ -1577,7 +1577,7 @@ static void device_links_purge(struct de
- #define FW_DEVLINK_FLAGS_RPM          (FW_DEVLINK_FLAGS_ON | \
-                                        DL_FLAG_PM_RUNTIME)
--static u32 fw_devlink_flags = FW_DEVLINK_FLAGS_ON;
-+static u32 fw_devlink_flags = FW_DEVLINK_FLAGS_PERMISSIVE;
- static int __init fw_devlink_setup(char *arg)
- {
-       if (!arg)
diff --git a/target/linux/generic/pending-5.15/100-compiler.h-only-include-asm-rwonce.h-for-kernel-code.patch b/target/linux/generic/pending-5.15/100-compiler.h-only-include-asm-rwonce.h-for-kernel-code.patch
deleted file mode 100644 (file)
index 22f52c1..0000000
+++ /dev/null
@@ -1,29 +0,0 @@
-From: Felix Fietkau <[email protected]>
-Date: Thu, 22 Oct 2020 22:00:03 +0200
-Subject: [PATCH] compiler.h: only include asm/rwonce.h for kernel code
-
-This header file is not in uapi, which makes any user space code that includes
-linux/compiler.h to fail with the error 'asm/rwonce.h: No such file or directory'
-
-Fixes: e506ea451254 ("compiler.h: Split {READ,WRITE}_ONCE definitions out into rwonce.h")
-Signed-off-by: Felix Fietkau <[email protected]>
----
-
---- a/include/linux/compiler.h
-+++ b/include/linux/compiler.h
-@@ -220,6 +220,8 @@ void ftrace_likely_update(struct ftrace_
- #define function_nocfi(x) (x)
- #endif
-+#include <asm/rwonce.h>
-+
- #endif /* __KERNEL__ */
- /*
-@@ -252,6 +254,4 @@ static inline void *offset_to_ptr(const
-  */
- #define prevent_tail_call_optimization()      mb()
--#include <asm/rwonce.h>
--
- #endif /* __LINUX_COMPILER_H */
diff --git a/target/linux/generic/pending-5.15/102-MIPS-only-process-negative-stack-offsets-on-stack-tr.patch b/target/linux/generic/pending-5.15/102-MIPS-only-process-negative-stack-offsets-on-stack-tr.patch
deleted file mode 100644 (file)
index 95a9656..0000000
+++ /dev/null
@@ -1,57 +0,0 @@
-From: Felix Fietkau <[email protected]>
-Date: Wed, 18 Apr 2018 10:50:05 +0200
-Subject: [PATCH] MIPS: only process negative stack offsets on stack traces
-
-Fixes endless back traces in cases where the compiler emits a stack
-pointer increase in a branch delay slot (probably for some form of
-function return).
-
-[    3.475442] BUG: MAX_STACK_TRACE_ENTRIES too low!
-[    3.480070] turning off the locking correctness validator.
-[    3.485521] CPU: 0 PID: 1 Comm: swapper/0 Not tainted 4.14.34 #0
-[    3.491475] Stack : 00000000 00000000 00000000 00000000 80e0fce2 00000034 00000000 00000000
-[    3.499764]         87c3838c 80696377 8061047c 00000000 00000001 00000001 87c2d850 6534689f
-[    3.508059]         00000000 00000000 80e10000 00000000 00000000 000000cf 0000000f 00000000
-[    3.516353]         00000000 806a0000 00076891 00000000 00000000 00000000 ffffffff 00000000
-[    3.524648]         806c0000 00000004 80e10000 806a0000 00000003 80690000 00000000 80700000
-[    3.532942]         ...
-[    3.535362] Call Trace:
-[    3.537818] [<80010a48>] show_stack+0x58/0x100
-[    3.542207] [<804c2f78>] dump_stack+0xe8/0x170
-[    3.546613] [<80079f90>] save_trace+0xf0/0x110
-[    3.551010] [<8007b1ec>] mark_lock+0x33c/0x78c
-[    3.555413] [<8007bf48>] __lock_acquire+0x2ac/0x1a08
-[    3.560337] [<8007de60>] lock_acquire+0x64/0x8c
-[    3.564846] [<804e1570>] _raw_spin_lock_irqsave+0x54/0x78
-[    3.570186] [<801b618c>] kernfs_notify+0x94/0xac
-[    3.574770] [<801b7b10>] sysfs_notify+0x74/0xa0
-[    3.579257] [<801b618c>] kernfs_notify+0x94/0xac
-[    3.583839] [<801b7b10>] sysfs_notify+0x74/0xa0
-[    3.588329] [<801b618c>] kernfs_notify+0x94/0xac
-[    3.592911] [<801b7b10>] sysfs_notify+0x74/0xa0
-[    3.597401] [<801b618c>] kernfs_notify+0x94/0xac
-[    3.601983] [<801b7b10>] sysfs_notify+0x74/0xa0
-[    3.606473] [<801b618c>] kernfs_notify+0x94/0xac
-[    3.611055] [<801b7b10>] sysfs_notify+0x74/0xa0
-[    3.615545] [<801b618c>] kernfs_notify+0x94/0xac
-[    3.620125] [<801b7b10>] sysfs_notify+0x74/0xa0
-[    3.624619] [<801b618c>] kernfs_notify+0x94/0xac
-[    3.629197] [<801b7b10>] sysfs_notify+0x74/0xa0
-[    3.633691] [<801b618c>] kernfs_notify+0x94/0xac
-[    3.638269] [<801b7b10>] sysfs_notify+0x74/0xa0
-[    3.642763] [<801b618c>] kernfs_notify+0x94/0xac
-
-Signed-off-by: Felix Fietkau <[email protected]>
----
-
---- a/arch/mips/kernel/process.c
-+++ b/arch/mips/kernel/process.c
-@@ -393,6 +393,8 @@ static inline int is_sp_move_ins(union m
-       if (ip->i_format.opcode == addiu_op ||
-           ip->i_format.opcode == daddiu_op) {
-+              if (ip->i_format.simmediate > 0)
-+                      return 0;
-               *frame_size = -ip->i_format.simmediate;
-               return 1;
-       }
diff --git a/target/linux/generic/pending-5.15/103-kbuild-export-SUBARCH.patch b/target/linux/generic/pending-5.15/103-kbuild-export-SUBARCH.patch
deleted file mode 100644 (file)
index 120b6e4..0000000
+++ /dev/null
@@ -1,21 +0,0 @@
-From 173019b66dcc9d68ad9333aa744dad1e369b5aa8 Mon Sep 17 00:00:00 2001
-From: Felix Fietkau <[email protected]>
-Date: Sun, 9 Jul 2017 00:26:53 +0200
-Subject: [PATCH 34/34] kernel: add compile fix for linux 4.9 on x86
-
-Signed-off-by: Felix Fietkau <[email protected]>
----
- Makefile | 4 ++--
- 1 file changed, 2 insertions(+), 2 deletions(-)
-
---- a/Makefile
-+++ b/Makefile
-@@ -534,7 +534,7 @@ KBUILD_LDFLAGS_MODULE :=
- KBUILD_LDFLAGS :=
- CLANG_FLAGS :=
--export ARCH SRCARCH CONFIG_SHELL BASH HOSTCC KBUILD_HOSTCFLAGS CROSS_COMPILE LD CC HOSTPKG_CONFIG
-+export ARCH SRCARCH SUBARCH CONFIG_SHELL BASH HOSTCC KBUILD_HOSTCFLAGS CROSS_COMPILE LD CC HOSTPKG_CONFIG
- export CPP AR NM STRIP OBJCOPY OBJDUMP READELF PAHOLE RESOLVE_BTFIDS LEX YACC AWK INSTALLKERNEL
- export PERL PYTHON3 CHECK CHECKFLAGS MAKE UTS_MACHINE HOSTCXX
- export KGZIP KBZIP2 KLZOP LZMA LZ4 XZ ZSTD
diff --git a/target/linux/generic/pending-5.15/111-watchdog-max63xx_wdt-Add-support-for-specifying-WDI-.patch b/target/linux/generic/pending-5.15/111-watchdog-max63xx_wdt-Add-support-for-specifying-WDI-.patch
deleted file mode 100644 (file)
index d6b1049..0000000
+++ /dev/null
@@ -1,75 +0,0 @@
-From bd1b9f66d5134e518419f4c4dacf1884c1616983 Mon Sep 17 00:00:00 2001
-From: =?UTF-8?q?Pali=20Roh=C3=A1r?= <[email protected]>
-Date: Thu, 28 Apr 2022 11:13:23 +0200
-Subject: [PATCH] watchdog: max63xx_wdt: Add support for specifying WDI logic
- via GPIO
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-On some boards is WDI logic of max6370 chip connected via GPIO.
-So extend max63xx_wdt driver to allow specifying WDI logic via GPIO.
-
-Signed-off-by: Pali Rohár <[email protected]>
----
- drivers/watchdog/max63xx_wdt.c | 24 ++++++++++++++++++++++++
- 1 file changed, 24 insertions(+)
-
---- a/drivers/watchdog/max63xx_wdt.c
-+++ b/drivers/watchdog/max63xx_wdt.c
-@@ -27,6 +27,7 @@
- #include <linux/io.h>
- #include <linux/slab.h>
- #include <linux/property.h>
-+#include <linux/gpio/consumer.h>
- #define DEFAULT_HEARTBEAT 60
- #define MAX_HEARTBEAT     60
-@@ -53,6 +54,9 @@ struct max63xx_wdt {
-       void __iomem *base;
-       spinlock_t lock;
-+      /* GPIOs */
-+      struct gpio_desc *gpio_wdi;
-+
-       /* WDI and WSET bits write access routines */
-       void (*ping)(struct max63xx_wdt *wdt);
-       void (*set)(struct max63xx_wdt *wdt, u8 set);
-@@ -158,6 +162,17 @@ static const struct watchdog_info max63x
-       .identity = "max63xx Watchdog",
- };
-+static void max63xx_gpio_ping(struct max63xx_wdt *wdt)
-+{
-+      spin_lock(&wdt->lock);
-+
-+      gpiod_set_value(wdt->gpio_wdi, 1);
-+      udelay(1);
-+      gpiod_set_value(wdt->gpio_wdi, 0);
-+
-+      spin_unlock(&wdt->lock);
-+}
-+
- static void max63xx_mmap_ping(struct max63xx_wdt *wdt)
- {
-       u8 val;
-@@ -225,10 +240,19 @@ static int max63xx_wdt_probe(struct plat
-               return -EINVAL;
-       }
-+      wdt->gpio_wdi = devm_gpiod_get(dev, NULL, GPIOD_FLAGS_BIT_DIR_OUT);
-+      if (IS_ERR(wdt->gpio_wdi) && PTR_ERR(wdt->gpio_wdi) != -ENOENT)
-+              return dev_err_probe(dev, PTR_ERR(wdt->gpio_wdi),
-+                                   "unable to request gpio: %ld\n",
-+                                   PTR_ERR(wdt->gpio_wdi));
-+
-       err = max63xx_mmap_init(pdev, wdt);
-       if (err)
-               return err;
-+      if (!IS_ERR(wdt->gpio_wdi))
-+              wdt->ping = max63xx_gpio_ping;
-+
-       platform_set_drvdata(pdev, &wdt->wdd);
-       watchdog_set_drvdata(&wdt->wdd, wdt);
diff --git a/target/linux/generic/pending-5.15/120-Fix-alloc_node_mem_map-with-ARCH_PFN_OFFSET-calcu.patch b/target/linux/generic/pending-5.15/120-Fix-alloc_node_mem_map-with-ARCH_PFN_OFFSET-calcu.patch
deleted file mode 100644 (file)
index 42f5a8c..0000000
+++ /dev/null
@@ -1,82 +0,0 @@
-From: Tobias Wolf <[email protected]>
-Subject: mm: Fix alloc_node_mem_map with ARCH_PFN_OFFSET calculation
-
-An rt288x (ralink) based router (Belkin F5D8235 v1) does not boot with any
-kernel beyond version 4.3 resulting in:
-
-BUG: Bad page state in process swapper  pfn:086ac
-
-bisect resulted in:
-
-a1c34a3bf00af2cede839879502e12dc68491ad5 is the first bad commit
-commit a1c34a3bf00af2cede839879502e12dc68491ad5
-Author: Laura Abbott <[email protected]>
-Date:   Thu Nov 5 18:48:46 2015 -0800
-
-    mm: Don't offset memmap for flatmem
-
-    Srinivas Kandagatla reported bad page messages when trying to remove the
-    bottom 2MB on an ARM based IFC6410 board
-
-      BUG: Bad page state in process swapper  pfn:fffa8
-      page:ef7fb500 count:0 mapcount:0 mapping:  (null) index:0x0
-      flags: 0x96640253(locked|error|dirty|active|arch_1|reclaim|mlocked)
-      page dumped because: PAGE_FLAGS_CHECK_AT_FREE flag(s) set
-      bad because of flags:
-      flags: 0x200041(locked|active|mlocked)
-      Modules linked in:
-      CPU: 0 PID: 0 Comm: swapper Not tainted 3.19.0-rc3-00007-g412f9ba-dirty
-#816
-      Hardware name: Qualcomm (Flattened Device Tree)
-        unwind_backtrace
-        show_stack
-        dump_stack
-        bad_page
-        free_pages_prepare
-        free_hot_cold_page
-        __free_pages
-        free_highmem_page
-        mem_init
-        start_kernel
-      Disabling lock debugging due to kernel taint
-    [...]
-:040000 040000 2de013c372345fd471cd58f0553c9b38b0ef1cc4
-0a8156f848733dfa21e16c196dfb6c0a76290709 M      mm
-
-This fix for ARM does not account ARCH_PFN_OFFSET for mem_map as later used by
-page_to_pfn anymore.
-
-The following output was generated with two hacked in printk statements:
-
-printk("before %p vs. %p or %p\n", mem_map, mem_map - offset, mem_map -
-(pgdat->node_start_pfn - ARCH_PFN_OFFSET));
-               if (page_to_pfn(mem_map) != pgdat->node_start_pfn)
-                       mem_map -= offset + (pgdat->node_start_pfn - ARCH_PFN_OFFSET);
-printk("after %p\n", mem_map);
-
-Output:
-
-[    0.000000] before 8861b280 vs. 8861b280 or 8851b280
-[    0.000000] after 8851b280
-
-As seen in the first line mem_map with subtraction of offset does not equal the
-mem_map after subtraction of ARCH_PFN_OFFSET.
-
-After adding the offset of ARCH_PFN_OFFSET as well to mem_map as the
-previously calculated offset is zero for the named platform it is able to boot
-4.4 and 4.9-rc7 again.
-
-Signed-off-by: Tobias Wolf <[email protected]>
----
-
---- a/mm/page_alloc.c
-+++ b/mm/page_alloc.c
-@@ -7622,7 +7622,7 @@ static void __init alloc_node_mem_map(st
-       if (pgdat == NODE_DATA(0)) {
-               mem_map = NODE_DATA(0)->node_mem_map;
-               if (page_to_pfn(mem_map) != pgdat->node_start_pfn)
--                      mem_map -= offset;
-+                      mem_map -= offset + (pgdat->node_start_pfn - ARCH_PFN_OFFSET);
-       }
- #endif
- }
diff --git a/target/linux/generic/pending-5.15/140-jffs2-use-.rename2-and-add-RENAME_WHITEOUT-support.patch b/target/linux/generic/pending-5.15/140-jffs2-use-.rename2-and-add-RENAME_WHITEOUT-support.patch
deleted file mode 100644 (file)
index 8f40ae3..0000000
+++ /dev/null
@@ -1,81 +0,0 @@
-From: Felix Fietkau <[email protected]>
-Subject: jffs2: use .rename2 and add RENAME_WHITEOUT support
-
-It is required for renames on overlayfs
-
-Signed-off-by: Felix Fietkau <[email protected]>
----
-
---- a/fs/jffs2/dir.c
-+++ b/fs/jffs2/dir.c
-@@ -614,8 +614,8 @@ static int jffs2_rmdir (struct inode *di
-       return ret;
- }
--static int jffs2_mknod (struct user_namespace *mnt_userns, struct inode *dir_i,
--                      struct dentry *dentry, umode_t mode, dev_t rdev)
-+static int __jffs2_mknod (struct user_namespace *mnt_userns, struct inode *dir_i,
-+                        struct dentry *dentry, umode_t mode, dev_t rdev, bool whiteout)
- {
-       struct jffs2_inode_info *f, *dir_f;
-       struct jffs2_sb_info *c;
-@@ -754,7 +754,11 @@ static int jffs2_mknod (struct user_name
-       mutex_unlock(&dir_f->sem);
-       jffs2_complete_reservation(c);
--      d_instantiate_new(dentry, inode);
-+      if (!whiteout)
-+              d_instantiate_new(dentry, inode);
-+      else
-+              unlock_new_inode(inode);
-+
-       return 0;
-  fail:
-@@ -762,6 +766,19 @@ static int jffs2_mknod (struct user_name
-       return ret;
- }
-+static int jffs2_mknod (struct user_namespace *mnt_userns, struct inode *dir_i,
-+                        struct dentry *dentry, umode_t mode, dev_t rdev)
-+{
-+      return __jffs2_mknod(mnt_userns, dir_i, dentry, mode, rdev, false);
-+}
-+
-+static int jffs2_whiteout (struct user_namespace *mnt_userns, struct inode *old_dir,
-+                          struct dentry *old_dentry)
-+{
-+      return __jffs2_mknod(mnt_userns, old_dir, old_dentry, S_IFCHR | WHITEOUT_MODE,
-+                           WHITEOUT_DEV, true);
-+}
-+
- static int jffs2_rename (struct user_namespace *mnt_userns,
-                        struct inode *old_dir_i, struct dentry *old_dentry,
-                        struct inode *new_dir_i, struct dentry *new_dentry,
-@@ -773,7 +790,7 @@ static int jffs2_rename (struct user_nam
-       uint8_t type;
-       uint32_t now;
--      if (flags & ~RENAME_NOREPLACE)
-+      if (flags & ~(RENAME_NOREPLACE|RENAME_WHITEOUT))
-               return -EINVAL;
-       /* The VFS will check for us and prevent trying to rename a
-@@ -839,9 +856,14 @@ static int jffs2_rename (struct user_nam
-       if (d_is_dir(old_dentry) && !victim_f)
-               inc_nlink(new_dir_i);
--      /* Unlink the original */
--      ret = jffs2_do_unlink(c, JFFS2_INODE_INFO(old_dir_i),
--                            old_dentry->d_name.name, old_dentry->d_name.len, NULL, now);
-+      if (flags & RENAME_WHITEOUT)
-+              /* Replace with whiteout */
-+              ret = jffs2_whiteout(mnt_userns, old_dir_i, old_dentry);
-+      else
-+              /* Unlink the original */
-+              ret = jffs2_do_unlink(c, JFFS2_INODE_INFO(old_dir_i),
-+                                    old_dentry->d_name.name,
-+                                    old_dentry->d_name.len, NULL, now);
-       /* We don't touch inode->i_nlink */
diff --git a/target/linux/generic/pending-5.15/141-jffs2-add-RENAME_EXCHANGE-support.patch b/target/linux/generic/pending-5.15/141-jffs2-add-RENAME_EXCHANGE-support.patch
deleted file mode 100644 (file)
index f58fc79..0000000
+++ /dev/null
@@ -1,73 +0,0 @@
-From: Felix Fietkau <[email protected]>
-Subject: jffs2: add RENAME_EXCHANGE support
-
-Signed-off-by: Felix Fietkau <[email protected]>
----
-
---- a/fs/jffs2/dir.c
-+++ b/fs/jffs2/dir.c
-@@ -787,18 +787,31 @@ static int jffs2_rename (struct user_nam
-       int ret;
-       struct jffs2_sb_info *c = JFFS2_SB_INFO(old_dir_i->i_sb);
-       struct jffs2_inode_info *victim_f = NULL;
-+      struct inode *fst_inode = d_inode(old_dentry);
-+      struct inode *snd_inode = d_inode(new_dentry);
-       uint8_t type;
-       uint32_t now;
--      if (flags & ~(RENAME_NOREPLACE|RENAME_WHITEOUT))
-+      if (flags & ~(RENAME_NOREPLACE|RENAME_WHITEOUT|RENAME_EXCHANGE))
-               return -EINVAL;
-+      if ((flags & RENAME_EXCHANGE) && (old_dir_i != new_dir_i)) {
-+              if (S_ISDIR(fst_inode->i_mode) && !S_ISDIR(snd_inode->i_mode)) {
-+                      inc_nlink(new_dir_i);
-+                      drop_nlink(old_dir_i);
-+              }
-+              else if (!S_ISDIR(fst_inode->i_mode) && S_ISDIR(snd_inode->i_mode)) {
-+                      drop_nlink(new_dir_i);
-+                      inc_nlink(old_dir_i);
-+              }
-+      }
-+
-       /* The VFS will check for us and prevent trying to rename a
-        * file over a directory and vice versa, but if it's a directory,
-        * the VFS can't check whether the victim is empty. The filesystem
-        * needs to do that for itself.
-        */
--      if (d_really_is_positive(new_dentry)) {
-+      if (d_really_is_positive(new_dentry) && !(flags & RENAME_EXCHANGE)) {
-               victim_f = JFFS2_INODE_INFO(d_inode(new_dentry));
-               if (d_is_dir(new_dentry)) {
-                       struct jffs2_full_dirent *fd;
-@@ -833,7 +846,7 @@ static int jffs2_rename (struct user_nam
-       if (ret)
-               return ret;
--      if (victim_f) {
-+      if (victim_f && !(flags & RENAME_EXCHANGE)) {
-               /* There was a victim. Kill it off nicely */
-               if (d_is_dir(new_dentry))
-                       clear_nlink(d_inode(new_dentry));
-@@ -859,6 +872,12 @@ static int jffs2_rename (struct user_nam
-       if (flags & RENAME_WHITEOUT)
-               /* Replace with whiteout */
-               ret = jffs2_whiteout(mnt_userns, old_dir_i, old_dentry);
-+      else if (flags & RENAME_EXCHANGE)
-+              /* Replace the original */
-+              ret = jffs2_do_link(c, JFFS2_INODE_INFO(old_dir_i),
-+                                  d_inode(new_dentry)->i_ino, type,
-+                                  old_dentry->d_name.name, old_dentry->d_name.len,
-+                                  now);
-       else
-               /* Unlink the original */
-               ret = jffs2_do_unlink(c, JFFS2_INODE_INFO(old_dir_i),
-@@ -890,7 +909,7 @@ static int jffs2_rename (struct user_nam
-               return ret;
-       }
--      if (d_is_dir(old_dentry))
-+      if (d_is_dir(old_dentry) && !(flags & RENAME_EXCHANGE))
-               drop_nlink(old_dir_i);
-       new_dir_i->i_mtime = new_dir_i->i_ctime = old_dir_i->i_mtime = old_dir_i->i_ctime = ITIME(now);
diff --git a/target/linux/generic/pending-5.15/142-jffs2-add-splice-ops.patch b/target/linux/generic/pending-5.15/142-jffs2-add-splice-ops.patch
deleted file mode 100644 (file)
index de847a1..0000000
+++ /dev/null
@@ -1,20 +0,0 @@
-From: Felix Fietkau <[email protected]>
-Subject: jffs2: add splice ops
-
-Add splice_read using generic_file_splice_read.
-Add splice_write using iter_file_splice_write
-
-Signed-off-by: Felix Fietkau <[email protected]>
----
-
---- a/fs/jffs2/file.c
-+++ b/fs/jffs2/file.c
-@@ -53,6 +53,8 @@ const struct file_operations jffs2_file_
-       .open =         generic_file_open,
-       .read_iter =    generic_file_read_iter,
-       .write_iter =   generic_file_write_iter,
-+      .splice_read =  generic_file_splice_read,
-+      .splice_write = iter_file_splice_write,
-       .unlocked_ioctl=jffs2_ioctl,
-       .mmap =         generic_file_readonly_mmap,
-       .fsync =        jffs2_fsync,
diff --git a/target/linux/generic/pending-5.15/150-bridge_allow_receiption_on_disabled_port.patch b/target/linux/generic/pending-5.15/150-bridge_allow_receiption_on_disabled_port.patch
deleted file mode 100644 (file)
index a64d302..0000000
+++ /dev/null
@@ -1,45 +0,0 @@
-From: Stephen Hemminger <[email protected]>
-Subject: bridge: allow receiption on disabled port
-
-When an ethernet device is enslaved to a bridge, and the bridge STP
-detects loss of carrier (or operational state down), then normally
-packet receiption is blocked.
-
-This breaks control applications like WPA which maybe expecting to
-receive packets to negotiate to bring link up. The bridge needs to
-block forwarding packets from these disabled ports, but there is no
-hard requirement to not allow local packet delivery.
-
-Signed-off-by: Stephen Hemminger <[email protected]>
-Signed-off-by: Felix Fietkau <[email protected]>
-
---- a/net/bridge/br_input.c
-+++ b/net/bridge/br_input.c
-@@ -209,6 +209,9 @@ static void __br_handle_local_finish(str
- /* note: already called with rcu_read_lock */
- static int br_handle_local_finish(struct net *net, struct sock *sk, struct sk_buff *skb)
- {
-+      struct net_bridge_port *p = br_port_get_rcu(skb->dev);
-+
-+      if (p->state != BR_STATE_DISABLED)
-       __br_handle_local_finish(skb);
-       /* return 1 to signal the okfn() was called so it's ok to use the skb */
-@@ -376,6 +379,17 @@ static rx_handler_result_t br_handle_fra
- forward:
-       switch (p->state) {
-+      case BR_STATE_DISABLED:
-+              if (ether_addr_equal(p->br->dev->dev_addr, dest))
-+                      skb->pkt_type = PACKET_HOST;
-+
-+              if (NF_HOOK(NFPROTO_BRIDGE, NF_BR_PRE_ROUTING,
-+                      dev_net(skb->dev), NULL, skb, skb->dev, NULL,
-+                      br_handle_local_finish) == 1) {
-+                      return RX_HANDLER_PASS;
-+              }
-+              break;
-+
-       case BR_STATE_FORWARDING:
-       case BR_STATE_LEARNING:
-               if (ether_addr_equal(p->br->dev->dev_addr, dest))
diff --git a/target/linux/generic/pending-5.15/151-net-bridge-do-not-send-arp-replies-if-src-and-target.patch b/target/linux/generic/pending-5.15/151-net-bridge-do-not-send-arp-replies-if-src-and-target.patch
deleted file mode 100644 (file)
index f420d21..0000000
+++ /dev/null
@@ -1,37 +0,0 @@
-From: Felix Fietkau <[email protected]>
-Date: Thu, 4 Jan 2024 15:21:21 +0100
-Subject: [PATCH] net: bridge: do not send arp replies if src and target hw
- addr is the same
-
-There are broken devices in the wild that handle duplicate IP address
-detection by sending out ARP requests for the IP that they received from a
-DHCP server and refuse the address if they get a reply.
-When proxyarp is enabled, they would go into a loop of requesting an address
-and then NAKing it again.
-
-Link: https://github.com/openwrt/openwrt/issues/14309
-Signed-off-by: Felix Fietkau <[email protected]>
----
-
---- a/net/bridge/br_arp_nd_proxy.c
-+++ b/net/bridge/br_arp_nd_proxy.c
-@@ -204,7 +204,10 @@ void br_do_proxy_suppress_arp(struct sk_
-                       if ((p && (p->flags & BR_PROXYARP)) ||
-                           (f->dst && (f->dst->flags & (BR_PROXYARP_WIFI |
-                                                        BR_NEIGH_SUPPRESS)))) {
--                              if (!vid)
-+                              replied = true;
-+                              if (!memcmp(n->ha, sha, dev->addr_len))
-+                                      replied = false;
-+                              else if (!vid)
-                                       br_arp_send(br, p, skb->dev, sip, tip,
-                                                   sha, n->ha, sha, 0, 0);
-                               else
-@@ -212,7 +215,6 @@ void br_do_proxy_suppress_arp(struct sk_
-                                                   sha, n->ha, sha,
-                                                   skb->vlan_proto,
-                                                   skb_vlan_tag_get(skb));
--                              replied = true;
-                       }
-                       /* If we have replied or as long as we know the
diff --git a/target/linux/generic/pending-5.15/190-rtc-rs5c372-support_alarms_up_to_1_week.patch b/target/linux/generic/pending-5.15/190-rtc-rs5c372-support_alarms_up_to_1_week.patch
deleted file mode 100644 (file)
index 13b79b5..0000000
+++ /dev/null
@@ -1,94 +0,0 @@
-From: Daniel González Cabanelas <[email protected]>
-Subject: [PATCH 1/2] rtc: rs5c372: support alarms up to 1 week
-
-The Ricoh R2221x, R2223x, RS5C372, RV5C387A chips can handle 1 week
-alarms.
-
-Read the "wday" alarm register and convert it to a date to support up 1
-week in our driver.
-
-Signed-off-by: Daniel González Cabanelas <[email protected]>
----
- drivers/rtc/rtc-rs5c372.c | 48 ++++++++++++++++++++++++++++++++++-----
- 1 file changed, 42 insertions(+), 6 deletions(-)
-
---- a/drivers/rtc/rtc-rs5c372.c
-+++ b/drivers/rtc/rtc-rs5c372.c
-@@ -393,7 +393,9 @@ static int rs5c_read_alarm(struct device
- {
-       struct i2c_client       *client = to_i2c_client(dev);
-       struct rs5c372          *rs5c = i2c_get_clientdata(client);
--      int                     status;
-+      int                     status, wday_offs;
-+      struct rtc_time         rtc;
-+      unsigned long           alarm_secs;
-       status = rs5c_get_regs(rs5c);
-       if (status < 0)
-@@ -403,6 +405,30 @@ static int rs5c_read_alarm(struct device
-       t->time.tm_sec = 0;
-       t->time.tm_min = bcd2bin(rs5c->regs[RS5C_REG_ALARM_A_MIN] & 0x7f);
-       t->time.tm_hour = rs5c_reg2hr(rs5c, rs5c->regs[RS5C_REG_ALARM_A_HOURS]);
-+      t->time.tm_wday = ffs(rs5c->regs[RS5C_REG_ALARM_A_WDAY] & 0x7f) - 1;
-+
-+      /* determine the day, month and year based on alarm wday, taking as a
-+       * reference the current time from the rtc
-+       */
-+      status = rs5c372_rtc_read_time(dev, &rtc);
-+      if (status < 0)
-+              return status;
-+
-+      wday_offs = t->time.tm_wday - rtc.tm_wday;
-+      alarm_secs = mktime64(rtc.tm_year + 1900,
-+                            rtc.tm_mon + 1,
-+                            rtc.tm_mday + wday_offs,
-+                            t->time.tm_hour,
-+                            t->time.tm_min,
-+                            t->time.tm_sec);
-+
-+      if (wday_offs < 0 || (wday_offs == 0 &&
-+                            (t->time.tm_hour < rtc.tm_hour ||
-+                             (t->time.tm_hour == rtc.tm_hour &&
-+                              t->time.tm_min <= rtc.tm_min))))
-+              alarm_secs += 7 * 86400;
-+
-+      rtc_time64_to_tm(alarm_secs, &t->time);
-       /* ... and status */
-       t->enabled = !!(rs5c->regs[RS5C_REG_CTRL1] & RS5C_CTRL1_AALE);
-@@ -417,12 +443,20 @@ static int rs5c_set_alarm(struct device
-       struct rs5c372          *rs5c = i2c_get_clientdata(client);
-       int                     status, addr, i;
-       unsigned char           buf[3];
-+      struct rtc_time         rtc_tm;
-+      unsigned long           rtc_secs, alarm_secs;
--      /* only handle up to 24 hours in the future, like RTC_ALM_SET */
--      if (t->time.tm_mday != -1
--                      || t->time.tm_mon != -1
--                      || t->time.tm_year != -1)
-+      /* chip only can handle alarms up to one week in the future*/
-+      status = rs5c372_rtc_read_time(dev, &rtc_tm);
-+      if (status)
-+              return status;
-+      rtc_secs = rtc_tm_to_time64(&rtc_tm);
-+      alarm_secs = rtc_tm_to_time64(&t->time);
-+      if (alarm_secs >= rtc_secs + 7 * 86400) {
-+              dev_err(dev, "%s: alarm maximum is one week in the future (%d)\n",
-+                      __func__, status);
-               return -EINVAL;
-+      }
-       /* REVISIT: round up tm_sec */
-@@ -443,7 +477,9 @@ static int rs5c_set_alarm(struct device
-       /* set alarm */
-       buf[0] = bin2bcd(t->time.tm_min);
-       buf[1] = rs5c_hr2reg(rs5c, t->time.tm_hour);
--      buf[2] = 0x7f;  /* any/all days */
-+      /* each bit is the day of the week, 0x7f means all days */
-+      buf[2] = (t->time.tm_wday >= 0 && t->time.tm_wday < 7) ?
-+                BIT(t->time.tm_wday) : 0x7f;
-       for (i = 0; i < sizeof(buf); i++) {
-               addr = RS5C_ADDR(RS5C_REG_ALARM_A_MIN + i);
diff --git a/target/linux/generic/pending-5.15/191-rtc-rs5c372-let_the_alarm_to_be_used_as_wakeup_source.patch b/target/linux/generic/pending-5.15/191-rtc-rs5c372-let_the_alarm_to_be_used_as_wakeup_source.patch
deleted file mode 100644 (file)
index 7e9d0e6..0000000
+++ /dev/null
@@ -1,70 +0,0 @@
-From: Daniel González Cabanelas <[email protected]>
-Subject: [PATCH 2/2] rtc: rs5c372: let the alarm to be used as wakeup source
-
-Currently there is no use for the interrupts on the rs5c372 RTC and the
-wakealarm isn't enabled. There are some devices like NASes which use this
-RTC to wake up from the power off state when the INTR pin is activated by
-the alarm clock.
-
-Enable the alarm and let to be used as a wakeup source.
-
-Tested on a Buffalo LS421DE NAS.
-
-Signed-off-by: Daniel González Cabanelas <[email protected]>
----
- drivers/rtc/rtc-rs5c372.c | 16 ++++++++++++++++
- 1 file changed, 16 insertions(+)
-
---- a/drivers/rtc/rtc-rs5c372.c
-+++ b/drivers/rtc/rtc-rs5c372.c
-@@ -654,6 +654,7 @@ static int rs5c372_probe(struct i2c_clie
-       int err = 0;
-       int smbus_mode = 0;
-       struct rs5c372 *rs5c372;
-+      bool rs5c372_can_wakeup_device = false;
-       dev_dbg(&client->dev, "%s\n", __func__);
-@@ -689,6 +690,12 @@ static int rs5c372_probe(struct i2c_clie
-       else
-               rs5c372->type = id->driver_data;
-+#ifdef CONFIG_OF
-+      if(of_property_read_bool(client->dev.of_node,
-+                                            "wakeup-source"))
-+              rs5c372_can_wakeup_device = true;
-+#endif
-+
-       /* we read registers 0x0f then 0x00-0x0f; skip the first one */
-       rs5c372->regs = &rs5c372->buf[1];
-       rs5c372->smbus = smbus_mode;
-@@ -722,6 +729,8 @@ static int rs5c372_probe(struct i2c_clie
-               goto exit;
-       }
-+      rs5c372->has_irq = 1;
-+
-       /* if the oscillator lost power and no other software (like
-        * the bootloader) set it up, do it here.
-        *
-@@ -748,6 +757,10 @@ static int rs5c372_probe(struct i2c_clie
-                       );
-       /* REVISIT use client->irq to register alarm irq ... */
-+      if (rs5c372_can_wakeup_device) {
-+              device_init_wakeup(&client->dev, true);
-+      }
-+
-       rs5c372->rtc = devm_rtc_device_register(&client->dev,
-                                       rs5c372_driver.driver.name,
-                                       &rs5c372_rtc_ops, THIS_MODULE);
-@@ -761,6 +774,9 @@ static int rs5c372_probe(struct i2c_clie
-       if (err)
-               goto exit;
-+      /* the rs5c372 alarm only supports a minute accuracy */
-+      rs5c372->rtc->uie_unsupported = 1;
-+
-       return 0;
- exit:
diff --git a/target/linux/generic/pending-5.15/203-kallsyms_uncompressed.patch b/target/linux/generic/pending-5.15/203-kallsyms_uncompressed.patch
deleted file mode 100644 (file)
index fc4fe6d..0000000
+++ /dev/null
@@ -1,119 +0,0 @@
-From: Felix Fietkau <[email protected]>
-Subject: kernel: add a config option for keeping the kallsyms table uncompressed, saving ~9kb kernel size after lzma on ar71xx
-
-[[email protected]: added to my upstream queue 30.12.2016]
-lede-commit: e0e3509b5ce2ccf93d4d67ea907613f5f7ec2eed
-Signed-off-by: Felix Fietkau <[email protected]>
----
- init/Kconfig            | 11 +++++++++++
- kernel/kallsyms.c       |  8 ++++++++
- scripts/kallsyms.c      | 12 ++++++++++++
- scripts/link-vmlinux.sh |  4 ++++
- 4 files changed, 35 insertions(+)
-
---- a/init/Kconfig
-+++ b/init/Kconfig
-@@ -1447,6 +1447,17 @@ config SYSCTL_ARCH_UNALIGN_ALLOW
-         the unaligned access emulation.
-         see arch/parisc/kernel/unaligned.c for reference
-+config KALLSYMS_UNCOMPRESSED
-+      bool "Keep kallsyms uncompressed"
-+      depends on KALLSYMS
-+      help
-+              Normally kallsyms contains compressed symbols (using a token table),
-+              reducing the uncompressed kernel image size. Keeping the symbol table
-+              uncompressed significantly improves the size of this part in compressed
-+              kernel images.
-+
-+              Say N unless you need compressed kernel images to be small.
-+
- config HAVE_PCSPKR_PLATFORM
-       bool
---- a/kernel/kallsyms.c
-+++ b/kernel/kallsyms.c
-@@ -88,6 +88,11 @@ static unsigned int kallsyms_expand_symb
-        * For every byte on the compressed symbol data, copy the table
-        * entry for that byte.
-        */
-+#ifdef CONFIG_KALLSYMS_UNCOMPRESSED
-+      memcpy(result, data + 1, len - 1);
-+      result += len - 1;
-+      len = 0;
-+#endif
-       while (len) {
-               tptr = &kallsyms_token_table[kallsyms_token_index[*data]];
-               data++;
-@@ -120,6 +125,9 @@ tail:
-  */
- static char kallsyms_get_symbol_type(unsigned int off)
- {
-+#ifdef CONFIG_KALLSYMS_UNCOMPRESSED
-+      return kallsyms_names[off + 1];
-+#endif
-       /*
-        * Get just the first code, look it up in the token table,
-        * and return the first char from this token.
---- a/scripts/kallsyms.c
-+++ b/scripts/kallsyms.c
-@@ -58,6 +58,7 @@ static struct addr_range percpu_range =
- static struct sym_entry **table;
- static unsigned int table_size, table_cnt;
- static int all_symbols;
-+static int uncompressed;
- static int absolute_percpu;
- static int base_relative;
-@@ -509,6 +510,9 @@ static void write_src(void)
-       free(markers);
-+      if (uncompressed)
-+              return;
-+
-       output_label("kallsyms_token_table");
-       off = 0;
-       for (i = 0; i < 256; i++) {
-@@ -560,6 +564,9 @@ static unsigned char *find_token(unsigne
- {
-       int i;
-+      if (uncompressed)
-+              return NULL;
-+
-       for (i = 0; i < len - 1; i++) {
-               if (str[i] == token[0] && str[i+1] == token[1])
-                       return &str[i];
-@@ -632,6 +639,9 @@ static void optimize_result(void)
- {
-       int i, best;
-+      if (uncompressed)
-+              return;
-+
-       /* using the '\0' symbol last allows compress_symbols to use standard
-        * fast string functions */
-       for (i = 255; i >= 0; i--) {
-@@ -796,6 +806,8 @@ int main(int argc, char **argv)
-                               absolute_percpu = 1;
-                       else if (strcmp(argv[i], "--base-relative") == 0)
-                               base_relative = 1;
-+                      else if (strcmp(argv[i], "--uncompressed") == 0)
-+                              uncompressed = 1;
-                       else
-                               usage();
-               }
---- a/scripts/link-vmlinux.sh
-+++ b/scripts/link-vmlinux.sh
-@@ -262,6 +262,10 @@ kallsyms()
-               kallsymopt="${kallsymopt} --base-relative"
-       fi
-+      if [ -n "${CONFIG_KALLSYMS_UNCOMPRESSED}" ]; then
-+              kallsymopt="${kallsymopt} --uncompressed"
-+      fi
-+
-       info KSYMS ${2}
-       ${NM} -n ${1} | scripts/kallsyms ${kallsymopt} > ${2}
- }
diff --git a/target/linux/generic/pending-5.15/205-backtrace_module_info.patch b/target/linux/generic/pending-5.15/205-backtrace_module_info.patch
deleted file mode 100644 (file)
index 6379ce0..0000000
+++ /dev/null
@@ -1,41 +0,0 @@
-From: Felix Fietkau <[email protected]>
-Subject: kernel: when KALLSYMS is disabled, print module address + size for matching backtrace entries
-
-[[email protected]: felix will add this to his upstream queue]
-
-lede-commit 53827cdc824556cda910b23ce5030c363b8f1461
-Signed-off-by: Felix Fietkau <[email protected]>
----
- lib/vsprintf.c | 15 +++++++++++----
- 1 file changed, 11 insertions(+), 4 deletions(-)
-
---- a/lib/vsprintf.c
-+++ b/lib/vsprintf.c
-@@ -1003,8 +1003,10 @@ char *symbol_string(char *buf, char *end
-                   struct printf_spec spec, const char *fmt)
- {
-       unsigned long value;
--#ifdef CONFIG_KALLSYMS
-       char sym[KSYM_SYMBOL_LEN];
-+#ifndef CONFIG_KALLSYMS
-+      struct module *mod;
-+      int len;
- #endif
-       if (fmt[1] == 'R')
-@@ -1025,8 +1027,14 @@ char *symbol_string(char *buf, char *end
-       return string_nocheck(buf, end, sym, spec);
- #else
--      return special_hex_number(buf, end, value, sizeof(void *));
-+      len = snprintf(sym, sizeof(sym), "0x%lx", value);
-+      mod = __module_address(value);
-+      if (mod)
-+              snprintf(sym + len, sizeof(sym) - len, " [%s@%p+0x%x]",
-+                       mod->name, mod->core_layout.base,
-+                       mod->core_layout.size);
- #endif
-+      return string(buf, end, sym, spec);
- }
- static const struct printf_spec default_str_spec = {
diff --git a/target/linux/generic/pending-5.15/240-remove-unsane-filenames-from-deps_initramfs-list.patch b/target/linux/generic/pending-5.15/240-remove-unsane-filenames-from-deps_initramfs-list.patch
deleted file mode 100644 (file)
index 29cfade..0000000
+++ /dev/null
@@ -1,30 +0,0 @@
-From: Gabor Juhos <[email protected]>
-Subject: usr: sanitize deps_initramfs list
-
-If any filename in the intramfs dependency
-list contains a colon, that causes a kernel
-build error like this:
-
-/devel/openwrt/build_dir/linux-ar71xx_generic/linux-3.6.6/usr/Makefile:58: *** multiple target patterns.  Stop.
-make[5]: *** [usr] Error 2
-
-Fix it by removing such filenames from the
-deps_initramfs list.
-
-Signed-off-by: Gabor Juhos <[email protected]>
-Signed-off-by: Felix Fietkau <[email protected]>
----
- usr/Makefile | 8 +++++---
- 1 file changed, 5 insertions(+), 3 deletions(-)
-
---- a/usr/Makefile
-+++ b/usr/Makefile
-@@ -61,6 +61,8 @@ hostprogs := gen_init_cpio
- # The dependency list is generated by gen_initramfs.sh -l
- -include $(obj)/.initramfs_data.cpio.d
-+deps_initramfs := $(foreach v,$(deps_initramfs),$(if $(findstring :,$(v)),,$(v)))
-+
- # do not try to update files included in initramfs
- $(deps_initramfs): ;
diff --git a/target/linux/generic/pending-5.15/261-enable_wilink_platform_without_drivers.patch b/target/linux/generic/pending-5.15/261-enable_wilink_platform_without_drivers.patch
deleted file mode 100644 (file)
index cd31f9d..0000000
+++ /dev/null
@@ -1,20 +0,0 @@
-From: Imre Kaloz <[email protected]>
-Subject: [PATCH] hack: net: wireless: make the wl12xx glue code available with
- compat-wireless, too
-
-Signed-off-by: Imre Kaloz <[email protected]>
----
- drivers/net/wireless/ti/Kconfig | 2 +-
- 1 file changed, 1 insertion(+), 1 deletion(-)
-
---- a/drivers/net/wireless/ti/Kconfig
-+++ b/drivers/net/wireless/ti/Kconfig
-@@ -20,7 +20,7 @@ source "drivers/net/wireless/ti/wlcore/K
- config WILINK_PLATFORM_DATA
-       bool "TI WiLink platform data"
--      depends on WLCORE_SDIO || WL1251_SDIO
-+      depends on WLCORE_SDIO || WL1251_SDIO || ARCH_OMAP2PLUS
-       default y
-       help
-       Small platform data bit needed to pass data to the sdio modules.
diff --git a/target/linux/generic/pending-5.15/270-platform-mikrotik-build-bits.patch b/target/linux/generic/pending-5.15/270-platform-mikrotik-build-bits.patch
deleted file mode 100644 (file)
index 99f83bb..0000000
+++ /dev/null
@@ -1,31 +0,0 @@
-From c2deb5ef01a0ef09088832744cbace9e239a6ee0 Mon Sep 17 00:00:00 2001
-From: =?UTF-8?q?Thibaut=20VAR=C3=88NE?= <[email protected]>
-Date: Sat, 28 Mar 2020 12:11:50 +0100
-Subject: [PATCH] generic: platform/mikrotik build bits (5.4)
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-This patch adds platform/mikrotik kernel build bits
-
-Signed-off-by: Thibaut VARÈNE <[email protected]>
----
- drivers/platform/Kconfig  | 2 ++
- drivers/platform/Makefile | 1 +
- 2 files changed, 3 insertions(+)
-
---- a/drivers/platform/Kconfig
-+++ b/drivers/platform/Kconfig
-@@ -15,3 +15,5 @@ source "drivers/platform/mellanox/Kconfi
- source "drivers/platform/olpc/Kconfig"
- source "drivers/platform/surface/Kconfig"
-+
-+source "drivers/platform/mikrotik/Kconfig"
---- a/drivers/platform/Makefile
-+++ b/drivers/platform/Makefile
-@@ -10,3 +10,4 @@ obj-$(CONFIG_OLPC_EC)                += olpc/
- obj-$(CONFIG_GOLDFISH)                += goldfish/
- obj-$(CONFIG_CHROME_PLATFORMS)        += chrome/
- obj-$(CONFIG_SURFACE_PLATFORMS)       += surface/
-+obj-$(CONFIG_MIKROTIK)                += mikrotik/
diff --git a/target/linux/generic/pending-5.15/300-mips_expose_boot_raw.patch b/target/linux/generic/pending-5.15/300-mips_expose_boot_raw.patch
deleted file mode 100644 (file)
index be4dacf..0000000
+++ /dev/null
@@ -1,40 +0,0 @@
-From: Mark Miller <[email protected]>
-Subject: mips: expose CONFIG_BOOT_RAW
-
-This exposes the CONFIG_BOOT_RAW symbol in Kconfig. This is needed on
-certain Broadcom chipsets running CFE in order to load the kernel.
-
-Signed-off-by: Mark Miller <[email protected]>
-Acked-by: Rob Landley <[email protected]>
----
---- a/arch/mips/Kconfig
-+++ b/arch/mips/Kconfig
-@@ -1103,9 +1103,6 @@ config FW_ARC
- config ARCH_MAY_HAVE_PC_FDC
-       bool
--config BOOT_RAW
--      bool
--
- config CEVT_BCM1480
-       bool
-@@ -3186,6 +3183,18 @@ choice
-               bool "Extend builtin kernel arguments with bootloader arguments"
- endchoice
-+config BOOT_RAW
-+      bool "Enable the kernel to be executed from the load address"
-+      default n
-+      help
-+       Allow the kernel to be executed from the load address for
-+       bootloaders which cannot read the ELF format. This places
-+       a jump to start_kernel at the load address.
-+
-+       If unsure, say N.
-+
-+
-+
- endmenu
- config LOCKDEP_SUPPORT
diff --git a/target/linux/generic/pending-5.15/301-MIPS-Add-barriers-between-dcache-icache-flushes.patch b/target/linux/generic/pending-5.15/301-MIPS-Add-barriers-between-dcache-icache-flushes.patch
deleted file mode 100644 (file)
index 726c884..0000000
+++ /dev/null
@@ -1,71 +0,0 @@
-From e6e6ef4275978823ec3a84133fc91f4ffbef5c84 Mon Sep 17 00:00:00 2001
-From: Paul Burton <[email protected]>
-Date: Mon, 22 Feb 2016 18:09:44 +0000
-Subject: [PATCH] MIPS: Add barriers between dcache & icache flushes
-
-Index-based cache operations may be arbitrarily reordered by out of
-order CPUs. Thus code which writes back the dcache & then invalidates
-the icache using indexed cache ops must include a barrier between
-operating on the 2 caches in order to prevent the scenario in which:
-
-  - icache invalidation occurs.
-
-  - icache fetch occurs, due to speculation.
-
-  - dcache writeback occurs.
-
-If the above were allowed to happen then the icache would contain stale
-data. Forcing the dcache writeback to complete before the icache
-invalidation avoids this.
-
-Signed-off-by: Paul Burton <[email protected]>
-Cc: James Hogan <[email protected]>
----
- arch/mips/mm/c-r4k.c | 13 +++++++++++--
- 1 file changed, 11 insertions(+), 2 deletions(-)
-
---- a/arch/mips/mm/c-r4k.c
-+++ b/arch/mips/mm/c-r4k.c
-@@ -515,6 +515,7 @@ static inline void local_r4k___flush_cac
-       default:
-               r4k_blast_dcache();
-+              mb(); /* cache instructions may be reordered */
-               r4k_blast_icache();
-               break;
-       }
-@@ -595,8 +596,10 @@ static inline void local_r4k_flush_cache
-       if (cpu_has_dc_aliases || (exec && !cpu_has_ic_fills_f_dc))
-               r4k_blast_dcache();
-       /* If executable, blast stale lines from icache */
--      if (exec)
-+      if (exec) {
-+              mb(); /* cache instructions may be reordered */
-               r4k_blast_icache();
-+      }
- }
- static void r4k_flush_cache_range(struct vm_area_struct *vma,
-@@ -697,8 +700,13 @@ static inline void local_r4k_flush_cache
-       if (cpu_has_dc_aliases || (exec && !cpu_has_ic_fills_f_dc)) {
-               vaddr ? r4k_blast_dcache_page(addr) :
-                       r4k_blast_dcache_user_page(addr);
--              if (exec && !cpu_icache_snoops_remote_store)
-+              if (exec)
-+                      mb(); /* cache instructions may be reordered */
-+
-+              if (exec && !cpu_icache_snoops_remote_store) {
-                       r4k_blast_scache_page(addr);
-+                      mb(); /* cache instructions may be reordered */
-+              }
-       }
-       if (exec) {
-               if (vaddr && cpu_has_vtag_icache && mm == current->active_mm) {
-@@ -765,6 +773,7 @@ static inline void __local_r4k_flush_ica
-                       else
-                               blast_dcache_range(start, end);
-               }
-+              mb(); /* cache instructions may be reordered */
-       }
-       if (type == R4K_INDEX ||
diff --git a/target/linux/generic/pending-5.15/302-mips_no_branch_likely.patch b/target/linux/generic/pending-5.15/302-mips_no_branch_likely.patch
deleted file mode 100644 (file)
index 271923f..0000000
+++ /dev/null
@@ -1,22 +0,0 @@
-From: Felix Fietkau <[email protected]>
-Subject: mips: use -mno-branch-likely for kernel and userspace
-
-saves ~11k kernel size after lzma and ~12k squashfs size in the
-
-lede-commit: 41a039f46450ffae9483d6216422098669da2900
-Signed-off-by: Felix Fietkau <[email protected]>
----
- arch/mips/Makefile | 2 +-
- 1 file changed, 1 insertion(+), 1 deletion(-)
-
---- a/arch/mips/Makefile
-+++ b/arch/mips/Makefile
-@@ -95,7 +95,7 @@ all-$(CONFIG_SYS_SUPPORTS_ZBOOT)+= vmlin
- # machines may also.  Since BFD is incredibly buggy with respect to
- # crossformat linking we rely on the elf2ecoff tool for format conversion.
- #
--cflags-y                      += -G 0 -mno-abicalls -fno-pic -pipe
-+cflags-y                      += -G 0 -mno-abicalls -fno-pic -pipe -mno-branch-likely
- cflags-y                      += -msoft-float
- LDFLAGS_vmlinux                       += -G 0 -static -n -nostdlib
- KBUILD_AFLAGS_MODULE          += -mlong-calls
diff --git a/target/linux/generic/pending-5.15/305-mips_module_reloc.patch b/target/linux/generic/pending-5.15/305-mips_module_reloc.patch
deleted file mode 100644 (file)
index bbea1f6..0000000
+++ /dev/null
@@ -1,370 +0,0 @@
-From: Felix Fietkau <[email protected]>
-Subject: mips: replace -mlong-calls with -mno-long-calls to make function calls faster in kernel modules to achieve this, try to
-
-lede-commit: 3b3d64743ba2a874df9d70cd19e242205b0a788c
-Signed-off-by: Felix Fietkau <[email protected]>
----
- arch/mips/Makefile             |   5 +
- arch/mips/include/asm/module.h |   5 +
- arch/mips/kernel/module.c      | 279 ++++++++++++++++++++++++++++++++++++++++-
- 3 files changed, 284 insertions(+), 5 deletions(-)
-
---- a/arch/mips/Makefile
-+++ b/arch/mips/Makefile
-@@ -98,8 +98,18 @@ all-$(CONFIG_SYS_SUPPORTS_ZBOOT)+= vmlin
- cflags-y                      += -G 0 -mno-abicalls -fno-pic -pipe -mno-branch-likely
- cflags-y                      += -msoft-float
- LDFLAGS_vmlinux                       += -G 0 -static -n -nostdlib
-+ifdef CONFIG_64BIT
- KBUILD_AFLAGS_MODULE          += -mlong-calls
- KBUILD_CFLAGS_MODULE          += -mlong-calls
-+else
-+  ifdef CONFIG_DYNAMIC_FTRACE
-+    KBUILD_AFLAGS_MODULE      += -mlong-calls
-+    KBUILD_CFLAGS_MODULE      += -mlong-calls
-+  else
-+    KBUILD_AFLAGS_MODULE      += -mno-long-calls
-+    KBUILD_CFLAGS_MODULE      += -mno-long-calls
-+  endif
-+endif
- ifeq ($(CONFIG_RELOCATABLE),y)
- LDFLAGS_vmlinux                       += --emit-relocs
---- a/arch/mips/include/asm/module.h
-+++ b/arch/mips/include/asm/module.h
-@@ -12,6 +12,11 @@ struct mod_arch_specific {
-       const struct exception_table_entry *dbe_start;
-       const struct exception_table_entry *dbe_end;
-       struct mips_hi16 *r_mips_hi16_list;
-+
-+      void *phys_plt_tbl;
-+      void *virt_plt_tbl;
-+      unsigned int phys_plt_offset;
-+      unsigned int virt_plt_offset;
- };
- typedef uint8_t Elf64_Byte;           /* Type for a 8-bit quantity.  */
---- a/arch/mips/kernel/module.c
-+++ b/arch/mips/kernel/module.c
-@@ -31,23 +31,261 @@ struct mips_hi16 {
- static LIST_HEAD(dbe_list);
- static DEFINE_SPINLOCK(dbe_lock);
--#ifdef MODULE_START
-+/*
-+ * Get the potential max trampolines size required of the init and
-+ * non-init sections. Only used if we cannot find enough contiguous
-+ * physically mapped memory to put the module into.
-+ */
-+static unsigned int
-+get_plt_size(const Elf_Ehdr *hdr, const Elf_Shdr *sechdrs,
-+             const char *secstrings, unsigned int symindex, bool is_init)
-+{
-+      unsigned long ret = 0;
-+      unsigned int i, j;
-+      Elf_Sym *syms;
-+
-+      /* Everything marked ALLOC (this includes the exported symbols) */
-+      for (i = 1; i < hdr->e_shnum; ++i) {
-+              unsigned int info = sechdrs[i].sh_info;
-+
-+              if (sechdrs[i].sh_type != SHT_REL
-+                  && sechdrs[i].sh_type != SHT_RELA)
-+                      continue;
-+
-+              /* Not a valid relocation section? */
-+              if (info >= hdr->e_shnum)
-+                      continue;
-+
-+              /* Don't bother with non-allocated sections */
-+              if (!(sechdrs[info].sh_flags & SHF_ALLOC))
-+                      continue;
-+
-+              /* If it's called *.init*, and we're not init, we're
-+                   not interested */
-+              if ((strstr(secstrings + sechdrs[i].sh_name, ".init") != 0)
-+                  != is_init)
-+                      continue;
-+
-+              syms = (Elf_Sym *) sechdrs[symindex].sh_addr;
-+              if (sechdrs[i].sh_type == SHT_REL) {
-+                      Elf_Mips_Rel *rel = (void *) sechdrs[i].sh_addr;
-+                      unsigned int size = sechdrs[i].sh_size / sizeof(*rel);
-+
-+                      for (j = 0; j < size; ++j) {
-+                              Elf_Sym *sym;
-+
-+                              if (ELF_MIPS_R_TYPE(rel[j]) != R_MIPS_26)
-+                                      continue;
-+
-+                              sym = syms + ELF_MIPS_R_SYM(rel[j]);
-+                              if (!is_init && sym->st_shndx != SHN_UNDEF)
-+                                      continue;
-+
-+                              ret += 4 * sizeof(int);
-+                      }
-+              } else {
-+                      Elf_Mips_Rela *rela = (void *) sechdrs[i].sh_addr;
-+                      unsigned int size = sechdrs[i].sh_size / sizeof(*rela);
-+
-+                      for (j = 0; j < size; ++j) {
-+                              Elf_Sym *sym;
-+
-+                              if (ELF_MIPS_R_TYPE(rela[j]) != R_MIPS_26)
-+                                      continue;
-+
-+                              sym = syms + ELF_MIPS_R_SYM(rela[j]);
-+                              if (!is_init && sym->st_shndx != SHN_UNDEF)
-+                                      continue;
-+
-+                              ret += 4 * sizeof(int);
-+                      }
-+              }
-+      }
-+
-+      return ret;
-+}
-+
-+#ifndef MODULE_START
-+static void *alloc_phys(unsigned long size)
-+{
-+      unsigned order;
-+      struct page *page;
-+      struct page *p;
-+
-+      size = PAGE_ALIGN(size);
-+      order = get_order(size);
-+
-+      page = alloc_pages(GFP_KERNEL | __GFP_NORETRY | __GFP_NOWARN |
-+                      __GFP_THISNODE, order);
-+      if (!page)
-+              return NULL;
-+
-+      split_page(page, order);
-+
-+      /* mark all pages except for the last one */
-+      for (p = page; p + 1 < page + (size >> PAGE_SHIFT); ++p)
-+              set_bit(PG_owner_priv_1, &p->flags);
-+
-+      for (p = page + (size >> PAGE_SHIFT); p < page + (1 << order); ++p)
-+              __free_page(p);
-+
-+      return page_address(page);
-+}
-+#endif
-+
-+static void free_phys(void *ptr)
-+{
-+      struct page *page;
-+      bool free;
-+
-+      page = virt_to_page(ptr);
-+      do {
-+              free = test_and_clear_bit(PG_owner_priv_1, &page->flags);
-+              __free_page(page);
-+              page++;
-+      } while (free);
-+}
-+
-+
- void *module_alloc(unsigned long size)
- {
-+#ifdef MODULE_START
-       return __vmalloc_node_range(size, 1, MODULE_START, MODULE_END,
-                               GFP_KERNEL, PAGE_KERNEL, 0, NUMA_NO_NODE,
-                               __builtin_return_address(0));
-+#else
-+      void *ptr;
-+
-+      if (size == 0)
-+              return NULL;
-+
-+      ptr = alloc_phys(size);
-+
-+      /* If we failed to allocate physically contiguous memory,
-+       * fall back to regular vmalloc. The module loader code will
-+       * create jump tables to handle long jumps */
-+      if (!ptr)
-+              return vmalloc(size);
-+
-+      return ptr;
-+#endif
- }
-+
-+static inline bool is_phys_addr(void *ptr)
-+{
-+#ifdef CONFIG_64BIT
-+      return (KSEGX((unsigned long)ptr) == CKSEG0);
-+#else
-+      return (KSEGX(ptr) == KSEG0);
- #endif
-+}
-+
-+/* Free memory returned from module_alloc */
-+void module_memfree(void *module_region)
-+{
-+      if (is_phys_addr(module_region))
-+              free_phys(module_region);
-+      else
-+              vfree(module_region);
-+}
-+
-+static void *__module_alloc(int size, bool phys)
-+{
-+      void *ptr;
-+
-+      if (phys)
-+              ptr = kmalloc(size, GFP_KERNEL);
-+      else
-+              ptr = vmalloc(size);
-+      return ptr;
-+}
-+
-+static void __module_free(void *ptr)
-+{
-+      if (is_phys_addr(ptr))
-+              kfree(ptr);
-+      else
-+              vfree(ptr);
-+}
-+
-+int module_frob_arch_sections(Elf_Ehdr *hdr, Elf_Shdr *sechdrs,
-+                            char *secstrings, struct module *mod)
-+{
-+      unsigned int symindex = 0;
-+      unsigned int core_size, init_size;
-+      int i;
-+
-+      mod->arch.phys_plt_offset = 0;
-+      mod->arch.virt_plt_offset = 0;
-+      mod->arch.phys_plt_tbl = NULL;
-+      mod->arch.virt_plt_tbl = NULL;
-+
-+      if (IS_ENABLED(CONFIG_64BIT))
-+              return 0;
-+
-+      for (i = 1; i < hdr->e_shnum; i++)
-+              if (sechdrs[i].sh_type == SHT_SYMTAB)
-+                      symindex = i;
-+
-+      core_size = get_plt_size(hdr, sechdrs, secstrings, symindex, false);
-+      init_size = get_plt_size(hdr, sechdrs, secstrings, symindex, true);
-+
-+      if ((core_size + init_size) == 0)
-+              return 0;
-+
-+      mod->arch.phys_plt_tbl = __module_alloc(core_size + init_size, 1);
-+      if (!mod->arch.phys_plt_tbl)
-+              return -ENOMEM;
-+
-+      mod->arch.virt_plt_tbl = __module_alloc(core_size + init_size, 0);
-+      if (!mod->arch.virt_plt_tbl) {
-+              __module_free(mod->arch.phys_plt_tbl);
-+              mod->arch.phys_plt_tbl = NULL;
-+              return -ENOMEM;
-+      }
-+
-+      return 0;
-+}
- static void apply_r_mips_32(u32 *location, u32 base, Elf_Addr v)
- {
-       *location = base + v;
- }
-+static Elf_Addr add_plt_entry_to(unsigned *plt_offset,
-+                               void *start, Elf_Addr v)
-+{
-+      unsigned *tramp = start + *plt_offset;
-+      *plt_offset += 4 * sizeof(int);
-+
-+      /* adjust carry for addiu */
-+      if (v & 0x00008000)
-+              v += 0x10000;
-+
-+      tramp[0] = 0x3c190000 | (v >> 16);      /* lui t9, hi16 */
-+      tramp[1] = 0x27390000 | (v & 0xffff);   /* addiu t9, t9, lo16 */
-+      tramp[2] = 0x03200008;                  /* jr t9 */
-+      tramp[3] = 0x00000000;                  /* nop */
-+
-+      return (Elf_Addr) tramp;
-+}
-+
-+static Elf_Addr add_plt_entry(struct module *me, void *location, Elf_Addr v)
-+{
-+      if (is_phys_addr(location))
-+              return add_plt_entry_to(&me->arch.phys_plt_offset,
-+                              me->arch.phys_plt_tbl, v);
-+      else
-+              return add_plt_entry_to(&me->arch.virt_plt_offset,
-+                              me->arch.virt_plt_tbl, v);
-+
-+}
-+
- static int apply_r_mips_26(struct module *me, u32 *location, u32 base,
-                          Elf_Addr v)
- {
-+      u32 ofs = base & 0x03ffffff;
-+
-       if (v % 4) {
-               pr_err("module %s: dangerous R_MIPS_26 relocation\n",
-                      me->name);
-@@ -55,13 +293,17 @@ static int apply_r_mips_26(struct module
-       }
-       if ((v & 0xf0000000) != (((unsigned long)location + 4) & 0xf0000000)) {
--              pr_err("module %s: relocation overflow\n",
--                     me->name);
--              return -ENOEXEC;
-+              v = add_plt_entry(me, location, v + (ofs << 2));
-+              if (!v) {
-+                      pr_err("module %s: relocation overflow\n",
-+                             me->name);
-+                      return -ENOEXEC;
-+              }
-+              ofs = 0;
-       }
-       *location = (*location & ~0x03ffffff) |
--                  ((base + (v >> 2)) & 0x03ffffff);
-+                  ((ofs + (v >> 2)) & 0x03ffffff);
-       return 0;
- }
-@@ -441,9 +683,36 @@ int module_finalize(const Elf_Ehdr *hdr,
-               list_add(&me->arch.dbe_list, &dbe_list);
-               spin_unlock_irq(&dbe_lock);
-       }
-+
-+      /* Get rid of the fixup trampoline if we're running the module
-+       * from physically mapped address space */
-+      if (me->arch.phys_plt_offset == 0) {
-+              __module_free(me->arch.phys_plt_tbl);
-+              me->arch.phys_plt_tbl = NULL;
-+      }
-+      if (me->arch.virt_plt_offset == 0) {
-+              __module_free(me->arch.virt_plt_tbl);
-+              me->arch.virt_plt_tbl = NULL;
-+      }
-+
-       return 0;
- }
-+void module_arch_freeing_init(struct module *mod)
-+{
-+      if (mod->state == MODULE_STATE_LIVE)
-+              return;
-+
-+      if (mod->arch.phys_plt_tbl) {
-+              __module_free(mod->arch.phys_plt_tbl);
-+              mod->arch.phys_plt_tbl = NULL;
-+      }
-+      if (mod->arch.virt_plt_tbl) {
-+              __module_free(mod->arch.virt_plt_tbl);
-+              mod->arch.virt_plt_tbl = NULL;
-+      }
-+}
-+
- void module_arch_cleanup(struct module *mod)
- {
-       spin_lock_irq(&dbe_lock);
diff --git a/target/linux/generic/pending-5.15/308-mips32r2_tune.patch b/target/linux/generic/pending-5.15/308-mips32r2_tune.patch
deleted file mode 100644 (file)
index ef92a5d..0000000
+++ /dev/null
@@ -1,22 +0,0 @@
-From: Felix Fietkau <[email protected]>
-Subject: kernel: add -mtune=34kc to MIPS CFLAGS when building for mips32r2
-
-This provides a good tradeoff across at least 24Kc-74Kc, while also
-producing smaller code.
-
-Signed-off-by: Felix Fietkau <[email protected]>
----
- arch/mips/Makefile | 2 +-
- 1 file changed, 1 insertion(+), 1 deletion(-)
-
---- a/arch/mips/Makefile
-+++ b/arch/mips/Makefile
-@@ -175,7 +175,7 @@ cflags-$(CONFIG_CPU_VR41XX)        += -march=r4
- cflags-$(CONFIG_CPU_R4X00)    += -march=r4600 -Wa,--trap
- cflags-$(CONFIG_CPU_TX49XX)   += -march=r4600 -Wa,--trap
- cflags-$(CONFIG_CPU_MIPS32_R1)        += -march=mips32 -Wa,--trap
--cflags-$(CONFIG_CPU_MIPS32_R2)        += -march=mips32r2 -Wa,--trap
-+cflags-$(CONFIG_CPU_MIPS32_R2)        += -march=mips32r2 -mtune=34kc -Wa,--trap
- cflags-$(CONFIG_CPU_MIPS32_R5)        += -march=mips32r5 -Wa,--trap -modd-spreg
- cflags-$(CONFIG_CPU_MIPS32_R6)        += -march=mips32r6 -Wa,--trap -modd-spreg
- cflags-$(CONFIG_CPU_MIPS64_R1)        += -march=mips64 -Wa,--trap
diff --git a/target/linux/generic/pending-5.15/310-arm_module_unresolved_weak_sym.patch b/target/linux/generic/pending-5.15/310-arm_module_unresolved_weak_sym.patch
deleted file mode 100644 (file)
index 191dc6a..0000000
+++ /dev/null
@@ -1,22 +0,0 @@
-From: Felix Fietkau <[email protected]>
-Subject: fix errors in unresolved weak symbols on arm
-
-lede-commit: 570699d4838a907c3ef9f2819bf19eb72997b32f
-Signed-off-by: Felix Fietkau <[email protected]>
----
- arch/arm/kernel/module.c | 4 ++++
- 1 file changed, 4 insertions(+)
-
---- a/arch/arm/kernel/module.c
-+++ b/arch/arm/kernel/module.c
-@@ -105,6 +105,10 @@ apply_relocate(Elf32_Shdr *sechdrs, cons
-                       return -ENOEXEC;
-               }
-+              if ((IS_ERR_VALUE(sym->st_value) || !sym->st_value) &&
-+                  ELF_ST_BIND(sym->st_info) == STB_WEAK)
-+                      continue;
-+
-               loc = dstsec->sh_addr + rel->r_offset;
-               switch (ELF32_R_TYPE(rel->r_info)) {
diff --git a/target/linux/generic/pending-5.15/330-MIPS-kexec-Accept-command-line-parameters-from-users.patch b/target/linux/generic/pending-5.15/330-MIPS-kexec-Accept-command-line-parameters-from-users.patch
deleted file mode 100644 (file)
index 3f553b2..0000000
+++ /dev/null
@@ -1,282 +0,0 @@
-From: Yousong Zhou <[email protected]>
-Subject: MIPS: kexec: Accept command line parameters from userspace.
-
-Signed-off-by: Yousong Zhou <[email protected]>
----
- arch/mips/kernel/machine_kexec.c   |  153 +++++++++++++++++++++++++++++++-----
- arch/mips/kernel/machine_kexec.h   |   20 +++++
- arch/mips/kernel/relocate_kernel.S |   21 +++--
- 3 files changed, 167 insertions(+), 27 deletions(-)
- create mode 100644 arch/mips/kernel/machine_kexec.h
-
---- a/arch/mips/kernel/machine_kexec.c
-+++ b/arch/mips/kernel/machine_kexec.c
-@@ -9,14 +9,11 @@
- #include <linux/delay.h>
- #include <linux/libfdt.h>
-+#include <asm/bootinfo.h>
- #include <asm/cacheflush.h>
- #include <asm/page.h>
--
--extern const unsigned char relocate_new_kernel[];
--extern const size_t relocate_new_kernel_size;
--
--extern unsigned long kexec_start_address;
--extern unsigned long kexec_indirection_page;
-+#include <linux/uaccess.h>
-+#include "machine_kexec.h"
- static unsigned long reboot_code_buffer;
-@@ -30,6 +27,101 @@ void (*_crash_smp_send_stop)(void) = NUL
- void (*_machine_kexec_shutdown)(void) = NULL;
- void (*_machine_crash_shutdown)(struct pt_regs *regs) = NULL;
-+static void machine_kexec_print_args(void)
-+{
-+      unsigned long argc = (int)kexec_args[0];
-+      int i;
-+
-+      pr_info("kexec_args[0] (argc): %lu\n", argc);
-+      pr_info("kexec_args[1] (argv): %p\n", (void *)kexec_args[1]);
-+      pr_info("kexec_args[2] (env ): %p\n", (void *)kexec_args[2]);
-+      pr_info("kexec_args[3] (desc): %p\n", (void *)kexec_args[3]);
-+
-+      for (i = 0; i < argc; i++) {
-+              pr_info("kexec_argv[%d] = %p, %s\n",
-+                              i, kexec_argv[i], kexec_argv[i]);
-+      }
-+}
-+
-+static void machine_kexec_init_argv(struct kimage *image)
-+{
-+      void __user *buf = NULL;
-+      size_t bufsz;
-+      size_t size;
-+      int i;
-+
-+      bufsz = 0;
-+      for (i = 0; i < image->nr_segments; i++) {
-+              struct kexec_segment *seg;
-+
-+              seg = &image->segment[i];
-+              if (seg->bufsz < 6)
-+                      continue;
-+
-+              if (strncmp((char *) seg->buf, "kexec ", 6))
-+                      continue;
-+
-+              buf = seg->buf;
-+              bufsz = seg->bufsz;
-+              break;
-+      }
-+
-+      if (!buf)
-+              return;
-+
-+      size = KEXEC_COMMAND_LINE_SIZE;
-+      size = min(size, bufsz);
-+      if (size < bufsz)
-+              pr_warn("kexec command line truncated to %zd bytes\n", size);
-+
-+      /* Copy to kernel space */
-+      if (copy_from_user(kexec_argv_buf, buf, size))
-+              pr_warn("kexec command line copy to kernel space failed\n");
-+
-+      kexec_argv_buf[size - 1] = 0;
-+}
-+
-+static void machine_kexec_parse_argv(struct kimage *image)
-+{
-+      char *reboot_code_buffer;
-+      int reloc_delta;
-+      char *ptr;
-+      int argc;
-+      int i;
-+
-+      ptr = kexec_argv_buf;
-+      argc = 0;
-+
-+      /*
-+       * convert command line string to array of parameters
-+       * (as bootloader does).
-+       */
-+      while (ptr && *ptr && (KEXEC_MAX_ARGC > argc)) {
-+              if (*ptr == ' ') {
-+                      *ptr++ = '\0';
-+                      continue;
-+              }
-+
-+              kexec_argv[argc++] = ptr;
-+              ptr = strchr(ptr, ' ');
-+      }
-+
-+      if (!argc)
-+              return;
-+
-+      kexec_args[0] = argc;
-+      kexec_args[1] = (unsigned long)kexec_argv;
-+      kexec_args[2] = 0;
-+      kexec_args[3] = 0;
-+
-+      reboot_code_buffer = page_address(image->control_code_page);
-+      reloc_delta = reboot_code_buffer - (char *)kexec_relocate_new_kernel;
-+
-+      kexec_args[1] += reloc_delta;
-+      for (i = 0; i < argc; i++)
-+              kexec_argv[i] += reloc_delta;
-+}
-+
- static void kexec_image_info(const struct kimage *kimage)
- {
-       unsigned long i;
-@@ -99,6 +191,18 @@ machine_kexec_prepare(struct kimage *kim
- #endif
-       kexec_image_info(kimage);
-+      /*
-+       * Whenever arguments passed from kexec-tools, Init the arguments as
-+       * the original ones to try avoiding booting failure.
-+       */
-+
-+      kexec_args[0] = fw_arg0;
-+      kexec_args[1] = fw_arg1;
-+      kexec_args[2] = fw_arg2;
-+      kexec_args[3] = fw_arg3;
-+
-+      machine_kexec_init_argv(kimage);
-+      machine_kexec_parse_argv(kimage);
-       if (_machine_kexec_prepare)
-               return _machine_kexec_prepare(kimage);
-@@ -161,7 +265,7 @@ machine_crash_shutdown(struct pt_regs *r
- void kexec_nonboot_cpu_jump(void)
- {
-       local_flush_icache_range((unsigned long)relocated_kexec_smp_wait,
--                               reboot_code_buffer + relocate_new_kernel_size);
-+                               reboot_code_buffer + KEXEC_RELOCATE_NEW_KERNEL_SIZE);
-       relocated_kexec_smp_wait(NULL);
- }
-@@ -199,7 +303,7 @@ void kexec_reboot(void)
-        * machine_kexec() CPU.
-        */
-       local_flush_icache_range(reboot_code_buffer,
--                               reboot_code_buffer + relocate_new_kernel_size);
-+                               reboot_code_buffer + KEXEC_RELOCATE_NEW_KERNEL_SIZE);
-       do_kexec = (void *)reboot_code_buffer;
-       do_kexec();
-@@ -212,10 +316,12 @@ machine_kexec(struct kimage *image)
-       unsigned long *ptr;
-       reboot_code_buffer =
--        (unsigned long)page_address(image->control_code_page);
-+              (unsigned long)page_address(image->control_code_page);
-+      pr_info("reboot_code_buffer = %p\n", (void *)reboot_code_buffer);
-       kexec_start_address =
-               (unsigned long) phys_to_virt(image->start);
-+      pr_info("kexec_start_address = %p\n", (void *)kexec_start_address);
-       if (image->type == KEXEC_TYPE_DEFAULT) {
-               kexec_indirection_page =
-@@ -223,9 +329,19 @@ machine_kexec(struct kimage *image)
-       } else {
-               kexec_indirection_page = (unsigned long)&image->head;
-       }
-+      pr_info("kexec_indirection_page = %p\n", (void *)kexec_indirection_page);
--      memcpy((void*)reboot_code_buffer, relocate_new_kernel,
--             relocate_new_kernel_size);
-+      pr_info("Where is memcpy: %p\n", memcpy);
-+      pr_info("kexec_relocate_new_kernel = %p, kexec_relocate_new_kernel_end = %p\n",
-+              (void *)kexec_relocate_new_kernel, &kexec_relocate_new_kernel_end);
-+      pr_info("Copy %lu bytes from %p to %p\n", KEXEC_RELOCATE_NEW_KERNEL_SIZE,
-+              (void *)kexec_relocate_new_kernel, (void *)reboot_code_buffer);
-+      memcpy((void*)reboot_code_buffer, kexec_relocate_new_kernel,
-+             KEXEC_RELOCATE_NEW_KERNEL_SIZE);
-+
-+      pr_info("Before _print_args().\n");
-+      machine_kexec_print_args();
-+      pr_info("Before eval loop.\n");
-       /*
-        * The generic kexec code builds a page list with physical
-@@ -256,7 +372,7 @@ machine_kexec(struct kimage *image)
- #ifdef CONFIG_SMP
-       /* All secondary cpus now may jump to kexec_wait cycle */
-       relocated_kexec_smp_wait = reboot_code_buffer +
--              (void *)(kexec_smp_wait - relocate_new_kernel);
-+              (void *)(kexec_smp_wait - kexec_relocate_new_kernel);
-       smp_wmb();
-       atomic_set(&kexec_ready_to_reboot, 1);
- #endif
---- /dev/null
-+++ b/arch/mips/kernel/machine_kexec.h
-@@ -0,0 +1,20 @@
-+#ifndef _MACHINE_KEXEC_H
-+#define _MACHINE_KEXEC_H
-+
-+#ifndef __ASSEMBLY__
-+extern const unsigned char kexec_relocate_new_kernel[];
-+extern unsigned long kexec_relocate_new_kernel_end;
-+extern unsigned long kexec_start_address;
-+extern unsigned long kexec_indirection_page;
-+
-+extern char kexec_argv_buf[];
-+extern char *kexec_argv[];
-+
-+#define KEXEC_RELOCATE_NEW_KERNEL_SIZE        ((unsigned long)&kexec_relocate_new_kernel_end - (unsigned long)kexec_relocate_new_kernel)
-+#endif /* !__ASSEMBLY__ */
-+
-+#define KEXEC_COMMAND_LINE_SIZE               256
-+#define KEXEC_ARGV_SIZE                       (KEXEC_COMMAND_LINE_SIZE / 16)
-+#define KEXEC_MAX_ARGC                        (KEXEC_ARGV_SIZE / sizeof(long))
-+
-+#endif
---- a/arch/mips/kernel/relocate_kernel.S
-+++ b/arch/mips/kernel/relocate_kernel.S
-@@ -10,10 +10,11 @@
- #include <asm/mipsregs.h>
- #include <asm/stackframe.h>
- #include <asm/addrspace.h>
-+#include "machine_kexec.h"
- #include <kernel-entry-init.h>
--LEAF(relocate_new_kernel)
-+LEAF(kexec_relocate_new_kernel)
-       PTR_L a0,       arg0
-       PTR_L a1,       arg1
-       PTR_L a2,       arg2
-@@ -98,7 +99,7 @@ done:
- #endif
-       /* jump to kexec_start_address */
-       j               s1
--      END(relocate_new_kernel)
-+      END(kexec_relocate_new_kernel)
- #ifdef CONFIG_SMP
- /*
-@@ -177,8 +178,15 @@ EXPORT(kexec_indirection_page)
-       PTR_WD          0
-       .size           kexec_indirection_page, PTRSIZE
--relocate_new_kernel_end:
-+kexec_argv_buf:
-+      EXPORT(kexec_argv_buf)
-+      .skip           KEXEC_COMMAND_LINE_SIZE
-+      .size           kexec_argv_buf, KEXEC_COMMAND_LINE_SIZE
-+
-+kexec_argv:
-+      EXPORT(kexec_argv)
-+      .skip           KEXEC_ARGV_SIZE
-+      .size           kexec_argv, KEXEC_ARGV_SIZE
--EXPORT(relocate_new_kernel_size)
--      PTR_WD          relocate_new_kernel_end - relocate_new_kernel
--      .size           relocate_new_kernel_size, PTRSIZE
-+kexec_relocate_new_kernel_end:
-+      EXPORT(kexec_relocate_new_kernel_end)
diff --git a/target/linux/generic/pending-5.15/332-arc-add-OWRTDTB-section.patch b/target/linux/generic/pending-5.15/332-arc-add-OWRTDTB-section.patch
deleted file mode 100644 (file)
index 30158cf..0000000
+++ /dev/null
@@ -1,84 +0,0 @@
-From bb0c3b0175240bf152fd7c644821a0cf9f77c37c Mon Sep 17 00:00:00 2001
-From: Evgeniy Didin <[email protected]>
-Date: Fri, 15 Mar 2019 18:53:38 +0300
-Subject: [PATCH] arc add OWRTDTB section
-
-This change allows OpenWRT to patch resulting kernel binary with
-external .dtb.
-
-That allows us to re-use exactky the same vmlinux on different boards
-given its ARC core configurations match (at least cache line sizes etc).
-
-""patch-dtb" searches for ASCII "OWRTDTB:" strign and copies external
-.dtb right after it, keeping the string in place.
-
-Signed-off-by: Eugeniy Paltsev <[email protected]>
-Signed-off-by: Alexey Brodkin <[email protected]>
-Signed-off-by: Evgeniy Didin <[email protected]>
----
- arch/arc/kernel/head.S        | 10 ++++++++++
- arch/arc/kernel/setup.c       |  4 +++-
- arch/arc/kernel/vmlinux.lds.S | 13 +++++++++++++
- 3 files changed, 26 insertions(+), 1 deletion(-)
-
---- a/arch/arc/kernel/head.S
-+++ b/arch/arc/kernel/head.S
-@@ -88,6 +88,16 @@
-       DSP_EARLY_INIT
- .endm
-+      ; Here "patch-dtb" will embed external .dtb
-+      ; Note "patch-dtb" searches for ASCII "OWRTDTB:" string
-+      ; and pastes .dtb right after it, hense the string precedes
-+      ; __image_dtb symbol.
-+      .section .owrt, "aw",@progbits
-+      .ascii  "OWRTDTB:"
-+ENTRY(__image_dtb)
-+      .fill   0x4000
-+END(__image_dtb)
-+
-       .section .init.text, "ax",@progbits
- ;----------------------------------------------------------------
---- a/arch/arc/kernel/setup.c
-+++ b/arch/arc/kernel/setup.c
-@@ -495,6 +495,8 @@ static inline bool uboot_arg_invalid(uns
- /* We always pass 0 as magic from U-boot */
- #define UBOOT_MAGIC_VALUE     0
-+extern struct boot_param_header __image_dtb;
-+
- void __init handle_uboot_args(void)
- {
-       bool use_embedded_dtb = true;
-@@ -533,7 +535,7 @@ void __init handle_uboot_args(void)
- ignore_uboot_args:
-       if (use_embedded_dtb) {
--              machine_desc = setup_machine_fdt(__dtb_start);
-+              machine_desc = setup_machine_fdt(&__image_dtb);
-               if (!machine_desc)
-                       panic("Embedded DT invalid\n");
-       }
---- a/arch/arc/kernel/vmlinux.lds.S
-+++ b/arch/arc/kernel/vmlinux.lds.S
-@@ -27,6 +27,19 @@ SECTIONS
-       . = CONFIG_LINUX_LINK_BASE;
-+      /*
-+      * In OpenWRT we want to patch built binary embedding .dtb of choice.
-+      * This is implemented with "patch-dtb" utility which searches for
-+      * "OWRTDTB:" string in first 16k of image and if it is found
-+      * copies .dtb right after mentioned string.
-+      *
-+      * Note: "OWRTDTB:" won't be overwritten with .dtb, .dtb will follow it.
-+      */
-+      .owrt : {
-+              *(.owrt)
-+      . = ALIGN(PAGE_SIZE);
-+      }
-+
-       _int_vec_base_lds = .;
-       .vector : {
-               *(.vector)
diff --git a/target/linux/generic/pending-5.15/333-arc-enable-unaligned-access-in-kernel-mode.patch b/target/linux/generic/pending-5.15/333-arc-enable-unaligned-access-in-kernel-mode.patch
deleted file mode 100644 (file)
index 1848a84..0000000
+++ /dev/null
@@ -1,24 +0,0 @@
-From: Alexey Brodkin <[email protected]>
-Subject: arc: enable unaligned access in kernel mode
-
-This enables misaligned access handling even in kernel mode.
-Some wireless drivers (ath9k-htc and mt7601u) use misaligned accesses
-here and there and to cope with that without fixing stuff in the drivers
-we're just gracefully handling it on ARC.
-
-Signed-off-by: Alexey Brodkin <[email protected]>
----
- arch/arc/kernel/unaligned.c | 2 +-
- 1 file changed, 1 insertion(+), 1 deletion(-)
-
---- a/arch/arc/kernel/unaligned.c
-+++ b/arch/arc/kernel/unaligned.c
-@@ -202,7 +202,7 @@ int misaligned_fixup(unsigned long addre
-       char buf[TASK_COMM_LEN];
-       /* handle user mode only and only if enabled by sysadmin */
--      if (!user_mode(regs) || !unaligned_enabled)
-+      if (!unaligned_enabled)
-               return 1;
-       if (no_unaligned_warning) {
diff --git a/target/linux/generic/pending-5.15/342-powerpc-Enable-kernel-XZ-compression-option-on-PPC_8.patch b/target/linux/generic/pending-5.15/342-powerpc-Enable-kernel-XZ-compression-option-on-PPC_8.patch
deleted file mode 100644 (file)
index 082b122..0000000
+++ /dev/null
@@ -1,25 +0,0 @@
-From 66770a004afe10df11d3902e16eaa0c2c39436bb Mon Sep 17 00:00:00 2001
-From: Pawel Dembicki <[email protected]>
-Date: Fri, 24 May 2019 17:56:19 +0200
-Subject: [PATCH] powerpc: Enable kernel XZ compression option on PPC_85xx
-
-Enable kernel XZ compression option on PPC_85xx. Tested with
-simpleImage on TP-Link TL-WDR4900 (Freescale P1014 processor).
-
-Suggested-by: Christian Lamparter <[email protected]>
-Signed-off-by: Pawel Dembicki <[email protected]>
----
- arch/powerpc/Kconfig | 2 +-
- 1 file changed, 1 insertion(+), 1 deletion(-)
-
---- a/arch/powerpc/Kconfig
-+++ b/arch/powerpc/Kconfig
-@@ -221,7 +221,7 @@ config PPC
-       select HAVE_KERNEL_GZIP
-       select HAVE_KERNEL_LZMA                 if DEFAULT_UIMAGE
-       select HAVE_KERNEL_LZO                  if DEFAULT_UIMAGE
--      select HAVE_KERNEL_XZ                   if PPC_BOOK3S || 44x
-+      select HAVE_KERNEL_XZ                   if PPC_BOOK3S || 44x || PPC_85xx
-       select HAVE_KPROBES
-       select HAVE_KPROBES_ON_FTRACE
-       select HAVE_KRETPROBES
diff --git a/target/linux/generic/pending-5.15/351-irqchip-bcm-6345-l1-request-memory-region.patch b/target/linux/generic/pending-5.15/351-irqchip-bcm-6345-l1-request-memory-region.patch
deleted file mode 100644 (file)
index 91654cc..0000000
+++ /dev/null
@@ -1,113 +0,0 @@
-From patchwork Thu Mar 16 19:28:33 2023
-Content-Type: text/plain; charset="utf-8"
-MIME-Version: 1.0
-Content-Transfer-Encoding: 8bit
-X-Patchwork-Submitter: =?utf-8?q?=C3=81lvaro_Fern=C3=A1ndez_Rojas?=
-X-Patchwork-Id: 13178238
-Return-Path: <[email protected]>
-X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on
-       aws-us-west-2-korg-lkml-1.web.codeaurora.org
-Received: from vger.kernel.org (vger.kernel.org [23.128.96.18])
-       by smtp.lore.kernel.org (Postfix) with ESMTP id 5EF2AC6FD19
-       for <[email protected]>; Thu, 16 Mar 2023 19:28:43 +0000 (UTC)
-Received: ([email protected]) by vger.kernel.org via listexpand
-        id S230076AbjCPT2l (ORCPT <rfc822;[email protected]>);
-        Thu, 16 Mar 2023 15:28:41 -0400
-Received: from lindbergh.monkeyblade.net ([23.128.96.19]:56412 "EHLO
-        lindbergh.monkeyblade.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org
-        with ESMTP id S230039AbjCPT2k (ORCPT
-        <rfc822;[email protected]>); Thu, 16 Mar 2023 15:28:40 -0400
-Received: from mail-wr1-x42f.google.com (mail-wr1-x42f.google.com
- [IPv6:2a00:1450:4864:20::42f])
-        by lindbergh.monkeyblade.net (Postfix) with ESMTPS id 7259B7D9F;
-        Thu, 16 Mar 2023 12:28:38 -0700 (PDT)
-Received: by mail-wr1-x42f.google.com with SMTP id y14so2539231wrq.4;
-        Thu, 16 Mar 2023 12:28:38 -0700 (PDT)
-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed;
-        d=gmail.com; s=20210112; t=1678994917;
-        h=content-transfer-encoding:mime-version:references:in-reply-to
-         :message-id:date:subject:cc:to:from:from:to:cc:subject:date
-         :message-id:reply-to;
-        bh=j8afldfRZftLeVmekmQfoh01jVdumsVP7nkKoPaU3Q0=;
-        b=FzMRr5ekh/fDiJqTlezNj6nLjzvn5z92FtYeB8MquVSMB8PuvarccnyqAzsXiccf+v
-         uwRFIomnTWNLGVjzc1xrB2hGiCKD3jBo5n1u8p/yEV6rpolbxVjfM7eTHXyAHXGXz7ZJ
-         TPeVbWfAlxiSD6+BPtXr/efehcdI64fIoL6G/U1WHNMo01Tzr/Obf3y5tug17N0fGcXg
-         CH6E5a2HguZUtwrm26LcK9IOV/7xEx5eIE1cOvTLMxPbGWaZwEjjP16HylJr06xRLhaf
-         RpiYBT3mXwwuOx0jLOhqavY/2kZ9GVbZRWMMwZrZv9xNO13SBwc1VUVgD4k3FntnSk7Z
-         AaOQ==
-X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed;
-        d=1e100.net; s=20210112; t=1678994917;
-        h=content-transfer-encoding:mime-version:references:in-reply-to
-         :message-id:date:subject:cc:to:from:x-gm-message-state:from:to:cc
-         :subject:date:message-id:reply-to;
-        bh=j8afldfRZftLeVmekmQfoh01jVdumsVP7nkKoPaU3Q0=;
-        b=OaA5DMgqalrfqO5iOtmmxFPsH90MkN7l4EJpyVnzuiO1Wd6rSCpqPOR7xpxZno8OPP
-         tdfm4vzn9Ie4AUDbFKDTUlPG+tgkmIruo3K9C0VnY9DD2PRZMEYBbWaJKU1otqKt0NKu
-         IAAHNvxvQvCESKzbXFLYwWbRKFScOSMGmGBTDfgThz51A18Ff1hJy/BmnuZk7M2TLgHO
-         wQpy9t7oeB/Hkxl41y46emLc/nESsvwvAG/fx/zPzCe9UiaQLrdZq+BKeOwSBedktzK5
-         U/ZTfgzU2UGSI67aGRqqGnI0uXq+MAJMK18qzM0VByxj6W+AXJ6BJr5P0quljeQ8upSg
-         bEUg==
-X-Gm-Message-State: AO0yUKWnqTlccBDnqwCSRdqOBGc2FyfiLy1Tg7EjPENlISpzXuDYwW/R
-        lJSI06rrfq+Vel/SigfpGJI=
-X-Google-Smtp-Source: 
- AK7set/jYfYl9ttVzIXJO+ZQVfa6cE/yOsP8fx4teiTmGNNWyVlIJRzMAlF3IUGqRAXAmY3hAabIuQ==
-X-Received: by 2002:a5d:40ce:0:b0:2cd:ceab:df1a with SMTP id
- b14-20020a5d40ce000000b002cdceabdf1amr381006wrq.32.1678994916642;
-        Thu, 16 Mar 2023 12:28:36 -0700 (PDT)
-Received: from atlantis.lan (255.red-79-146-124.dynamicip.rima-tde.net.
- [79.146.124.255])
-        by smtp.gmail.com with ESMTPSA id
- l10-20020a5d4bca000000b002cfea3c49d5sm180041wrt.52.2023.03.16.12.28.35
-        (version=TLS1_3 cipher=TLS_AES_256_GCM_SHA384 bits=256/256);
-        Thu, 16 Mar 2023 12:28:35 -0700 (PDT)
-From: =?utf-8?q?=C3=81lvaro_Fern=C3=A1ndez_Rojas?=  <[email protected]>
-        [email protected]
-Cc: =?utf-8?q?=C3=81lvaro_Fern=C3=A1ndez_Rojas?=  <[email protected]>
-Subject: [PATCH v2] irqchip/bcm-6345-l1: request memory region
-Date: Thu, 16 Mar 2023 20:28:33 +0100
-Message-Id: <[email protected]>
-X-Mailer: git-send-email 2.30.2
-In-Reply-To: <[email protected]>
-References: <[email protected]>
-MIME-Version: 1.0
-Precedence: bulk
-List-ID: <linux-mips.vger.kernel.org>
-X-Mailing-List: [email protected]
-
-Request memory region in order to display it in /proc/iomem.
-Also stop printing the MMIO address since it just displays (ptrval).
-
-Signed-off-by: Álvaro Fernández Rojas <[email protected]>
-Acked-by: Florian Fainelli <[email protected]>
----
- v2: request memory region and stop displaying MMIO address.
-
- drivers/irqchip/irq-bcm6345-l1.c | 6 ++++--
- 1 file changed, 4 insertions(+), 2 deletions(-)
-
---- a/drivers/irqchip/irq-bcm6345-l1.c
-+++ b/drivers/irqchip/irq-bcm6345-l1.c
-@@ -257,6 +257,9 @@ static int __init bcm6345_l1_init_one(st
-       if (!cpu->map_base)
-               return -ENOMEM;
-+      if (!request_mem_region(res.start, sz, res.name))
-+              pr_err("failed to request intc memory");
-+
-       for (i = 0; i < n_words; i++) {
-               cpu->enable_cache[i] = 0;
-               __raw_writel(0, cpu->map_base + reg_enable(intc, i));
-@@ -335,8 +338,7 @@ static int __init bcm6345_l1_of_init(str
-       for_each_cpu(idx, &intc->cpumask) {
-               struct bcm6345_l1_cpu *cpu = intc->cpus[idx];
--              pr_info("  CPU%u at MMIO 0x%p (irq = %d)\n", idx,
--                              cpu->map_base, cpu->parent_irq);
-+              pr_info("  CPU%u (irq = %d)\n", idx, cpu->parent_irq);
-       }
-       return 0;
diff --git a/target/linux/generic/pending-5.15/400-mtd-mtdsplit-support.patch b/target/linux/generic/pending-5.15/400-mtd-mtdsplit-support.patch
deleted file mode 100644 (file)
index 46ef15d..0000000
+++ /dev/null
@@ -1,328 +0,0 @@
-From 39717277d5c87bdb183cf2f258957b44ba99b4df Mon Sep 17 00:00:00 2001
-From: OpenWrt community <[email protected]>
-Date: Wed, 13 Jul 2022 11:47:35 +0200
-Subject: [PATCH] mtd: mtdsplit support
-
----
- drivers/mtd/Kconfig            |  19 ++++
- drivers/mtd/Makefile           |   2 +
- drivers/mtd/mtdpart.c          | 169 ++++++++++++++++++++++++++++-----
- include/linux/mtd/mtd.h        |  25 +++++
- include/linux/mtd/partitions.h |   7 ++
- 5 files changed, 197 insertions(+), 25 deletions(-)
-
---- a/drivers/mtd/Kconfig
-+++ b/drivers/mtd/Kconfig
-@@ -12,6 +12,25 @@ menuconfig MTD
- if MTD
-+menu "OpenWrt specific MTD options"
-+
-+config MTD_ROOTFS_ROOT_DEV
-+      bool "Automatically set 'rootfs' partition to be root filesystem"
-+      default y
-+
-+config MTD_SPLIT_FIRMWARE
-+      bool "Automatically split firmware partition for kernel+rootfs"
-+      default y
-+
-+config MTD_SPLIT_FIRMWARE_NAME
-+      string "Firmware partition name"
-+      depends on MTD_SPLIT_FIRMWARE
-+      default "firmware"
-+
-+source "drivers/mtd/mtdsplit/Kconfig"
-+
-+endmenu
-+
- config MTD_TESTS
-       tristate "MTD tests support (DANGEROUS)"
-       depends on m
---- a/drivers/mtd/Makefile
-+++ b/drivers/mtd/Makefile
-@@ -9,6 +9,8 @@ mtd-y                          := mtdcore.o mtdsuper.o mtdconc
- obj-y                         += parsers/
-+obj-$(CONFIG_MTD_SPLIT)               += mtdsplit/
-+
- # 'Users' - code which presents functionality to userspace.
- obj-$(CONFIG_MTD_BLKDEVS)     += mtd_blkdevs.o
- obj-$(CONFIG_MTD_BLOCK)               += mtdblock.o
---- a/drivers/mtd/mtdpart.c
-+++ b/drivers/mtd/mtdpart.c
-@@ -15,11 +15,13 @@
- #include <linux/kmod.h>
- #include <linux/mtd/mtd.h>
- #include <linux/mtd/partitions.h>
-+#include <linux/magic.h>
- #include <linux/err.h>
- #include <linux/of.h>
- #include <linux/of_platform.h>
- #include "mtdcore.h"
-+#include "mtdsplit/mtdsplit.h"
- /*
-  * MTD methods which simply translate the effective address and pass through
-@@ -236,6 +238,147 @@ static int mtd_add_partition_attrs(struc
-       return ret;
- }
-+static DEFINE_SPINLOCK(part_parser_lock);
-+static LIST_HEAD(part_parsers);
-+
-+static struct mtd_part_parser *mtd_part_parser_get(const char *name)
-+{
-+      struct mtd_part_parser *p, *ret = NULL;
-+
-+      spin_lock(&part_parser_lock);
-+
-+      list_for_each_entry(p, &part_parsers, list)
-+              if (!strcmp(p->name, name) && try_module_get(p->owner)) {
-+                      ret = p;
-+                      break;
-+              }
-+
-+      spin_unlock(&part_parser_lock);
-+
-+      return ret;
-+}
-+
-+static inline void mtd_part_parser_put(const struct mtd_part_parser *p)
-+{
-+      module_put(p->owner);
-+}
-+
-+static struct mtd_part_parser *
-+get_partition_parser_by_type(enum mtd_parser_type type,
-+                           struct mtd_part_parser *start)
-+{
-+      struct mtd_part_parser *p, *ret = NULL;
-+
-+      spin_lock(&part_parser_lock);
-+
-+      p = list_prepare_entry(start, &part_parsers, list);
-+      if (start)
-+              mtd_part_parser_put(start);
-+
-+      list_for_each_entry_continue(p, &part_parsers, list) {
-+              if (p->type == type && try_module_get(p->owner)) {
-+                      ret = p;
-+                      break;
-+              }
-+      }
-+
-+      spin_unlock(&part_parser_lock);
-+
-+      return ret;
-+}
-+
-+static int parse_mtd_partitions_by_type(struct mtd_info *master,
-+                                      enum mtd_parser_type type,
-+                                      const struct mtd_partition **pparts,
-+                                      struct mtd_part_parser_data *data)
-+{
-+      struct mtd_part_parser *prev = NULL;
-+      int ret = 0;
-+
-+      while (1) {
-+              struct mtd_part_parser *parser;
-+
-+              parser = get_partition_parser_by_type(type, prev);
-+              if (!parser)
-+                      break;
-+
-+              ret = (*parser->parse_fn)(master, pparts, data);
-+
-+              if (ret > 0) {
-+                      mtd_part_parser_put(parser);
-+                      printk(KERN_NOTICE
-+                             "%d %s partitions found on MTD device %s\n",
-+                             ret, parser->name, master->name);
-+                      break;
-+              }
-+
-+              prev = parser;
-+      }
-+
-+      return ret;
-+}
-+
-+static int
-+run_parsers_by_type(struct mtd_info *child, enum mtd_parser_type type)
-+{
-+      struct mtd_partition *parts;
-+      int nr_parts;
-+      int i;
-+
-+      nr_parts = parse_mtd_partitions_by_type(child, type, (const struct mtd_partition **)&parts,
-+                                              NULL);
-+      if (nr_parts <= 0)
-+              return nr_parts;
-+
-+      if (WARN_ON(!parts))
-+              return 0;
-+
-+      for (i = 0; i < nr_parts; i++) {
-+              /* adjust partition offsets */
-+              parts[i].offset += child->part.offset;
-+
-+              mtd_add_partition(child->parent,
-+                                parts[i].name,
-+                                parts[i].offset,
-+                                parts[i].size);
-+      }
-+
-+      kfree(parts);
-+
-+      return nr_parts;
-+}
-+
-+#ifdef CONFIG_MTD_SPLIT_FIRMWARE_NAME
-+#define SPLIT_FIRMWARE_NAME   CONFIG_MTD_SPLIT_FIRMWARE_NAME
-+#else
-+#define SPLIT_FIRMWARE_NAME   "unused"
-+#endif
-+
-+static void split_firmware(struct mtd_info *master, struct mtd_info *part)
-+{
-+      run_parsers_by_type(part, MTD_PARSER_TYPE_FIRMWARE);
-+}
-+
-+static void mtd_partition_split(struct mtd_info *master, struct mtd_info *part)
-+{
-+      static int rootfs_found = 0;
-+
-+      if (rootfs_found)
-+              return;
-+
-+      if (of_find_property(mtd_get_of_node(part), "linux,rootfs", NULL) ||
-+          !strcmp(part->name, "rootfs")) {
-+              run_parsers_by_type(part, MTD_PARSER_TYPE_ROOTFS);
-+
-+              rootfs_found = 1;
-+      }
-+
-+      if (IS_ENABLED(CONFIG_MTD_SPLIT_FIRMWARE) &&
-+          !strcmp(part->name, SPLIT_FIRMWARE_NAME) &&
-+          !of_find_property(mtd_get_of_node(part), "compatible", NULL))
-+              split_firmware(master, part);
-+}
-+
- int mtd_add_partition(struct mtd_info *parent, const char *name,
-                     long long offset, long long length)
- {
-@@ -274,6 +417,7 @@ int mtd_add_partition(struct mtd_info *p
-       if (ret)
-               goto err_remove_part;
-+      mtd_partition_split(parent, child);
-       mtd_add_partition_attrs(child);
-       return 0;
-@@ -422,6 +566,7 @@ int add_mtd_partitions(struct mtd_info *
-                       goto err_del_partitions;
-               }
-+              mtd_partition_split(master, child);
-               mtd_add_partition_attrs(child);
-               /* Look for subpartitions */
-@@ -438,31 +583,6 @@ err_del_partitions:
-       return ret;
- }
--static DEFINE_SPINLOCK(part_parser_lock);
--static LIST_HEAD(part_parsers);
--
--static struct mtd_part_parser *mtd_part_parser_get(const char *name)
--{
--      struct mtd_part_parser *p, *ret = NULL;
--
--      spin_lock(&part_parser_lock);
--
--      list_for_each_entry(p, &part_parsers, list)
--              if (!strcmp(p->name, name) && try_module_get(p->owner)) {
--                      ret = p;
--                      break;
--              }
--
--      spin_unlock(&part_parser_lock);
--
--      return ret;
--}
--
--static inline void mtd_part_parser_put(const struct mtd_part_parser *p)
--{
--      module_put(p->owner);
--}
--
- /*
-  * Many partition parsers just expected the core to kfree() all their data in
-  * one chunk. Do that by default.
---- a/include/linux/mtd/mtd.h
-+++ b/include/linux/mtd/mtd.h
-@@ -620,6 +620,24 @@ static inline void mtd_align_erase_req(s
-               req->len += mtd->erasesize - mod;
- }
-+static inline uint64_t mtd_roundup_to_eb(uint64_t sz, struct mtd_info *mtd)
-+{
-+      if (mtd_mod_by_eb(sz, mtd) == 0)
-+              return sz;
-+
-+      /* Round up to next erase block */
-+      return (mtd_div_by_eb(sz, mtd) + 1) * mtd->erasesize;
-+}
-+
-+static inline uint64_t mtd_rounddown_to_eb(uint64_t sz, struct mtd_info *mtd)
-+{
-+      if (mtd_mod_by_eb(sz, mtd) == 0)
-+              return sz;
-+
-+      /* Round down to the start of the current erase block */
-+      return (mtd_div_by_eb(sz, mtd)) * mtd->erasesize;
-+}
-+
- static inline uint32_t mtd_div_by_ws(uint64_t sz, struct mtd_info *mtd)
- {
-       if (mtd->writesize_shift)
-@@ -693,6 +711,13 @@ extern struct mtd_info *of_get_mtd_devic
- extern struct mtd_info *get_mtd_device_nm(const char *name);
- extern void put_mtd_device(struct mtd_info *mtd);
-+static inline uint64_t mtdpart_get_offset(const struct mtd_info *mtd)
-+{
-+      if (!mtd_is_partition(mtd))
-+              return 0;
-+
-+      return mtd->part.offset;
-+}
- struct mtd_notifier {
-       void (*add)(struct mtd_info *mtd);
---- a/include/linux/mtd/partitions.h
-+++ b/include/linux/mtd/partitions.h
-@@ -75,6 +75,12 @@ struct mtd_part_parser_data {
-  * Functions dealing with the various ways of partitioning the space
-  */
-+enum mtd_parser_type {
-+      MTD_PARSER_TYPE_DEVICE = 0,
-+      MTD_PARSER_TYPE_ROOTFS,
-+      MTD_PARSER_TYPE_FIRMWARE,
-+};
-+
- struct mtd_part_parser {
-       struct list_head list;
-       struct module *owner;
-@@ -83,6 +89,7 @@ struct mtd_part_parser {
-       int (*parse_fn)(struct mtd_info *, const struct mtd_partition **,
-                       struct mtd_part_parser_data *);
-       void (*cleanup)(const struct mtd_partition *pparts, int nr_parts);
-+      enum mtd_parser_type type;
- };
- /* Container for passing around a set of parsed partitions */
diff --git a/target/linux/generic/pending-5.15/401-mtd-don-t-register-NVMEM-devices-for-partitions-with.patch b/target/linux/generic/pending-5.15/401-mtd-don-t-register-NVMEM-devices-for-partitions-with.patch
deleted file mode 100644 (file)
index 650e10a..0000000
+++ /dev/null
@@ -1,48 +0,0 @@
-From: =?UTF-8?q?Rafa=C5=82=20Mi=C5=82ecki?= <[email protected]>
-Date: Tue, 31 Oct 2023 15:51:01 +0100
-Subject: [PATCH] mtd: don't register NVMEM devices for partitions with custom
- drivers
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-This fixes issue exposed by upstream commit f4cf4e5db331 ("Revert
-"nvmem: add new config option"").
-
-Signed-off-by: Rafał Miłecki <[email protected]>
----
- drivers/mtd/mtdcore.c | 23 +++++++++++++++++++++++
- 1 file changed, 23 insertions(+)
-
---- a/drivers/mtd/mtdcore.c
-+++ b/drivers/mtd/mtdcore.c
-@@ -537,6 +537,29 @@ static int mtd_nvmem_add(struct mtd_info
-       struct device_node *node = mtd_get_of_node(mtd);
-       struct nvmem_config config = {};
-+      /*
-+       * Do NOT register NVMEM device for any partition that is meant to be
-+       * handled by a U-Boot env driver. That would result in associating two
-+       * different NVMEM devices with the same OF node.
-+       *
-+       * An example of unwanted behaviour of above (forwardtrace):
-+       * of_get_mac_addr_nvmem()
-+       * of_nvmem_cell_get()
-+       * __nvmem_device_get()
-+       *
-+       * We can't have __nvmem_device_get() return "mtdX" NVMEM device instead
-+       * of U-Boot env NVMEM device. That would result in failing to find
-+       * NVMEM cell.
-+       *
-+       * This issue seems to affect U-Boot env case only and will go away with
-+       * switch to NVMEM layouts.
-+       */
-+      if (of_device_is_compatible(node, "u-boot,env") ||
-+          of_device_is_compatible(node, "u-boot,env-redundant-bool") ||
-+          of_device_is_compatible(node, "u-boot,env-redundant-count") ||
-+          of_device_is_compatible(node, "brcm,env"))
-+              return 0;
-+
-       config.id = -1;
-       config.dev = &mtd->dev;
-       config.name = dev_name(&mtd->dev);
diff --git a/target/linux/generic/pending-5.15/402-mtd-spi-nor-write-support-for-minor-aligned-partitions.patch b/target/linux/generic/pending-5.15/402-mtd-spi-nor-write-support-for-minor-aligned-partitions.patch
deleted file mode 100644 (file)
index 0a12132..0000000
+++ /dev/null
@@ -1,245 +0,0 @@
-From acacdac272927ae1d96e0bca51eb82899671eaea Mon Sep 17 00:00:00 2001
-From: John Thomson <[email protected]>
-Date: Fri, 25 Dec 2020 18:50:08 +1000
-Subject: [PATCH] mtd: spi-nor: write support for minor aligned partitions
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-Do not prevent writing to mtd partitions where a partition boundary sits
-on a minor erasesize boundary.
-This addresses a FIXME that has been present since the start of the
-linux git history:
-/* Doesn't start on a boundary of major erase size */
-/* FIXME: Let it be writable if it is on a boundary of
- * _minor_ erase size though */
-
-Allow a uniform erase region spi-nor device to be configured
-to use the non-uniform erase regions code path for an erase with:
-CONFIG_MTD_SPI_NOR_USE_VARIABLE_ERASE=y
-
-On supporting hardware (SECT_4K: majority of current SPI-NOR device)
-provide the facility for an erase to use the least number
-of SPI-NOR operations, as well as access to 4K erase without
-requiring CONFIG_MTD_SPI_NOR_USE_4K_SECTORS
-
-Introduce erasesize_minor to the mtd struct,
-the smallest erasesize supported by the device
-
-On existing devices, this is useful where write support is wanted
-for data on a 4K partition, such as some u-boot-env partitions,
-or RouterBoot soft_config, while still netting the performance
-benefits of using 64K sectors
-
-Performance:
-time mtd erase firmware
-OpenWrt 5.10 ramips MT7621 w25q128jv 0xfc0000 partition length
-
-Without this patch
-MTD_SPI_NOR_USE_4K_SECTORS=y   |n
-real    2m 11.66s              |0m 50.86s
-user    0m 0.00s               |0m 0.00s
-sys     1m 56.20s              |0m 50.80s
-
-With this patch
-MTD_SPI_NOR_USE_VARIABLE_ERASE=n|y             |4K_SECTORS=y
-real    0m 51.68s              |0m 50.85s      |2m 12.89s
-user    0m 0.00s               |0m 0.00s       |0m 0.01s
-sys     0m 46.94s              |0m 50.38s      |2m 12.46s
-
-Signed-off-by: John Thomson <[email protected]>
-Signed-off-by: Thibaut VARÈNE <[email protected]>
-
----
-
-checkpatch does not like the printk(KERN_WARNING
-these should be changed separately beforehand?
-
-Changes v1 -> v2:
-Added mtdcore sysfs for erasesize_minor
-Removed finding minor erasesize for variable erase regions device,
-as untested and no responses regarding it.
-Moved IF_ENABLED for SPINOR variable erase to guard setting
-erasesize_minor in spi-nor/core.c
-Removed setting erasesize to minor where partition boundaries require
-minor erase to be writable
-Simplified minor boundary check by relying on minor being a factor of
-major
-
-Changes RFC -> v1:
-Fix uninitialized variable smatch warning
-Reported-by: kernel test robot <[email protected]>
-Reported-by: Dan Carpenter <[email protected]>
----
- drivers/mtd/mtdcore.c       | 10 ++++++++++
- drivers/mtd/mtdpart.c       | 35 +++++++++++++++++++++++++----------
- drivers/mtd/spi-nor/Kconfig | 10 ++++++++++
- drivers/mtd/spi-nor/core.c  | 11 +++++++++--
- include/linux/mtd/mtd.h     |  2 ++
- 5 files changed, 56 insertions(+), 12 deletions(-)
-
---- a/drivers/mtd/mtdcore.c
-+++ b/drivers/mtd/mtdcore.c
-@@ -169,6 +169,15 @@ static ssize_t mtd_erasesize_show(struct
- }
- MTD_DEVICE_ATTR_RO(erasesize);
-+static ssize_t mtd_erasesize_minor_show(struct device *dev,
-+              struct device_attribute *attr, char *buf)
-+{
-+      struct mtd_info *mtd = dev_get_drvdata(dev);
-+
-+      return sysfs_emit(buf, "%lu\n", (unsigned long)mtd->erasesize_minor);
-+}
-+MTD_DEVICE_ATTR_RO(erasesize_minor);
-+
- static ssize_t mtd_writesize_show(struct device *dev,
-               struct device_attribute *attr, char *buf)
- {
-@@ -314,6 +323,7 @@ static struct attribute *mtd_attrs[] = {
-       &dev_attr_flags.attr,
-       &dev_attr_size.attr,
-       &dev_attr_erasesize.attr,
-+      &dev_attr_erasesize_minor.attr,
-       &dev_attr_writesize.attr,
-       &dev_attr_subpagesize.attr,
-       &dev_attr_oobsize.attr,
---- a/drivers/mtd/mtdpart.c
-+++ b/drivers/mtd/mtdpart.c
-@@ -41,6 +41,7 @@ static struct mtd_info *allocate_partiti
-       struct mtd_info *master = mtd_get_master(parent);
-       int wr_alignment = (parent->flags & MTD_NO_ERASE) ?
-                          master->writesize : master->erasesize;
-+      int wr_alignment_minor = 0;
-       u64 parent_size = mtd_is_partition(parent) ?
-                         parent->part.size : parent->size;
-       struct mtd_info *child;
-@@ -165,6 +166,7 @@ static struct mtd_info *allocate_partiti
-       } else {
-               /* Single erase size */
-               child->erasesize = master->erasesize;
-+              child->erasesize_minor = master->erasesize_minor;
-       }
-       /*
-@@ -172,26 +174,39 @@ static struct mtd_info *allocate_partiti
-        * exposes several regions with different erasesize. Adjust
-        * wr_alignment accordingly.
-        */
--      if (!(child->flags & MTD_NO_ERASE))
-+      if (!(child->flags & MTD_NO_ERASE)) {
-               wr_alignment = child->erasesize;
-+              wr_alignment_minor = child->erasesize_minor;
-+      }
-       tmp = mtd_get_master_ofs(child, 0);
-       remainder = do_div(tmp, wr_alignment);
-       if ((child->flags & MTD_WRITEABLE) && remainder) {
--              /* Doesn't start on a boundary of major erase size */
--              /* FIXME: Let it be writable if it is on a boundary of
--               * _minor_ erase size though */
--              child->flags &= ~MTD_WRITEABLE;
--              printk(KERN_WARNING"mtd: partition \"%s\" doesn't start on an erase/write block boundary -- force read-only\n",
--                      part->name);
-+              if (wr_alignment_minor) {
-+                      /* rely on minor being a factor of major erasesize */
-+                      tmp = remainder;
-+                      remainder = do_div(tmp, wr_alignment_minor);
-+              }
-+              if (remainder) {
-+                      child->flags &= ~MTD_WRITEABLE;
-+                      printk(KERN_WARNING"mtd: partition \"%s\" doesn't start on an erase/write block boundary -- force read-only\n",
-+                              part->name);
-+              }
-       }
-       tmp = mtd_get_master_ofs(child, 0) + child->part.size;
-       remainder = do_div(tmp, wr_alignment);
-       if ((child->flags & MTD_WRITEABLE) && remainder) {
--              child->flags &= ~MTD_WRITEABLE;
--              printk(KERN_WARNING"mtd: partition \"%s\" doesn't end on an erase/write block -- force read-only\n",
--                      part->name);
-+              if (wr_alignment_minor) {
-+                      tmp = remainder;
-+                      remainder = do_div(tmp, wr_alignment_minor);
-+              }
-+
-+              if (remainder) {
-+                      child->flags &= ~MTD_WRITEABLE;
-+                      printk(KERN_WARNING"mtd: partition \"%s\" doesn't end on an erase/write block -- force read-only\n",
-+                              part->name);
-+              }
-       }
-       child->size = child->part.size;
---- a/drivers/mtd/spi-nor/Kconfig
-+++ b/drivers/mtd/spi-nor/Kconfig
-@@ -10,6 +10,16 @@ menuconfig MTD_SPI_NOR
- if MTD_SPI_NOR
-+config MTD_SPI_NOR_USE_VARIABLE_ERASE
-+      bool "Disable uniform_erase to allow use of all hardware supported erasesizes"
-+      depends on !MTD_SPI_NOR_USE_4K_SECTORS
-+      default n
-+      help
-+        Allow mixed use of all hardware supported erasesizes,
-+        by forcing spi_nor to use the multiple eraseregions code path.
-+        For example: A 68K erase will use one 64K erase, and one 4K erase
-+        on supporting hardware.
-+
- config MTD_SPI_NOR_USE_4K_SECTORS
-       bool "Use small 4096 B erase sectors"
-       default y
---- a/drivers/mtd/spi-nor/core.c
-+++ b/drivers/mtd/spi-nor/core.c
-@@ -1272,6 +1272,8 @@ static u8 spi_nor_convert_3to4_erase(u8
- static bool spi_nor_has_uniform_erase(const struct spi_nor *nor)
- {
-+      if (IS_ENABLED(CONFIG_MTD_SPI_NOR_USE_VARIABLE_ERASE))
-+              return false;
-       return !!nor->params->erase_map.uniform_erase_type;
- }
-@@ -2401,6 +2403,7 @@ static int spi_nor_select_erase(struct s
- {
-       struct spi_nor_erase_map *map = &nor->params->erase_map;
-       const struct spi_nor_erase_type *erase = NULL;
-+      const struct spi_nor_erase_type *erase_minor = NULL;
-       struct mtd_info *mtd = &nor->mtd;
-       u32 wanted_size = nor->info->sector_size;
-       int i;
-@@ -2433,8 +2436,9 @@ static int spi_nor_select_erase(struct s
-        */
-       for (i = SNOR_ERASE_TYPE_MAX - 1; i >= 0; i--) {
-               if (map->erase_type[i].size) {
--                      erase = &map->erase_type[i];
--                      break;
-+                      if (!erase)
-+                              erase = &map->erase_type[i];
-+                      erase_minor = &map->erase_type[i];
-               }
-       }
-@@ -2442,6 +2446,9 @@ static int spi_nor_select_erase(struct s
-               return -EINVAL;
-       mtd->erasesize = erase->size;
-+      if (IS_ENABLED(CONFIG_MTD_SPI_NOR_USE_VARIABLE_ERASE) &&
-+                      erase_minor && erase_minor->size < erase->size)
-+              mtd->erasesize_minor = erase_minor->size;
-       return 0;
- }
---- a/include/linux/mtd/mtd.h
-+++ b/include/linux/mtd/mtd.h
-@@ -250,6 +250,8 @@ struct mtd_info {
-        * information below if they desire
-        */
-       uint32_t erasesize;
-+      /* "Minor" (smallest) erase size supported by the whole device */
-+      uint32_t erasesize_minor;
-       /* Minimal writable flash unit size. In case of NOR flash it is 1 (even
-        * though individual bits can be cleared), in case of NAND flash it is
-        * one NAND page (or half, or one-fourths of it), in case of ECC-ed NOR
diff --git a/target/linux/generic/pending-5.15/405-mtd-spi-nor-Add-support-for-BoHong-bh25q128as.patch b/target/linux/generic/pending-5.15/405-mtd-spi-nor-Add-support-for-BoHong-bh25q128as.patch
deleted file mode 100644 (file)
index 6363cb6..0000000
+++ /dev/null
@@ -1,75 +0,0 @@
-From 52d14545d2fc276b1bf9ccf48d4612fab6edfb6a Mon Sep 17 00:00:00 2001
-From: David Bauer <[email protected]>
-Date: Thu, 6 May 2021 17:49:55 +0200
-Subject: [PATCH] mtd: spi-nor: Add support for BoHong bh25q128as
-
-Add MTD support for the BoHong bh25q128as SPI NOR chip.
-The chip has 16MB of total capacity, divided into a total of 256
-sectors, each 64KB sized. The chip also supports 4KB sectors.
-Additionally, it supports dual and quad read modes.
-
-Functionality was verified on an Tenbay WR1800K / MTK MT7621 board.
-
-Signed-off-by: David Bauer <[email protected]>
----
- drivers/mtd/spi-nor/Makefile |  1 +
- drivers/mtd/spi-nor/bohong.c | 21 +++++++++++++++++++++
- drivers/mtd/spi-nor/core.c   |  1 +
- drivers/mtd/spi-nor/core.h   |  1 +
- 4 files changed, 24 insertions(+)
- create mode 100644 drivers/mtd/spi-nor/bohong.c
-
---- a/drivers/mtd/spi-nor/Makefile
-+++ b/drivers/mtd/spi-nor/Makefile
-@@ -2,6 +2,7 @@
- spi-nor-objs                  := core.o sfdp.o swp.o otp.o sysfs.o
- spi-nor-objs                  += atmel.o
-+spi-nor-objs                  += bohong.o
- spi-nor-objs                  += catalyst.o
- spi-nor-objs                  += eon.o
- spi-nor-objs                  += esmt.o
---- /dev/null
-+++ b/drivers/mtd/spi-nor/bohong.c
-@@ -0,0 +1,21 @@
-+// SPDX-License-Identifier: GPL-2.0
-+/*
-+ * Copyright (C) 2005, Intec Automation Inc.
-+ * Copyright (C) 2014, Freescale Semiconductor, Inc.
-+ */
-+
-+#include <linux/mtd/spi-nor.h>
-+
-+#include "core.h"
-+
-+static const struct flash_info bohong_parts[] = {
-+      /* BoHong Microelectronics */
-+      { "bh25q128as", INFO(0x684018, 0, 64 * 1024, 256,
-+                           SECT_4K | SPI_NOR_DUAL_READ | SPI_NOR_QUAD_READ) },
-+};
-+
-+const struct spi_nor_manufacturer spi_nor_bohong = {
-+      .name = "bohong",
-+      .parts = bohong_parts,
-+      .nparts = ARRAY_SIZE(bohong_parts),
-+};
---- a/drivers/mtd/spi-nor/core.c
-+++ b/drivers/mtd/spi-nor/core.c
-@@ -1844,6 +1844,7 @@ int spi_nor_sr2_bit7_quad_enable(struct
- static const struct spi_nor_manufacturer *manufacturers[] = {
-       &spi_nor_atmel,
-+      &spi_nor_bohong,
-       &spi_nor_catalyst,
-       &spi_nor_eon,
-       &spi_nor_esmt,
---- a/drivers/mtd/spi-nor/core.h
-+++ b/drivers/mtd/spi-nor/core.h
-@@ -473,6 +473,7 @@ struct sfdp {
- /* Manufacturer drivers. */
- extern const struct spi_nor_manufacturer spi_nor_atmel;
-+extern const struct spi_nor_manufacturer spi_nor_bohong;
- extern const struct spi_nor_manufacturer spi_nor_catalyst;
- extern const struct spi_nor_manufacturer spi_nor_eon;
- extern const struct spi_nor_manufacturer spi_nor_esmt;
diff --git a/target/linux/generic/pending-5.15/420-mtd-redboot_space.patch b/target/linux/generic/pending-5.15/420-mtd-redboot_space.patch
deleted file mode 100644 (file)
index 5518ea7..0000000
+++ /dev/null
@@ -1,41 +0,0 @@
-From: Felix Fietkau <[email protected]>
-Subject: add patch for including unpartitioned space in the rootfs partition for redboot devices (if applicable)
-
-[[email protected]: used by ixp and others]
-
-lede-commit: 394918851f84e4d00fa16eb900e7700e95091f00
-Signed-off-by: Felix Fietkau <[email protected]>
----
- drivers/mtd/redboot.c | 19 +++++++++++++------
- 1 file changed, 13 insertions(+), 6 deletions(-)
-
---- a/drivers/mtd/parsers/redboot.c
-+++ b/drivers/mtd/parsers/redboot.c
-@@ -278,14 +278,21 @@ nogood:
- #endif
-               names += strlen(names) + 1;
--#ifdef CONFIG_MTD_REDBOOT_PARTS_UNALLOCATED
-               if (fl->next && fl->img->flash_base + fl->img->size + master->erasesize <= fl->next->img->flash_base) {
--                      i++;
--                      parts[i].offset = parts[i - 1].size + parts[i - 1].offset;
--                      parts[i].size = fl->next->img->flash_base - parts[i].offset;
--                      parts[i].name = nullname;
--              }
-+                      if (!strcmp(parts[i].name, "rootfs")) {
-+                              parts[i].size = fl->next->img->flash_base;
-+                              parts[i].size &= ~(master->erasesize - 1);
-+                              parts[i].size -= parts[i].offset;
-+#ifdef CONFIG_MTD_REDBOOT_PARTS_UNALLOCATED
-+                              nrparts--;
-+                      } else {
-+                              i++;
-+                              parts[i].offset = parts[i-1].size + parts[i-1].offset;
-+                              parts[i].size = fl->next->img->flash_base - parts[i].offset;
-+                              parts[i].name = nullname;
- #endif
-+                      }
-+              }
-               tmp_fl = fl;
-               fl = fl->next;
-               kfree(tmp_fl);
diff --git a/target/linux/generic/pending-5.15/430-mtd-add-myloader-partition-parser.patch b/target/linux/generic/pending-5.15/430-mtd-add-myloader-partition-parser.patch
deleted file mode 100644 (file)
index c7a8d9d..0000000
+++ /dev/null
@@ -1,229 +0,0 @@
-From: Florian Fainelli <[email protected]>
-Subject: Add myloader partition table parser
-
-[[email protected]: shoud be upstreamable]
-
-lede-commit: d8bf22859b51faa09d22c056fe221a45d2f7a3b8
-Signed-off-by: Florian Fainelli <[email protected]>
-[adjust for kernel 5.4, add myloader.c to patch]
-Signed-off-by: Adrian Schmutzler <[email protected]>
-
---- a/drivers/mtd/parsers/Kconfig
-+++ b/drivers/mtd/parsers/Kconfig
-@@ -57,6 +57,22 @@ config MTD_CMDLINE_PARTS
-         If unsure, say 'N'.
-+config MTD_MYLOADER_PARTS
-+      tristate "MyLoader partition parsing"
-+      depends on ADM5120 || ATH79
-+      help
-+        MyLoader is a bootloader which allows the user to define partitions
-+        in flash devices, by putting a table in the second erase block
-+        on the device, similar to a partition table. This table gives the
-+        offsets and lengths of the user defined partitions.
-+
-+        If you need code which can detect and parse these tables, and
-+        register MTD 'partitions' corresponding to each image detected,
-+        enable this option.
-+
-+        You will still need the parsing functions to be called by the driver
-+        for your particular device. It won't happen automatically.
-+
- config MTD_OF_PARTS
-       tristate "OpenFirmware (device tree) partitioning parser"
-       default y
---- a/drivers/mtd/parsers/Makefile
-+++ b/drivers/mtd/parsers/Makefile
-@@ -3,6 +3,7 @@ obj-$(CONFIG_MTD_AR7_PARTS)            += ar7part.
- obj-$(CONFIG_MTD_BCM47XX_PARTS)               += bcm47xxpart.o
- obj-$(CONFIG_MTD_BCM63XX_PARTS)               += bcm63xxpart.o
- obj-$(CONFIG_MTD_CMDLINE_PARTS)               += cmdlinepart.o
-+obj-$(CONFIG_MTD_MYLOADER_PARTS)              += myloader.o
- obj-$(CONFIG_MTD_OF_PARTS)            += ofpart.o
- ofpart-y                              += ofpart_core.o
- ofpart-$(CONFIG_MTD_OF_PARTS_BCM4908) += ofpart_bcm4908.o
---- /dev/null
-+++ b/drivers/mtd/parsers/myloader.c
-@@ -0,0 +1,181 @@
-+/*
-+ *  Parse MyLoader-style flash partition tables and produce a Linux partition
-+ *  array to match.
-+ *
-+ *  Copyright (C) 2007-2009 Gabor Juhos <[email protected]>
-+ *
-+ *  This file was based on drivers/mtd/redboot.c
-+ *  Author: Red Hat, Inc. - David Woodhouse <[email protected]>
-+ *
-+ *  This program is free software; you can redistribute it and/or modify it
-+ *  under the terms of the GNU General Public License version 2 as published
-+ *  by the Free Software Foundation.
-+ */
-+
-+#include <linux/kernel.h>
-+#include <linux/module.h>
-+#include <linux/version.h>
-+#include <linux/slab.h>
-+#include <linux/init.h>
-+#include <linux/vmalloc.h>
-+#include <linux/mtd/mtd.h>
-+#include <linux/mtd/partitions.h>
-+#include <linux/byteorder/generic.h>
-+#include <linux/myloader.h>
-+
-+#define BLOCK_LEN_MIN         0x10000
-+#define PART_NAME_LEN         32
-+
-+struct part_data {
-+      struct mylo_partition_table     tab;
-+      char names[MYLO_MAX_PARTITIONS][PART_NAME_LEN];
-+};
-+
-+static int myloader_parse_partitions(struct mtd_info *master,
-+                                   const struct mtd_partition **pparts,
-+                                   struct mtd_part_parser_data *data)
-+{
-+      struct part_data *buf;
-+      struct mylo_partition_table *tab;
-+      struct mylo_partition *part;
-+      struct mtd_partition *mtd_parts;
-+      struct mtd_partition *mtd_part;
-+      int num_parts;
-+      int ret, i;
-+      size_t retlen;
-+      char *names;
-+      unsigned long offset;
-+      unsigned long blocklen;
-+
-+      buf = vmalloc(sizeof(*buf));
-+      if (!buf) {
-+              return -ENOMEM;
-+              goto out;
-+      }
-+      tab = &buf->tab;
-+
-+      blocklen = master->erasesize;
-+      if (blocklen < BLOCK_LEN_MIN)
-+              blocklen = BLOCK_LEN_MIN;
-+
-+      offset = blocklen;
-+
-+      /* Find the partition table */
-+      for (i = 0; i < 4; i++, offset += blocklen) {
-+              printk(KERN_DEBUG "%s: searching for MyLoader partition table"
-+                              " at offset 0x%lx\n", master->name, offset);
-+
-+              ret = mtd_read(master, offset, sizeof(*buf), &retlen,
-+                             (void *)buf);
-+              if (ret)
-+                      goto out_free_buf;
-+
-+              if (retlen != sizeof(*buf)) {
-+                      ret = -EIO;
-+                      goto out_free_buf;
-+              }
-+
-+              /* Check for Partition Table magic number */
-+              if (tab->magic == le32_to_cpu(MYLO_MAGIC_PARTITIONS))
-+                      break;
-+
-+      }
-+
-+      if (tab->magic != le32_to_cpu(MYLO_MAGIC_PARTITIONS)) {
-+              printk(KERN_DEBUG "%s: no MyLoader partition table found\n",
-+                      master->name);
-+              ret = 0;
-+              goto out_free_buf;
-+      }
-+
-+      /* The MyLoader and the Partition Table is always present */
-+      num_parts = 2;
-+
-+      /* Detect number of used partitions */
-+      for (i = 0; i < MYLO_MAX_PARTITIONS; i++) {
-+              part = &tab->partitions[i];
-+
-+              if (le16_to_cpu(part->type) == PARTITION_TYPE_FREE)
-+                      continue;
-+
-+              num_parts++;
-+      }
-+
-+      mtd_parts = kzalloc((num_parts * sizeof(*mtd_part) +
-+                              num_parts * PART_NAME_LEN), GFP_KERNEL);
-+
-+      if (!mtd_parts) {
-+              ret = -ENOMEM;
-+              goto out_free_buf;
-+      }
-+
-+      mtd_part = mtd_parts;
-+      names = (char *)&mtd_parts[num_parts];
-+
-+      strncpy(names, "myloader", PART_NAME_LEN);
-+      mtd_part->name = names;
-+      mtd_part->offset = 0;
-+      mtd_part->size = offset;
-+      mtd_part->mask_flags = MTD_WRITEABLE;
-+      mtd_part++;
-+      names += PART_NAME_LEN;
-+
-+      strncpy(names, "partition_table", PART_NAME_LEN);
-+      mtd_part->name = names;
-+      mtd_part->offset = offset;
-+      mtd_part->size = blocklen;
-+      mtd_part->mask_flags = MTD_WRITEABLE;
-+      mtd_part++;
-+      names += PART_NAME_LEN;
-+
-+      for (i = 0; i < MYLO_MAX_PARTITIONS; i++) {
-+              part = &tab->partitions[i];
-+
-+              if (le16_to_cpu(part->type) == PARTITION_TYPE_FREE)
-+                      continue;
-+
-+              if ((buf->names[i][0]) && (buf->names[i][0] != '\xff'))
-+                      strncpy(names, buf->names[i], PART_NAME_LEN);
-+              else
-+                      snprintf(names, PART_NAME_LEN, "partition%d", i);
-+
-+              mtd_part->offset = le32_to_cpu(part->addr);
-+              mtd_part->size = le32_to_cpu(part->size);
-+              mtd_part->name = names;
-+              mtd_part++;
-+              names += PART_NAME_LEN;
-+      }
-+
-+      *pparts = mtd_parts;
-+      ret = num_parts;
-+
-+ out_free_buf:
-+      vfree(buf);
-+ out:
-+      return ret;
-+}
-+
-+static struct mtd_part_parser myloader_mtd_parser = {
-+      .owner          = THIS_MODULE,
-+      .parse_fn       = myloader_parse_partitions,
-+      .name           = "MyLoader",
-+};
-+
-+static int __init myloader_mtd_parser_init(void)
-+{
-+      register_mtd_parser(&myloader_mtd_parser);
-+
-+      return 0;
-+}
-+
-+static void __exit myloader_mtd_parser_exit(void)
-+{
-+      deregister_mtd_parser(&myloader_mtd_parser);
-+}
-+
-+module_init(myloader_mtd_parser_init);
-+module_exit(myloader_mtd_parser_exit);
-+
-+MODULE_AUTHOR("Gabor Juhos <[email protected]>");
-+MODULE_DESCRIPTION("Parsing code for MyLoader partition tables");
-+MODULE_LICENSE("GPL v2");
diff --git a/target/linux/generic/pending-5.15/431-mtd-bcm47xxpart-check-for-bad-blocks-when-calculatin.patch b/target/linux/generic/pending-5.15/431-mtd-bcm47xxpart-check-for-bad-blocks-when-calculatin.patch
deleted file mode 100644 (file)
index bcea45d..0000000
+++ /dev/null
@@ -1,68 +0,0 @@
-From: =?UTF-8?q?Rafa=C5=82=20Mi=C5=82ecki?= <[email protected]>
-Subject: [PATCH] mtd: bcm47xxpart: check for bad blocks when calculating offsets
-
-Signed-off-by: Rafał Miłecki <[email protected]>
----
-
---- a/drivers/mtd/parsers/parser_trx.c
-+++ b/drivers/mtd/parsers/parser_trx.c
-@@ -25,6 +25,33 @@ struct trx_header {
-       uint32_t offset[3];
- } __packed;
-+/*
-+ * Calculate real end offset (address) for a given amount of data. It checks
-+ * all blocks skipping bad ones.
-+ */
-+static size_t parser_trx_real_offset(struct mtd_info *mtd, size_t bytes)
-+{
-+      size_t real_offset = 0;
-+
-+      if (mtd_block_isbad(mtd, real_offset))
-+              pr_warn("Base offset shouldn't be at bad block");
-+
-+      while (bytes >= mtd->erasesize) {
-+              bytes -= mtd->erasesize;
-+              real_offset += mtd->erasesize;
-+              while (mtd_block_isbad(mtd, real_offset)) {
-+                      real_offset += mtd->erasesize;
-+
-+                      if (real_offset >= mtd->size)
-+                              return real_offset - mtd->erasesize;
-+              }
-+      }
-+
-+      real_offset += bytes;
-+
-+      return real_offset;
-+}
-+
- static const char *parser_trx_data_part_name(struct mtd_info *master,
-                                            size_t offset)
- {
-@@ -86,21 +113,21 @@ static int parser_trx_parse(struct mtd_i
-       if (trx.offset[2]) {
-               part = &parts[curr_part++];
-               part->name = "loader";
--              part->offset = trx.offset[i];
-+              part->offset = parser_trx_real_offset(mtd, trx.offset[i]);
-               i++;
-       }
-       if (trx.offset[i]) {
-               part = &parts[curr_part++];
-               part->name = "linux";
--              part->offset = trx.offset[i];
-+              part->offset = parser_trx_real_offset(mtd, trx.offset[i]);
-               i++;
-       }
-       if (trx.offset[i]) {
-               part = &parts[curr_part++];
--              part->name = parser_trx_data_part_name(mtd, trx.offset[i]);
--              part->offset = trx.offset[i];
-+              part->offset = parser_trx_real_offset(mtd, trx.offset[i]);
-+              part->name = parser_trx_data_part_name(mtd, part->offset);
-               i++;
-       }
diff --git a/target/linux/generic/pending-5.15/432-mtd-bcm47xxpart-detect-T_Meter-partition.patch b/target/linux/generic/pending-5.15/432-mtd-bcm47xxpart-detect-T_Meter-partition.patch
deleted file mode 100644 (file)
index 852654d..0000000
+++ /dev/null
@@ -1,37 +0,0 @@
-From: =?UTF-8?q?Rafa=C5=82=20Mi=C5=82ecki?= <[email protected]>
-Subject: mtd: bcm47xxpart: detect T_Meter partition
-
-It can be found on many Netgear devices. It consists of many 0x30 blocks
-starting with 4D 54.
-
-Signed-off-by: Rafał Miłecki <[email protected]>
----
- drivers/mtd/bcm47xxpart.c | 10 ++++++++++
- 1 file changed, 10 insertions(+)
-
---- a/drivers/mtd/parsers/bcm47xxpart.c
-+++ b/drivers/mtd/parsers/bcm47xxpart.c
-@@ -35,6 +35,7 @@
- #define NVRAM_HEADER                  0x48534C46      /* FLSH */
- #define POT_MAGIC1                    0x54544f50      /* POTT */
- #define POT_MAGIC2                    0x504f          /* OP */
-+#define T_METER_MAGIC                 0x4D540000      /* MT */
- #define ML_MAGIC1                     0x39685a42
- #define ML_MAGIC2                     0x26594131
- #define TRX_MAGIC                     0x30524448
-@@ -178,6 +179,15 @@ static int bcm47xxpart_parse(struct mtd_
-                                            MTD_WRITEABLE);
-                       continue;
-               }
-+
-+              /* T_Meter */
-+              if ((le32_to_cpu(buf[0x000 / 4]) & 0xFFFF0000) == T_METER_MAGIC &&
-+                  (le32_to_cpu(buf[0x030 / 4]) & 0xFFFF0000) == T_METER_MAGIC &&
-+                  (le32_to_cpu(buf[0x060 / 4]) & 0xFFFF0000) == T_METER_MAGIC) {
-+                      bcm47xxpart_add_part(&parts[curr_part++], "T_Meter", offset,
-+                                           MTD_WRITEABLE);
-+                      continue;
-+              }
-               /* TRX */
-               if (buf[0x000 / 4] == TRX_MAGIC) {
diff --git a/target/linux/generic/pending-5.15/435-mtd-add-routerbootpart-parser-config.patch b/target/linux/generic/pending-5.15/435-mtd-add-routerbootpart-parser-config.patch
deleted file mode 100644 (file)
index ee949f7..0000000
+++ /dev/null
@@ -1,38 +0,0 @@
-From 4437e01fb6bca63fccdba5d6c44888b0935885c2 Mon Sep 17 00:00:00 2001
-From: =?UTF-8?q?Thibaut=20VAR=C3=88NE?= <[email protected]>
-Date: Tue, 24 Mar 2020 11:45:07 +0100
-Subject: [PATCH] generic: routerboot partition build bits (5.4)
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-This patch adds routerbootpart kernel build bits
-
-Signed-off-by: Thibaut VARÈNE <[email protected]>
----
- drivers/mtd/parsers/Kconfig  | 9 +++++++++
- drivers/mtd/parsers/Makefile | 1 +
- 2 files changed, 10 insertions(+)
-
---- a/drivers/mtd/parsers/Kconfig
-+++ b/drivers/mtd/parsers/Kconfig
-@@ -226,3 +226,12 @@ config MTD_SERCOMM_PARTS
-         partition map. This partition table contains real partition
-         offsets, which may differ from device to device depending on the
-         number and location of bad blocks on NAND.
-+
-+config MTD_ROUTERBOOT_PARTS
-+      tristate "RouterBoot flash partition parser"
-+      depends on MTD && OF
-+      help
-+       MikroTik RouterBoot is implemented as a multi segment system on the
-+       flash, some of which are fixed and some of which are located at
-+       variable offsets. This parser handles both cases via properly
-+       formatted DTS.
---- a/drivers/mtd/parsers/Makefile
-+++ b/drivers/mtd/parsers/Makefile
-@@ -16,3 +16,4 @@ obj-$(CONFIG_MTD_SERCOMM_PARTS)              += scpa
- obj-$(CONFIG_MTD_SHARPSL_PARTS)               += sharpslpart.o
- obj-$(CONFIG_MTD_REDBOOT_PARTS)               += redboot.o
- obj-$(CONFIG_MTD_QCOMSMEM_PARTS)      += qcomsmempart.o
-+obj-$(CONFIG_MTD_ROUTERBOOT_PARTS)            += routerbootpart.o
diff --git a/target/linux/generic/pending-5.15/460-mtd-cfi_cmdset_0002-no-erase_suspend.patch b/target/linux/generic/pending-5.15/460-mtd-cfi_cmdset_0002-no-erase_suspend.patch
deleted file mode 100644 (file)
index 0be74a5..0000000
+++ /dev/null
@@ -1,25 +0,0 @@
-From: Felix Fietkau <[email protected]>
-Subject: kernel: disable cfi cmdset 0002 erase suspend
-
-on some platforms, erase suspend leads to data corruption and lockups when write
-ops collide with erase ops. this has been observed on the buffalo wzr-hp-g300nh.
-rather than play whack-a-mole with a hard to reproduce issue on a variety of devices,
-simply disable erase suspend, as it will usually not produce any useful gain on
-the small filesystems used on embedded hardware.
-
-Signed-off-by: Felix Fietkau <[email protected]>
----
- drivers/mtd/chips/cfi_cmdset_0002.c | 2 +-
- 1 file changed, 1 insertion(+), 1 deletion(-)
-
---- a/drivers/mtd/chips/cfi_cmdset_0002.c
-+++ b/drivers/mtd/chips/cfi_cmdset_0002.c
-@@ -907,7 +907,7 @@ static int get_chip(struct map_info *map
-               return 0;
-       case FL_ERASING:
--              if (!cfip || !(cfip->EraseSuspend & (0x1|0x2)) ||
-+              if (1 /* no suspend */ || !cfip || !(cfip->EraseSuspend & (0x1|0x2)) ||
-                   !(mode == FL_READY || mode == FL_POINT ||
-                   (mode == FL_WRITING && (cfip->EraseSuspend & 0x2))))
-                       goto sleep;
diff --git a/target/linux/generic/pending-5.15/461-mtd-cfi_cmdset_0002-add-buffer-write-cmd-timeout.patch b/target/linux/generic/pending-5.15/461-mtd-cfi_cmdset_0002-add-buffer-write-cmd-timeout.patch
deleted file mode 100644 (file)
index ca56de8..0000000
+++ /dev/null
@@ -1,17 +0,0 @@
-From: George Kashperko <[email protected]>
-Subject: Issue map read after Write Buffer Load command to ensure chip is ready to receive data.
-
-Signed-off-by: George Kashperko <[email protected]>
----
- drivers/mtd/chips/cfi_cmdset_0002.c |    1 +
- 1 file changed, 1 insertion(+)
---- a/drivers/mtd/chips/cfi_cmdset_0002.c
-+++ b/drivers/mtd/chips/cfi_cmdset_0002.c
-@@ -2051,6 +2051,7 @@ static int __xipram do_write_buffer(stru
-       /* Write Buffer Load */
-       map_write(map, CMD(0x25), cmd_adr);
-+      (void) map_read(map, cmd_adr);
-       chip->state = FL_WRITING_TO_BUFFER;
diff --git a/target/linux/generic/pending-5.15/465-m25p80-mx-disable-software-protection.patch b/target/linux/generic/pending-5.15/465-m25p80-mx-disable-software-protection.patch
deleted file mode 100644 (file)
index f58d545..0000000
+++ /dev/null
@@ -1,18 +0,0 @@
-From: Felix Fietkau <[email protected]>
-Subject: Disable software protection bits for Macronix flashes.
-
-Signed-off-by: Felix Fietkau <[email protected]>
----
- drivers/mtd/spi-nor/spi-nor.c | 1 +
- 1 file changed, 1 insertion(+)
-
---- a/drivers/mtd/spi-nor/macronix.c
-+++ b/drivers/mtd/spi-nor/macronix.c
-@@ -93,6 +93,7 @@ static void macronix_default_init(struct
- {
-       nor->params->quad_enable = spi_nor_sr1_bit6_quad_enable;
-       nor->params->set_4byte_addr_mode = spi_nor_set_4byte_addr_mode;
-+      nor->flags |= SNOR_F_HAS_LOCK;
- }
- static const struct spi_nor_fixups macronix_fixups = {
diff --git a/target/linux/generic/pending-5.15/476-mtd-spi-nor-add-eon-en25q128.patch b/target/linux/generic/pending-5.15/476-mtd-spi-nor-add-eon-en25q128.patch
deleted file mode 100644 (file)
index 9383e48..0000000
+++ /dev/null
@@ -1,18 +0,0 @@
-From: Piotr Dymacz <[email protected]>
-Subject: kernel/mtd: add support for EON EN25Q128
-
-Signed-off-by: Piotr Dymacz <[email protected]>
----
- drivers/mtd/spi-nor/spi-nor.c | 1 +
- 1 file changed, 1 insertion(+)
-
---- a/drivers/mtd/spi-nor/eon.c
-+++ b/drivers/mtd/spi-nor/eon.c
-@@ -25,6 +25,7 @@ static const struct flash_info eon_parts
-       { "en25q32b",   INFO(0x1c3016, 0, 64 * 1024,   64, 0) },
-       { "en25p64",    INFO(0x1c2017, 0, 64 * 1024,  128, 0) },
-       { "en25q64",    INFO(0x1c3017, 0, 64 * 1024,  128, SECT_4K) },
-+      { "en25q128",   INFO(0x1c3018, 0, 64 * 1024,  256, SECT_4K) },
-       { "en25q80a",   INFO(0x1c3014, 0, 64 * 1024,   16,
-                            SECT_4K | SPI_NOR_DUAL_READ) },
-       { "en25qh16",   INFO(0x1c7015, 0, 64 * 1024,   32,
diff --git a/target/linux/generic/pending-5.15/477-mtd-spi-nor-add-eon-en25qx128a.patch b/target/linux/generic/pending-5.15/477-mtd-spi-nor-add-eon-en25qx128a.patch
deleted file mode 100644 (file)
index 3c579e5..0000000
+++ /dev/null
@@ -1,21 +0,0 @@
-From: Christian Marangi <[email protected]>
-Subject: kernel/mtd: add support for EON EN25QX128A
-
-Add support for EON EN25QX128A with no flags as it does
-support SFDP parsing.
-
-Signed-off-by: Christian Marangi <[email protected]>
----
- drivers/mtd/spi-nor/spi-nor.c | 1 +
- 1 file changed, 1 insertion(+)
-
---- a/drivers/mtd/spi-nor/eon.c
-+++ b/drivers/mtd/spi-nor/eon.c
-@@ -26,6 +26,7 @@ static const struct flash_info eon_parts
-       { "en25p64",    INFO(0x1c2017, 0, 64 * 1024,  128, 0) },
-       { "en25q64",    INFO(0x1c3017, 0, 64 * 1024,  128, SECT_4K) },
-       { "en25q128",   INFO(0x1c3018, 0, 64 * 1024,  256, SECT_4K) },
-+      { "en25qx128a", INFO(0x1c7118, 0, 64 * 1024, 256, 0) },
-       { "en25q80a",   INFO(0x1c3014, 0, 64 * 1024,   16,
-                            SECT_4K | SPI_NOR_DUAL_READ) },
-       { "en25qh16",   INFO(0x1c7015, 0, 64 * 1024,   32,
diff --git a/target/linux/generic/pending-5.15/479-mtd-spi-nor-add-xtx-xt25f128b.patch b/target/linux/generic/pending-5.15/479-mtd-spi-nor-add-xtx-xt25f128b.patch
deleted file mode 100644 (file)
index 4647158..0000000
+++ /dev/null
@@ -1,79 +0,0 @@
-From patchwork Thu Feb  6 17:19:41 2020
-Content-Type: text/plain; charset="utf-8"
-MIME-Version: 1.0
-Content-Transfer-Encoding: 7bit
-X-Patchwork-Submitter: Daniel Golle <[email protected]>
-X-Patchwork-Id: 1234465
-Date: Thu, 6 Feb 2020 19:19:41 +0200
-From: Daniel Golle <[email protected]>
-Subject: [PATCH v2] mtd: spi-nor: Add support for xt25f128b chip
-Message-ID: <[email protected]>
-MIME-Version: 1.0
-Content-Disposition: inline
-List-Subscribe: <http://lists.infradead.org/mailman/listinfo/linux-mtd>,
- <mailto:[email protected]?subject=subscribe>
-Cc: Eitan Cohen <[email protected]>, Piotr Dymacz <[email protected]>,
- Tudor Ambarus <[email protected]>
-Sender: "linux-mtd" <[email protected]>
-Errors-To: linux-mtd-bounces+incoming=patchwork.ozlabs.org@lists.infradead.org
-
-Add XT25F128B made by XTX Technology (Shenzhen) Limited.
-This chip supports dual and quad read and uniform 4K-byte erase.
-Verified on Teltonika RUT955 which comes with XT25F128B in recent
-versions of the device.
-
-Signed-off-by: Daniel Golle <[email protected]>
-Signed-off-by: Felix Fietkau <[email protected]>
----
- drivers/mtd/spi-nor/spi-nor.c | 4 ++++
- 1 file changed, 4 insertions(+)
-
---- a/drivers/mtd/spi-nor/Makefile
-+++ b/drivers/mtd/spi-nor/Makefile
-@@ -18,6 +18,7 @@ spi-nor-objs                 += sst.o
- spi-nor-objs                  += winbond.o
- spi-nor-objs                  += xilinx.o
- spi-nor-objs                  += xmc.o
-+spi-nor-objs                  += xtx.o
- obj-$(CONFIG_MTD_SPI_NOR)     += spi-nor.o
- obj-$(CONFIG_MTD_SPI_NOR)     += controllers/
---- /dev/null
-+++ b/drivers/mtd/spi-nor/xtx.c
-@@ -0,0 +1,15 @@
-+// SPDX-License-Identifier: GPL-2.0
-+#include <linux/mtd/spi-nor.h>
-+
-+#include "core.h"
-+
-+static const struct flash_info xtx_parts[] = {
-+      /* XTX Technology (Shenzhen) Limited */
-+      { "xt25f128b", INFO(0x0B4018, 0, 64 * 1024, 256, SECT_4K | SPI_NOR_DUAL_READ | SPI_NOR_QUAD_READ) },
-+};
-+
-+const struct spi_nor_manufacturer spi_nor_xtx = {
-+      .name = "xtx",
-+      .parts = xtx_parts,
-+      .nparts = ARRAY_SIZE(xtx_parts),
-+};
---- a/drivers/mtd/spi-nor/core.c
-+++ b/drivers/mtd/spi-nor/core.c
-@@ -1861,6 +1861,7 @@ static const struct spi_nor_manufacturer
-       &spi_nor_winbond,
-       &spi_nor_xilinx,
-       &spi_nor_xmc,
-+      &spi_nor_xtx,
- };
- static const struct flash_info *
---- a/drivers/mtd/spi-nor/core.h
-+++ b/drivers/mtd/spi-nor/core.h
-@@ -490,6 +490,7 @@ extern const struct spi_nor_manufacturer
- extern const struct spi_nor_manufacturer spi_nor_winbond;
- extern const struct spi_nor_manufacturer spi_nor_xilinx;
- extern const struct spi_nor_manufacturer spi_nor_xmc;
-+extern const struct spi_nor_manufacturer spi_nor_xtx;
- extern const struct attribute_group *spi_nor_sysfs_groups[];
diff --git a/target/linux/generic/pending-5.15/481-mtd-spi-nor-add-support-for-Gigadevice-GD25D05.patch b/target/linux/generic/pending-5.15/481-mtd-spi-nor-add-support-for-Gigadevice-GD25D05.patch
deleted file mode 100644 (file)
index c32cde5..0000000
+++ /dev/null
@@ -1,22 +0,0 @@
-From d68b4aa22e8c625685bfad642dd7337948dc0ad1 Mon Sep 17 00:00:00 2001
-From: Koen Vandeputte <[email protected]>
-Date: Mon, 6 Jan 2020 13:07:56 +0100
-Subject: [PATCH] mtd: spi-nor: add support for Gigadevice GD25D05
-
-Signed-off-by: Koen Vandeputte <[email protected]>
----
- drivers/mtd/spi-nor/spi-nor.c | 5 +++++
- 1 file changed, 5 insertions(+)
-
---- a/drivers/mtd/spi-nor/gigadevice.c
-+++ b/drivers/mtd/spi-nor/gigadevice.c
-@@ -24,6 +24,9 @@ static struct spi_nor_fixups gd25q256_fi
- };
- static const struct flash_info gigadevice_parts[] = {
-+      { "gd25q05", INFO(0xc84010, 0, 64 * 1024,  1,
-+                        SECT_4K | SPI_NOR_DUAL_READ | SPI_NOR_QUAD_READ |
-+                        SPI_NOR_HAS_LOCK | SPI_NOR_HAS_TB) },
-       { "gd25q16", INFO(0xc84015, 0, 64 * 1024,  32,
-                         SECT_4K | SPI_NOR_DUAL_READ | SPI_NOR_QUAD_READ |
-                         SPI_NOR_HAS_LOCK | SPI_NOR_HAS_TB) },
diff --git a/target/linux/generic/pending-5.15/482-mtd-spi-nor-add-gd25q512.patch b/target/linux/generic/pending-5.15/482-mtd-spi-nor-add-gd25q512.patch
deleted file mode 100644 (file)
index 7c8b686..0000000
+++ /dev/null
@@ -1,21 +0,0 @@
-From f8943df3beb0d3f9754bb35320c3a378727175a8 Mon Sep 17 00:00:00 2001
-From: OpenWrt community <[email protected]>
-Date: Thu, 14 Jul 2022 08:38:07 +0200
-Subject: [PATCH] spi-nor/gigadevic: add gd25q512
-
----
- drivers/mtd/spi-nor/gigadevice.c | 3 +++
- 1 file changed, 3 insertions(+)
-
---- a/drivers/mtd/spi-nor/gigadevice.c
-+++ b/drivers/mtd/spi-nor/gigadevice.c
-@@ -53,6 +53,9 @@ static const struct flash_info gigadevic
-                          SPI_NOR_4B_OPCODES | SPI_NOR_HAS_LOCK |
-                          SPI_NOR_HAS_TB | SPI_NOR_TB_SR_BIT6)
-               .fixups = &gd25q256_fixups },
-+      { "gd25q512", INFO(0xc84020, 0, 64 * 1024, 1024,
-+                         SECT_4K | SPI_NOR_DUAL_READ | SPI_NOR_QUAD_READ |
-+                         SPI_NOR_HAS_LOCK | SPI_NOR_HAS_TB | SPI_NOR_4B_OPCODES) },
- };
- const struct spi_nor_manufacturer spi_nor_gigadevice = {
diff --git a/target/linux/generic/pending-5.15/484-mtd-spi-nor-add-esmt-f25l16pa.patch b/target/linux/generic/pending-5.15/484-mtd-spi-nor-add-esmt-f25l16pa.patch
deleted file mode 100644 (file)
index ab402e6..0000000
+++ /dev/null
@@ -1,23 +0,0 @@
-From 87363cc0e522de3294ea6ae10fb468d2a8d6fb2f Mon Sep 17 00:00:00 2001
-From: OpenWrt community <[email protected]>
-Date: Wed, 13 Jul 2022 12:17:21 +0200
-Subject: [PATCH] spi-nor/esmt.c: add esmt f25l16pa
-
-This fixes support for Dongwon T&I DW02-412H which uses F25L16PA(2S)
-flash.
-
----
- drivers/mtd/spi-nor/esmt.c | 2 ++
- 1 file changed, 2 insertions(+)
-
---- a/drivers/mtd/spi-nor/esmt.c
-+++ b/drivers/mtd/spi-nor/esmt.c
-@@ -10,6 +10,8 @@
- static const struct flash_info esmt_parts[] = {
-       /* ESMT */
-+      { "f25l16pa-2s", INFO(0x8c2115, 0, 64 * 1024, 32,
-+                         SECT_4K | SPI_NOR_HAS_LOCK) },
-       { "f25l32pa", INFO(0x8c2016, 0, 64 * 1024, 64,
-                          SECT_4K | SPI_NOR_HAS_LOCK | SPI_NOR_SWP_IS_VOLATILE) },
-       { "f25l32qa", INFO(0x8c4116, 0, 64 * 1024, 64,
diff --git a/target/linux/generic/pending-5.15/485-mtd-spi-nor-add-xmc-xm25qh128c.patch b/target/linux/generic/pending-5.15/485-mtd-spi-nor-add-xmc-xm25qh128c.patch
deleted file mode 100644 (file)
index 68e373e..0000000
+++ /dev/null
@@ -1,24 +0,0 @@
-From f6b33d850f7f12555df2fa0e3349b33427bf5890 Mon Sep 17 00:00:00 2001
-From: OpenWrt community <[email protected]>
-Date: Wed, 13 Jul 2022 12:19:01 +0200
-Subject: [PATCH] spi-nor/xmc.c: add xm25qh128c
-
-The XMC XM25QH128C is a 16MB SPI NOR chip. The patch is verified on
-Ruijie RG-EW3200GX PRO.
-Datasheet available at https://www.xmcwh.com/uploads/435/XM25QH128C.pdf
-
----
- drivers/mtd/spi-nor/xmc.c | 2 ++
- 1 file changed, 2 insertions(+)
-
---- a/drivers/mtd/spi-nor/xmc.c
-+++ b/drivers/mtd/spi-nor/xmc.c
-@@ -14,6 +14,8 @@ static const struct flash_info xmc_parts
-                           SECT_4K | SPI_NOR_DUAL_READ | SPI_NOR_QUAD_READ) },
-       { "XM25QH128A", INFO(0x207018, 0, 64 * 1024, 256,
-                            SECT_4K | SPI_NOR_DUAL_READ | SPI_NOR_QUAD_READ) },
-+      { "XM25QH128C", INFO(0x204018, 0, 64 * 1024, 256,
-+                           SECT_4K | SPI_NOR_DUAL_READ | SPI_NOR_QUAD_READ) },
- };
- const struct spi_nor_manufacturer spi_nor_xmc = {
diff --git a/target/linux/generic/pending-5.15/486-01-mtd-spinand-add-support-for-ESMT-F50x1G41LB.patch b/target/linux/generic/pending-5.15/486-01-mtd-spinand-add-support-for-ESMT-F50x1G41LB.patch
deleted file mode 100644 (file)
index d117cfe..0000000
+++ /dev/null
@@ -1,143 +0,0 @@
-From a43b844cb40bf1b783055fdc81b7f991e21e7e76 Mon Sep 17 00:00:00 2001
-From: Chuanhong Guo <[email protected]>
-Date: Wed, 13 Apr 2022 11:58:17 +0800
-Subject: [PATCH] mtd: spinand: add support for ESMT F50x1G41LB
-
-This patch adds support for ESMT F50L1G41LB and F50D1G41LB.
-It seems that ESMT likes to use random JEDEC ID from other vendors.
-Their 1G chips uses 0xc8 from GigaDevice and 2G/4G chips uses 0x2c from
-Micron. For this reason, the ESMT entry is named esmt_c8 with explicit
-JEDEC ID in variable name.
-
-Datasheets:
-https://www.esmt.com.tw/upload/pdf/ESMT/datasheets/F50L1G41LB(2M).pdf
-https://www.esmt.com.tw/upload/pdf/ESMT/datasheets/F50D1G41LB(2M).pdf
-
-Signed-off-by: Chuanhong Guo <[email protected]>
----
- drivers/mtd/nand/spi/Makefile |  2 +-
- drivers/mtd/nand/spi/core.c   |  1 +
- drivers/mtd/nand/spi/esmt.c   | 89 +++++++++++++++++++++++++++++++++++
- include/linux/mtd/spinand.h   |  1 +
- 4 files changed, 92 insertions(+), 1 deletion(-)
- create mode 100644 drivers/mtd/nand/spi/esmt.c
-
---- a/drivers/mtd/nand/spi/Makefile
-+++ b/drivers/mtd/nand/spi/Makefile
-@@ -1,3 +1,3 @@
- # SPDX-License-Identifier: GPL-2.0
--spinand-objs := core.o gigadevice.o macronix.o micron.o paragon.o toshiba.o winbond.o xtx.o
-+spinand-objs := core.o esmt.o gigadevice.o macronix.o micron.o paragon.o toshiba.o winbond.o xtx.o
- obj-$(CONFIG_MTD_SPI_NAND) += spinand.o
---- a/drivers/mtd/nand/spi/core.c
-+++ b/drivers/mtd/nand/spi/core.c
-@@ -906,6 +906,7 @@ static const struct nand_ops spinand_ops
- };
- static const struct spinand_manufacturer *spinand_manufacturers[] = {
-+      &esmt_c8_spinand_manufacturer,
-       &gigadevice_spinand_manufacturer,
-       &macronix_spinand_manufacturer,
-       &micron_spinand_manufacturer,
---- /dev/null
-+++ b/drivers/mtd/nand/spi/esmt.c
-@@ -0,0 +1,89 @@
-+// SPDX-License-Identifier: GPL-2.0
-+/*
-+ * Author:
-+ *    Chuanhong Guo <[email protected]>
-+ */
-+
-+#include <linux/device.h>
-+#include <linux/kernel.h>
-+#include <linux/mtd/spinand.h>
-+
-+/* ESMT uses GigaDevice 0xc8 JECDEC ID on some SPI NANDs */
-+#define SPINAND_MFR_ESMT_C8                   0xc8
-+
-+static SPINAND_OP_VARIANTS(read_cache_variants,
-+                         SPINAND_PAGE_READ_FROM_CACHE_QUADIO_OP(0, 2, NULL, 0),
-+                         SPINAND_PAGE_READ_FROM_CACHE_X4_OP(0, 1, NULL, 0),
-+                         SPINAND_PAGE_READ_FROM_CACHE_DUALIO_OP(0, 1, NULL, 0),
-+                         SPINAND_PAGE_READ_FROM_CACHE_X2_OP(0, 1, NULL, 0),
-+                         SPINAND_PAGE_READ_FROM_CACHE_OP(true, 0, 1, NULL, 0),
-+                         SPINAND_PAGE_READ_FROM_CACHE_OP(false, 0, 1, NULL, 0));
-+
-+static SPINAND_OP_VARIANTS(write_cache_variants,
-+                         SPINAND_PROG_LOAD_X4(true, 0, NULL, 0),
-+                         SPINAND_PROG_LOAD(true, 0, NULL, 0));
-+
-+static SPINAND_OP_VARIANTS(update_cache_variants,
-+                         SPINAND_PROG_LOAD_X4(false, 0, NULL, 0),
-+                         SPINAND_PROG_LOAD(false, 0, NULL, 0));
-+
-+static int f50l1g41lb_ooblayout_ecc(struct mtd_info *mtd, int section,
-+                                  struct mtd_oob_region *region)
-+{
-+      if (section > 3)
-+              return -ERANGE;
-+
-+      region->offset = 16 * section + 8;
-+      region->length = 8;
-+
-+      return 0;
-+}
-+
-+static int f50l1g41lb_ooblayout_free(struct mtd_info *mtd, int section,
-+                                   struct mtd_oob_region *region)
-+{
-+      if (section > 3)
-+              return -ERANGE;
-+
-+      region->offset = 16 * section + 2;
-+      region->length = 6;
-+
-+      return 0;
-+}
-+
-+static const struct mtd_ooblayout_ops f50l1g41lb_ooblayout = {
-+      .ecc = f50l1g41lb_ooblayout_ecc,
-+      .free = f50l1g41lb_ooblayout_free,
-+};
-+
-+static const struct spinand_info esmt_c8_spinand_table[] = {
-+      SPINAND_INFO("F50L1G41LB",
-+                   SPINAND_ID(SPINAND_READID_METHOD_OPCODE_ADDR, 0x01),
-+                   NAND_MEMORG(1, 2048, 64, 64, 1024, 20, 1, 1, 1),
-+                   NAND_ECCREQ(1, 512),
-+                   SPINAND_INFO_OP_VARIANTS(&read_cache_variants,
-+                                            &write_cache_variants,
-+                                            &update_cache_variants),
-+                   0,
-+                   SPINAND_ECCINFO(&f50l1g41lb_ooblayout, NULL)),
-+      SPINAND_INFO("F50D1G41LB",
-+                   SPINAND_ID(SPINAND_READID_METHOD_OPCODE_ADDR, 0x11),
-+                   NAND_MEMORG(1, 2048, 64, 64, 1024, 20, 1, 1, 1),
-+                   NAND_ECCREQ(1, 512),
-+                   SPINAND_INFO_OP_VARIANTS(&read_cache_variants,
-+                                            &write_cache_variants,
-+                                            &update_cache_variants),
-+                   0,
-+                   SPINAND_ECCINFO(&f50l1g41lb_ooblayout, NULL)),
-+};
-+
-+static const struct spinand_manufacturer_ops esmt_spinand_manuf_ops = {
-+};
-+
-+const struct spinand_manufacturer esmt_c8_spinand_manufacturer = {
-+      .id = SPINAND_MFR_ESMT_C8,
-+      .name = "ESMT",
-+      .chips = esmt_c8_spinand_table,
-+      .nchips = ARRAY_SIZE(esmt_c8_spinand_table),
-+      .ops = &esmt_spinand_manuf_ops,
-+};
---- a/include/linux/mtd/spinand.h
-+++ b/include/linux/mtd/spinand.h
-@@ -260,6 +260,7 @@ struct spinand_manufacturer {
- };
- /* SPI NAND manufacturers */
-+extern const struct spinand_manufacturer esmt_c8_spinand_manufacturer;
- extern const struct spinand_manufacturer gigadevice_spinand_manufacturer;
- extern const struct spinand_manufacturer macronix_spinand_manufacturer;
- extern const struct spinand_manufacturer micron_spinand_manufacturer;
diff --git a/target/linux/generic/pending-5.15/487-mtd-spinand-Add-support-for-Etron-EM73D044VCx.patch b/target/linux/generic/pending-5.15/487-mtd-spinand-Add-support-for-Etron-EM73D044VCx.patch
deleted file mode 100644 (file)
index 7e20e14..0000000
+++ /dev/null
@@ -1,168 +0,0 @@
-From f32085fc0b87049491b07e198d924d738a1a2834 Mon Sep 17 00:00:00 2001
-From: Daniel Danzberger <[email protected]>
-Date: Wed, 3 Aug 2022 17:31:03 +0200
-Subject: [PATCH] mtd: spinand: Add support for Etron EM73D044VCx
-
-Airoha is a new ARM platform based on Cortex-A53 which has recently been
-merged into linux-next.
-
-Due to BootROM limitations on this platform, the Cortex-A53 can't run in
-Aarch64 mode and code must be compiled for 32-Bit ARM.
-
-This support is based mostly on those linux-next commits backported
-for kernel 5.15.
-
-Patches:
-1 - platform support = linux-next
-2 - clock driver = linux-next
-3 - gpio driver = linux-next
-4 - linux,usable-memory-range dts support = linux-next
-5 - mtd spinand driver
-6 - spi driver
-7 - pci driver (kconfig only, uses mediatek PCI) = linux-next
-
-Still missing:
-- Ethernet driver
-- Sysupgrade support
-
-A.t.m there exists one subtarget EN7523 with only one evaluation
-board.
-
-The initramfs can be run with the following commands from u-boot:
--
-u-boot> setenv bootfile \
-       openwrt-airoha-airoha_en7523-evb-initramfs-kernel.bin
-u-boot> tftpboot
-u-boot> bootm 0x81800000
--
-
-Submitted-by: Daniel Danzberger <[email protected]>
-
---- a/drivers/mtd/nand/spi/Makefile
-+++ b/drivers/mtd/nand/spi/Makefile
-@@ -1,3 +1,3 @@
- # SPDX-License-Identifier: GPL-2.0
--spinand-objs := core.o esmt.o gigadevice.o macronix.o micron.o paragon.o toshiba.o winbond.o xtx.o
-+spinand-objs := core.o esmt.o etron.o gigadevice.o macronix.o micron.o paragon.o toshiba.o winbond.o xtx.o
- obj-$(CONFIG_MTD_SPI_NAND) += spinand.o
---- a/drivers/mtd/nand/spi/core.c
-+++ b/drivers/mtd/nand/spi/core.c
-@@ -908,6 +908,7 @@ static const struct nand_ops spinand_ops
- static const struct spinand_manufacturer *spinand_manufacturers[] = {
-       &esmt_c8_spinand_manufacturer,
-       &gigadevice_spinand_manufacturer,
-+      &etron_spinand_manufacturer,
-       &macronix_spinand_manufacturer,
-       &micron_spinand_manufacturer,
-       &paragon_spinand_manufacturer,
---- /dev/null
-+++ b/drivers/mtd/nand/spi/etron.c
-@@ -0,0 +1,98 @@
-+// SPDX-License-Identifier: GPL-2.0
-+
-+#include <linux/device.h>
-+#include <linux/kernel.h>
-+#include <linux/mtd/spinand.h>
-+
-+#define SPINAND_MFR_ETRON                     0xd5
-+
-+
-+static SPINAND_OP_VARIANTS(read_cache_variants,
-+              SPINAND_PAGE_READ_FROM_CACHE_QUADIO_OP(0, 1, NULL, 0),
-+              SPINAND_PAGE_READ_FROM_CACHE_X4_OP(0, 1, NULL, 0),
-+              SPINAND_PAGE_READ_FROM_CACHE_DUALIO_OP(0, 1, NULL, 0),
-+              SPINAND_PAGE_READ_FROM_CACHE_X2_OP(0, 1, NULL, 0),
-+              SPINAND_PAGE_READ_FROM_CACHE_OP(true, 0, 1, NULL, 0),
-+              SPINAND_PAGE_READ_FROM_CACHE_OP(false, 0, 1, NULL, 0));
-+
-+static SPINAND_OP_VARIANTS(write_cache_variants,
-+              SPINAND_PROG_LOAD_X4(true, 0, NULL, 0),
-+              SPINAND_PROG_LOAD(true, 0, NULL, 0));
-+
-+static SPINAND_OP_VARIANTS(update_cache_variants,
-+              SPINAND_PROG_LOAD_X4(false, 0, NULL, 0),
-+              SPINAND_PROG_LOAD(false, 0, NULL, 0));
-+
-+static int etron_ooblayout_ecc(struct mtd_info *mtd, int section,
-+                                      struct mtd_oob_region *oobregion)
-+{
-+      if (section)
-+              return -ERANGE;
-+
-+      oobregion->offset = 72;
-+      oobregion->length = 56;
-+
-+      return 0;
-+}
-+
-+static int etron_ooblayout_free(struct mtd_info *mtd, int section,
-+                         struct mtd_oob_region *oobregion)
-+{
-+      if (section)
-+              return -ERANGE;
-+
-+      oobregion->offset = 1;
-+      oobregion->length = 71;
-+
-+      return 0;
-+}
-+
-+static int etron_ecc_get_status(struct spinand_device *spinand, u8 status)
-+{
-+      switch (status & STATUS_ECC_MASK) {
-+      case STATUS_ECC_NO_BITFLIPS:
-+              return 0;
-+
-+      case STATUS_ECC_HAS_BITFLIPS:
-+              /* Between 1-7 bitflips were corrected */
-+              return 7;
-+
-+      case STATUS_ECC_MASK:
-+              /* Maximum bitflips were corrected */
-+              return 8;
-+
-+      case STATUS_ECC_UNCOR_ERROR:
-+              return -EBADMSG;
-+      }
-+
-+      return -EINVAL;
-+}
-+
-+static const struct mtd_ooblayout_ops etron_ooblayout = {
-+      .ecc = etron_ooblayout_ecc,
-+      .free = etron_ooblayout_free,
-+};
-+
-+static const struct spinand_info etron_spinand_table[] = {
-+      SPINAND_INFO("EM73D044VCx",
-+                   SPINAND_ID(SPINAND_READID_METHOD_OPCODE_ADDR, 0x1f),
-+                   // bpc, pagesize, oobsize, pagesperblock, bperlun, maxbadplun, ppl, lpt, #t
-+                   NAND_MEMORG(1, 2048, 128, 64, 2048, 40, 1, 1, 1),
-+                   NAND_ECCREQ(8, 512),
-+                   SPINAND_INFO_OP_VARIANTS(&read_cache_variants,
-+                                            &write_cache_variants,
-+                                            &update_cache_variants),
-+                   SPINAND_HAS_QE_BIT,
-+                   SPINAND_ECCINFO(&etron_ooblayout, etron_ecc_get_status)),
-+};
-+
-+static const struct spinand_manufacturer_ops etron_spinand_manuf_ops = {
-+};
-+
-+const struct spinand_manufacturer etron_spinand_manufacturer = {
-+      .id = SPINAND_MFR_ETRON,
-+      .name = "Etron",
-+      .chips = etron_spinand_table,
-+      .nchips = ARRAY_SIZE(etron_spinand_table),
-+      .ops = &etron_spinand_manuf_ops,
-+};
---- a/include/linux/mtd/spinand.h
-+++ b/include/linux/mtd/spinand.h
-@@ -261,6 +261,7 @@ struct spinand_manufacturer {
- /* SPI NAND manufacturers */
- extern const struct spinand_manufacturer esmt_c8_spinand_manufacturer;
-+extern const struct spinand_manufacturer etron_spinand_manufacturer;
- extern const struct spinand_manufacturer gigadevice_spinand_manufacturer;
- extern const struct spinand_manufacturer macronix_spinand_manufacturer;
- extern const struct spinand_manufacturer micron_spinand_manufacturer;
diff --git a/target/linux/generic/pending-5.15/488-mtd-spi-nor-add-xmc-xm25qh64c.patch b/target/linux/generic/pending-5.15/488-mtd-spi-nor-add-xmc-xm25qh64c.patch
deleted file mode 100644 (file)
index 236d1c2..0000000
+++ /dev/null
@@ -1,22 +0,0 @@
-From: Joe Mullally <[email protected]>
-Subject: mtd/spi-nor/xmc: add support for XMC XM25QH64C
-
-The XMC XM25QH64C is a 8MB SPI NOR chip. The patch is verified on TL-WPA8631P v3.
-Datasheet available at https://www.xmcwh.com/uploads/442/XM25QH64C.pdf
-
-Signed-off-by: Joe Mullally <[email protected]>
----
- drivers/mtd/spi-nor/xmc.c                             | 2 ++
- 1 file changed, 2 insertions(+)
-
---- a/drivers/mtd/spi-nor/xmc.c
-+++ b/drivers/mtd/spi-nor/xmc.c
-@@ -12,6 +12,8 @@ static const struct flash_info xmc_parts
-       /* XMC (Wuhan Xinxin Semiconductor Manufacturing Corp.) */
-       { "XM25QH64A", INFO(0x207017, 0, 64 * 1024, 128,
-                           SECT_4K | SPI_NOR_DUAL_READ | SPI_NOR_QUAD_READ) },
-+      { "XM25QH64C", INFO(0x204017, 0, 64 * 1024, 128,
-+                          SECT_4K | SPI_NOR_DUAL_READ | SPI_NOR_QUAD_READ) },
-       { "XM25QH128A", INFO(0x207018, 0, 64 * 1024, 256,
-                            SECT_4K | SPI_NOR_DUAL_READ | SPI_NOR_QUAD_READ) },
-       { "XM25QH128C", INFO(0x204018, 0, 64 * 1024, 256,
diff --git a/target/linux/generic/pending-5.15/490-ubi-auto-attach-mtd-device-named-ubi-or-data-on-boot.patch b/target/linux/generic/pending-5.15/490-ubi-auto-attach-mtd-device-named-ubi-or-data-on-boot.patch
deleted file mode 100644 (file)
index e8da36e..0000000
+++ /dev/null
@@ -1,97 +0,0 @@
-From: Daniel Golle <[email protected]>
-Subject: ubi: auto-attach mtd device named "ubi" or "data" on boot
-
-Signed-off-by: Daniel Golle <[email protected]>
----
- drivers/mtd/ubi/build.c | 36 ++++++++++++++++++++++++++++++++++++
- 1 file changed, 36 insertions(+)
-
---- a/drivers/mtd/ubi/build.c
-+++ b/drivers/mtd/ubi/build.c
-@@ -1207,6 +1207,73 @@ static struct mtd_info * __init open_mtd
-       return mtd;
- }
-+/*
-+ * This function tries attaching mtd partitions named either "ubi" or "data"
-+ * during boot.
-+ */
-+static void __init ubi_auto_attach(void)
-+{
-+      int err;
-+      struct mtd_info *mtd;
-+      loff_t offset = 0;
-+      size_t len;
-+      char magic[4];
-+
-+      /* try attaching mtd device named "ubi" or "data" */
-+      mtd = open_mtd_device("ubi");
-+      if (IS_ERR(mtd))
-+              mtd = open_mtd_device("data");
-+
-+      if (IS_ERR(mtd))
-+              return;
-+
-+      /* get the first not bad block */
-+      if (mtd_can_have_bb(mtd))
-+              while (mtd_block_isbad(mtd, offset)) {
-+                      offset += mtd->erasesize;
-+
-+                      if (offset > mtd->size) {
-+                              pr_err("UBI error: Failed to find a non-bad "
-+                                     "block on mtd%d\n", mtd->index);
-+                              goto cleanup;
-+                      }
-+              }
-+
-+      /* check if the read from flash was successful */
-+      err = mtd_read(mtd, offset, 4, &len, (void *) magic);
-+      if ((err && !mtd_is_bitflip(err)) || len != 4) {
-+              pr_err("UBI error: unable to read from mtd%d\n", mtd->index);
-+              goto cleanup;
-+      }
-+
-+      /* check for a valid ubi magic */
-+      if (strncmp(magic, "UBI#", 4)) {
-+              pr_err("UBI error: no valid UBI magic found inside mtd%d\n", mtd->index);
-+              goto cleanup;
-+      }
-+
-+      /* don't auto-add media types where UBI doesn't makes sense */
-+      if (mtd->type != MTD_NANDFLASH &&
-+          mtd->type != MTD_NORFLASH &&
-+          mtd->type != MTD_DATAFLASH &&
-+          mtd->type != MTD_MLCNANDFLASH)
-+              goto cleanup;
-+
-+      mutex_lock(&ubi_devices_mutex);
-+      pr_notice("UBI: auto-attach mtd%d\n", mtd->index);
-+      err = ubi_attach_mtd_dev(mtd, UBI_DEV_NUM_AUTO, 0, 0);
-+      mutex_unlock(&ubi_devices_mutex);
-+      if (err < 0) {
-+              pr_err("UBI error: cannot attach mtd%d\n", mtd->index);
-+              goto cleanup;
-+      }
-+
-+      return;
-+
-+cleanup:
-+      put_mtd_device(mtd);
-+}
-+
- static int __init ubi_init(void)
- {
-       int err, i, k;
-@@ -1290,6 +1357,12 @@ static int __init ubi_init(void)
-               }
-       }
-+      /* auto-attach mtd devices only if built-in to the kernel and no ubi.mtd
-+       * parameter was given */
-+      if (IS_ENABLED(CONFIG_MTD_ROOTFS_ROOT_DEV) &&
-+          !ubi_is_module() && !mtd_devs)
-+              ubi_auto_attach();
-+
-       err = ubiblock_init();
-       if (err) {
-               pr_err("UBI error: block: cannot initialize, error %d\n", err);
diff --git a/target/linux/generic/pending-5.15/491-ubi-auto-create-ubiblock-device-for-rootfs.patch b/target/linux/generic/pending-5.15/491-ubi-auto-create-ubiblock-device-for-rootfs.patch
deleted file mode 100644 (file)
index 4ddd27a..0000000
+++ /dev/null
@@ -1,69 +0,0 @@
-From: Daniel Golle <[email protected]>
-Subject: ubi: auto-create ubiblock device for rootfs
-
-Signed-off-by: Daniel Golle <[email protected]>
----
- drivers/mtd/ubi/block.c | 42 ++++++++++++++++++++++++++++++++++++++++++
- 1 file changed, 42 insertions(+)
-
---- a/drivers/mtd/ubi/block.c
-+++ b/drivers/mtd/ubi/block.c
-@@ -642,6 +642,47 @@ static void __init ubiblock_create_from_
-       }
- }
-+#define UBIFS_NODE_MAGIC  0x06101831
-+static inline int ubi_vol_is_ubifs(struct ubi_volume_desc *desc)
-+{
-+      int ret;
-+      uint32_t magic_of, magic;
-+      ret = ubi_read(desc, 0, (char *)&magic_of, 0, 4);
-+      if (ret)
-+              return 0;
-+      magic = le32_to_cpu(magic_of);
-+      return magic == UBIFS_NODE_MAGIC;
-+}
-+
-+static void ubiblock_create_auto_rootfs(void)
-+{
-+      int ubi_num, ret, is_ubifs;
-+      struct ubi_volume_desc *desc;
-+      struct ubi_volume_info vi;
-+
-+      for (ubi_num = 0; ubi_num < UBI_MAX_DEVICES; ubi_num++) {
-+              desc = ubi_open_volume_nm(ubi_num, "rootfs", UBI_READONLY);
-+              if (IS_ERR(desc))
-+                      desc = ubi_open_volume_nm(ubi_num, "fit", UBI_READONLY);;
-+
-+              if (IS_ERR(desc))
-+                      continue;
-+
-+              ubi_get_volume_info(desc, &vi);
-+              is_ubifs = ubi_vol_is_ubifs(desc);
-+              ubi_close_volume(desc);
-+              if (is_ubifs)
-+                      break;
-+
-+              ret = ubiblock_create(&vi);
-+              if (ret)
-+                      pr_err("UBI error: block: can't add '%s' volume, err=%d\n",
-+                              vi.name, ret);
-+              /* always break if we get here */
-+              break;
-+      }
-+}
-+
- static void ubiblock_remove_all(void)
- {
-       struct ubiblock *next;
-@@ -674,6 +715,10 @@ int __init ubiblock_init(void)
-        */
-       ubiblock_create_from_param();
-+      /* auto-attach "rootfs" volume if existing and non-ubifs */
-+      if (IS_ENABLED(CONFIG_MTD_ROOTFS_ROOT_DEV))
-+              ubiblock_create_auto_rootfs();
-+
-       /*
-        * Block devices are only created upon user requests, so we ignore
-        * existing volumes.
diff --git a/target/linux/generic/pending-5.15/492-try-auto-mounting-ubi0-rootfs-in-init-do_mounts.c.patch b/target/linux/generic/pending-5.15/492-try-auto-mounting-ubi0-rootfs-in-init-do_mounts.c.patch
deleted file mode 100644 (file)
index cf41c8c..0000000
+++ /dev/null
@@ -1,53 +0,0 @@
-From: Daniel Golle <[email protected]>
-Subject: try auto-mounting ubi0:rootfs in init/do_mounts.c
-
-Signed-off-by: Daniel Golle <[email protected]>
----
- init/do_mounts.c | 26 +++++++++++++++++++++++++-
- 1 file changed, 25 insertions(+), 1 deletion(-)
-
---- a/init/do_mounts.c
-+++ b/init/do_mounts.c
-@@ -447,7 +447,30 @@ retry:
- out:
-       put_page(page);
- }
-- 
-+
-+#ifdef CONFIG_MTD_ROOTFS_ROOT_DEV
-+static int __init mount_ubi_rootfs(void)
-+{
-+      int flags = MS_SILENT;
-+      int err, tried = 0;
-+
-+      while (tried < 2) {
-+              err = do_mount_root("ubi0:rootfs", "ubifs", flags, \
-+                                      root_mount_data);
-+              switch (err) {
-+                      case -EACCES:
-+                              flags |= MS_RDONLY;
-+                              tried++;
-+                              break;
-+                      default:
-+                              return err;
-+              }
-+      }
-+
-+      return -EINVAL;
-+}
-+#endif
-+
- #ifdef CONFIG_ROOT_NFS
- #define NFSROOT_TIMEOUT_MIN   5
-@@ -580,6 +603,10 @@ void __init mount_root(void)
-               return;
-       }
- #endif
-+#ifdef CONFIG_MTD_ROOTFS_ROOT_DEV
-+      if (!mount_ubi_rootfs())
-+              return;
-+#endif
-       if (ROOT_DEV == 0 && root_device_name && root_fs_names) {
-               if (mount_nodev_root() == 0)
-                       return;
diff --git a/target/linux/generic/pending-5.15/493-ubi-set-ROOT_DEV-to-ubiblock-rootfs-if-unset.patch b/target/linux/generic/pending-5.15/493-ubi-set-ROOT_DEV-to-ubiblock-rootfs-if-unset.patch
deleted file mode 100644 (file)
index 266a633..0000000
+++ /dev/null
@@ -1,34 +0,0 @@
-From: Daniel Golle <[email protected]>
-Subject: ubi: set ROOT_DEV to ubiblock "rootfs" if unset
-
-Signed-off-by: Daniel Golle <[email protected]>
----
- drivers/mtd/ubi/block.c | 10 ++++++++++
- 1 file changed, 10 insertions(+)
-
---- a/drivers/mtd/ubi/block.c
-+++ b/drivers/mtd/ubi/block.c
-@@ -42,6 +42,7 @@
- #include <linux/scatterlist.h>
- #include <linux/idr.h>
- #include <asm/div64.h>
-+#include <linux/root_dev.h>
- #include "ubi-media.h"
- #include "ubi.h"
-@@ -451,6 +452,15 @@ int ubiblock_create(struct ubi_volume_in
-       dev_info(disk_to_dev(dev->gd), "created from ubi%d:%d(%s)",
-                dev->ubi_num, dev->vol_id, vi->name);
-       mutex_unlock(&devices_mutex);
-+
-+      if (!strcmp(vi->name, "rootfs") &&
-+          IS_ENABLED(CONFIG_MTD_ROOTFS_ROOT_DEV) &&
-+          ROOT_DEV == 0) {
-+              pr_notice("ubiblock: device ubiblock%d_%d (%s) set to be root filesystem\n",
-+                        dev->ubi_num, dev->vol_id, vi->name);
-+              ROOT_DEV = MKDEV(gd->major, gd->first_minor);
-+      }
-+
-       return 0;
- out_remove_minor:
diff --git a/target/linux/generic/pending-5.15/494-mtd-ubi-add-EOF-marker-support.patch b/target/linux/generic/pending-5.15/494-mtd-ubi-add-EOF-marker-support.patch
deleted file mode 100644 (file)
index 4134317..0000000
+++ /dev/null
@@ -1,60 +0,0 @@
-From: Gabor Juhos <[email protected]>
-Subject: mtd: add EOF marker support to the UBI layer
-
-Signed-off-by: Gabor Juhos <[email protected]>
----
- drivers/mtd/ubi/attach.c | 25 ++++++++++++++++++++++---
- drivers/mtd/ubi/ubi.h    |  1 +
- 2 files changed, 23 insertions(+), 3 deletions(-)
-
---- a/drivers/mtd/ubi/attach.c
-+++ b/drivers/mtd/ubi/attach.c
-@@ -926,6 +926,13 @@ static bool vol_ignored(int vol_id)
- #endif
- }
-+static bool ec_hdr_has_eof(struct ubi_ec_hdr *ech)
-+{
-+      return ech->padding1[0] == 'E' &&
-+             ech->padding1[1] == 'O' &&
-+             ech->padding1[2] == 'F';
-+}
-+
- /**
-  * scan_peb - scan and process UBI headers of a PEB.
-  * @ubi: UBI device description object
-@@ -958,9 +965,21 @@ static int scan_peb(struct ubi_device *u
-               return 0;
-       }
--      err = ubi_io_read_ec_hdr(ubi, pnum, ech, 0);
--      if (err < 0)
--              return err;
-+      if (!ai->eof_found) {
-+              err = ubi_io_read_ec_hdr(ubi, pnum, ech, 0);
-+              if (err < 0)
-+                      return err;
-+
-+              if (ec_hdr_has_eof(ech)) {
-+                      pr_notice("UBI: EOF marker found, PEBs from %d will be erased\n",
-+                              pnum);
-+                      ai->eof_found = true;
-+              }
-+      }
-+
-+      if (ai->eof_found)
-+              err = UBI_IO_FF_BITFLIPS;
-+
-       switch (err) {
-       case 0:
-               break;
---- a/drivers/mtd/ubi/ubi.h
-+++ b/drivers/mtd/ubi/ubi.h
-@@ -778,6 +778,7 @@ struct ubi_attach_info {
-       int mean_ec;
-       uint64_t ec_sum;
-       int ec_count;
-+      bool eof_found;
-       struct kmem_cache *aeb_slab_cache;
-       struct ubi_ec_hdr *ech;
-       struct ubi_vid_io_buf *vidb;
diff --git a/target/linux/generic/pending-5.15/496-dt-bindings-add-bindings-for-mtd-concat-devices.patch b/target/linux/generic/pending-5.15/496-dt-bindings-add-bindings-for-mtd-concat-devices.patch
deleted file mode 100644 (file)
index 01f3b9e..0000000
+++ /dev/null
@@ -1,52 +0,0 @@
-From 5734c6669fba7ddb5ef491ccff7159d15dba0b59 Mon Sep 17 00:00:00 2001
-From: Bernhard Frauendienst <[email protected]>
-Date: Wed, 5 Sep 2018 01:32:51 +0200
-Subject: [PATCH 496/497] dt-bindings: add bindings for mtd-concat devices
-
-Document virtual mtd-concat device bindings.
-
-Signed-off-by: Bernhard Frauendienst <[email protected]>
----
- .../devicetree/bindings/mtd/mtd-concat.txt    | 36 +++++++++++++++++++
- 1 file changed, 36 insertions(+)
- create mode 100644 Documentation/devicetree/bindings/mtd/mtd-concat.txt
-
---- /dev/null
-+++ b/Documentation/devicetree/bindings/mtd/mtd-concat.txt
-@@ -0,0 +1,36 @@
-+Virtual MTD concat device
-+
-+Requires properties:
-+- devices: list of phandles to mtd nodes that should be concatenated
-+
-+Example:
-+
-+&spi {
-+      flash0: flash@0 {
-+              ...
-+      };
-+      flash1: flash@1 {
-+              ...
-+      };
-+};
-+
-+flash {
-+      compatible = "mtd-concat";
-+
-+      devices = <&flash0 &flash1>;
-+
-+      partitions {
-+              compatible = "fixed-partitions";
-+
-+              partition@0 {
-+                      label = "boot";
-+                      reg = <0x0000000 0x0040000>;
-+                      read-only;
-+              };
-+
-+              partition@40000 {
-+                      label = "firmware";
-+                      reg = <0x0040000 0x1fc0000>;
-+              };
-+      }
-+}
diff --git a/target/linux/generic/pending-5.15/497-mtd-mtdconcat-add-dt-driver-for-concat-devices.patch b/target/linux/generic/pending-5.15/497-mtd-mtdconcat-add-dt-driver-for-concat-devices.patch
deleted file mode 100644 (file)
index e0cbc45..0000000
+++ /dev/null
@@ -1,216 +0,0 @@
-From e53f712d8eac71f54399b61038ccf87d2cee99d7 Mon Sep 17 00:00:00 2001
-From: Bernhard Frauendienst <[email protected]>
-Date: Sat, 25 Aug 2018 12:35:22 +0200
-Subject: [PATCH 497/497] mtd: mtdconcat: add dt driver for concat devices
-
-Some mtd drivers like physmap variants have support for concatenating
-multiple mtd devices, but there is no generic way to define such a
-concat device from within the device tree.
-
-This is useful for some SoC boards that use multiple flash chips as
-memory banks of a single mtd device, with partitions spanning chip
-borders.
-
-This commit adds a driver for creating virtual mtd-concat devices. They
-must have a compatible = "mtd-concat" line, and define a list of devices
-to concat in the 'devices' property, for example:
-
-flash {
-  compatible = "mtd-concat";
-
-  devices = <&flash0 &flash1>;
-
-  partitions {
-    ...
-  };
-};
-
-The driver is added to the very end of the mtd Makefile to increase the
-likelyhood of all child devices already being loaded at the time of
-probing, preventing unnecessary deferred probes.
-
-Signed-off-by: Bernhard Frauendienst <[email protected]>
----
- drivers/mtd/Kconfig                 |   2 +
- drivers/mtd/Makefile                |   3 +
- drivers/mtd/composite/Kconfig       |  12 +++
- drivers/mtd/composite/Makefile      |   6 ++
- drivers/mtd/composite/virt_concat.c | 128 ++++++++++++++++++++++++++++
- 5 files changed, 151 insertions(+)
- create mode 100644 drivers/mtd/composite/Kconfig
- create mode 100644 drivers/mtd/composite/Makefile
- create mode 100644 drivers/mtd/composite/virt_concat.c
-
---- a/drivers/mtd/Kconfig
-+++ b/drivers/mtd/Kconfig
-@@ -241,4 +241,6 @@ source "drivers/mtd/ubi/Kconfig"
- source "drivers/mtd/hyperbus/Kconfig"
-+source "drivers/mtd/composite/Kconfig"
-+
- endif # MTD
---- a/drivers/mtd/Makefile
-+++ b/drivers/mtd/Makefile
-@@ -33,3 +33,6 @@ obj-y                += chips/ lpddr/ maps/ devices/ n
- obj-$(CONFIG_MTD_SPI_NOR)     += spi-nor/
- obj-$(CONFIG_MTD_UBI)         += ubi/
- obj-$(CONFIG_MTD_HYPERBUS)    += hyperbus/
-+
-+# Composite drivers must be loaded last
-+obj-y                         += composite/
---- /dev/null
-+++ b/drivers/mtd/composite/Kconfig
-@@ -0,0 +1,12 @@
-+menu "Composite MTD device drivers"
-+      depends on MTD!=n
-+
-+config MTD_VIRT_CONCAT
-+      tristate "Virtual concat MTD device"
-+      help
-+        This driver allows creation of a virtual MTD concat device, which
-+        concatenates multiple underlying MTD devices to a single device.
-+        This is required by some SoC boards where multiple memory banks are
-+        used as one device with partitions spanning across device boundaries.
-+
-+endmenu
---- /dev/null
-+++ b/drivers/mtd/composite/Makefile
-@@ -0,0 +1,6 @@
-+# SPDX-License-Identifier: GPL-2.0
-+#
-+# linux/drivers/mtd/composite/Makefile
-+#
-+
-+obj-$(CONFIG_MTD_VIRT_CONCAT)   += virt_concat.o
---- /dev/null
-+++ b/drivers/mtd/composite/virt_concat.c
-@@ -0,0 +1,128 @@
-+// SPDX-License-Identifier: GPL-2.0+
-+/*
-+ * Virtual concat MTD device driver
-+ *
-+ * Copyright (C) 2018 Bernhard Frauendienst
-+ * Author: Bernhard Frauendienst, [email protected]
-+ */
-+
-+#include <linux/module.h>
-+#include <linux/device.h>
-+#include <linux/mtd/concat.h>
-+#include <linux/mtd/mtd.h>
-+#include <linux/mtd/partitions.h>
-+#include <linux/of.h>
-+#include <linux/of_platform.h>
-+#include <linux/slab.h>
-+
-+/*
-+ * struct of_virt_concat - platform device driver data.
-+ * @cmtd the final mtd_concat device
-+ * @num_devices the number of devices in @devices
-+ * @devices points to an array of devices already loaded
-+ */
-+struct of_virt_concat {
-+      struct mtd_info *cmtd;
-+      int num_devices;
-+      struct mtd_info **devices;
-+};
-+
-+static int virt_concat_remove(struct platform_device *pdev)
-+{
-+      struct of_virt_concat *info;
-+      int i;
-+
-+      info = platform_get_drvdata(pdev);
-+      if (!info)
-+              return 0;
-+
-+      // unset data for when this is called after a probe error
-+      platform_set_drvdata(pdev, NULL);
-+
-+      if (info->cmtd) {
-+              mtd_device_unregister(info->cmtd);
-+              mtd_concat_destroy(info->cmtd);
-+      }
-+
-+      if (info->devices) {
-+              for (i = 0; i < info->num_devices; i++)
-+                      put_mtd_device(info->devices[i]);
-+      }
-+
-+      return 0;
-+}
-+
-+static int virt_concat_probe(struct platform_device *pdev)
-+{
-+      struct device_node *node = pdev->dev.of_node;
-+      struct of_phandle_iterator it;
-+      struct of_virt_concat *info;
-+      struct mtd_info *mtd;
-+      int err = 0, count;
-+
-+      count = of_count_phandle_with_args(node, "devices", NULL);
-+      if (count <= 0)
-+              return -EINVAL;
-+
-+      info = devm_kzalloc(&pdev->dev, sizeof(*info), GFP_KERNEL);
-+      if (!info)
-+              return -ENOMEM;
-+      info->devices = devm_kcalloc(&pdev->dev, count,
-+                                   sizeof(*(info->devices)), GFP_KERNEL);
-+      if (!info->devices) {
-+              err = -ENOMEM;
-+              goto err_remove;
-+      }
-+
-+      platform_set_drvdata(pdev, info);
-+
-+      of_for_each_phandle(&it, err, node, "devices", NULL, 0) {
-+              mtd = of_get_mtd_device_by_node(it.node);
-+              if (IS_ERR(mtd)) {
-+                      of_node_put(it.node);
-+                      err = -EPROBE_DEFER;
-+                      goto err_remove;
-+              }
-+
-+              info->devices[info->num_devices++] = mtd;
-+      }
-+
-+      info->cmtd = mtd_concat_create(info->devices, info->num_devices,
-+                                     dev_name(&pdev->dev));
-+      if (!info->cmtd) {
-+              err = -ENXIO;
-+              goto err_remove;
-+      }
-+
-+      info->cmtd->dev.parent = &pdev->dev;
-+      mtd_set_of_node(info->cmtd, node);
-+      mtd_device_register(info->cmtd, NULL, 0);
-+
-+      return 0;
-+
-+err_remove:
-+      virt_concat_remove(pdev);
-+
-+      return err;
-+}
-+
-+static const struct of_device_id virt_concat_of_match[] = {
-+      { .compatible = "mtd-concat", },
-+      { /* sentinel */ }
-+};
-+MODULE_DEVICE_TABLE(of, virt_concat_of_match);
-+
-+static struct platform_driver virt_concat_driver = {
-+      .probe = virt_concat_probe,
-+      .remove = virt_concat_remove,
-+      .driver  = {
-+              .name   = "virt-mtdconcat",
-+              .of_match_table = virt_concat_of_match,
-+      },
-+};
-+
-+module_platform_driver(virt_concat_driver);
-+
-+MODULE_LICENSE("GPL v2");
-+MODULE_AUTHOR("Bernhard Frauendienst <[email protected]>");
-+MODULE_DESCRIPTION("Virtual concat MTD device driver");
diff --git a/target/linux/generic/pending-5.15/498-mtd-spi-nor-locking-support-for-MX25L6405D.patch b/target/linux/generic/pending-5.15/498-mtd-spi-nor-locking-support-for-MX25L6405D.patch
deleted file mode 100644 (file)
index 81de764..0000000
+++ /dev/null
@@ -1,34 +0,0 @@
-From 8bf2ce6ea4ee840b70f55a27f80e1cd308051b13 Mon Sep 17 00:00:00 2001
-From: Nick Hainke <[email protected]>
-Date: Mon, 27 Dec 2021 00:38:13 +0100
-Subject: [PATCH 1/2] mtd: spi-nor: locking support for MX25L6405D
-
-Macronix MX25L6405D supports locking with four block-protection bits.
-Currently, the driver only sets three bits.  If the bootloader does not
-sustain the flash chip in an unlocked state, the flash might be
-non-writeable. Add the corresponding flag to enable locking support with
-four bits in the status register.
-
-Tested on Nanostation M2 XM.
-
-Similar to commit 7ea40b54e83b ("mtd: spi-nor: enable locking support for
-MX25L12805D")
-
-Signed-off-by: David Bauer <[email protected]>
-Signed-off-by: Nick Hainke <[email protected]>
----
- drivers/mtd/spi-nor/macronix.c | 3 ++-
- 1 file changed, 2 insertions(+), 1 deletion(-)
-
---- a/drivers/mtd/spi-nor/macronix.c
-+++ b/drivers/mtd/spi-nor/macronix.c
-@@ -41,7 +41,8 @@ static const struct flash_info macronix_
-       { "mx25l1606e",  INFO(0xc22015, 0, 64 * 1024,  32, SECT_4K) },
-       { "mx25l3205d",  INFO(0xc22016, 0, 64 * 1024,  64, SECT_4K) },
-       { "mx25l3255e",  INFO(0xc29e16, 0, 64 * 1024,  64, SECT_4K) },
--      { "mx25l6405d",  INFO(0xc22017, 0, 64 * 1024, 128, SECT_4K) },
-+      { "mx25l6405d",  INFO(0xc22017, 0, 64 * 1024, 128, SECT_4K |
-+                            SPI_NOR_HAS_LOCK | SPI_NOR_4BIT_BP) },
-       { "mx25u2033e",  INFO(0xc22532, 0, 64 * 1024,   4, SECT_4K) },
-       { "mx25u3235f",  INFO(0xc22536, 0, 64 * 1024,  64,
-                             SECT_4K | SPI_NOR_DUAL_READ |
diff --git a/target/linux/generic/pending-5.15/499-mtd-spi-nor-disable-16-bit-sr-for-macronix.patch b/target/linux/generic/pending-5.15/499-mtd-spi-nor-disable-16-bit-sr-for-macronix.patch
deleted file mode 100644 (file)
index ec14f63..0000000
+++ /dev/null
@@ -1,30 +0,0 @@
-From 245224608b5368c10407da07557e546743d3c489 Mon Sep 17 00:00:00 2001
-From: Nick Hainke <[email protected]>
-Date: Mon, 27 Dec 2021 09:33:13 +0100
-Subject: [PATCH 2/2] mtd: spi-nor: disable 16-bit-sr for macronix
-
-Macronix flash chips seem to consist of only one status register.
-These chips will not work with the "16-bit Write Status (01h) Command".
-Disable SNOR_F_HAS_16BIT_SR for all Macronix chips.
-
-Tested with MX25L6405D.
-
-Fixes: 39d1e3340c73 ("mtd: spi-nor: Fix clearing of QE bit on
-lock()/unlock()")
-
-Signed-off-by: David Bauer <[email protected]>
-Signed-off-by: Nick Hainke <[email protected]>
----
- drivers/mtd/spi-nor/macronix.c | 1 +
- 1 file changed, 1 insertion(+)
-
---- a/drivers/mtd/spi-nor/macronix.c
-+++ b/drivers/mtd/spi-nor/macronix.c
-@@ -94,6 +94,7 @@ static void macronix_default_init(struct
- {
-       nor->params->quad_enable = spi_nor_sr1_bit6_quad_enable;
-       nor->params->set_4byte_addr_mode = spi_nor_set_4byte_addr_mode;
-+      nor->flags &= ~SNOR_F_HAS_16BIT_SR;
-       nor->flags |= SNOR_F_HAS_LOCK;
- }
diff --git a/target/linux/generic/pending-5.15/500-fs_cdrom_dependencies.patch b/target/linux/generic/pending-5.15/500-fs_cdrom_dependencies.patch
deleted file mode 100644 (file)
index 2053c0f..0000000
+++ /dev/null
@@ -1,52 +0,0 @@
-From af7b91bcecce0eae24e90acd35d96ecee73e1407 Mon Sep 17 00:00:00 2001
-From: OpenWrt community <[email protected]>
-Date: Wed, 13 Jul 2022 12:21:15 +0200
-Subject: [PATCH] fs: add cdrom dependency
-
----
- fs/hfs/Kconfig     | 1 +
- fs/hfsplus/Kconfig | 1 +
- fs/isofs/Kconfig   | 1 +
- fs/udf/Kconfig     | 1 +
- 4 files changed, 4 insertions(+)
-
---- a/fs/hfs/Kconfig
-+++ b/fs/hfs/Kconfig
-@@ -2,6 +2,7 @@
- config HFS_FS
-       tristate "Apple Macintosh file system support"
-       depends on BLOCK
-+      select CDROM
-       select NLS
-       help
-         If you say Y here, you will be able to mount Macintosh-formatted
---- a/fs/hfsplus/Kconfig
-+++ b/fs/hfsplus/Kconfig
-@@ -2,6 +2,7 @@
- config HFSPLUS_FS
-       tristate "Apple Extended HFS file system support"
-       depends on BLOCK
-+      select CDROM
-       select NLS
-       select NLS_UTF8
-       help
---- a/fs/isofs/Kconfig
-+++ b/fs/isofs/Kconfig
-@@ -1,6 +1,7 @@
- # SPDX-License-Identifier: GPL-2.0-only
- config ISO9660_FS
-       tristate "ISO 9660 CDROM file system support"
-+      select CDROM
-       help
-         This is the standard file system used on CD-ROMs.  It was previously
-         known as "High Sierra File System" and is called "hsfs" on other
---- a/fs/udf/Kconfig
-+++ b/fs/udf/Kconfig
-@@ -1,6 +1,7 @@
- # SPDX-License-Identifier: GPL-2.0-only
- config UDF_FS
-       tristate "UDF file system support"
-+      select CDROM
-       select CRC_ITU_T
-       select NLS
-       help
diff --git a/target/linux/generic/pending-5.15/530-jffs2_make_lzma_available.patch b/target/linux/generic/pending-5.15/530-jffs2_make_lzma_available.patch
deleted file mode 100644 (file)
index f236657..0000000
+++ /dev/null
@@ -1,4581 +0,0 @@
-From: Alexandros C. Couloumbis <[email protected]>
-Subject: fs: add jffs2/lzma support (not activated by default yet)
-
-lede-commit: c2c88d315fa0e881f8b19da07b62859b915b11b2
-Signed-off-by: Alexandros C. Couloumbis <[email protected]>
----
- fs/jffs2/Kconfig             |    9 +
- fs/jffs2/Makefile            |    3 +
- fs/jffs2/compr.c             |    6 +
- fs/jffs2/compr.h             |   10 +-
- fs/jffs2/compr_lzma.c        |  128 +++
- fs/jffs2/super.c             |   33 +-
- include/linux/lzma.h         |   62 ++
- include/linux/lzma/LzFind.h  |  115 +++
- include/linux/lzma/LzHash.h  |   54 +
- include/linux/lzma/LzmaDec.h |  231 +++++
- include/linux/lzma/LzmaEnc.h |   80 ++
- include/linux/lzma/Types.h   |  226 +++++
- include/uapi/linux/jffs2.h   |    1 +
- lib/Kconfig                  |    6 +
- lib/Makefile                 |   12 +
- lib/lzma/LzFind.c            |  761 ++++++++++++++
- lib/lzma/LzmaDec.c           |  999 +++++++++++++++++++
- lib/lzma/LzmaEnc.c           | 2271 ++++++++++++++++++++++++++++++++++++++++++
- lib/lzma/Makefile            |    7 +
- 19 files changed, 5008 insertions(+), 6 deletions(-)
- create mode 100644 fs/jffs2/compr_lzma.c
- create mode 100644 include/linux/lzma.h
- create mode 100644 include/linux/lzma/LzFind.h
- create mode 100644 include/linux/lzma/LzHash.h
- create mode 100644 include/linux/lzma/LzmaDec.h
- create mode 100644 include/linux/lzma/LzmaEnc.h
- create mode 100644 include/linux/lzma/Types.h
- create mode 100644 lib/lzma/LzFind.c
- create mode 100644 lib/lzma/LzmaDec.c
- create mode 100644 lib/lzma/LzmaEnc.c
- create mode 100644 lib/lzma/Makefile
-
---- a/fs/jffs2/Kconfig
-+++ b/fs/jffs2/Kconfig
-@@ -136,6 +136,15 @@ config JFFS2_LZO
-         This feature was added in July, 2007. Say 'N' if you need
-         compatibility with older bootloaders or kernels.
-+config JFFS2_LZMA
-+      bool "JFFS2 LZMA compression support" if JFFS2_COMPRESSION_OPTIONS
-+      select LZMA_COMPRESS
-+      select LZMA_DECOMPRESS
-+      depends on JFFS2_FS
-+      default n
-+      help
-+        JFFS2 wrapper to the LZMA C SDK
-+
- config JFFS2_RTIME
-       bool "JFFS2 RTIME compression support" if JFFS2_COMPRESSION_OPTIONS
-       depends on JFFS2_FS
---- a/fs/jffs2/Makefile
-+++ b/fs/jffs2/Makefile
-@@ -19,4 +19,7 @@ jffs2-$(CONFIG_JFFS2_RUBIN)  += compr_rub
- jffs2-$(CONFIG_JFFS2_RTIME)   += compr_rtime.o
- jffs2-$(CONFIG_JFFS2_ZLIB)    += compr_zlib.o
- jffs2-$(CONFIG_JFFS2_LZO)     += compr_lzo.o
-+jffs2-$(CONFIG_JFFS2_LZMA)    += compr_lzma.o
- jffs2-$(CONFIG_JFFS2_SUMMARY)   += summary.o
-+
-+CFLAGS_compr_lzma.o += -Iinclude/linux -Ilib/lzma
---- a/fs/jffs2/compr.c
-+++ b/fs/jffs2/compr.c
-@@ -378,6 +378,9 @@ int __init jffs2_compressors_init(void)
- #ifdef CONFIG_JFFS2_LZO
-       jffs2_lzo_init();
- #endif
-+#ifdef CONFIG_JFFS2_LZMA
-+      jffs2_lzma_init();
-+#endif
- /* Setting default compression mode */
- #ifdef CONFIG_JFFS2_CMODE_NONE
-       jffs2_compression_mode = JFFS2_COMPR_MODE_NONE;
-@@ -401,6 +404,9 @@ int __init jffs2_compressors_init(void)
- int jffs2_compressors_exit(void)
- {
- /* Unregistering compressors */
-+#ifdef CONFIG_JFFS2_LZMA
-+      jffs2_lzma_exit();
-+#endif
- #ifdef CONFIG_JFFS2_LZO
-       jffs2_lzo_exit();
- #endif
---- a/fs/jffs2/compr.h
-+++ b/fs/jffs2/compr.h
-@@ -29,9 +29,9 @@
- #define JFFS2_DYNRUBIN_PRIORITY  20
- #define JFFS2_LZARI_PRIORITY     30
- #define JFFS2_RTIME_PRIORITY     50
--#define JFFS2_ZLIB_PRIORITY      60
--#define JFFS2_LZO_PRIORITY       80
--
-+#define JFFS2_LZMA_PRIORITY      70
-+#define JFFS2_ZLIB_PRIORITY      80
-+#define JFFS2_LZO_PRIORITY       90
- #define JFFS2_RUBINMIPS_DISABLED /* RUBINs will be used only */
- #define JFFS2_DYNRUBIN_DISABLED  /*      for decompression */
-@@ -101,5 +101,9 @@ void jffs2_zlib_exit(void);
- int jffs2_lzo_init(void);
- void jffs2_lzo_exit(void);
- #endif
-+#ifdef CONFIG_JFFS2_LZMA
-+int jffs2_lzma_init(void);
-+void jffs2_lzma_exit(void);
-+#endif
- #endif /* __JFFS2_COMPR_H__ */
---- /dev/null
-+++ b/fs/jffs2/compr_lzma.c
-@@ -0,0 +1,128 @@
-+/*
-+ * JFFS2 -- Journalling Flash File System, Version 2.
-+ *
-+ * For licensing information, see the file 'LICENCE' in this directory.
-+ *
-+ * JFFS2 wrapper to the LZMA C SDK
-+ *
-+ */
-+
-+#include <linux/lzma.h>
-+#include "compr.h"
-+
-+#ifdef __KERNEL__
-+      static DEFINE_MUTEX(deflate_mutex);
-+#endif
-+
-+CLzmaEncHandle *p;
-+Byte propsEncoded[LZMA_PROPS_SIZE];
-+SizeT propsSize = sizeof(propsEncoded);
-+
-+STATIC void lzma_free_workspace(void)
-+{
-+      LzmaEnc_Destroy(p, &lzma_alloc, &lzma_alloc);
-+}
-+
-+STATIC int INIT lzma_alloc_workspace(CLzmaEncProps *props)
-+{
-+      if ((p = (CLzmaEncHandle *)LzmaEnc_Create(&lzma_alloc)) == NULL)
-+      {
-+              PRINT_ERROR("Failed to allocate lzma deflate workspace\n");
-+              return -ENOMEM;
-+      }
-+
-+      if (LzmaEnc_SetProps(p, props) != SZ_OK)
-+      {
-+              lzma_free_workspace();
-+              return -1;
-+      }
-+
-+      if (LzmaEnc_WriteProperties(p, propsEncoded, &propsSize) != SZ_OK)
-+      {
-+              lzma_free_workspace();
-+              return -1;
-+      }
-+
-+      return 0;
-+}
-+
-+STATIC int jffs2_lzma_compress(unsigned char *data_in, unsigned char *cpage_out,
-+                            uint32_t *sourcelen, uint32_t *dstlen)
-+{
-+      SizeT compress_size = (SizeT)(*dstlen);
-+      int ret;
-+
-+      #ifdef __KERNEL__
-+              mutex_lock(&deflate_mutex);
-+      #endif
-+
-+      ret = LzmaEnc_MemEncode(p, cpage_out, &compress_size, data_in, *sourcelen,
-+              0, NULL, &lzma_alloc, &lzma_alloc);
-+
-+      #ifdef __KERNEL__
-+              mutex_unlock(&deflate_mutex);
-+      #endif
-+
-+      if (ret != SZ_OK)
-+              return -1;
-+
-+      *dstlen = (uint32_t)compress_size;
-+
-+      return 0;
-+}
-+
-+STATIC int jffs2_lzma_decompress(unsigned char *data_in, unsigned char *cpage_out,
-+                               uint32_t srclen, uint32_t destlen)
-+{
-+      int ret;
-+      SizeT dl = (SizeT)destlen;
-+      SizeT sl = (SizeT)srclen;
-+      ELzmaStatus status;
-+
-+      ret = LzmaDecode(cpage_out, &dl, data_in, &sl, propsEncoded,
-+              propsSize, LZMA_FINISH_ANY, &status, &lzma_alloc);
-+
-+      if (ret != SZ_OK || status == LZMA_STATUS_NOT_FINISHED || dl != (SizeT)destlen)
-+              return -1;
-+
-+      return 0;
-+}
-+
-+static struct jffs2_compressor jffs2_lzma_comp = {
-+      .priority = JFFS2_LZMA_PRIORITY,
-+      .name = "lzma",
-+      .compr = JFFS2_COMPR_LZMA,
-+      .compress = &jffs2_lzma_compress,
-+      .decompress = &jffs2_lzma_decompress,
-+      .disabled = 0,
-+};
-+
-+int INIT jffs2_lzma_init(void)
-+{
-+      int ret;
-+      CLzmaEncProps props;
-+      LzmaEncProps_Init(&props);
-+
-+      props.dictSize = LZMA_BEST_DICT(0x2000);
-+      props.level = LZMA_BEST_LEVEL;
-+      props.lc = LZMA_BEST_LC;
-+      props.lp = LZMA_BEST_LP;
-+      props.pb = LZMA_BEST_PB;
-+      props.fb = LZMA_BEST_FB;
-+
-+      ret = lzma_alloc_workspace(&props);
-+      if (ret < 0)
-+              return ret;
-+
-+      ret = jffs2_register_compressor(&jffs2_lzma_comp);
-+      if (ret)
-+              lzma_free_workspace();
-+
-+      return ret;
-+}
-+
-+void jffs2_lzma_exit(void)
-+{
-+      jffs2_unregister_compressor(&jffs2_lzma_comp);
-+      lzma_free_workspace();
-+}
---- a/fs/jffs2/super.c
-+++ b/fs/jffs2/super.c
-@@ -374,14 +374,41 @@ static int __init init_jffs2_fs(void)
-       BUILD_BUG_ON(sizeof(struct jffs2_raw_inode) != 68);
-       BUILD_BUG_ON(sizeof(struct jffs2_raw_summary) != 32);
--      pr_info("version 2.2."
-+      pr_info("version 2.2"
- #ifdef CONFIG_JFFS2_FS_WRITEBUFFER
-              " (NAND)"
- #endif
- #ifdef CONFIG_JFFS2_SUMMARY
--             " (SUMMARY) "
-+             " (SUMMARY)"
- #endif
--             " © 2001-2006 Red Hat, Inc.\n");
-+#ifdef CONFIG_JFFS2_ZLIB
-+             " (ZLIB)"
-+#endif
-+#ifdef CONFIG_JFFS2_LZO
-+             " (LZO)"
-+#endif
-+#ifdef CONFIG_JFFS2_LZMA
-+             " (LZMA)"
-+#endif
-+#ifdef CONFIG_JFFS2_RTIME
-+             " (RTIME)"
-+#endif
-+#ifdef CONFIG_JFFS2_RUBIN
-+             " (RUBIN)"
-+#endif
-+#ifdef  CONFIG_JFFS2_CMODE_NONE
-+             " (CMODE_NONE)"
-+#endif
-+#ifdef CONFIG_JFFS2_CMODE_PRIORITY
-+             " (CMODE_PRIORITY)"
-+#endif
-+#ifdef CONFIG_JFFS2_CMODE_SIZE
-+             " (CMODE_SIZE)"
-+#endif
-+#ifdef CONFIG_JFFS2_CMODE_FAVOURLZO
-+             " (CMODE_FAVOURLZO)"
-+#endif
-+             " (c) 2001-2006 Red Hat, Inc.\n");
-       jffs2_inode_cachep = kmem_cache_create("jffs2_i",
-                                            sizeof(struct jffs2_inode_info),
---- /dev/null
-+++ b/include/linux/lzma.h
-@@ -0,0 +1,62 @@
-+#ifndef __LZMA_H__
-+#define __LZMA_H__
-+
-+#ifdef __KERNEL__
-+      #include <linux/kernel.h>
-+      #include <linux/sched.h>
-+      #include <linux/slab.h>
-+      #include <linux/vmalloc.h>
-+      #include <linux/init.h>
-+      #define LZMA_MALLOC vmalloc
-+      #define LZMA_FREE vfree
-+      #define PRINT_ERROR(msg) printk(KERN_WARNING #msg)
-+      #define INIT __init
-+      #define STATIC static
-+#else
-+      #include <stdint.h>
-+      #include <stdlib.h>
-+      #include <stdio.h>
-+      #include <unistd.h>
-+      #include <string.h>
-+      #include <asm/types.h>
-+      #include <errno.h>
-+      #include <linux/jffs2.h>
-+      #ifndef PAGE_SIZE
-+              extern int page_size;
-+              #define PAGE_SIZE page_size
-+      #endif
-+      #define LZMA_MALLOC malloc
-+      #define LZMA_FREE free
-+      #define PRINT_ERROR(msg) fprintf(stderr, msg)
-+      #define INIT
-+      #define STATIC
-+#endif
-+
-+#include "lzma/LzmaDec.h"
-+#include "lzma/LzmaEnc.h"
-+
-+#define LZMA_BEST_LEVEL (9)
-+#define LZMA_BEST_LC    (0)
-+#define LZMA_BEST_LP    (0)
-+#define LZMA_BEST_PB    (0)
-+#define LZMA_BEST_FB  (273)
-+
-+#define LZMA_BEST_DICT(n) (((int)((n) / 2)) * 2)
-+
-+static void *p_lzma_malloc(void *p, size_t size)
-+{
-+      if (size == 0)
-+              return NULL;
-+
-+      return LZMA_MALLOC(size);
-+}
-+
-+static void p_lzma_free(void *p, void *address)
-+{
-+      if (address != NULL)
-+              LZMA_FREE(address);
-+}
-+
-+static ISzAlloc lzma_alloc = { .Alloc = p_lzma_malloc, .Free = p_lzma_free };
-+
-+#endif
---- /dev/null
-+++ b/include/linux/lzma/LzFind.h
-@@ -0,0 +1,98 @@
-+/* LzFind.h -- Match finder for LZ algorithms
-+2009-04-22 : Igor Pavlov : Public domain */
-+
-+#ifndef __LZ_FIND_H
-+#define __LZ_FIND_H
-+
-+#include "Types.h"
-+
-+#ifdef __cplusplus
-+extern "C" {
-+#endif
-+
-+typedef UInt32 CLzRef;
-+
-+typedef struct _CMatchFinder
-+{
-+  Byte *buffer;
-+  UInt32 pos;
-+  UInt32 posLimit;
-+  UInt32 streamPos;
-+  UInt32 lenLimit;
-+
-+  UInt32 cyclicBufferPos;
-+  UInt32 cyclicBufferSize; /* it must be = (historySize + 1) */
-+
-+  UInt32 matchMaxLen;
-+  CLzRef *hash;
-+  CLzRef *son;
-+  UInt32 hashMask;
-+  UInt32 cutValue;
-+
-+  Byte *bufferBase;
-+  ISeqInStream *stream;
-+  int streamEndWasReached;
-+
-+  UInt32 blockSize;
-+  UInt32 keepSizeBefore;
-+  UInt32 keepSizeAfter;
-+
-+  UInt32 numHashBytes;
-+  int directInput;
-+  size_t directInputRem;
-+  int btMode;
-+  int bigHash;
-+  UInt32 historySize;
-+  UInt32 fixedHashSize;
-+  UInt32 hashSizeSum;
-+  UInt32 numSons;
-+  SRes result;
-+  UInt32 crc[256];
-+} CMatchFinder;
-+
-+#define Inline_MatchFinder_GetPointerToCurrentPos(p) ((p)->buffer)
-+#define Inline_MatchFinder_GetIndexByte(p, index) ((p)->buffer[(Int32)(index)])
-+
-+#define Inline_MatchFinder_GetNumAvailableBytes(p) ((p)->streamPos - (p)->pos)
-+
-+void MatchFinder_Construct(CMatchFinder *p);
-+
-+/* Conditions:
-+     historySize <= 3 GB
-+     keepAddBufferBefore + matchMaxLen + keepAddBufferAfter < 511MB
-+*/
-+int MatchFinder_Create(CMatchFinder *p, UInt32 historySize,
-+    UInt32 keepAddBufferBefore, UInt32 matchMaxLen, UInt32 keepAddBufferAfter,
-+    ISzAlloc *alloc);
-+void MatchFinder_Free(CMatchFinder *p, ISzAlloc *alloc);
-+
-+/*
-+Conditions:
-+  Mf_GetNumAvailableBytes_Func must be called before each Mf_GetMatchLen_Func.
-+  Mf_GetPointerToCurrentPos_Func's result must be used only before any other function
-+*/
-+
-+typedef void (*Mf_Init_Func)(void *object);
-+typedef Byte (*Mf_GetIndexByte_Func)(void *object, Int32 index);
-+typedef UInt32 (*Mf_GetNumAvailableBytes_Func)(void *object);
-+typedef const Byte * (*Mf_GetPointerToCurrentPos_Func)(void *object);
-+typedef UInt32 (*Mf_GetMatches_Func)(void *object, UInt32 *distances);
-+typedef void (*Mf_Skip_Func)(void *object, UInt32);
-+
-+typedef struct _IMatchFinder
-+{
-+  Mf_Init_Func Init;
-+  Mf_GetIndexByte_Func GetIndexByte;
-+  Mf_GetNumAvailableBytes_Func GetNumAvailableBytes;
-+  Mf_GetPointerToCurrentPos_Func GetPointerToCurrentPos;
-+  Mf_GetMatches_Func GetMatches;
-+  Mf_Skip_Func Skip;
-+} IMatchFinder;
-+
-+void MatchFinder_CreateVTable(CMatchFinder *p, IMatchFinder *vTable);
-+
-+#ifdef __cplusplus
-+}
-+#endif
-+
-+#endif
---- /dev/null
-+++ b/include/linux/lzma/LzHash.h
-@@ -0,0 +1,54 @@
-+/* LzHash.h -- HASH functions for LZ algorithms
-+2009-02-07 : Igor Pavlov : Public domain */
-+
-+#ifndef __LZ_HASH_H
-+#define __LZ_HASH_H
-+
-+#define kHash2Size (1 << 10)
-+#define kHash3Size (1 << 16)
-+#define kHash4Size (1 << 20)
-+
-+#define kFix3HashSize (kHash2Size)
-+#define kFix4HashSize (kHash2Size + kHash3Size)
-+#define kFix5HashSize (kHash2Size + kHash3Size + kHash4Size)
-+
-+#define HASH2_CALC hashValue = cur[0] | ((UInt32)cur[1] << 8);
-+
-+#define HASH3_CALC { \
-+  UInt32 temp = p->crc[cur[0]] ^ cur[1]; \
-+  hash2Value = temp & (kHash2Size - 1); \
-+  hashValue = (temp ^ ((UInt32)cur[2] << 8)) & p->hashMask; }
-+
-+#define HASH4_CALC { \
-+  UInt32 temp = p->crc[cur[0]] ^ cur[1]; \
-+  hash2Value = temp & (kHash2Size - 1); \
-+  hash3Value = (temp ^ ((UInt32)cur[2] << 8)) & (kHash3Size - 1); \
-+  hashValue = (temp ^ ((UInt32)cur[2] << 8) ^ (p->crc[cur[3]] << 5)) & p->hashMask; }
-+
-+#define HASH5_CALC { \
-+  UInt32 temp = p->crc[cur[0]] ^ cur[1]; \
-+  hash2Value = temp & (kHash2Size - 1); \
-+  hash3Value = (temp ^ ((UInt32)cur[2] << 8)) & (kHash3Size - 1); \
-+  hash4Value = (temp ^ ((UInt32)cur[2] << 8) ^ (p->crc[cur[3]] << 5)); \
-+  hashValue = (hash4Value ^ (p->crc[cur[4]] << 3)) & p->hashMask; \
-+  hash4Value &= (kHash4Size - 1); }
-+
-+/* #define HASH_ZIP_CALC hashValue = ((cur[0] | ((UInt32)cur[1] << 8)) ^ p->crc[cur[2]]) & 0xFFFF; */
-+#define HASH_ZIP_CALC hashValue = ((cur[2] | ((UInt32)cur[0] << 8)) ^ p->crc[cur[1]]) & 0xFFFF;
-+
-+
-+#define MT_HASH2_CALC \
-+  hash2Value = (p->crc[cur[0]] ^ cur[1]) & (kHash2Size - 1);
-+
-+#define MT_HASH3_CALC { \
-+  UInt32 temp = p->crc[cur[0]] ^ cur[1]; \
-+  hash2Value = temp & (kHash2Size - 1); \
-+  hash3Value = (temp ^ ((UInt32)cur[2] << 8)) & (kHash3Size - 1); }
-+
-+#define MT_HASH4_CALC { \
-+  UInt32 temp = p->crc[cur[0]] ^ cur[1]; \
-+  hash2Value = temp & (kHash2Size - 1); \
-+  hash3Value = (temp ^ ((UInt32)cur[2] << 8)) & (kHash3Size - 1); \
-+  hash4Value = (temp ^ ((UInt32)cur[2] << 8) ^ (p->crc[cur[3]] << 5)) & (kHash4Size - 1); }
-+
-+#endif
---- /dev/null
-+++ b/include/linux/lzma/LzmaDec.h
-@@ -0,0 +1,130 @@
-+/* LzmaDec.h -- LZMA Decoder
-+2009-02-07 : Igor Pavlov : Public domain */
-+
-+#ifndef __LZMA_DEC_H
-+#define __LZMA_DEC_H
-+
-+#include "Types.h"
-+
-+#ifdef __cplusplus
-+extern "C" {
-+#endif
-+
-+/* #define _LZMA_PROB32 */
-+/* _LZMA_PROB32 can increase the speed on some CPUs,
-+   but memory usage for CLzmaDec::probs will be doubled in that case */
-+
-+#ifdef _LZMA_PROB32
-+#define CLzmaProb UInt32
-+#else
-+#define CLzmaProb UInt16
-+#endif
-+
-+
-+/* ---------- LZMA Properties ---------- */
-+
-+#define LZMA_PROPS_SIZE 5
-+
-+typedef struct _CLzmaProps
-+{
-+  unsigned lc, lp, pb;
-+  UInt32 dicSize;
-+} CLzmaProps;
-+
-+
-+/* ---------- LZMA Decoder state ---------- */
-+
-+/* LZMA_REQUIRED_INPUT_MAX = number of required input bytes for worst case.
-+   Num bits = log2((2^11 / 31) ^ 22) + 26 < 134 + 26 = 160; */
-+
-+#define LZMA_REQUIRED_INPUT_MAX 20
-+
-+typedef struct
-+{
-+  CLzmaProps prop;
-+  CLzmaProb *probs;
-+  Byte *dic;
-+  const Byte *buf;
-+  UInt32 range, code;
-+  SizeT dicPos;
-+  SizeT dicBufSize;
-+  UInt32 processedPos;
-+  UInt32 checkDicSize;
-+  unsigned state;
-+  UInt32 reps[4];
-+  unsigned remainLen;
-+  int needFlush;
-+  int needInitState;
-+  UInt32 numProbs;
-+  unsigned tempBufSize;
-+  Byte tempBuf[LZMA_REQUIRED_INPUT_MAX];
-+} CLzmaDec;
-+
-+#define LzmaDec_Construct(p) { (p)->dic = 0; (p)->probs = 0; }
-+
-+/* There are two types of LZMA streams:
-+     0) Stream with end mark. That end mark adds about 6 bytes to compressed size.
-+     1) Stream without end mark. You must know exact uncompressed size to decompress such stream. */
-+
-+typedef enum
-+{
-+  LZMA_FINISH_ANY,   /* finish at any point */
-+  LZMA_FINISH_END    /* block must be finished at the end */
-+} ELzmaFinishMode;
-+
-+/* ELzmaFinishMode has meaning only if the decoding reaches output limit !!!
-+
-+   You must use LZMA_FINISH_END, when you know that current output buffer
-+   covers last bytes of block. In other cases you must use LZMA_FINISH_ANY.
-+
-+   If LZMA decoder sees end marker before reaching output limit, it returns SZ_OK,
-+   and output value of destLen will be less than output buffer size limit.
-+   You can check status result also.
-+
-+   You can use multiple checks to test data integrity after full decompression:
-+     1) Check Result and "status" variable.
-+     2) Check that output(destLen) = uncompressedSize, if you know real uncompressedSize.
-+     3) Check that output(srcLen) = compressedSize, if you know real compressedSize.
-+        You must use correct finish mode in that case. */
-+
-+typedef enum
-+{
-+  LZMA_STATUS_NOT_SPECIFIED,               /* use main error code instead */
-+  LZMA_STATUS_FINISHED_WITH_MARK,          /* stream was finished with end mark. */
-+  LZMA_STATUS_NOT_FINISHED,                /* stream was not finished */
-+  LZMA_STATUS_NEEDS_MORE_INPUT,            /* you must provide more input bytes */
-+  LZMA_STATUS_MAYBE_FINISHED_WITHOUT_MARK  /* there is probability that stream was finished without end mark */
-+} ELzmaStatus;
-+
-+/* ELzmaStatus is used only as output value for function call */
-+
-+/* ---------- One Call Interface ---------- */
-+
-+/* LzmaDecode
-+
-+finishMode:
-+  It has meaning only if the decoding reaches output limit (*destLen).
-+  LZMA_FINISH_ANY - Decode just destLen bytes.
-+  LZMA_FINISH_END - Stream must be finished after (*destLen).
-+
-+Returns:
-+  SZ_OK
-+    status:
-+      LZMA_STATUS_FINISHED_WITH_MARK
-+      LZMA_STATUS_NOT_FINISHED
-+      LZMA_STATUS_MAYBE_FINISHED_WITHOUT_MARK
-+  SZ_ERROR_DATA - Data error
-+  SZ_ERROR_MEM  - Memory allocation error
-+  SZ_ERROR_UNSUPPORTED - Unsupported properties
-+  SZ_ERROR_INPUT_EOF - It needs more bytes in input buffer (src).
-+*/
-+
-+SRes LzmaDecode(Byte *dest, SizeT *destLen, const Byte *src, SizeT *srcLen,
-+    const Byte *propData, unsigned propSize, ELzmaFinishMode finishMode,
-+    ELzmaStatus *status, ISzAlloc *alloc);
-+
-+#ifdef __cplusplus
-+}
-+#endif
-+
-+#endif
---- /dev/null
-+++ b/include/linux/lzma/LzmaEnc.h
-@@ -0,0 +1,60 @@
-+/*  LzmaEnc.h -- LZMA Encoder
-+2009-02-07 : Igor Pavlov : Public domain */
-+
-+#ifndef __LZMA_ENC_H
-+#define __LZMA_ENC_H
-+
-+#include "Types.h"
-+
-+#ifdef __cplusplus
-+extern "C" {
-+#endif
-+
-+#define LZMA_PROPS_SIZE 5
-+
-+typedef struct _CLzmaEncProps
-+{
-+  int level;       /*  0 <= level <= 9 */
-+  UInt32 dictSize; /* (1 << 12) <= dictSize <= (1 << 27) for 32-bit version
-+                      (1 << 12) <= dictSize <= (1 << 30) for 64-bit version
-+                       default = (1 << 24) */
-+  int lc;          /* 0 <= lc <= 8, default = 3 */
-+  int lp;          /* 0 <= lp <= 4, default = 0 */
-+  int pb;          /* 0 <= pb <= 4, default = 2 */
-+  int algo;        /* 0 - fast, 1 - normal, default = 1 */
-+  int fb;          /* 5 <= fb <= 273, default = 32 */
-+  int btMode;      /* 0 - hashChain Mode, 1 - binTree mode - normal, default = 1 */
-+  int numHashBytes; /* 2, 3 or 4, default = 4 */
-+  UInt32 mc;        /* 1 <= mc <= (1 << 30), default = 32 */
-+  unsigned writeEndMark;  /* 0 - do not write EOPM, 1 - write EOPM, default = 0 */
-+  int numThreads;  /* 1 or 2, default = 2 */
-+} CLzmaEncProps;
-+
-+void LzmaEncProps_Init(CLzmaEncProps *p);
-+
-+/* ---------- CLzmaEncHandle Interface ---------- */
-+
-+/* LzmaEnc_* functions can return the following exit codes:
-+Returns:
-+  SZ_OK           - OK
-+  SZ_ERROR_MEM    - Memory allocation error
-+  SZ_ERROR_PARAM  - Incorrect paramater in props
-+  SZ_ERROR_WRITE  - Write callback error.
-+  SZ_ERROR_PROGRESS - some break from progress callback
-+  SZ_ERROR_THREAD - errors in multithreading functions (only for Mt version)
-+*/
-+
-+typedef void * CLzmaEncHandle;
-+
-+CLzmaEncHandle LzmaEnc_Create(ISzAlloc *alloc);
-+void LzmaEnc_Destroy(CLzmaEncHandle p, ISzAlloc *alloc, ISzAlloc *allocBig);
-+SRes LzmaEnc_SetProps(CLzmaEncHandle p, const CLzmaEncProps *props);
-+SRes LzmaEnc_WriteProperties(CLzmaEncHandle p, Byte *properties, SizeT *size);
-+SRes LzmaEnc_MemEncode(CLzmaEncHandle p, Byte *dest, SizeT *destLen, const Byte *src, SizeT srcLen,
-+    int writeEndMark, ICompressProgress *progress, ISzAlloc *alloc, ISzAlloc *allocBig);
-+
-+#ifdef __cplusplus
-+}
-+#endif
-+
-+#endif
---- /dev/null
-+++ b/include/linux/lzma/Types.h
-@@ -0,0 +1,226 @@
-+/* Types.h -- Basic types
-+2009-11-23 : Igor Pavlov : Public domain */
-+
-+#ifndef __7Z_TYPES_H
-+#define __7Z_TYPES_H
-+
-+#include <stddef.h>
-+
-+#ifdef _WIN32
-+#include <windows.h>
-+#endif
-+
-+#ifndef EXTERN_C_BEGIN
-+#ifdef __cplusplus
-+#define EXTERN_C_BEGIN extern "C" {
-+#define EXTERN_C_END }
-+#else
-+#define EXTERN_C_BEGIN
-+#define EXTERN_C_END
-+#endif
-+#endif
-+
-+EXTERN_C_BEGIN
-+
-+#define SZ_OK 0
-+
-+#define SZ_ERROR_DATA 1
-+#define SZ_ERROR_MEM 2
-+#define SZ_ERROR_CRC 3
-+#define SZ_ERROR_UNSUPPORTED 4
-+#define SZ_ERROR_PARAM 5
-+#define SZ_ERROR_INPUT_EOF 6
-+#define SZ_ERROR_OUTPUT_EOF 7
-+#define SZ_ERROR_READ 8
-+#define SZ_ERROR_WRITE 9
-+#define SZ_ERROR_PROGRESS 10
-+#define SZ_ERROR_FAIL 11
-+#define SZ_ERROR_THREAD 12
-+
-+#define SZ_ERROR_ARCHIVE 16
-+#define SZ_ERROR_NO_ARCHIVE 17
-+
-+typedef int SRes;
-+
-+#ifdef _WIN32
-+typedef DWORD WRes;
-+#else
-+typedef int WRes;
-+#endif
-+
-+#ifndef RINOK
-+#define RINOK(x) { int __result__ = (x); if (__result__ != 0) return __result__; }
-+#endif
-+
-+typedef unsigned char Byte;
-+typedef short Int16;
-+typedef unsigned short UInt16;
-+
-+#ifdef _LZMA_UINT32_IS_ULONG
-+typedef long Int32;
-+typedef unsigned long UInt32;
-+#else
-+typedef int Int32;
-+typedef unsigned int UInt32;
-+#endif
-+
-+#ifdef _SZ_NO_INT_64
-+
-+/* define _SZ_NO_INT_64, if your compiler doesn't support 64-bit integers.
-+   NOTES: Some code will work incorrectly in that case! */
-+
-+typedef long Int64;
-+typedef unsigned long UInt64;
-+
-+#else
-+
-+#if defined(_MSC_VER) || defined(__BORLANDC__)
-+typedef __int64 Int64;
-+typedef unsigned __int64 UInt64;
-+#else
-+typedef long long int Int64;
-+typedef unsigned long long int UInt64;
-+#endif
-+
-+#endif
-+
-+#ifdef _LZMA_NO_SYSTEM_SIZE_T
-+typedef UInt32 SizeT;
-+#else
-+typedef size_t SizeT;
-+#endif
-+
-+typedef int Bool;
-+#define True 1
-+#define False 0
-+
-+
-+#ifdef _WIN32
-+#define MY_STD_CALL __stdcall
-+#else
-+#define MY_STD_CALL
-+#endif
-+
-+#ifdef _MSC_VER
-+
-+#if _MSC_VER >= 1300
-+#define MY_NO_INLINE __declspec(noinline)
-+#else
-+#define MY_NO_INLINE
-+#endif
-+
-+#define MY_CDECL __cdecl
-+#define MY_FAST_CALL __fastcall
-+
-+#else
-+
-+#define MY_CDECL
-+#define MY_FAST_CALL
-+
-+#endif
-+
-+
-+/* The following interfaces use first parameter as pointer to structure */
-+
-+typedef struct
-+{
-+  SRes (*Read)(void *p, void *buf, size_t *size);
-+    /* if (input(*size) != 0 && output(*size) == 0) means end_of_stream.
-+       (output(*size) < input(*size)) is allowed */
-+} ISeqInStream;
-+
-+/* it can return SZ_ERROR_INPUT_EOF */
-+SRes SeqInStream_Read(ISeqInStream *stream, void *buf, size_t size);
-+SRes SeqInStream_Read2(ISeqInStream *stream, void *buf, size_t size, SRes errorType);
-+SRes SeqInStream_ReadByte(ISeqInStream *stream, Byte *buf);
-+
-+typedef struct
-+{
-+  size_t (*Write)(void *p, const void *buf, size_t size);
-+    /* Returns: result - the number of actually written bytes.
-+       (result < size) means error */
-+} ISeqOutStream;
-+
-+typedef enum
-+{
-+  SZ_SEEK_SET = 0,
-+  SZ_SEEK_CUR = 1,
-+  SZ_SEEK_END = 2
-+} ESzSeek;
-+
-+typedef struct
-+{
-+  SRes (*Read)(void *p, void *buf, size_t *size);  /* same as ISeqInStream::Read */
-+  SRes (*Seek)(void *p, Int64 *pos, ESzSeek origin);
-+} ISeekInStream;
-+
-+typedef struct
-+{
-+  SRes (*Look)(void *p, void **buf, size_t *size);
-+    /* if (input(*size) != 0 && output(*size) == 0) means end_of_stream.
-+       (output(*size) > input(*size)) is not allowed
-+       (output(*size) < input(*size)) is allowed */
-+  SRes (*Skip)(void *p, size_t offset);
-+    /* offset must be <= output(*size) of Look */
-+
-+  SRes (*Read)(void *p, void *buf, size_t *size);
-+    /* reads directly (without buffer). It's same as ISeqInStream::Read */
-+  SRes (*Seek)(void *p, Int64 *pos, ESzSeek origin);
-+} ILookInStream;
-+
-+SRes LookInStream_LookRead(ILookInStream *stream, void *buf, size_t *size);
-+SRes LookInStream_SeekTo(ILookInStream *stream, UInt64 offset);
-+
-+/* reads via ILookInStream::Read */
-+SRes LookInStream_Read2(ILookInStream *stream, void *buf, size_t size, SRes errorType);
-+SRes LookInStream_Read(ILookInStream *stream, void *buf, size_t size);
-+
-+#define LookToRead_BUF_SIZE (1 << 14)
-+
-+typedef struct
-+{
-+  ILookInStream s;
-+  ISeekInStream *realStream;
-+  size_t pos;
-+  size_t size;
-+  Byte buf[LookToRead_BUF_SIZE];
-+} CLookToRead;
-+
-+void LookToRead_CreateVTable(CLookToRead *p, int lookahead);
-+void LookToRead_Init(CLookToRead *p);
-+
-+typedef struct
-+{
-+  ISeqInStream s;
-+  ILookInStream *realStream;
-+} CSecToLook;
-+
-+void SecToLook_CreateVTable(CSecToLook *p);
-+
-+typedef struct
-+{
-+  ISeqInStream s;
-+  ILookInStream *realStream;
-+} CSecToRead;
-+
-+void SecToRead_CreateVTable(CSecToRead *p);
-+
-+typedef struct
-+{
-+  SRes (*Progress)(void *p, UInt64 inSize, UInt64 outSize);
-+    /* Returns: result. (result != SZ_OK) means break.
-+       Value (UInt64)(Int64)-1 for size means unknown value. */
-+} ICompressProgress;
-+
-+typedef struct
-+{
-+  void *(*Alloc)(void *p, size_t size);
-+  void (*Free)(void *p, void *address); /* address can be 0 */
-+} ISzAlloc;
-+
-+#define IAlloc_Alloc(p, size) (p)->Alloc((p), size)
-+#define IAlloc_Free(p, a) (p)->Free((p), a)
-+
-+EXTERN_C_END
-+
-+#endif
---- a/include/uapi/linux/jffs2.h
-+++ b/include/uapi/linux/jffs2.h
-@@ -46,6 +46,7 @@
- #define JFFS2_COMPR_DYNRUBIN  0x05
- #define JFFS2_COMPR_ZLIB      0x06
- #define JFFS2_COMPR_LZO               0x07
-+#define JFFS2_COMPR_LZMA      0x08
- /* Compatibility flags. */
- #define JFFS2_COMPAT_MASK 0xc000      /* What do to if an unknown nodetype is found */
- #define JFFS2_NODE_ACCURATE 0x2000
---- a/lib/Kconfig
-+++ b/lib/Kconfig
-@@ -340,6 +340,12 @@ config ZSTD_DECOMPRESS
- source "lib/xz/Kconfig"
-+config LZMA_COMPRESS
-+    tristate
-+
-+config LZMA_DECOMPRESS
-+    tristate
-+
- #
- # These all provide a common interface (hence the apparent duplication with
- # ZLIB_INFLATE; DECOMPRESS_GZIP is just a wrapper.)
---- a/lib/Makefile
-+++ b/lib/Makefile
-@@ -135,6 +135,16 @@ CFLAGS_kobject.o += -DDEBUG
- CFLAGS_kobject_uevent.o += -DDEBUG
- endif
-+ifdef CONFIG_JFFS2_ZLIB
-+  CONFIG_ZLIB_INFLATE:=y
-+  CONFIG_ZLIB_DEFLATE:=y
-+endif
-+
-+ifdef CONFIG_JFFS2_LZMA
-+  CONFIG_LZMA_DECOMPRESS:=y
-+  CONFIG_LZMA_COMPRESS:=y
-+endif
-+
- obj-$(CONFIG_DEBUG_INFO_REDUCED) += debug_info.o
- CFLAGS_debug_info.o += $(call cc-option, -femit-struct-debug-detailed=any)
-@@ -192,6 +202,8 @@ obj-$(CONFIG_ZSTD_COMPRESS) += zstd/
- obj-$(CONFIG_ZSTD_DECOMPRESS) += zstd/
- obj-$(CONFIG_XZ_DEC) += xz/
- obj-$(CONFIG_RAID6_PQ) += raid6/
-+obj-$(CONFIG_LZMA_COMPRESS) += lzma/
-+obj-$(CONFIG_LZMA_DECOMPRESS) += lzma/
- lib-$(CONFIG_DECOMPRESS_GZIP) += decompress_inflate.o
- lib-$(CONFIG_DECOMPRESS_BZIP2) += decompress_bunzip2.o
---- /dev/null
-+++ b/lib/lzma/LzFind.c
-@@ -0,0 +1,522 @@
-+/* LzFind.c -- Match finder for LZ algorithms
-+2009-04-22 : Igor Pavlov : Public domain */
-+
-+#include <string.h>
-+
-+#include "LzFind.h"
-+#include "LzHash.h"
-+
-+#define kEmptyHashValue 0
-+#define kMaxValForNormalize ((UInt32)0xFFFFFFFF)
-+#define kNormalizeStepMin (1 << 10) /* it must be power of 2 */
-+#define kNormalizeMask (~(kNormalizeStepMin - 1))
-+#define kMaxHistorySize ((UInt32)3 << 30)
-+
-+#define kStartMaxLen 3
-+
-+#if 0
-+#define DIRECT_INPUT  p->directInput
-+#else
-+#define DIRECT_INPUT  1
-+#endif
-+
-+static void LzInWindow_Free(CMatchFinder *p, ISzAlloc *alloc)
-+{
-+  if (!DIRECT_INPUT)
-+  {
-+    alloc->Free(alloc, p->bufferBase);
-+    p->bufferBase = 0;
-+  }
-+}
-+
-+/* keepSizeBefore + keepSizeAfter + keepSizeReserv must be < 4G) */
-+
-+static int LzInWindow_Create(CMatchFinder *p, UInt32 keepSizeReserv, ISzAlloc *alloc)
-+{
-+  UInt32 blockSize = p->keepSizeBefore + p->keepSizeAfter + keepSizeReserv;
-+  if (DIRECT_INPUT)
-+  {
-+    p->blockSize = blockSize;
-+    return 1;
-+  }
-+  if (p->bufferBase == 0 || p->blockSize != blockSize)
-+  {
-+    LzInWindow_Free(p, alloc);
-+    p->blockSize = blockSize;
-+    p->bufferBase = (Byte *)alloc->Alloc(alloc, (size_t)blockSize);
-+  }
-+  return (p->bufferBase != 0);
-+}
-+
-+static Byte *MatchFinder_GetPointerToCurrentPos(CMatchFinder *p) { return p->buffer; }
-+static Byte MatchFinder_GetIndexByte(CMatchFinder *p, Int32 index) { return p->buffer[index]; }
-+
-+static UInt32 MatchFinder_GetNumAvailableBytes(CMatchFinder *p) { return p->streamPos - p->pos; }
-+
-+static void MatchFinder_ReduceOffsets(CMatchFinder *p, UInt32 subValue)
-+{
-+  p->posLimit -= subValue;
-+  p->pos -= subValue;
-+  p->streamPos -= subValue;
-+}
-+
-+static void MatchFinder_ReadBlock(CMatchFinder *p)
-+{
-+  if (p->streamEndWasReached || p->result != SZ_OK)
-+    return;
-+  if (DIRECT_INPUT)
-+  {
-+    UInt32 curSize = 0xFFFFFFFF - p->streamPos;
-+    if (curSize > p->directInputRem)
-+      curSize = (UInt32)p->directInputRem;
-+    p->directInputRem -= curSize;
-+    p->streamPos += curSize;
-+    if (p->directInputRem == 0)
-+      p->streamEndWasReached = 1;
-+    return;
-+  }
-+  for (;;)
-+  {
-+    Byte *dest = p->buffer + (p->streamPos - p->pos);
-+    size_t size = (p->bufferBase + p->blockSize - dest);
-+    if (size == 0)
-+      return;
-+    p->result = p->stream->Read(p->stream, dest, &size);
-+    if (p->result != SZ_OK)
-+      return;
-+    if (size == 0)
-+    {
-+      p->streamEndWasReached = 1;
-+      return;
-+    }
-+    p->streamPos += (UInt32)size;
-+    if (p->streamPos - p->pos > p->keepSizeAfter)
-+      return;
-+  }
-+}
-+
-+static void MatchFinder_MoveBlock(CMatchFinder *p)
-+{
-+  memmove(p->bufferBase,
-+    p->buffer - p->keepSizeBefore,
-+    (size_t)(p->streamPos - p->pos + p->keepSizeBefore));
-+  p->buffer = p->bufferBase + p->keepSizeBefore;
-+}
-+
-+static int MatchFinder_NeedMove(CMatchFinder *p)
-+{
-+  if (DIRECT_INPUT)
-+    return 0;
-+  /* if (p->streamEndWasReached) return 0; */
-+  return ((size_t)(p->bufferBase + p->blockSize - p->buffer) <= p->keepSizeAfter);
-+}
-+
-+static void MatchFinder_CheckAndMoveAndRead(CMatchFinder *p)
-+{
-+  if (MatchFinder_NeedMove(p))
-+    MatchFinder_MoveBlock(p);
-+  MatchFinder_ReadBlock(p);
-+}
-+
-+static void MatchFinder_SetDefaultSettings(CMatchFinder *p)
-+{
-+  p->cutValue = 32;
-+  p->btMode = 1;
-+  p->numHashBytes = 4;
-+  p->bigHash = 0;
-+}
-+
-+#define kCrcPoly 0xEDB88320
-+
-+void MatchFinder_Construct(CMatchFinder *p)
-+{
-+  UInt32 i;
-+  p->bufferBase = 0;
-+  p->directInput = 0;
-+  p->hash = 0;
-+  MatchFinder_SetDefaultSettings(p);
-+
-+  for (i = 0; i < 256; i++)
-+  {
-+    UInt32 r = i;
-+    int j;
-+    for (j = 0; j < 8; j++)
-+      r = (r >> 1) ^ (kCrcPoly & ~((r & 1) - 1));
-+    p->crc[i] = r;
-+  }
-+}
-+
-+static void MatchFinder_FreeThisClassMemory(CMatchFinder *p, ISzAlloc *alloc)
-+{
-+  alloc->Free(alloc, p->hash);
-+  p->hash = 0;
-+}
-+
-+void MatchFinder_Free(CMatchFinder *p, ISzAlloc *alloc)
-+{
-+  MatchFinder_FreeThisClassMemory(p, alloc);
-+  LzInWindow_Free(p, alloc);
-+}
-+
-+static CLzRef* AllocRefs(UInt32 num, ISzAlloc *alloc)
-+{
-+  size_t sizeInBytes = (size_t)num * sizeof(CLzRef);
-+  if (sizeInBytes / sizeof(CLzRef) != num)
-+    return 0;
-+  return (CLzRef *)alloc->Alloc(alloc, sizeInBytes);
-+}
-+
-+int MatchFinder_Create(CMatchFinder *p, UInt32 historySize,
-+    UInt32 keepAddBufferBefore, UInt32 matchMaxLen, UInt32 keepAddBufferAfter,
-+    ISzAlloc *alloc)
-+{
-+  UInt32 sizeReserv;
-+  if (historySize > kMaxHistorySize)
-+  {
-+    MatchFinder_Free(p, alloc);
-+    return 0;
-+  }
-+  sizeReserv = historySize >> 1;
-+  if (historySize > ((UInt32)2 << 30))
-+    sizeReserv = historySize >> 2;
-+  sizeReserv += (keepAddBufferBefore + matchMaxLen + keepAddBufferAfter) / 2 + (1 << 19);
-+
-+  p->keepSizeBefore = historySize + keepAddBufferBefore + 1;
-+  p->keepSizeAfter = matchMaxLen + keepAddBufferAfter;
-+  /* we need one additional byte, since we use MoveBlock after pos++ and before dictionary using */
-+  if (LzInWindow_Create(p, sizeReserv, alloc))
-+  {
-+    UInt32 newCyclicBufferSize = historySize + 1;
-+    UInt32 hs;
-+    p->matchMaxLen = matchMaxLen;
-+    {
-+      p->fixedHashSize = 0;
-+      if (p->numHashBytes == 2)
-+        hs = (1 << 16) - 1;
-+      else
-+      {
-+        hs = historySize - 1;
-+        hs |= (hs >> 1);
-+        hs |= (hs >> 2);
-+        hs |= (hs >> 4);
-+        hs |= (hs >> 8);
-+        hs >>= 1;
-+        hs |= 0xFFFF; /* don't change it! It's required for Deflate */
-+        if (hs > (1 << 24))
-+        {
-+          if (p->numHashBytes == 3)
-+            hs = (1 << 24) - 1;
-+          else
-+            hs >>= 1;
-+        }
-+      }
-+      p->hashMask = hs;
-+      hs++;
-+      if (p->numHashBytes > 2) p->fixedHashSize += kHash2Size;
-+      if (p->numHashBytes > 3) p->fixedHashSize += kHash3Size;
-+      if (p->numHashBytes > 4) p->fixedHashSize += kHash4Size;
-+      hs += p->fixedHashSize;
-+    }
-+
-+    {
-+      UInt32 prevSize = p->hashSizeSum + p->numSons;
-+      UInt32 newSize;
-+      p->historySize = historySize;
-+      p->hashSizeSum = hs;
-+      p->cyclicBufferSize = newCyclicBufferSize;
-+      p->numSons = (p->btMode ? newCyclicBufferSize * 2 : newCyclicBufferSize);
-+      newSize = p->hashSizeSum + p->numSons;
-+      if (p->hash != 0 && prevSize == newSize)
-+        return 1;
-+      MatchFinder_FreeThisClassMemory(p, alloc);
-+      p->hash = AllocRefs(newSize, alloc);
-+      if (p->hash != 0)
-+      {
-+        p->son = p->hash + p->hashSizeSum;
-+        return 1;
-+      }
-+    }
-+  }
-+  MatchFinder_Free(p, alloc);
-+  return 0;
-+}
-+
-+static void MatchFinder_SetLimits(CMatchFinder *p)
-+{
-+  UInt32 limit = kMaxValForNormalize - p->pos;
-+  UInt32 limit2 = p->cyclicBufferSize - p->cyclicBufferPos;
-+  if (limit2 < limit)
-+    limit = limit2;
-+  limit2 = p->streamPos - p->pos;
-+  if (limit2 <= p->keepSizeAfter)
-+  {
-+    if (limit2 > 0)
-+      limit2 = 1;
-+  }
-+  else
-+    limit2 -= p->keepSizeAfter;
-+  if (limit2 < limit)
-+    limit = limit2;
-+  {
-+    UInt32 lenLimit = p->streamPos - p->pos;
-+    if (lenLimit > p->matchMaxLen)
-+      lenLimit = p->matchMaxLen;
-+    p->lenLimit = lenLimit;
-+  }
-+  p->posLimit = p->pos + limit;
-+}
-+
-+static void MatchFinder_Init(CMatchFinder *p)
-+{
-+  UInt32 i;
-+  for (i = 0; i < p->hashSizeSum; i++)
-+    p->hash[i] = kEmptyHashValue;
-+  p->cyclicBufferPos = 0;
-+  p->buffer = p->bufferBase;
-+  p->pos = p->streamPos = p->cyclicBufferSize;
-+  p->result = SZ_OK;
-+  p->streamEndWasReached = 0;
-+  MatchFinder_ReadBlock(p);
-+  MatchFinder_SetLimits(p);
-+}
-+
-+static UInt32 MatchFinder_GetSubValue(CMatchFinder *p)
-+{
-+  return (p->pos - p->historySize - 1) & kNormalizeMask;
-+}
-+
-+static void MatchFinder_Normalize3(UInt32 subValue, CLzRef *items, UInt32 numItems)
-+{
-+  UInt32 i;
-+  for (i = 0; i < numItems; i++)
-+  {
-+    UInt32 value = items[i];
-+    if (value <= subValue)
-+      value = kEmptyHashValue;
-+    else
-+      value -= subValue;
-+    items[i] = value;
-+  }
-+}
-+
-+static void MatchFinder_Normalize(CMatchFinder *p)
-+{
-+  UInt32 subValue = MatchFinder_GetSubValue(p);
-+  MatchFinder_Normalize3(subValue, p->hash, p->hashSizeSum + p->numSons);
-+  MatchFinder_ReduceOffsets(p, subValue);
-+}
-+
-+static void MatchFinder_CheckLimits(CMatchFinder *p)
-+{
-+  if (p->pos == kMaxValForNormalize)
-+    MatchFinder_Normalize(p);
-+  if (!p->streamEndWasReached && p->keepSizeAfter == p->streamPos - p->pos)
-+    MatchFinder_CheckAndMoveAndRead(p);
-+  if (p->cyclicBufferPos == p->cyclicBufferSize)
-+    p->cyclicBufferPos = 0;
-+  MatchFinder_SetLimits(p);
-+}
-+
-+static UInt32 * GetMatchesSpec1(UInt32 lenLimit, UInt32 curMatch, UInt32 pos, const Byte *cur, CLzRef *son,
-+    UInt32 _cyclicBufferPos, UInt32 _cyclicBufferSize, UInt32 cutValue,
-+    UInt32 *distances, UInt32 maxLen)
-+{
-+  CLzRef *ptr0 = son + (_cyclicBufferPos << 1) + 1;
-+  CLzRef *ptr1 = son + (_cyclicBufferPos << 1);
-+  UInt32 len0 = 0, len1 = 0;
-+  for (;;)
-+  {
-+    UInt32 delta = pos - curMatch;
-+    if (cutValue-- == 0 || delta >= _cyclicBufferSize)
-+    {
-+      *ptr0 = *ptr1 = kEmptyHashValue;
-+      return distances;
-+    }
-+    {
-+      CLzRef *pair = son + ((_cyclicBufferPos - delta + ((delta > _cyclicBufferPos) ? _cyclicBufferSize : 0)) << 1);
-+      const Byte *pb = cur - delta;
-+      UInt32 len = (len0 < len1 ? len0 : len1);
-+      if (pb[len] == cur[len])
-+      {
-+        if (++len != lenLimit && pb[len] == cur[len])
-+          while (++len != lenLimit)
-+            if (pb[len] != cur[len])
-+              break;
-+        if (maxLen < len)
-+        {
-+          *distances++ = maxLen = len;
-+          *distances++ = delta - 1;
-+          if (len == lenLimit)
-+          {
-+            *ptr1 = pair[0];
-+            *ptr0 = pair[1];
-+            return distances;
-+          }
-+        }
-+      }
-+      if (pb[len] < cur[len])
-+      {
-+        *ptr1 = curMatch;
-+        ptr1 = pair + 1;
-+        curMatch = *ptr1;
-+        len1 = len;
-+      }
-+      else
-+      {
-+        *ptr0 = curMatch;
-+        ptr0 = pair;
-+        curMatch = *ptr0;
-+        len0 = len;
-+      }
-+    }
-+  }
-+}
-+
-+static void SkipMatchesSpec(UInt32 lenLimit, UInt32 curMatch, UInt32 pos, const Byte *cur, CLzRef *son,
-+    UInt32 _cyclicBufferPos, UInt32 _cyclicBufferSize, UInt32 cutValue)
-+{
-+  CLzRef *ptr0 = son + (_cyclicBufferPos << 1) + 1;
-+  CLzRef *ptr1 = son + (_cyclicBufferPos << 1);
-+  UInt32 len0 = 0, len1 = 0;
-+  for (;;)
-+  {
-+    UInt32 delta = pos - curMatch;
-+    if (cutValue-- == 0 || delta >= _cyclicBufferSize)
-+    {
-+      *ptr0 = *ptr1 = kEmptyHashValue;
-+      return;
-+    }
-+    {
-+      CLzRef *pair = son + ((_cyclicBufferPos - delta + ((delta > _cyclicBufferPos) ? _cyclicBufferSize : 0)) << 1);
-+      const Byte *pb = cur - delta;
-+      UInt32 len = (len0 < len1 ? len0 : len1);
-+      if (pb[len] == cur[len])
-+      {
-+        while (++len != lenLimit)
-+          if (pb[len] != cur[len])
-+            break;
-+        {
-+          if (len == lenLimit)
-+          {
-+            *ptr1 = pair[0];
-+            *ptr0 = pair[1];
-+            return;
-+          }
-+        }
-+      }
-+      if (pb[len] < cur[len])
-+      {
-+        *ptr1 = curMatch;
-+        ptr1 = pair + 1;
-+        curMatch = *ptr1;
-+        len1 = len;
-+      }
-+      else
-+      {
-+        *ptr0 = curMatch;
-+        ptr0 = pair;
-+        curMatch = *ptr0;
-+        len0 = len;
-+      }
-+    }
-+  }
-+}
-+
-+#define MOVE_POS \
-+  ++p->cyclicBufferPos; \
-+  p->buffer++; \
-+  if (++p->pos == p->posLimit) MatchFinder_CheckLimits(p);
-+
-+static void MatchFinder_MovePos(CMatchFinder *p) { MOVE_POS; }
-+
-+#define MOVE_POS_RET MatchFinder_MovePos(p); return offset;
-+
-+#define GET_MATCHES_HEADER2(minLen, ret_op) \
-+  UInt32 lenLimit; UInt32 hashValue; const Byte *cur; UInt32 curMatch; \
-+  lenLimit = p->lenLimit; { if (lenLimit < minLen) { MatchFinder_MovePos(p); ret_op; }} \
-+  cur = p->buffer;
-+
-+#define GET_MATCHES_HEADER(minLen) GET_MATCHES_HEADER2(minLen, return 0)
-+#define SKIP_HEADER(minLen)        GET_MATCHES_HEADER2(minLen, continue)
-+
-+#define MF_PARAMS(p) p->pos, p->buffer, p->son, p->cyclicBufferPos, p->cyclicBufferSize, p->cutValue
-+
-+#define GET_MATCHES_FOOTER(offset, maxLen) \
-+  offset = (UInt32)(GetMatchesSpec1(lenLimit, curMatch, MF_PARAMS(p), \
-+  distances + offset, maxLen) - distances); MOVE_POS_RET;
-+
-+#define SKIP_FOOTER \
-+  SkipMatchesSpec(lenLimit, curMatch, MF_PARAMS(p)); MatchFinder_MovePos(p);
-+
-+static UInt32 Bt4_MatchFinder_GetMatches(CMatchFinder *p, UInt32 *distances)
-+{
-+  UInt32 hash2Value, hash3Value, delta2, delta3, maxLen, offset;
-+  GET_MATCHES_HEADER(4)
-+
-+  HASH4_CALC;
-+
-+  delta2 = p->pos - p->hash[                hash2Value];
-+  delta3 = p->pos - p->hash[kFix3HashSize + hash3Value];
-+  curMatch = p->hash[kFix4HashSize + hashValue];
-+
-+  p->hash[                hash2Value] =
-+  p->hash[kFix3HashSize + hash3Value] =
-+  p->hash[kFix4HashSize + hashValue] = p->pos;
-+
-+  maxLen = 1;
-+  offset = 0;
-+  if (delta2 < p->cyclicBufferSize && *(cur - delta2) == *cur)
-+  {
-+    distances[0] = maxLen = 2;
-+    distances[1] = delta2 - 1;
-+    offset = 2;
-+  }
-+  if (delta2 != delta3 && delta3 < p->cyclicBufferSize && *(cur - delta3) == *cur)
-+  {
-+    maxLen = 3;
-+    distances[offset + 1] = delta3 - 1;
-+    offset += 2;
-+    delta2 = delta3;
-+  }
-+  if (offset != 0)
-+  {
-+    for (; maxLen != lenLimit; maxLen++)
-+      if (cur[(ptrdiff_t)maxLen - delta2] != cur[maxLen])
-+        break;
-+    distances[offset - 2] = maxLen;
-+    if (maxLen == lenLimit)
-+    {
-+      SkipMatchesSpec(lenLimit, curMatch, MF_PARAMS(p));
-+      MOVE_POS_RET;
-+    }
-+  }
-+  if (maxLen < 3)
-+    maxLen = 3;
-+  GET_MATCHES_FOOTER(offset, maxLen)
-+}
-+
-+static void Bt4_MatchFinder_Skip(CMatchFinder *p, UInt32 num)
-+{
-+  do
-+  {
-+    UInt32 hash2Value, hash3Value;
-+    SKIP_HEADER(4)
-+    HASH4_CALC;
-+    curMatch = p->hash[kFix4HashSize + hashValue];
-+    p->hash[                hash2Value] =
-+    p->hash[kFix3HashSize + hash3Value] = p->pos;
-+    p->hash[kFix4HashSize + hashValue] = p->pos;
-+    SKIP_FOOTER
-+  }
-+  while (--num != 0);
-+}
-+
-+void MatchFinder_CreateVTable(CMatchFinder *p, IMatchFinder *vTable)
-+{
-+  vTable->Init = (Mf_Init_Func)MatchFinder_Init;
-+  vTable->GetIndexByte = (Mf_GetIndexByte_Func)MatchFinder_GetIndexByte;
-+  vTable->GetNumAvailableBytes = (Mf_GetNumAvailableBytes_Func)MatchFinder_GetNumAvailableBytes;
-+  vTable->GetPointerToCurrentPos = (Mf_GetPointerToCurrentPos_Func)MatchFinder_GetPointerToCurrentPos;
-+  vTable->GetMatches = (Mf_GetMatches_Func)Bt4_MatchFinder_GetMatches;
-+  vTable->Skip = (Mf_Skip_Func)Bt4_MatchFinder_Skip;
-+}
---- /dev/null
-+++ b/lib/lzma/LzmaDec.c
-@@ -0,0 +1,925 @@
-+/* LzmaDec.c -- LZMA Decoder
-+2009-09-20 : Igor Pavlov : Public domain */
-+
-+#include "LzmaDec.h"
-+
-+#include <string.h>
-+
-+#define kNumTopBits 24
-+#define kTopValue ((UInt32)1 << kNumTopBits)
-+
-+#define kNumBitModelTotalBits 11
-+#define kBitModelTotal (1 << kNumBitModelTotalBits)
-+#define kNumMoveBits 5
-+
-+#define RC_INIT_SIZE 5
-+
-+#define NORMALIZE if (range < kTopValue) { range <<= 8; code = (code << 8) | (*buf++); }
-+
-+#define IF_BIT_0(p) ttt = *(p); NORMALIZE; bound = (range >> kNumBitModelTotalBits) * ttt; if (code < bound)
-+#define UPDATE_0(p) range = bound; *(p) = (CLzmaProb)(ttt + ((kBitModelTotal - ttt) >> kNumMoveBits));
-+#define UPDATE_1(p) range -= bound; code -= bound; *(p) = (CLzmaProb)(ttt - (ttt >> kNumMoveBits));
-+#define GET_BIT2(p, i, A0, A1) IF_BIT_0(p) \
-+  { UPDATE_0(p); i = (i + i); A0; } else \
-+  { UPDATE_1(p); i = (i + i) + 1; A1; }
-+#define GET_BIT(p, i) GET_BIT2(p, i, ; , ;)
-+
-+#define TREE_GET_BIT(probs, i) { GET_BIT((probs + i), i); }
-+#define TREE_DECODE(probs, limit, i) \
-+  { i = 1; do { TREE_GET_BIT(probs, i); } while (i < limit); i -= limit; }
-+
-+/* #define _LZMA_SIZE_OPT */
-+
-+#ifdef _LZMA_SIZE_OPT
-+#define TREE_6_DECODE(probs, i) TREE_DECODE(probs, (1 << 6), i)
-+#else
-+#define TREE_6_DECODE(probs, i) \
-+  { i = 1; \
-+  TREE_GET_BIT(probs, i); \
-+  TREE_GET_BIT(probs, i); \
-+  TREE_GET_BIT(probs, i); \
-+  TREE_GET_BIT(probs, i); \
-+  TREE_GET_BIT(probs, i); \
-+  TREE_GET_BIT(probs, i); \
-+  i -= 0x40; }
-+#endif
-+
-+#define NORMALIZE_CHECK if (range < kTopValue) { if (buf >= bufLimit) return DUMMY_ERROR; range <<= 8; code = (code << 8) | (*buf++); }
-+
-+#define IF_BIT_0_CHECK(p) ttt = *(p); NORMALIZE_CHECK; bound = (range >> kNumBitModelTotalBits) * ttt; if (code < bound)
-+#define UPDATE_0_CHECK range = bound;
-+#define UPDATE_1_CHECK range -= bound; code -= bound;
-+#define GET_BIT2_CHECK(p, i, A0, A1) IF_BIT_0_CHECK(p) \
-+  { UPDATE_0_CHECK; i = (i + i); A0; } else \
-+  { UPDATE_1_CHECK; i = (i + i) + 1; A1; }
-+#define GET_BIT_CHECK(p, i) GET_BIT2_CHECK(p, i, ; , ;)
-+#define TREE_DECODE_CHECK(probs, limit, i) \
-+  { i = 1; do { GET_BIT_CHECK(probs + i, i) } while (i < limit); i -= limit; }
-+
-+
-+#define kNumPosBitsMax 4
-+#define kNumPosStatesMax (1 << kNumPosBitsMax)
-+
-+#define kLenNumLowBits 3
-+#define kLenNumLowSymbols (1 << kLenNumLowBits)
-+#define kLenNumMidBits 3
-+#define kLenNumMidSymbols (1 << kLenNumMidBits)
-+#define kLenNumHighBits 8
-+#define kLenNumHighSymbols (1 << kLenNumHighBits)
-+
-+#define LenChoice 0
-+#define LenChoice2 (LenChoice + 1)
-+#define LenLow (LenChoice2 + 1)
-+#define LenMid (LenLow + (kNumPosStatesMax << kLenNumLowBits))
-+#define LenHigh (LenMid + (kNumPosStatesMax << kLenNumMidBits))
-+#define kNumLenProbs (LenHigh + kLenNumHighSymbols)
-+
-+
-+#define kNumStates 12
-+#define kNumLitStates 7
-+
-+#define kStartPosModelIndex 4
-+#define kEndPosModelIndex 14
-+#define kNumFullDistances (1 << (kEndPosModelIndex >> 1))
-+
-+#define kNumPosSlotBits 6
-+#define kNumLenToPosStates 4
-+
-+#define kNumAlignBits 4
-+#define kAlignTableSize (1 << kNumAlignBits)
-+
-+#define kMatchMinLen 2
-+#define kMatchSpecLenStart (kMatchMinLen + kLenNumLowSymbols + kLenNumMidSymbols + kLenNumHighSymbols)
-+
-+#define IsMatch 0
-+#define IsRep (IsMatch + (kNumStates << kNumPosBitsMax))
-+#define IsRepG0 (IsRep + kNumStates)
-+#define IsRepG1 (IsRepG0 + kNumStates)
-+#define IsRepG2 (IsRepG1 + kNumStates)
-+#define IsRep0Long (IsRepG2 + kNumStates)
-+#define PosSlot (IsRep0Long + (kNumStates << kNumPosBitsMax))
-+#define SpecPos (PosSlot + (kNumLenToPosStates << kNumPosSlotBits))
-+#define Align (SpecPos + kNumFullDistances - kEndPosModelIndex)
-+#define LenCoder (Align + kAlignTableSize)
-+#define RepLenCoder (LenCoder + kNumLenProbs)
-+#define Literal (RepLenCoder + kNumLenProbs)
-+
-+#define LZMA_BASE_SIZE 1846
-+#define LZMA_LIT_SIZE 768
-+
-+#define LzmaProps_GetNumProbs(p) ((UInt32)LZMA_BASE_SIZE + (LZMA_LIT_SIZE << ((p)->lc + (p)->lp)))
-+
-+#if Literal != LZMA_BASE_SIZE
-+StopCompilingDueBUG
-+#endif
-+
-+#define LZMA_DIC_MIN (1 << 12)
-+
-+/* First LZMA-symbol is always decoded.
-+And it decodes new LZMA-symbols while (buf < bufLimit), but "buf" is without last normalization
-+Out:
-+  Result:
-+    SZ_OK - OK
-+    SZ_ERROR_DATA - Error
-+  p->remainLen:
-+    < kMatchSpecLenStart : normal remain
-+    = kMatchSpecLenStart : finished
-+    = kMatchSpecLenStart + 1 : Flush marker
-+    = kMatchSpecLenStart + 2 : State Init Marker
-+*/
-+
-+static int MY_FAST_CALL LzmaDec_DecodeReal(CLzmaDec *p, SizeT limit, const Byte *bufLimit)
-+{
-+  CLzmaProb *probs = p->probs;
-+
-+  unsigned state = p->state;
-+  UInt32 rep0 = p->reps[0], rep1 = p->reps[1], rep2 = p->reps[2], rep3 = p->reps[3];
-+  unsigned pbMask = ((unsigned)1 << (p->prop.pb)) - 1;
-+  unsigned lpMask = ((unsigned)1 << (p->prop.lp)) - 1;
-+  unsigned lc = p->prop.lc;
-+
-+  Byte *dic = p->dic;
-+  SizeT dicBufSize = p->dicBufSize;
-+  SizeT dicPos = p->dicPos;
-+
-+  UInt32 processedPos = p->processedPos;
-+  UInt32 checkDicSize = p->checkDicSize;
-+  unsigned len = 0;
-+
-+  const Byte *buf = p->buf;
-+  UInt32 range = p->range;
-+  UInt32 code = p->code;
-+
-+  do
-+  {
-+    CLzmaProb *prob;
-+    UInt32 bound;
-+    unsigned ttt;
-+    unsigned posState = processedPos & pbMask;
-+
-+    prob = probs + IsMatch + (state << kNumPosBitsMax) + posState;
-+    IF_BIT_0(prob)
-+    {
-+      unsigned symbol;
-+      UPDATE_0(prob);
-+      prob = probs + Literal;
-+      if (checkDicSize != 0 || processedPos != 0)
-+        prob += (LZMA_LIT_SIZE * (((processedPos & lpMask) << lc) +
-+        (dic[(dicPos == 0 ? dicBufSize : dicPos) - 1] >> (8 - lc))));
-+
-+      if (state < kNumLitStates)
-+      {
-+        state -= (state < 4) ? state : 3;
-+        symbol = 1;
-+        do { GET_BIT(prob + symbol, symbol) } while (symbol < 0x100);
-+      }
-+      else
-+      {
-+        unsigned matchByte = p->dic[(dicPos - rep0) + ((dicPos < rep0) ? dicBufSize : 0)];
-+        unsigned offs = 0x100;
-+        state -= (state < 10) ? 3 : 6;
-+        symbol = 1;
-+        do
-+        {
-+          unsigned bit;
-+          CLzmaProb *probLit;
-+          matchByte <<= 1;
-+          bit = (matchByte & offs);
-+          probLit = prob + offs + bit + symbol;
-+          GET_BIT2(probLit, symbol, offs &= ~bit, offs &= bit)
-+        }
-+        while (symbol < 0x100);
-+      }
-+      dic[dicPos++] = (Byte)symbol;
-+      processedPos++;
-+      continue;
-+    }
-+    else
-+    {
-+      UPDATE_1(prob);
-+      prob = probs + IsRep + state;
-+      IF_BIT_0(prob)
-+      {
-+        UPDATE_0(prob);
-+        state += kNumStates;
-+        prob = probs + LenCoder;
-+      }
-+      else
-+      {
-+        UPDATE_1(prob);
-+        if (checkDicSize == 0 && processedPos == 0)
-+          return SZ_ERROR_DATA;
-+        prob = probs + IsRepG0 + state;
-+        IF_BIT_0(prob)
-+        {
-+          UPDATE_0(prob);
-+          prob = probs + IsRep0Long + (state << kNumPosBitsMax) + posState;
-+          IF_BIT_0(prob)
-+          {
-+            UPDATE_0(prob);
-+            dic[dicPos] = dic[(dicPos - rep0) + ((dicPos < rep0) ? dicBufSize : 0)];
-+            dicPos++;
-+            processedPos++;
-+            state = state < kNumLitStates ? 9 : 11;
-+            continue;
-+          }
-+          UPDATE_1(prob);
-+        }
-+        else
-+        {
-+          UInt32 distance;
-+          UPDATE_1(prob);
-+          prob = probs + IsRepG1 + state;
-+          IF_BIT_0(prob)
-+          {
-+            UPDATE_0(prob);
-+            distance = rep1;
-+          }
-+          else
-+          {
-+            UPDATE_1(prob);
-+            prob = probs + IsRepG2 + state;
-+            IF_BIT_0(prob)
-+            {
-+              UPDATE_0(prob);
-+              distance = rep2;
-+            }
-+            else
-+            {
-+              UPDATE_1(prob);
-+              distance = rep3;
-+              rep3 = rep2;
-+            }
-+            rep2 = rep1;
-+          }
-+          rep1 = rep0;
-+          rep0 = distance;
-+        }
-+        state = state < kNumLitStates ? 8 : 11;
-+        prob = probs + RepLenCoder;
-+      }
-+      {
-+        unsigned limit, offset;
-+        CLzmaProb *probLen = prob + LenChoice;
-+        IF_BIT_0(probLen)
-+        {
-+          UPDATE_0(probLen);
-+          probLen = prob + LenLow + (posState << kLenNumLowBits);
-+          offset = 0;
-+          limit = (1 << kLenNumLowBits);
-+        }
-+        else
-+        {
-+          UPDATE_1(probLen);
-+          probLen = prob + LenChoice2;
-+          IF_BIT_0(probLen)
-+          {
-+            UPDATE_0(probLen);
-+            probLen = prob + LenMid + (posState << kLenNumMidBits);
-+            offset = kLenNumLowSymbols;
-+            limit = (1 << kLenNumMidBits);
-+          }
-+          else
-+          {
-+            UPDATE_1(probLen);
-+            probLen = prob + LenHigh;
-+            offset = kLenNumLowSymbols + kLenNumMidSymbols;
-+            limit = (1 << kLenNumHighBits);
-+          }
-+        }
-+        TREE_DECODE(probLen, limit, len);
-+        len += offset;
-+      }
-+
-+      if (state >= kNumStates)
-+      {
-+        UInt32 distance;
-+        prob = probs + PosSlot +
-+            ((len < kNumLenToPosStates ? len : kNumLenToPosStates - 1) << kNumPosSlotBits);
-+        TREE_6_DECODE(prob, distance);
-+        if (distance >= kStartPosModelIndex)
-+        {
-+          unsigned posSlot = (unsigned)distance;
-+          int numDirectBits = (int)(((distance >> 1) - 1));
-+          distance = (2 | (distance & 1));
-+          if (posSlot < kEndPosModelIndex)
-+          {
-+            distance <<= numDirectBits;
-+            prob = probs + SpecPos + distance - posSlot - 1;
-+            {
-+              UInt32 mask = 1;
-+              unsigned i = 1;
-+              do
-+              {
-+                GET_BIT2(prob + i, i, ; , distance |= mask);
-+                mask <<= 1;
-+              }
-+              while (--numDirectBits != 0);
-+            }
-+          }
-+          else
-+          {
-+            numDirectBits -= kNumAlignBits;
-+            do
-+            {
-+              NORMALIZE
-+              range >>= 1;
-+
-+              {
-+                UInt32 t;
-+                code -= range;
-+                t = (0 - ((UInt32)code >> 31)); /* (UInt32)((Int32)code >> 31) */
-+                distance = (distance << 1) + (t + 1);
-+                code += range & t;
-+              }
-+              /*
-+              distance <<= 1;
-+              if (code >= range)
-+              {
-+                code -= range;
-+                distance |= 1;
-+              }
-+              */
-+            }
-+            while (--numDirectBits != 0);
-+            prob = probs + Align;
-+            distance <<= kNumAlignBits;
-+            {
-+              unsigned i = 1;
-+              GET_BIT2(prob + i, i, ; , distance |= 1);
-+              GET_BIT2(prob + i, i, ; , distance |= 2);
-+              GET_BIT2(prob + i, i, ; , distance |= 4);
-+              GET_BIT2(prob + i, i, ; , distance |= 8);
-+            }
-+            if (distance == (UInt32)0xFFFFFFFF)
-+            {
-+              len += kMatchSpecLenStart;
-+              state -= kNumStates;
-+              break;
-+            }
-+          }
-+        }
-+        rep3 = rep2;
-+        rep2 = rep1;
-+        rep1 = rep0;
-+        rep0 = distance + 1;
-+        if (checkDicSize == 0)
-+        {
-+          if (distance >= processedPos)
-+            return SZ_ERROR_DATA;
-+        }
-+        else if (distance >= checkDicSize)
-+          return SZ_ERROR_DATA;
-+        state = (state < kNumStates + kNumLitStates) ? kNumLitStates : kNumLitStates + 3;
-+      }
-+
-+      len += kMatchMinLen;
-+
-+      if (limit == dicPos)
-+        return SZ_ERROR_DATA;
-+      {
-+        SizeT rem = limit - dicPos;
-+        unsigned curLen = ((rem < len) ? (unsigned)rem : len);
-+        SizeT pos = (dicPos - rep0) + ((dicPos < rep0) ? dicBufSize : 0);
-+
-+        processedPos += curLen;
-+
-+        len -= curLen;
-+        if (pos + curLen <= dicBufSize)
-+        {
-+          Byte *dest = dic + dicPos;
-+          ptrdiff_t src = (ptrdiff_t)pos - (ptrdiff_t)dicPos;
-+          const Byte *lim = dest + curLen;
-+          dicPos += curLen;
-+          do
-+            *(dest) = (Byte)*(dest + src);
-+          while (++dest != lim);
-+        }
-+        else
-+        {
-+          do
-+          {
-+            dic[dicPos++] = dic[pos];
-+            if (++pos == dicBufSize)
-+              pos = 0;
-+          }
-+          while (--curLen != 0);
-+        }
-+      }
-+    }
-+  }
-+  while (dicPos < limit && buf < bufLimit);
-+  NORMALIZE;
-+  p->buf = buf;
-+  p->range = range;
-+  p->code = code;
-+  p->remainLen = len;
-+  p->dicPos = dicPos;
-+  p->processedPos = processedPos;
-+  p->reps[0] = rep0;
-+  p->reps[1] = rep1;
-+  p->reps[2] = rep2;
-+  p->reps[3] = rep3;
-+  p->state = state;
-+
-+  return SZ_OK;
-+}
-+
-+static void MY_FAST_CALL LzmaDec_WriteRem(CLzmaDec *p, SizeT limit)
-+{
-+  if (p->remainLen != 0 && p->remainLen < kMatchSpecLenStart)
-+  {
-+    Byte *dic = p->dic;
-+    SizeT dicPos = p->dicPos;
-+    SizeT dicBufSize = p->dicBufSize;
-+    unsigned len = p->remainLen;
-+    UInt32 rep0 = p->reps[0];
-+    if (limit - dicPos < len)
-+      len = (unsigned)(limit - dicPos);
-+
-+    if (p->checkDicSize == 0 && p->prop.dicSize - p->processedPos <= len)
-+      p->checkDicSize = p->prop.dicSize;
-+
-+    p->processedPos += len;
-+    p->remainLen -= len;
-+    while (len-- != 0)
-+    {
-+      dic[dicPos] = dic[(dicPos - rep0) + ((dicPos < rep0) ? dicBufSize : 0)];
-+      dicPos++;
-+    }
-+    p->dicPos = dicPos;
-+  }
-+}
-+
-+static int MY_FAST_CALL LzmaDec_DecodeReal2(CLzmaDec *p, SizeT limit, const Byte *bufLimit)
-+{
-+  do
-+  {
-+    SizeT limit2 = limit;
-+    if (p->checkDicSize == 0)
-+    {
-+      UInt32 rem = p->prop.dicSize - p->processedPos;
-+      if (limit - p->dicPos > rem)
-+        limit2 = p->dicPos + rem;
-+    }
-+    RINOK(LzmaDec_DecodeReal(p, limit2, bufLimit));
-+    if (p->processedPos >= p->prop.dicSize)
-+      p->checkDicSize = p->prop.dicSize;
-+    LzmaDec_WriteRem(p, limit);
-+  }
-+  while (p->dicPos < limit && p->buf < bufLimit && p->remainLen < kMatchSpecLenStart);
-+
-+  if (p->remainLen > kMatchSpecLenStart)
-+  {
-+    p->remainLen = kMatchSpecLenStart;
-+  }
-+  return 0;
-+}
-+
-+typedef enum
-+{
-+  DUMMY_ERROR, /* unexpected end of input stream */
-+  DUMMY_LIT,
-+  DUMMY_MATCH,
-+  DUMMY_REP
-+} ELzmaDummy;
-+
-+static ELzmaDummy LzmaDec_TryDummy(const CLzmaDec *p, const Byte *buf, SizeT inSize)
-+{
-+  UInt32 range = p->range;
-+  UInt32 code = p->code;
-+  const Byte *bufLimit = buf + inSize;
-+  CLzmaProb *probs = p->probs;
-+  unsigned state = p->state;
-+  ELzmaDummy res;
-+
-+  {
-+    CLzmaProb *prob;
-+    UInt32 bound;
-+    unsigned ttt;
-+    unsigned posState = (p->processedPos) & ((1 << p->prop.pb) - 1);
-+
-+    prob = probs + IsMatch + (state << kNumPosBitsMax) + posState;
-+    IF_BIT_0_CHECK(prob)
-+    {
-+      UPDATE_0_CHECK
-+
-+      /* if (bufLimit - buf >= 7) return DUMMY_LIT; */
-+
-+      prob = probs + Literal;
-+      if (p->checkDicSize != 0 || p->processedPos != 0)
-+        prob += (LZMA_LIT_SIZE *
-+          ((((p->processedPos) & ((1 << (p->prop.lp)) - 1)) << p->prop.lc) +
-+          (p->dic[(p->dicPos == 0 ? p->dicBufSize : p->dicPos) - 1] >> (8 - p->prop.lc))));
-+
-+      if (state < kNumLitStates)
-+      {
-+        unsigned symbol = 1;
-+        do { GET_BIT_CHECK(prob + symbol, symbol) } while (symbol < 0x100);
-+      }
-+      else
-+      {
-+        unsigned matchByte = p->dic[p->dicPos - p->reps[0] +
-+            ((p->dicPos < p->reps[0]) ? p->dicBufSize : 0)];
-+        unsigned offs = 0x100;
-+        unsigned symbol = 1;
-+        do
-+        {
-+          unsigned bit;
-+          CLzmaProb *probLit;
-+          matchByte <<= 1;
-+          bit = (matchByte & offs);
-+          probLit = prob + offs + bit + symbol;
-+          GET_BIT2_CHECK(probLit, symbol, offs &= ~bit, offs &= bit)
-+        }
-+        while (symbol < 0x100);
-+      }
-+      res = DUMMY_LIT;
-+    }
-+    else
-+    {
-+      unsigned len;
-+      UPDATE_1_CHECK;
-+
-+      prob = probs + IsRep + state;
-+      IF_BIT_0_CHECK(prob)
-+      {
-+        UPDATE_0_CHECK;
-+        state = 0;
-+        prob = probs + LenCoder;
-+        res = DUMMY_MATCH;
-+      }
-+      else
-+      {
-+        UPDATE_1_CHECK;
-+        res = DUMMY_REP;
-+        prob = probs + IsRepG0 + state;
-+        IF_BIT_0_CHECK(prob)
-+        {
-+          UPDATE_0_CHECK;
-+          prob = probs + IsRep0Long + (state << kNumPosBitsMax) + posState;
-+          IF_BIT_0_CHECK(prob)
-+          {
-+            UPDATE_0_CHECK;
-+            NORMALIZE_CHECK;
-+            return DUMMY_REP;
-+          }
-+          else
-+          {
-+            UPDATE_1_CHECK;
-+          }
-+        }
-+        else
-+        {
-+          UPDATE_1_CHECK;
-+          prob = probs + IsRepG1 + state;
-+          IF_BIT_0_CHECK(prob)
-+          {
-+            UPDATE_0_CHECK;
-+          }
-+          else
-+          {
-+            UPDATE_1_CHECK;
-+            prob = probs + IsRepG2 + state;
-+            IF_BIT_0_CHECK(prob)
-+            {
-+              UPDATE_0_CHECK;
-+            }
-+            else
-+            {
-+              UPDATE_1_CHECK;
-+            }
-+          }
-+        }
-+        state = kNumStates;
-+        prob = probs + RepLenCoder;
-+      }
-+      {
-+        unsigned limit, offset;
-+        CLzmaProb *probLen = prob + LenChoice;
-+        IF_BIT_0_CHECK(probLen)
-+        {
-+          UPDATE_0_CHECK;
-+          probLen = prob + LenLow + (posState << kLenNumLowBits);
-+          offset = 0;
-+          limit = 1 << kLenNumLowBits;
-+        }
-+        else
-+        {
-+          UPDATE_1_CHECK;
-+          probLen = prob + LenChoice2;
-+          IF_BIT_0_CHECK(probLen)
-+          {
-+            UPDATE_0_CHECK;
-+            probLen = prob + LenMid + (posState << kLenNumMidBits);
-+            offset = kLenNumLowSymbols;
-+            limit = 1 << kLenNumMidBits;
-+          }
-+          else
-+          {
-+            UPDATE_1_CHECK;
-+            probLen = prob + LenHigh;
-+            offset = kLenNumLowSymbols + kLenNumMidSymbols;
-+            limit = 1 << kLenNumHighBits;
-+          }
-+        }
-+        TREE_DECODE_CHECK(probLen, limit, len);
-+        len += offset;
-+      }
-+
-+      if (state < 4)
-+      {
-+        unsigned posSlot;
-+        prob = probs + PosSlot +
-+            ((len < kNumLenToPosStates ? len : kNumLenToPosStates - 1) <<
-+            kNumPosSlotBits);
-+        TREE_DECODE_CHECK(prob, 1 << kNumPosSlotBits, posSlot);
-+        if (posSlot >= kStartPosModelIndex)
-+        {
-+          int numDirectBits = ((posSlot >> 1) - 1);
-+
-+          /* if (bufLimit - buf >= 8) return DUMMY_MATCH; */
-+
-+          if (posSlot < kEndPosModelIndex)
-+          {
-+            prob = probs + SpecPos + ((2 | (posSlot & 1)) << numDirectBits) - posSlot - 1;
-+          }
-+          else
-+          {
-+            numDirectBits -= kNumAlignBits;
-+            do
-+            {
-+              NORMALIZE_CHECK
-+              range >>= 1;
-+              code -= range & (((code - range) >> 31) - 1);
-+              /* if (code >= range) code -= range; */
-+            }
-+            while (--numDirectBits != 0);
-+            prob = probs + Align;
-+            numDirectBits = kNumAlignBits;
-+          }
-+          {
-+            unsigned i = 1;
-+            do
-+            {
-+              GET_BIT_CHECK(prob + i, i);
-+            }
-+            while (--numDirectBits != 0);
-+          }
-+        }
-+      }
-+    }
-+  }
-+  NORMALIZE_CHECK;
-+  return res;
-+}
-+
-+
-+static void LzmaDec_InitRc(CLzmaDec *p, const Byte *data)
-+{
-+  p->code = ((UInt32)data[1] << 24) | ((UInt32)data[2] << 16) | ((UInt32)data[3] << 8) | ((UInt32)data[4]);
-+  p->range = 0xFFFFFFFF;
-+  p->needFlush = 0;
-+}
-+
-+static void LzmaDec_InitDicAndState(CLzmaDec *p, Bool initDic, Bool initState)
-+{
-+  p->needFlush = 1;
-+  p->remainLen = 0;
-+  p->tempBufSize = 0;
-+
-+  if (initDic)
-+  {
-+    p->processedPos = 0;
-+    p->checkDicSize = 0;
-+    p->needInitState = 1;
-+  }
-+  if (initState)
-+    p->needInitState = 1;
-+}
-+
-+static void LzmaDec_Init(CLzmaDec *p)
-+{
-+  p->dicPos = 0;
-+  LzmaDec_InitDicAndState(p, True, True);
-+}
-+
-+static void LzmaDec_InitStateReal(CLzmaDec *p)
-+{
-+  UInt32 numProbs = Literal + ((UInt32)LZMA_LIT_SIZE << (p->prop.lc + p->prop.lp));
-+  UInt32 i;
-+  CLzmaProb *probs = p->probs;
-+  for (i = 0; i < numProbs; i++)
-+    probs[i] = kBitModelTotal >> 1;
-+  p->reps[0] = p->reps[1] = p->reps[2] = p->reps[3] = 1;
-+  p->state = 0;
-+  p->needInitState = 0;
-+}
-+
-+static SRes LzmaDec_DecodeToDic(CLzmaDec *p, SizeT dicLimit, const Byte *src, SizeT *srcLen,
-+    ELzmaFinishMode finishMode, ELzmaStatus *status)
-+{
-+  SizeT inSize = *srcLen;
-+  (*srcLen) = 0;
-+  LzmaDec_WriteRem(p, dicLimit);
-+
-+  *status = LZMA_STATUS_NOT_SPECIFIED;
-+
-+  while (p->remainLen != kMatchSpecLenStart)
-+  {
-+      int checkEndMarkNow;
-+
-+      if (p->needFlush != 0)
-+      {
-+        for (; inSize > 0 && p->tempBufSize < RC_INIT_SIZE; (*srcLen)++, inSize--)
-+          p->tempBuf[p->tempBufSize++] = *src++;
-+        if (p->tempBufSize < RC_INIT_SIZE)
-+        {
-+          *status = LZMA_STATUS_NEEDS_MORE_INPUT;
-+          return SZ_OK;
-+        }
-+        if (p->tempBuf[0] != 0)
-+          return SZ_ERROR_DATA;
-+
-+        LzmaDec_InitRc(p, p->tempBuf);
-+        p->tempBufSize = 0;
-+      }
-+
-+      checkEndMarkNow = 0;
-+      if (p->dicPos >= dicLimit)
-+      {
-+        if (p->remainLen == 0 && p->code == 0)
-+        {
-+          *status = LZMA_STATUS_MAYBE_FINISHED_WITHOUT_MARK;
-+          return SZ_OK;
-+        }
-+        if (finishMode == LZMA_FINISH_ANY)
-+        {
-+          *status = LZMA_STATUS_NOT_FINISHED;
-+          return SZ_OK;
-+        }
-+        if (p->remainLen != 0)
-+        {
-+          *status = LZMA_STATUS_NOT_FINISHED;
-+          return SZ_ERROR_DATA;
-+        }
-+        checkEndMarkNow = 1;
-+      }
-+
-+      if (p->needInitState)
-+        LzmaDec_InitStateReal(p);
-+
-+      if (p->tempBufSize == 0)
-+      {
-+        SizeT processed;
-+        const Byte *bufLimit;
-+        if (inSize < LZMA_REQUIRED_INPUT_MAX || checkEndMarkNow)
-+        {
-+          int dummyRes = LzmaDec_TryDummy(p, src, inSize);
-+          if (dummyRes == DUMMY_ERROR)
-+          {
-+            memcpy(p->tempBuf, src, inSize);
-+            p->tempBufSize = (unsigned)inSize;
-+            (*srcLen) += inSize;
-+            *status = LZMA_STATUS_NEEDS_MORE_INPUT;
-+            return SZ_OK;
-+          }
-+          if (checkEndMarkNow && dummyRes != DUMMY_MATCH)
-+          {
-+            *status = LZMA_STATUS_NOT_FINISHED;
-+            return SZ_ERROR_DATA;
-+          }
-+          bufLimit = src;
-+        }
-+        else
-+          bufLimit = src + inSize - LZMA_REQUIRED_INPUT_MAX;
-+        p->buf = src;
-+        if (LzmaDec_DecodeReal2(p, dicLimit, bufLimit) != 0)
-+          return SZ_ERROR_DATA;
-+        processed = (SizeT)(p->buf - src);
-+        (*srcLen) += processed;
-+        src += processed;
-+        inSize -= processed;
-+      }
-+      else
-+      {
-+        unsigned rem = p->tempBufSize, lookAhead = 0;
-+        while (rem < LZMA_REQUIRED_INPUT_MAX && lookAhead < inSize)
-+          p->tempBuf[rem++] = src[lookAhead++];
-+        p->tempBufSize = rem;
-+        if (rem < LZMA_REQUIRED_INPUT_MAX || checkEndMarkNow)
-+        {
-+          int dummyRes = LzmaDec_TryDummy(p, p->tempBuf, rem);
-+          if (dummyRes == DUMMY_ERROR)
-+          {
-+            (*srcLen) += lookAhead;
-+            *status = LZMA_STATUS_NEEDS_MORE_INPUT;
-+            return SZ_OK;
-+          }
-+          if (checkEndMarkNow && dummyRes != DUMMY_MATCH)
-+          {
-+            *status = LZMA_STATUS_NOT_FINISHED;
-+            return SZ_ERROR_DATA;
-+          }
-+        }
-+        p->buf = p->tempBuf;
-+        if (LzmaDec_DecodeReal2(p, dicLimit, p->buf) != 0)
-+          return SZ_ERROR_DATA;
-+        lookAhead -= (rem - (unsigned)(p->buf - p->tempBuf));
-+        (*srcLen) += lookAhead;
-+        src += lookAhead;
-+        inSize -= lookAhead;
-+        p->tempBufSize = 0;
-+      }
-+  }
-+  if (p->code == 0)
-+    *status = LZMA_STATUS_FINISHED_WITH_MARK;
-+  return (p->code == 0) ? SZ_OK : SZ_ERROR_DATA;
-+}
-+
-+static void LzmaDec_FreeProbs(CLzmaDec *p, ISzAlloc *alloc)
-+{
-+  alloc->Free(alloc, p->probs);
-+  p->probs = 0;
-+}
-+
-+static SRes LzmaProps_Decode(CLzmaProps *p, const Byte *data, unsigned size)
-+{
-+  UInt32 dicSize;
-+  Byte d;
-+
-+  if (size < LZMA_PROPS_SIZE)
-+    return SZ_ERROR_UNSUPPORTED;
-+  else
-+    dicSize = data[1] | ((UInt32)data[2] << 8) | ((UInt32)data[3] << 16) | ((UInt32)data[4] << 24);
-+
-+  if (dicSize < LZMA_DIC_MIN)
-+    dicSize = LZMA_DIC_MIN;
-+  p->dicSize = dicSize;
-+
-+  d = data[0];
-+  if (d >= (9 * 5 * 5))
-+    return SZ_ERROR_UNSUPPORTED;
-+
-+  p->lc = d % 9;
-+  d /= 9;
-+  p->pb = d / 5;
-+  p->lp = d % 5;
-+
-+  return SZ_OK;
-+}
-+
-+static SRes LzmaDec_AllocateProbs2(CLzmaDec *p, const CLzmaProps *propNew, ISzAlloc *alloc)
-+{
-+  UInt32 numProbs = LzmaProps_GetNumProbs(propNew);
-+  if (p->probs == 0 || numProbs != p->numProbs)
-+  {
-+    LzmaDec_FreeProbs(p, alloc);
-+    p->probs = (CLzmaProb *)alloc->Alloc(alloc, numProbs * sizeof(CLzmaProb));
-+    p->numProbs = numProbs;
-+    if (p->probs == 0)
-+      return SZ_ERROR_MEM;
-+  }
-+  return SZ_OK;
-+}
-+
-+static SRes LzmaDec_AllocateProbs(CLzmaDec *p, const Byte *props, unsigned propsSize, ISzAlloc *alloc)
-+{
-+  CLzmaProps propNew;
-+  RINOK(LzmaProps_Decode(&propNew, props, propsSize));
-+  RINOK(LzmaDec_AllocateProbs2(p, &propNew, alloc));
-+  p->prop = propNew;
-+  return SZ_OK;
-+}
-+
-+SRes LzmaDecode(Byte *dest, SizeT *destLen, const Byte *src, SizeT *srcLen,
-+    const Byte *propData, unsigned propSize, ELzmaFinishMode finishMode,
-+    ELzmaStatus *status, ISzAlloc *alloc)
-+{
-+  CLzmaDec p;
-+  SRes res;
-+  SizeT inSize = *srcLen;
-+  SizeT outSize = *destLen;
-+  *srcLen = *destLen = 0;
-+  if (inSize < RC_INIT_SIZE)
-+    return SZ_ERROR_INPUT_EOF;
-+
-+  LzmaDec_Construct(&p);
-+  res = LzmaDec_AllocateProbs(&p, propData, propSize, alloc);
-+  if (res != 0)
-+    return res;
-+  p.dic = dest;
-+  p.dicBufSize = outSize;
-+
-+  LzmaDec_Init(&p);
-+
-+  *srcLen = inSize;
-+  res = LzmaDec_DecodeToDic(&p, outSize, src, srcLen, finishMode, status);
-+
-+  if (res == SZ_OK && *status == LZMA_STATUS_NEEDS_MORE_INPUT)
-+    res = SZ_ERROR_INPUT_EOF;
-+
-+  (*destLen) = p.dicPos;
-+  LzmaDec_FreeProbs(&p, alloc);
-+  return res;
-+}
---- /dev/null
-+++ b/lib/lzma/LzmaEnc.c
-@@ -0,0 +1,2123 @@
-+/* LzmaEnc.c -- LZMA Encoder
-+2009-11-24 : Igor Pavlov : Public domain */
-+
-+#include <string.h>
-+
-+/* #define SHOW_STAT */
-+/* #define SHOW_STAT2 */
-+
-+#if defined(SHOW_STAT) || defined(SHOW_STAT2)
-+#include <stdio.h>
-+#endif
-+
-+#include "LzmaEnc.h"
-+
-+/* disable MT */
-+#define _7ZIP_ST
-+
-+#include "LzFind.h"
-+#ifndef _7ZIP_ST
-+#include "LzFindMt.h"
-+#endif
-+
-+#ifdef SHOW_STAT
-+static int ttt = 0;
-+#endif
-+
-+#define kBlockSizeMax ((1 << LZMA_NUM_BLOCK_SIZE_BITS) - 1)
-+
-+#define kBlockSize (9 << 10)
-+#define kUnpackBlockSize (1 << 18)
-+#define kMatchArraySize (1 << 21)
-+#define kMatchRecordMaxSize ((LZMA_MATCH_LEN_MAX * 2 + 3) * LZMA_MATCH_LEN_MAX)
-+
-+#define kNumMaxDirectBits (31)
-+
-+#define kNumTopBits 24
-+#define kTopValue ((UInt32)1 << kNumTopBits)
-+
-+#define kNumBitModelTotalBits 11
-+#define kBitModelTotal (1 << kNumBitModelTotalBits)
-+#define kNumMoveBits 5
-+#define kProbInitValue (kBitModelTotal >> 1)
-+
-+#define kNumMoveReducingBits 4
-+#define kNumBitPriceShiftBits 4
-+#define kBitPrice (1 << kNumBitPriceShiftBits)
-+
-+void LzmaEncProps_Init(CLzmaEncProps *p)
-+{
-+  p->level = 5;
-+  p->dictSize = p->mc = 0;
-+  p->lc = p->lp = p->pb = p->algo = p->fb = p->btMode = p->numHashBytes = p->numThreads = -1;
-+  p->writeEndMark = 0;
-+}
-+
-+static void LzmaEncProps_Normalize(CLzmaEncProps *p)
-+{
-+  int level = p->level;
-+  if (level < 0) level = 5;
-+  p->level = level;
-+  if (p->dictSize == 0) p->dictSize = (level <= 5 ? (1 << (level * 2 + 14)) : (level == 6 ? (1 << 25) : (1 << 26)));
-+  if (p->lc < 0) p->lc = 3;
-+  if (p->lp < 0) p->lp = 0;
-+  if (p->pb < 0) p->pb = 2;
-+  if (p->algo < 0) p->algo = (level < 5 ? 0 : 1);
-+  if (p->fb < 0) p->fb = (level < 7 ? 32 : 64);
-+  if (p->btMode < 0) p->btMode = (p->algo == 0 ? 0 : 1);
-+  if (p->numHashBytes < 0) p->numHashBytes = 4;
-+  if (p->mc == 0)  p->mc = (16 + (p->fb >> 1)) >> (p->btMode ? 0 : 1);
-+  if (p->numThreads < 0)
-+    p->numThreads =
-+      #ifndef _7ZIP_ST
-+      ((p->btMode && p->algo) ? 2 : 1);
-+      #else
-+      1;
-+      #endif
-+}
-+
-+static UInt32 __maybe_unused LzmaEncProps_GetDictSize(const CLzmaEncProps *props2)
-+{
-+  CLzmaEncProps props = *props2;
-+  LzmaEncProps_Normalize(&props);
-+  return props.dictSize;
-+}
-+
-+/* #define LZMA_LOG_BSR */
-+/* Define it for Intel's CPU */
-+
-+
-+#ifdef LZMA_LOG_BSR
-+
-+#define kDicLogSizeMaxCompress 30
-+
-+#define BSR2_RET(pos, res) { unsigned long i; _BitScanReverse(&i, (pos)); res = (i + i) + ((pos >> (i - 1)) & 1); }
-+
-+static UInt32 GetPosSlot1(UInt32 pos)
-+{
-+  UInt32 res;
-+  BSR2_RET(pos, res);
-+  return res;
-+}
-+#define GetPosSlot2(pos, res) { BSR2_RET(pos, res); }
-+#define GetPosSlot(pos, res) { if (pos < 2) res = pos; else BSR2_RET(pos, res); }
-+
-+#else
-+
-+#define kNumLogBits (9 + (int)sizeof(size_t) / 2)
-+#define kDicLogSizeMaxCompress ((kNumLogBits - 1) * 2 + 7)
-+
-+static void LzmaEnc_FastPosInit(Byte *g_FastPos)
-+{
-+  int c = 2, slotFast;
-+  g_FastPos[0] = 0;
-+  g_FastPos[1] = 1;
-+
-+  for (slotFast = 2; slotFast < kNumLogBits * 2; slotFast++)
-+  {
-+    UInt32 k = (1 << ((slotFast >> 1) - 1));
-+    UInt32 j;
-+    for (j = 0; j < k; j++, c++)
-+      g_FastPos[c] = (Byte)slotFast;
-+  }
-+}
-+
-+#define BSR2_RET(pos, res) { UInt32 i = 6 + ((kNumLogBits - 1) & \
-+  (0 - (((((UInt32)1 << (kNumLogBits + 6)) - 1) - pos) >> 31))); \
-+  res = p->g_FastPos[pos >> i] + (i * 2); }
-+/*
-+#define BSR2_RET(pos, res) { res = (pos < (1 << (kNumLogBits + 6))) ? \
-+  p->g_FastPos[pos >> 6] + 12 : \
-+  p->g_FastPos[pos >> (6 + kNumLogBits - 1)] + (6 + (kNumLogBits - 1)) * 2; }
-+*/
-+
-+#define GetPosSlot1(pos) p->g_FastPos[pos]
-+#define GetPosSlot2(pos, res) { BSR2_RET(pos, res); }
-+#define GetPosSlot(pos, res) { if (pos < kNumFullDistances) res = p->g_FastPos[pos]; else BSR2_RET(pos, res); }
-+
-+#endif
-+
-+
-+#define LZMA_NUM_REPS 4
-+
-+typedef unsigned CState;
-+
-+typedef struct
-+{
-+  UInt32 price;
-+
-+  CState state;
-+  int prev1IsChar;
-+  int prev2;
-+
-+  UInt32 posPrev2;
-+  UInt32 backPrev2;
-+
-+  UInt32 posPrev;
-+  UInt32 backPrev;
-+  UInt32 backs[LZMA_NUM_REPS];
-+} COptimal;
-+
-+#define kNumOpts (1 << 12)
-+
-+#define kNumLenToPosStates 4
-+#define kNumPosSlotBits 6
-+#define kDicLogSizeMin 0
-+#define kDicLogSizeMax 32
-+#define kDistTableSizeMax (kDicLogSizeMax * 2)
-+
-+
-+#define kNumAlignBits 4
-+#define kAlignTableSize (1 << kNumAlignBits)
-+#define kAlignMask (kAlignTableSize - 1)
-+
-+#define kStartPosModelIndex 4
-+#define kEndPosModelIndex 14
-+#define kNumPosModels (kEndPosModelIndex - kStartPosModelIndex)
-+
-+#define kNumFullDistances (1 << (kEndPosModelIndex >> 1))
-+
-+#ifdef _LZMA_PROB32
-+#define CLzmaProb UInt32
-+#else
-+#define CLzmaProb UInt16
-+#endif
-+
-+#define LZMA_PB_MAX 4
-+#define LZMA_LC_MAX 8
-+#define LZMA_LP_MAX 4
-+
-+#define LZMA_NUM_PB_STATES_MAX (1 << LZMA_PB_MAX)
-+
-+
-+#define kLenNumLowBits 3
-+#define kLenNumLowSymbols (1 << kLenNumLowBits)
-+#define kLenNumMidBits 3
-+#define kLenNumMidSymbols (1 << kLenNumMidBits)
-+#define kLenNumHighBits 8
-+#define kLenNumHighSymbols (1 << kLenNumHighBits)
-+
-+#define kLenNumSymbolsTotal (kLenNumLowSymbols + kLenNumMidSymbols + kLenNumHighSymbols)
-+
-+#define LZMA_MATCH_LEN_MIN 2
-+#define LZMA_MATCH_LEN_MAX (LZMA_MATCH_LEN_MIN + kLenNumSymbolsTotal - 1)
-+
-+#define kNumStates 12
-+
-+typedef struct
-+{
-+  CLzmaProb choice;
-+  CLzmaProb choice2;
-+  CLzmaProb low[LZMA_NUM_PB_STATES_MAX << kLenNumLowBits];
-+  CLzmaProb mid[LZMA_NUM_PB_STATES_MAX << kLenNumMidBits];
-+  CLzmaProb high[kLenNumHighSymbols];
-+} CLenEnc;
-+
-+typedef struct
-+{
-+  CLenEnc p;
-+  UInt32 prices[LZMA_NUM_PB_STATES_MAX][kLenNumSymbolsTotal];
-+  UInt32 tableSize;
-+  UInt32 counters[LZMA_NUM_PB_STATES_MAX];
-+} CLenPriceEnc;
-+
-+typedef struct
-+{
-+  UInt32 range;
-+  Byte cache;
-+  UInt64 low;
-+  UInt64 cacheSize;
-+  Byte *buf;
-+  Byte *bufLim;
-+  Byte *bufBase;
-+  ISeqOutStream *outStream;
-+  UInt64 processed;
-+  SRes res;
-+} CRangeEnc;
-+
-+typedef struct
-+{
-+  CLzmaProb *litProbs;
-+
-+  CLzmaProb isMatch[kNumStates][LZMA_NUM_PB_STATES_MAX];
-+  CLzmaProb isRep[kNumStates];
-+  CLzmaProb isRepG0[kNumStates];
-+  CLzmaProb isRepG1[kNumStates];
-+  CLzmaProb isRepG2[kNumStates];
-+  CLzmaProb isRep0Long[kNumStates][LZMA_NUM_PB_STATES_MAX];
-+
-+  CLzmaProb posSlotEncoder[kNumLenToPosStates][1 << kNumPosSlotBits];
-+  CLzmaProb posEncoders[kNumFullDistances - kEndPosModelIndex];
-+  CLzmaProb posAlignEncoder[1 << kNumAlignBits];
-+
-+  CLenPriceEnc lenEnc;
-+  CLenPriceEnc repLenEnc;
-+
-+  UInt32 reps[LZMA_NUM_REPS];
-+  UInt32 state;
-+} CSaveState;
-+
-+typedef struct
-+{
-+  IMatchFinder matchFinder;
-+  void *matchFinderObj;
-+
-+  #ifndef _7ZIP_ST
-+  Bool mtMode;
-+  CMatchFinderMt matchFinderMt;
-+  #endif
-+
-+  CMatchFinder matchFinderBase;
-+
-+  #ifndef _7ZIP_ST
-+  Byte pad[128];
-+  #endif
-+
-+  UInt32 optimumEndIndex;
-+  UInt32 optimumCurrentIndex;
-+
-+  UInt32 longestMatchLength;
-+  UInt32 numPairs;
-+  UInt32 numAvail;
-+  COptimal opt[kNumOpts];
-+
-+  #ifndef LZMA_LOG_BSR
-+  Byte g_FastPos[1 << kNumLogBits];
-+  #endif
-+
-+  UInt32 ProbPrices[kBitModelTotal >> kNumMoveReducingBits];
-+  UInt32 matches[LZMA_MATCH_LEN_MAX * 2 + 2 + 1];
-+  UInt32 numFastBytes;
-+  UInt32 additionalOffset;
-+  UInt32 reps[LZMA_NUM_REPS];
-+  UInt32 state;
-+
-+  UInt32 posSlotPrices[kNumLenToPosStates][kDistTableSizeMax];
-+  UInt32 distancesPrices[kNumLenToPosStates][kNumFullDistances];
-+  UInt32 alignPrices[kAlignTableSize];
-+  UInt32 alignPriceCount;
-+
-+  UInt32 distTableSize;
-+
-+  unsigned lc, lp, pb;
-+  unsigned lpMask, pbMask;
-+
-+  CLzmaProb *litProbs;
-+
-+  CLzmaProb isMatch[kNumStates][LZMA_NUM_PB_STATES_MAX];
-+  CLzmaProb isRep[kNumStates];
-+  CLzmaProb isRepG0[kNumStates];
-+  CLzmaProb isRepG1[kNumStates];
-+  CLzmaProb isRepG2[kNumStates];
-+  CLzmaProb isRep0Long[kNumStates][LZMA_NUM_PB_STATES_MAX];
-+
-+  CLzmaProb posSlotEncoder[kNumLenToPosStates][1 << kNumPosSlotBits];
-+  CLzmaProb posEncoders[kNumFullDistances - kEndPosModelIndex];
-+  CLzmaProb posAlignEncoder[1 << kNumAlignBits];
-+
-+  CLenPriceEnc lenEnc;
-+  CLenPriceEnc repLenEnc;
-+
-+  unsigned lclp;
-+
-+  Bool fastMode;
-+
-+  CRangeEnc rc;
-+
-+  Bool writeEndMark;
-+  UInt64 nowPos64;
-+  UInt32 matchPriceCount;
-+  Bool finished;
-+  Bool multiThread;
-+
-+  SRes result;
-+  UInt32 dictSize;
-+  UInt32 matchFinderCycles;
-+
-+  int needInit;
-+
-+  CSaveState saveState;
-+} CLzmaEnc;
-+
-+SRes LzmaEnc_SetProps(CLzmaEncHandle pp, const CLzmaEncProps *props2)
-+{
-+  CLzmaEnc *p = (CLzmaEnc *)pp;
-+  CLzmaEncProps props = *props2;
-+  LzmaEncProps_Normalize(&props);
-+
-+  if (props.lc > LZMA_LC_MAX || props.lp > LZMA_LP_MAX || props.pb > LZMA_PB_MAX ||
-+      props.dictSize > (1 << kDicLogSizeMaxCompress) || props.dictSize > (1 << 30))
-+    return SZ_ERROR_PARAM;
-+  p->dictSize = props.dictSize;
-+  p->matchFinderCycles = props.mc;
-+  {
-+    unsigned fb = props.fb;
-+    if (fb < 5)
-+      fb = 5;
-+    if (fb > LZMA_MATCH_LEN_MAX)
-+      fb = LZMA_MATCH_LEN_MAX;
-+    p->numFastBytes = fb;
-+  }
-+  p->lc = props.lc;
-+  p->lp = props.lp;
-+  p->pb = props.pb;
-+  p->fastMode = (props.algo == 0);
-+  p->matchFinderBase.btMode = props.btMode;
-+  {
-+    UInt32 numHashBytes = 4;
-+    if (props.btMode)
-+    {
-+      if (props.numHashBytes < 2)
-+        numHashBytes = 2;
-+      else if (props.numHashBytes < 4)
-+        numHashBytes = props.numHashBytes;
-+    }
-+    p->matchFinderBase.numHashBytes = numHashBytes;
-+  }
-+
-+  p->matchFinderBase.cutValue = props.mc;
-+
-+  p->writeEndMark = props.writeEndMark;
-+
-+  #ifndef _7ZIP_ST
-+  /*
-+  if (newMultiThread != _multiThread)
-+  {
-+    ReleaseMatchFinder();
-+    _multiThread = newMultiThread;
-+  }
-+  */
-+  p->multiThread = (props.numThreads > 1);
-+  #endif
-+
-+  return SZ_OK;
-+}
-+
-+static const int kLiteralNextStates[kNumStates] = {0, 0, 0, 0, 1, 2, 3, 4,  5,  6,   4, 5};
-+static const int kMatchNextStates[kNumStates]   = {7, 7, 7, 7, 7, 7, 7, 10, 10, 10, 10, 10};
-+static const int kRepNextStates[kNumStates]     = {8, 8, 8, 8, 8, 8, 8, 11, 11, 11, 11, 11};
-+static const int kShortRepNextStates[kNumStates]= {9, 9, 9, 9, 9, 9, 9, 11, 11, 11, 11, 11};
-+
-+#define IsCharState(s) ((s) < 7)
-+
-+#define GetLenToPosState(len) (((len) < kNumLenToPosStates + 1) ? (len) - 2 : kNumLenToPosStates - 1)
-+
-+#define kInfinityPrice (1 << 30)
-+
-+static void RangeEnc_Construct(CRangeEnc *p)
-+{
-+  p->outStream = 0;
-+  p->bufBase = 0;
-+}
-+
-+#define RangeEnc_GetProcessed(p) ((p)->processed + ((p)->buf - (p)->bufBase) + (p)->cacheSize)
-+
-+#define RC_BUF_SIZE (1 << 16)
-+static int RangeEnc_Alloc(CRangeEnc *p, ISzAlloc *alloc)
-+{
-+  if (p->bufBase == 0)
-+  {
-+    p->bufBase = (Byte *)alloc->Alloc(alloc, RC_BUF_SIZE);
-+    if (p->bufBase == 0)
-+      return 0;
-+    p->bufLim = p->bufBase + RC_BUF_SIZE;
-+  }
-+  return 1;
-+}
-+
-+static void RangeEnc_Free(CRangeEnc *p, ISzAlloc *alloc)
-+{
-+  alloc->Free(alloc, p->bufBase);
-+  p->bufBase = 0;
-+}
-+
-+static void RangeEnc_Init(CRangeEnc *p)
-+{
-+  /* Stream.Init(); */
-+  p->low = 0;
-+  p->range = 0xFFFFFFFF;
-+  p->cacheSize = 1;
-+  p->cache = 0;
-+
-+  p->buf = p->bufBase;
-+
-+  p->processed = 0;
-+  p->res = SZ_OK;
-+}
-+
-+static void RangeEnc_FlushStream(CRangeEnc *p)
-+{
-+  size_t num;
-+  if (p->res != SZ_OK)
-+    return;
-+  num = p->buf - p->bufBase;
-+  if (num != p->outStream->Write(p->outStream, p->bufBase, num))
-+    p->res = SZ_ERROR_WRITE;
-+  p->processed += num;
-+  p->buf = p->bufBase;
-+}
-+
-+static void MY_FAST_CALL RangeEnc_ShiftLow(CRangeEnc *p)
-+{
-+  if ((UInt32)p->low < (UInt32)0xFF000000 || (int)(p->low >> 32) != 0)
-+  {
-+    Byte temp = p->cache;
-+    do
-+    {
-+      Byte *buf = p->buf;
-+      *buf++ = (Byte)(temp + (Byte)(p->low >> 32));
-+      p->buf = buf;
-+      if (buf == p->bufLim)
-+        RangeEnc_FlushStream(p);
-+      temp = 0xFF;
-+    }
-+    while (--p->cacheSize != 0);
-+    p->cache = (Byte)((UInt32)p->low >> 24);
-+  }
-+  p->cacheSize++;
-+  p->low = (UInt32)p->low << 8;
-+}
-+
-+static void RangeEnc_FlushData(CRangeEnc *p)
-+{
-+  int i;
-+  for (i = 0; i < 5; i++)
-+    RangeEnc_ShiftLow(p);
-+}
-+
-+static void RangeEnc_EncodeDirectBits(CRangeEnc *p, UInt32 value, int numBits)
-+{
-+  do
-+  {
-+    p->range >>= 1;
-+    p->low += p->range & (0 - ((value >> --numBits) & 1));
-+    if (p->range < kTopValue)
-+    {
-+      p->range <<= 8;
-+      RangeEnc_ShiftLow(p);
-+    }
-+  }
-+  while (numBits != 0);
-+}
-+
-+static void RangeEnc_EncodeBit(CRangeEnc *p, CLzmaProb *prob, UInt32 symbol)
-+{
-+  UInt32 ttt = *prob;
-+  UInt32 newBound = (p->range >> kNumBitModelTotalBits) * ttt;
-+  if (symbol == 0)
-+  {
-+    p->range = newBound;
-+    ttt += (kBitModelTotal - ttt) >> kNumMoveBits;
-+  }
-+  else
-+  {
-+    p->low += newBound;
-+    p->range -= newBound;
-+    ttt -= ttt >> kNumMoveBits;
-+  }
-+  *prob = (CLzmaProb)ttt;
-+  if (p->range < kTopValue)
-+  {
-+    p->range <<= 8;
-+    RangeEnc_ShiftLow(p);
-+  }
-+}
-+
-+static void LitEnc_Encode(CRangeEnc *p, CLzmaProb *probs, UInt32 symbol)
-+{
-+  symbol |= 0x100;
-+  do
-+  {
-+    RangeEnc_EncodeBit(p, probs + (symbol >> 8), (symbol >> 7) & 1);
-+    symbol <<= 1;
-+  }
-+  while (symbol < 0x10000);
-+}
-+
-+static void LitEnc_EncodeMatched(CRangeEnc *p, CLzmaProb *probs, UInt32 symbol, UInt32 matchByte)
-+{
-+  UInt32 offs = 0x100;
-+  symbol |= 0x100;
-+  do
-+  {
-+    matchByte <<= 1;
-+    RangeEnc_EncodeBit(p, probs + (offs + (matchByte & offs) + (symbol >> 8)), (symbol >> 7) & 1);
-+    symbol <<= 1;
-+    offs &= ~(matchByte ^ symbol);
-+  }
-+  while (symbol < 0x10000);
-+}
-+
-+static void LzmaEnc_InitPriceTables(UInt32 *ProbPrices)
-+{
-+  UInt32 i;
-+  for (i = (1 << kNumMoveReducingBits) / 2; i < kBitModelTotal; i += (1 << kNumMoveReducingBits))
-+  {
-+    const int kCyclesBits = kNumBitPriceShiftBits;
-+    UInt32 w = i;
-+    UInt32 bitCount = 0;
-+    int j;
-+    for (j = 0; j < kCyclesBits; j++)
-+    {
-+      w = w * w;
-+      bitCount <<= 1;
-+      while (w >= ((UInt32)1 << 16))
-+      {
-+        w >>= 1;
-+        bitCount++;
-+      }
-+    }
-+    ProbPrices[i >> kNumMoveReducingBits] = ((kNumBitModelTotalBits << kCyclesBits) - 15 - bitCount);
-+  }
-+}
-+
-+
-+#define GET_PRICE(prob, symbol) \
-+  p->ProbPrices[((prob) ^ (((-(int)(symbol))) & (kBitModelTotal - 1))) >> kNumMoveReducingBits];
-+
-+#define GET_PRICEa(prob, symbol) \
-+  ProbPrices[((prob) ^ ((-((int)(symbol))) & (kBitModelTotal - 1))) >> kNumMoveReducingBits];
-+
-+#define GET_PRICE_0(prob) p->ProbPrices[(prob) >> kNumMoveReducingBits]
-+#define GET_PRICE_1(prob) p->ProbPrices[((prob) ^ (kBitModelTotal - 1)) >> kNumMoveReducingBits]
-+
-+#define GET_PRICE_0a(prob) ProbPrices[(prob) >> kNumMoveReducingBits]
-+#define GET_PRICE_1a(prob) ProbPrices[((prob) ^ (kBitModelTotal - 1)) >> kNumMoveReducingBits]
-+
-+static UInt32 LitEnc_GetPrice(const CLzmaProb *probs, UInt32 symbol, UInt32 *ProbPrices)
-+{
-+  UInt32 price = 0;
-+  symbol |= 0x100;
-+  do
-+  {
-+    price += GET_PRICEa(probs[symbol >> 8], (symbol >> 7) & 1);
-+    symbol <<= 1;
-+  }
-+  while (symbol < 0x10000);
-+  return price;
-+}
-+
-+static UInt32 LitEnc_GetPriceMatched(const CLzmaProb *probs, UInt32 symbol, UInt32 matchByte, UInt32 *ProbPrices)
-+{
-+  UInt32 price = 0;
-+  UInt32 offs = 0x100;
-+  symbol |= 0x100;
-+  do
-+  {
-+    matchByte <<= 1;
-+    price += GET_PRICEa(probs[offs + (matchByte & offs) + (symbol >> 8)], (symbol >> 7) & 1);
-+    symbol <<= 1;
-+    offs &= ~(matchByte ^ symbol);
-+  }
-+  while (symbol < 0x10000);
-+  return price;
-+}
-+
-+
-+static void RcTree_Encode(CRangeEnc *rc, CLzmaProb *probs, int numBitLevels, UInt32 symbol)
-+{
-+  UInt32 m = 1;
-+  int i;
-+  for (i = numBitLevels; i != 0;)
-+  {
-+    UInt32 bit;
-+    i--;
-+    bit = (symbol >> i) & 1;
-+    RangeEnc_EncodeBit(rc, probs + m, bit);
-+    m = (m << 1) | bit;
-+  }
-+}
-+
-+static void RcTree_ReverseEncode(CRangeEnc *rc, CLzmaProb *probs, int numBitLevels, UInt32 symbol)
-+{
-+  UInt32 m = 1;
-+  int i;
-+  for (i = 0; i < numBitLevels; i++)
-+  {
-+    UInt32 bit = symbol & 1;
-+    RangeEnc_EncodeBit(rc, probs + m, bit);
-+    m = (m << 1) | bit;
-+    symbol >>= 1;
-+  }
-+}
-+
-+static UInt32 RcTree_GetPrice(const CLzmaProb *probs, int numBitLevels, UInt32 symbol, UInt32 *ProbPrices)
-+{
-+  UInt32 price = 0;
-+  symbol |= (1 << numBitLevels);
-+  while (symbol != 1)
-+  {
-+    price += GET_PRICEa(probs[symbol >> 1], symbol & 1);
-+    symbol >>= 1;
-+  }
-+  return price;
-+}
-+
-+static UInt32 RcTree_ReverseGetPrice(const CLzmaProb *probs, int numBitLevels, UInt32 symbol, UInt32 *ProbPrices)
-+{
-+  UInt32 price = 0;
-+  UInt32 m = 1;
-+  int i;
-+  for (i = numBitLevels; i != 0; i--)
-+  {
-+    UInt32 bit = symbol & 1;
-+    symbol >>= 1;
-+    price += GET_PRICEa(probs[m], bit);
-+    m = (m << 1) | bit;
-+  }
-+  return price;
-+}
-+
-+
-+static void LenEnc_Init(CLenEnc *p)
-+{
-+  unsigned i;
-+  p->choice = p->choice2 = kProbInitValue;
-+  for (i = 0; i < (LZMA_NUM_PB_STATES_MAX << kLenNumLowBits); i++)
-+    p->low[i] = kProbInitValue;
-+  for (i = 0; i < (LZMA_NUM_PB_STATES_MAX << kLenNumMidBits); i++)
-+    p->mid[i] = kProbInitValue;
-+  for (i = 0; i < kLenNumHighSymbols; i++)
-+    p->high[i] = kProbInitValue;
-+}
-+
-+static void LenEnc_Encode(CLenEnc *p, CRangeEnc *rc, UInt32 symbol, UInt32 posState)
-+{
-+  if (symbol < kLenNumLowSymbols)
-+  {
-+    RangeEnc_EncodeBit(rc, &p->choice, 0);
-+    RcTree_Encode(rc, p->low + (posState << kLenNumLowBits), kLenNumLowBits, symbol);
-+  }
-+  else
-+  {
-+    RangeEnc_EncodeBit(rc, &p->choice, 1);
-+    if (symbol < kLenNumLowSymbols + kLenNumMidSymbols)
-+    {
-+      RangeEnc_EncodeBit(rc, &p->choice2, 0);
-+      RcTree_Encode(rc, p->mid + (posState << kLenNumMidBits), kLenNumMidBits, symbol - kLenNumLowSymbols);
-+    }
-+    else
-+    {
-+      RangeEnc_EncodeBit(rc, &p->choice2, 1);
-+      RcTree_Encode(rc, p->high, kLenNumHighBits, symbol - kLenNumLowSymbols - kLenNumMidSymbols);
-+    }
-+  }
-+}
-+
-+static void LenEnc_SetPrices(CLenEnc *p, UInt32 posState, UInt32 numSymbols, UInt32 *prices, UInt32 *ProbPrices)
-+{
-+  UInt32 a0 = GET_PRICE_0a(p->choice);
-+  UInt32 a1 = GET_PRICE_1a(p->choice);
-+  UInt32 b0 = a1 + GET_PRICE_0a(p->choice2);
-+  UInt32 b1 = a1 + GET_PRICE_1a(p->choice2);
-+  UInt32 i = 0;
-+  for (i = 0; i < kLenNumLowSymbols; i++)
-+  {
-+    if (i >= numSymbols)
-+      return;
-+    prices[i] = a0 + RcTree_GetPrice(p->low + (posState << kLenNumLowBits), kLenNumLowBits, i, ProbPrices);
-+  }
-+  for (; i < kLenNumLowSymbols + kLenNumMidSymbols; i++)
-+  {
-+    if (i >= numSymbols)
-+      return;
-+    prices[i] = b0 + RcTree_GetPrice(p->mid + (posState << kLenNumMidBits), kLenNumMidBits, i - kLenNumLowSymbols, ProbPrices);
-+  }
-+  for (; i < numSymbols; i++)
-+    prices[i] = b1 + RcTree_GetPrice(p->high, kLenNumHighBits, i - kLenNumLowSymbols - kLenNumMidSymbols, ProbPrices);
-+}
-+
-+static void MY_FAST_CALL LenPriceEnc_UpdateTable(CLenPriceEnc *p, UInt32 posState, UInt32 *ProbPrices)
-+{
-+  LenEnc_SetPrices(&p->p, posState, p->tableSize, p->prices[posState], ProbPrices);
-+  p->counters[posState] = p->tableSize;
-+}
-+
-+static void LenPriceEnc_UpdateTables(CLenPriceEnc *p, UInt32 numPosStates, UInt32 *ProbPrices)
-+{
-+  UInt32 posState;
-+  for (posState = 0; posState < numPosStates; posState++)
-+    LenPriceEnc_UpdateTable(p, posState, ProbPrices);
-+}
-+
-+static void LenEnc_Encode2(CLenPriceEnc *p, CRangeEnc *rc, UInt32 symbol, UInt32 posState, Bool updatePrice, UInt32 *ProbPrices)
-+{
-+  LenEnc_Encode(&p->p, rc, symbol, posState);
-+  if (updatePrice)
-+    if (--p->counters[posState] == 0)
-+      LenPriceEnc_UpdateTable(p, posState, ProbPrices);
-+}
-+
-+
-+
-+
-+static void MovePos(CLzmaEnc *p, UInt32 num)
-+{
-+  #ifdef SHOW_STAT
-+  ttt += num;
-+  printf("\n MovePos %d", num);
-+  #endif
-+  if (num != 0)
-+  {
-+    p->additionalOffset += num;
-+    p->matchFinder.Skip(p->matchFinderObj, num);
-+  }
-+}
-+
-+static UInt32 ReadMatchDistances(CLzmaEnc *p, UInt32 *numDistancePairsRes)
-+{
-+  UInt32 lenRes = 0, numPairs;
-+  p->numAvail = p->matchFinder.GetNumAvailableBytes(p->matchFinderObj);
-+  numPairs = p->matchFinder.GetMatches(p->matchFinderObj, p->matches);
-+  #ifdef SHOW_STAT
-+  printf("\n i = %d numPairs = %d    ", ttt, numPairs / 2);
-+  ttt++;
-+  {
-+    UInt32 i;
-+    for (i = 0; i < numPairs; i += 2)
-+      printf("%2d %6d   | ", p->matches[i], p->matches[i + 1]);
-+  }
-+  #endif
-+  if (numPairs > 0)
-+  {
-+    lenRes = p->matches[numPairs - 2];
-+    if (lenRes == p->numFastBytes)
-+    {
-+      const Byte *pby = p->matchFinder.GetPointerToCurrentPos(p->matchFinderObj) - 1;
-+      UInt32 distance = p->matches[numPairs - 1] + 1;
-+      UInt32 numAvail = p->numAvail;
-+      if (numAvail > LZMA_MATCH_LEN_MAX)
-+        numAvail = LZMA_MATCH_LEN_MAX;
-+      {
-+        const Byte *pby2 = pby - distance;
-+        for (; lenRes < numAvail && pby[lenRes] == pby2[lenRes]; lenRes++);
-+      }
-+    }
-+  }
-+  p->additionalOffset++;
-+  *numDistancePairsRes = numPairs;
-+  return lenRes;
-+}
-+
-+
-+#define MakeAsChar(p) (p)->backPrev = (UInt32)(-1); (p)->prev1IsChar = False;
-+#define MakeAsShortRep(p) (p)->backPrev = 0; (p)->prev1IsChar = False;
-+#define IsShortRep(p) ((p)->backPrev == 0)
-+
-+static UInt32 GetRepLen1Price(CLzmaEnc *p, UInt32 state, UInt32 posState)
-+{
-+  return
-+    GET_PRICE_0(p->isRepG0[state]) +
-+    GET_PRICE_0(p->isRep0Long[state][posState]);
-+}
-+
-+static UInt32 GetPureRepPrice(CLzmaEnc *p, UInt32 repIndex, UInt32 state, UInt32 posState)
-+{
-+  UInt32 price;
-+  if (repIndex == 0)
-+  {
-+    price = GET_PRICE_0(p->isRepG0[state]);
-+    price += GET_PRICE_1(p->isRep0Long[state][posState]);
-+  }
-+  else
-+  {
-+    price = GET_PRICE_1(p->isRepG0[state]);
-+    if (repIndex == 1)
-+      price += GET_PRICE_0(p->isRepG1[state]);
-+    else
-+    {
-+      price += GET_PRICE_1(p->isRepG1[state]);
-+      price += GET_PRICE(p->isRepG2[state], repIndex - 2);
-+    }
-+  }
-+  return price;
-+}
-+
-+static UInt32 GetRepPrice(CLzmaEnc *p, UInt32 repIndex, UInt32 len, UInt32 state, UInt32 posState)
-+{
-+  return p->repLenEnc.prices[posState][len - LZMA_MATCH_LEN_MIN] +
-+    GetPureRepPrice(p, repIndex, state, posState);
-+}
-+
-+static UInt32 Backward(CLzmaEnc *p, UInt32 *backRes, UInt32 cur)
-+{
-+  UInt32 posMem = p->opt[cur].posPrev;
-+  UInt32 backMem = p->opt[cur].backPrev;
-+  p->optimumEndIndex = cur;
-+  do
-+  {
-+    if (p->opt[cur].prev1IsChar)
-+    {
-+      MakeAsChar(&p->opt[posMem])
-+      p->opt[posMem].posPrev = posMem - 1;
-+      if (p->opt[cur].prev2)
-+      {
-+        p->opt[posMem - 1].prev1IsChar = False;
-+        p->opt[posMem - 1].posPrev = p->opt[cur].posPrev2;
-+        p->opt[posMem - 1].backPrev = p->opt[cur].backPrev2;
-+      }
-+    }
-+    {
-+      UInt32 posPrev = posMem;
-+      UInt32 backCur = backMem;
-+
-+      backMem = p->opt[posPrev].backPrev;
-+      posMem = p->opt[posPrev].posPrev;
-+
-+      p->opt[posPrev].backPrev = backCur;
-+      p->opt[posPrev].posPrev = cur;
-+      cur = posPrev;
-+    }
-+  }
-+  while (cur != 0);
-+  *backRes = p->opt[0].backPrev;
-+  p->optimumCurrentIndex  = p->opt[0].posPrev;
-+  return p->optimumCurrentIndex;
-+}
-+
-+#define LIT_PROBS(pos, prevByte) (p->litProbs + ((((pos) & p->lpMask) << p->lc) + ((prevByte) >> (8 - p->lc))) * 0x300)
-+
-+static UInt32 GetOptimum(CLzmaEnc *p, UInt32 position, UInt32 *backRes)
-+{
-+  UInt32 numAvail, mainLen, numPairs, repMaxIndex, i, posState, lenEnd, len, cur;
-+  UInt32 matchPrice, repMatchPrice, normalMatchPrice;
-+  UInt32 reps[LZMA_NUM_REPS], repLens[LZMA_NUM_REPS];
-+  UInt32 *matches;
-+  const Byte *data;
-+  Byte curByte, matchByte;
-+  if (p->optimumEndIndex != p->optimumCurrentIndex)
-+  {
-+    const COptimal *opt = &p->opt[p->optimumCurrentIndex];
-+    UInt32 lenRes = opt->posPrev - p->optimumCurrentIndex;
-+    *backRes = opt->backPrev;
-+    p->optimumCurrentIndex = opt->posPrev;
-+    return lenRes;
-+  }
-+  p->optimumCurrentIndex = p->optimumEndIndex = 0;
-+
-+  if (p->additionalOffset == 0)
-+    mainLen = ReadMatchDistances(p, &numPairs);
-+  else
-+  {
-+    mainLen = p->longestMatchLength;
-+    numPairs = p->numPairs;
-+  }
-+
-+  numAvail = p->numAvail;
-+  if (numAvail < 2)
-+  {
-+    *backRes = (UInt32)(-1);
-+    return 1;
-+  }
-+  if (numAvail > LZMA_MATCH_LEN_MAX)
-+    numAvail = LZMA_MATCH_LEN_MAX;
-+
-+  data = p->matchFinder.GetPointerToCurrentPos(p->matchFinderObj) - 1;
-+  repMaxIndex = 0;
-+  for (i = 0; i < LZMA_NUM_REPS; i++)
-+  {
-+    UInt32 lenTest;
-+    const Byte *data2;
-+    reps[i] = p->reps[i];
-+    data2 = data - (reps[i] + 1);
-+    if (data[0] != data2[0] || data[1] != data2[1])
-+    {
-+      repLens[i] = 0;
-+      continue;
-+    }
-+    for (lenTest = 2; lenTest < numAvail && data[lenTest] == data2[lenTest]; lenTest++);
-+    repLens[i] = lenTest;
-+    if (lenTest > repLens[repMaxIndex])
-+      repMaxIndex = i;
-+  }
-+  if (repLens[repMaxIndex] >= p->numFastBytes)
-+  {
-+    UInt32 lenRes;
-+    *backRes = repMaxIndex;
-+    lenRes = repLens[repMaxIndex];
-+    MovePos(p, lenRes - 1);
-+    return lenRes;
-+  }
-+
-+  matches = p->matches;
-+  if (mainLen >= p->numFastBytes)
-+  {
-+    *backRes = matches[numPairs - 1] + LZMA_NUM_REPS;
-+    MovePos(p, mainLen - 1);
-+    return mainLen;
-+  }
-+  curByte = *data;
-+  matchByte = *(data - (reps[0] + 1));
-+
-+  if (mainLen < 2 && curByte != matchByte && repLens[repMaxIndex] < 2)
-+  {
-+    *backRes = (UInt32)-1;
-+    return 1;
-+  }
-+
-+  p->opt[0].state = (CState)p->state;
-+
-+  posState = (position & p->pbMask);
-+
-+  {
-+    const CLzmaProb *probs = LIT_PROBS(position, *(data - 1));
-+    p->opt[1].price = GET_PRICE_0(p->isMatch[p->state][posState]) +
-+        (!IsCharState(p->state) ?
-+          LitEnc_GetPriceMatched(probs, curByte, matchByte, p->ProbPrices) :
-+          LitEnc_GetPrice(probs, curByte, p->ProbPrices));
-+  }
-+
-+  MakeAsChar(&p->opt[1]);
-+
-+  matchPrice = GET_PRICE_1(p->isMatch[p->state][posState]);
-+  repMatchPrice = matchPrice + GET_PRICE_1(p->isRep[p->state]);
-+
-+  if (matchByte == curByte)
-+  {
-+    UInt32 shortRepPrice = repMatchPrice + GetRepLen1Price(p, p->state, posState);
-+    if (shortRepPrice < p->opt[1].price)
-+    {
-+      p->opt[1].price = shortRepPrice;
-+      MakeAsShortRep(&p->opt[1]);
-+    }
-+  }
-+  lenEnd = ((mainLen >= repLens[repMaxIndex]) ? mainLen : repLens[repMaxIndex]);
-+
-+  if (lenEnd < 2)
-+  {
-+    *backRes = p->opt[1].backPrev;
-+    return 1;
-+  }
-+
-+  p->opt[1].posPrev = 0;
-+  for (i = 0; i < LZMA_NUM_REPS; i++)
-+    p->opt[0].backs[i] = reps[i];
-+
-+  len = lenEnd;
-+  do
-+    p->opt[len--].price = kInfinityPrice;
-+  while (len >= 2);
-+
-+  for (i = 0; i < LZMA_NUM_REPS; i++)
-+  {
-+    UInt32 repLen = repLens[i];
-+    UInt32 price;
-+    if (repLen < 2)
-+      continue;
-+    price = repMatchPrice + GetPureRepPrice(p, i, p->state, posState);
-+    do
-+    {
-+      UInt32 curAndLenPrice = price + p->repLenEnc.prices[posState][repLen - 2];
-+      COptimal *opt = &p->opt[repLen];
-+      if (curAndLenPrice < opt->price)
-+      {
-+        opt->price = curAndLenPrice;
-+        opt->posPrev = 0;
-+        opt->backPrev = i;
-+        opt->prev1IsChar = False;
-+      }
-+    }
-+    while (--repLen >= 2);
-+  }
-+
-+  normalMatchPrice = matchPrice + GET_PRICE_0(p->isRep[p->state]);
-+
-+  len = ((repLens[0] >= 2) ? repLens[0] + 1 : 2);
-+  if (len <= mainLen)
-+  {
-+    UInt32 offs = 0;
-+    while (len > matches[offs])
-+      offs += 2;
-+    for (; ; len++)
-+    {
-+      COptimal *opt;
-+      UInt32 distance = matches[offs + 1];
-+
-+      UInt32 curAndLenPrice = normalMatchPrice + p->lenEnc.prices[posState][len - LZMA_MATCH_LEN_MIN];
-+      UInt32 lenToPosState = GetLenToPosState(len);
-+      if (distance < kNumFullDistances)
-+        curAndLenPrice += p->distancesPrices[lenToPosState][distance];
-+      else
-+      {
-+        UInt32 slot;
-+        GetPosSlot2(distance, slot);
-+        curAndLenPrice += p->alignPrices[distance & kAlignMask] + p->posSlotPrices[lenToPosState][slot];
-+      }
-+      opt = &p->opt[len];
-+      if (curAndLenPrice < opt->price)
-+      {
-+        opt->price = curAndLenPrice;
-+        opt->posPrev = 0;
-+        opt->backPrev = distance + LZMA_NUM_REPS;
-+        opt->prev1IsChar = False;
-+      }
-+      if (len == matches[offs])
-+      {
-+        offs += 2;
-+        if (offs == numPairs)
-+          break;
-+      }
-+    }
-+  }
-+
-+  cur = 0;
-+
-+    #ifdef SHOW_STAT2
-+    if (position >= 0)
-+    {
-+      unsigned i;
-+      printf("\n pos = %4X", position);
-+      for (i = cur; i <= lenEnd; i++)
-+      printf("\nprice[%4X] = %d", position - cur + i, p->opt[i].price);
-+    }
-+    #endif
-+
-+  for (;;)
-+  {
-+    UInt32 numAvailFull, newLen, numPairs, posPrev, state, posState, startLen;
-+    UInt32 curPrice, curAnd1Price, matchPrice, repMatchPrice;
-+    Bool nextIsChar;
-+    Byte curByte, matchByte;
-+    const Byte *data;
-+    COptimal *curOpt;
-+    COptimal *nextOpt;
-+
-+    cur++;
-+    if (cur == lenEnd)
-+      return Backward(p, backRes, cur);
-+
-+    newLen = ReadMatchDistances(p, &numPairs);
-+    if (newLen >= p->numFastBytes)
-+    {
-+      p->numPairs = numPairs;
-+      p->longestMatchLength = newLen;
-+      return Backward(p, backRes, cur);
-+    }
-+    position++;
-+    curOpt = &p->opt[cur];
-+    posPrev = curOpt->posPrev;
-+    if (curOpt->prev1IsChar)
-+    {
-+      posPrev--;
-+      if (curOpt->prev2)
-+      {
-+        state = p->opt[curOpt->posPrev2].state;
-+        if (curOpt->backPrev2 < LZMA_NUM_REPS)
-+          state = kRepNextStates[state];
-+        else
-+          state = kMatchNextStates[state];
-+      }
-+      else
-+        state = p->opt[posPrev].state;
-+      state = kLiteralNextStates[state];
-+    }
-+    else
-+      state = p->opt[posPrev].state;
-+    if (posPrev == cur - 1)
-+    {
-+      if (IsShortRep(curOpt))
-+        state = kShortRepNextStates[state];
-+      else
-+        state = kLiteralNextStates[state];
-+    }
-+    else
-+    {
-+      UInt32 pos;
-+      const COptimal *prevOpt;
-+      if (curOpt->prev1IsChar && curOpt->prev2)
-+      {
-+        posPrev = curOpt->posPrev2;
-+        pos = curOpt->backPrev2;
-+        state = kRepNextStates[state];
-+      }
-+      else
-+      {
-+        pos = curOpt->backPrev;
-+        if (pos < LZMA_NUM_REPS)
-+          state = kRepNextStates[state];
-+        else
-+          state = kMatchNextStates[state];
-+      }
-+      prevOpt = &p->opt[posPrev];
-+      if (pos < LZMA_NUM_REPS)
-+      {
-+        UInt32 i;
-+        reps[0] = prevOpt->backs[pos];
-+        for (i = 1; i <= pos; i++)
-+          reps[i] = prevOpt->backs[i - 1];
-+        for (; i < LZMA_NUM_REPS; i++)
-+          reps[i] = prevOpt->backs[i];
-+      }
-+      else
-+      {
-+        UInt32 i;
-+        reps[0] = (pos - LZMA_NUM_REPS);
-+        for (i = 1; i < LZMA_NUM_REPS; i++)
-+          reps[i] = prevOpt->backs[i - 1];
-+      }
-+    }
-+    curOpt->state = (CState)state;
-+
-+    curOpt->backs[0] = reps[0];
-+    curOpt->backs[1] = reps[1];
-+    curOpt->backs[2] = reps[2];
-+    curOpt->backs[3] = reps[3];
-+
-+    curPrice = curOpt->price;
-+    nextIsChar = False;
-+    data = p->matchFinder.GetPointerToCurrentPos(p->matchFinderObj) - 1;
-+    curByte = *data;
-+    matchByte = *(data - (reps[0] + 1));
-+
-+    posState = (position & p->pbMask);
-+
-+    curAnd1Price = curPrice + GET_PRICE_0(p->isMatch[state][posState]);
-+    {
-+      const CLzmaProb *probs = LIT_PROBS(position, *(data - 1));
-+      curAnd1Price +=
-+        (!IsCharState(state) ?
-+          LitEnc_GetPriceMatched(probs, curByte, matchByte, p->ProbPrices) :
-+          LitEnc_GetPrice(probs, curByte, p->ProbPrices));
-+    }
-+
-+    nextOpt = &p->opt[cur + 1];
-+
-+    if (curAnd1Price < nextOpt->price)
-+    {
-+      nextOpt->price = curAnd1Price;
-+      nextOpt->posPrev = cur;
-+      MakeAsChar(nextOpt);
-+      nextIsChar = True;
-+    }
-+
-+    matchPrice = curPrice + GET_PRICE_1(p->isMatch[state][posState]);
-+    repMatchPrice = matchPrice + GET_PRICE_1(p->isRep[state]);
-+
-+    if (matchByte == curByte && !(nextOpt->posPrev < cur && nextOpt->backPrev == 0))
-+    {
-+      UInt32 shortRepPrice = repMatchPrice + GetRepLen1Price(p, state, posState);
-+      if (shortRepPrice <= nextOpt->price)
-+      {
-+        nextOpt->price = shortRepPrice;
-+        nextOpt->posPrev = cur;
-+        MakeAsShortRep(nextOpt);
-+        nextIsChar = True;
-+      }
-+    }
-+    numAvailFull = p->numAvail;
-+    {
-+      UInt32 temp = kNumOpts - 1 - cur;
-+      if (temp < numAvailFull)
-+        numAvailFull = temp;
-+    }
-+
-+    if (numAvailFull < 2)
-+      continue;
-+    numAvail = (numAvailFull <= p->numFastBytes ? numAvailFull : p->numFastBytes);
-+
-+    if (!nextIsChar && matchByte != curByte) /* speed optimization */
-+    {
-+      /* try Literal + rep0 */
-+      UInt32 temp;
-+      UInt32 lenTest2;
-+      const Byte *data2 = data - (reps[0] + 1);
-+      UInt32 limit = p->numFastBytes + 1;
-+      if (limit > numAvailFull)
-+        limit = numAvailFull;
-+
-+      for (temp = 1; temp < limit && data[temp] == data2[temp]; temp++);
-+      lenTest2 = temp - 1;
-+      if (lenTest2 >= 2)
-+      {
-+        UInt32 state2 = kLiteralNextStates[state];
-+        UInt32 posStateNext = (position + 1) & p->pbMask;
-+        UInt32 nextRepMatchPrice = curAnd1Price +
-+            GET_PRICE_1(p->isMatch[state2][posStateNext]) +
-+            GET_PRICE_1(p->isRep[state2]);
-+        /* for (; lenTest2 >= 2; lenTest2--) */
-+        {
-+          UInt32 curAndLenPrice;
-+          COptimal *opt;
-+          UInt32 offset = cur + 1 + lenTest2;
-+          while (lenEnd < offset)
-+            p->opt[++lenEnd].price = kInfinityPrice;
-+          curAndLenPrice = nextRepMatchPrice + GetRepPrice(p, 0, lenTest2, state2, posStateNext);
-+          opt = &p->opt[offset];
-+          if (curAndLenPrice < opt->price)
-+          {
-+            opt->price = curAndLenPrice;
-+            opt->posPrev = cur + 1;
-+            opt->backPrev = 0;
-+            opt->prev1IsChar = True;
-+            opt->prev2 = False;
-+          }
-+        }
-+      }
-+    }
-+
-+    startLen = 2; /* speed optimization */
-+    {
-+    UInt32 repIndex;
-+    for (repIndex = 0; repIndex < LZMA_NUM_REPS; repIndex++)
-+    {
-+      UInt32 lenTest;
-+      UInt32 lenTestTemp;
-+      UInt32 price;
-+      const Byte *data2 = data - (reps[repIndex] + 1);
-+      if (data[0] != data2[0] || data[1] != data2[1])
-+        continue;
-+      for (lenTest = 2; lenTest < numAvail && data[lenTest] == data2[lenTest]; lenTest++);
-+      while (lenEnd < cur + lenTest)
-+        p->opt[++lenEnd].price = kInfinityPrice;
-+      lenTestTemp = lenTest;
-+      price = repMatchPrice + GetPureRepPrice(p, repIndex, state, posState);
-+      do
-+      {
-+        UInt32 curAndLenPrice = price + p->repLenEnc.prices[posState][lenTest - 2];
-+        COptimal *opt = &p->opt[cur + lenTest];
-+        if (curAndLenPrice < opt->price)
-+        {
-+          opt->price = curAndLenPrice;
-+          opt->posPrev = cur;
-+          opt->backPrev = repIndex;
-+          opt->prev1IsChar = False;
-+        }
-+      }
-+      while (--lenTest >= 2);
-+      lenTest = lenTestTemp;
-+
-+      if (repIndex == 0)
-+        startLen = lenTest + 1;
-+
-+      /* if (_maxMode) */
-+        {
-+          UInt32 lenTest2 = lenTest + 1;
-+          UInt32 limit = lenTest2 + p->numFastBytes;
-+          UInt32 nextRepMatchPrice;
-+          if (limit > numAvailFull)
-+            limit = numAvailFull;
-+          for (; lenTest2 < limit && data[lenTest2] == data2[lenTest2]; lenTest2++);
-+          lenTest2 -= lenTest + 1;
-+          if (lenTest2 >= 2)
-+          {
-+            UInt32 state2 = kRepNextStates[state];
-+            UInt32 posStateNext = (position + lenTest) & p->pbMask;
-+            UInt32 curAndLenCharPrice =
-+                price + p->repLenEnc.prices[posState][lenTest - 2] +
-+                GET_PRICE_0(p->isMatch[state2][posStateNext]) +
-+                LitEnc_GetPriceMatched(LIT_PROBS(position + lenTest, data[lenTest - 1]),
-+                    data[lenTest], data2[lenTest], p->ProbPrices);
-+            state2 = kLiteralNextStates[state2];
-+            posStateNext = (position + lenTest + 1) & p->pbMask;
-+            nextRepMatchPrice = curAndLenCharPrice +
-+                GET_PRICE_1(p->isMatch[state2][posStateNext]) +
-+                GET_PRICE_1(p->isRep[state2]);
-+
-+            /* for (; lenTest2 >= 2; lenTest2--) */
-+            {
-+              UInt32 curAndLenPrice;
-+              COptimal *opt;
-+              UInt32 offset = cur + lenTest + 1 + lenTest2;
-+              while (lenEnd < offset)
-+                p->opt[++lenEnd].price = kInfinityPrice;
-+              curAndLenPrice = nextRepMatchPrice + GetRepPrice(p, 0, lenTest2, state2, posStateNext);
-+              opt = &p->opt[offset];
-+              if (curAndLenPrice < opt->price)
-+              {
-+                opt->price = curAndLenPrice;
-+                opt->posPrev = cur + lenTest + 1;
-+                opt->backPrev = 0;
-+                opt->prev1IsChar = True;
-+                opt->prev2 = True;
-+                opt->posPrev2 = cur;
-+                opt->backPrev2 = repIndex;
-+              }
-+            }
-+          }
-+        }
-+    }
-+    }
-+    /* for (UInt32 lenTest = 2; lenTest <= newLen; lenTest++) */
-+    if (newLen > numAvail)
-+    {
-+      newLen = numAvail;
-+      for (numPairs = 0; newLen > matches[numPairs]; numPairs += 2);
-+      matches[numPairs] = newLen;
-+      numPairs += 2;
-+    }
-+    if (newLen >= startLen)
-+    {
-+      UInt32 normalMatchPrice = matchPrice + GET_PRICE_0(p->isRep[state]);
-+      UInt32 offs, curBack, posSlot;
-+      UInt32 lenTest;
-+      while (lenEnd < cur + newLen)
-+        p->opt[++lenEnd].price = kInfinityPrice;
-+
-+      offs = 0;
-+      while (startLen > matches[offs])
-+        offs += 2;
-+      curBack = matches[offs + 1];
-+      GetPosSlot2(curBack, posSlot);
-+      for (lenTest = /*2*/ startLen; ; lenTest++)
-+      {
-+        UInt32 curAndLenPrice = normalMatchPrice + p->lenEnc.prices[posState][lenTest - LZMA_MATCH_LEN_MIN];
-+        UInt32 lenToPosState = GetLenToPosState(lenTest);
-+        COptimal *opt;
-+        if (curBack < kNumFullDistances)
-+          curAndLenPrice += p->distancesPrices[lenToPosState][curBack];
-+        else
-+          curAndLenPrice += p->posSlotPrices[lenToPosState][posSlot] + p->alignPrices[curBack & kAlignMask];
-+
-+        opt = &p->opt[cur + lenTest];
-+        if (curAndLenPrice < opt->price)
-+        {
-+          opt->price = curAndLenPrice;
-+          opt->posPrev = cur;
-+          opt->backPrev = curBack + LZMA_NUM_REPS;
-+          opt->prev1IsChar = False;
-+        }
-+
-+        if (/*_maxMode && */lenTest == matches[offs])
-+        {
-+          /* Try Match + Literal + Rep0 */
-+          const Byte *data2 = data - (curBack + 1);
-+          UInt32 lenTest2 = lenTest + 1;
-+          UInt32 limit = lenTest2 + p->numFastBytes;
-+          UInt32 nextRepMatchPrice;
-+          if (limit > numAvailFull)
-+            limit = numAvailFull;
-+          for (; lenTest2 < limit && data[lenTest2] == data2[lenTest2]; lenTest2++);
-+          lenTest2 -= lenTest + 1;
-+          if (lenTest2 >= 2)
-+          {
-+            UInt32 state2 = kMatchNextStates[state];
-+            UInt32 posStateNext = (position + lenTest) & p->pbMask;
-+            UInt32 curAndLenCharPrice = curAndLenPrice +
-+                GET_PRICE_0(p->isMatch[state2][posStateNext]) +
-+                LitEnc_GetPriceMatched(LIT_PROBS(position + lenTest, data[lenTest - 1]),
-+                    data[lenTest], data2[lenTest], p->ProbPrices);
-+            state2 = kLiteralNextStates[state2];
-+            posStateNext = (posStateNext + 1) & p->pbMask;
-+            nextRepMatchPrice = curAndLenCharPrice +
-+                GET_PRICE_1(p->isMatch[state2][posStateNext]) +
-+                GET_PRICE_1(p->isRep[state2]);
-+
-+            /* for (; lenTest2 >= 2; lenTest2--) */
-+            {
-+              UInt32 offset = cur + lenTest + 1 + lenTest2;
-+              UInt32 curAndLenPrice;
-+              COptimal *opt;
-+              while (lenEnd < offset)
-+                p->opt[++lenEnd].price = kInfinityPrice;
-+              curAndLenPrice = nextRepMatchPrice + GetRepPrice(p, 0, lenTest2, state2, posStateNext);
-+              opt = &p->opt[offset];
-+              if (curAndLenPrice < opt->price)
-+              {
-+                opt->price = curAndLenPrice;
-+                opt->posPrev = cur + lenTest + 1;
-+                opt->backPrev = 0;
-+                opt->prev1IsChar = True;
-+                opt->prev2 = True;
-+                opt->posPrev2 = cur;
-+                opt->backPrev2 = curBack + LZMA_NUM_REPS;
-+              }
-+            }
-+          }
-+          offs += 2;
-+          if (offs == numPairs)
-+            break;
-+          curBack = matches[offs + 1];
-+          if (curBack >= kNumFullDistances)
-+            GetPosSlot2(curBack, posSlot);
-+        }
-+      }
-+    }
-+  }
-+}
-+
-+#define ChangePair(smallDist, bigDist) (((bigDist) >> 7) > (smallDist))
-+
-+static UInt32 GetOptimumFast(CLzmaEnc *p, UInt32 *backRes)
-+{
-+  UInt32 numAvail, mainLen, mainDist, numPairs, repIndex, repLen, i;
-+  const Byte *data;
-+  const UInt32 *matches;
-+
-+  if (p->additionalOffset == 0)
-+    mainLen = ReadMatchDistances(p, &numPairs);
-+  else
-+  {
-+    mainLen = p->longestMatchLength;
-+    numPairs = p->numPairs;
-+  }
-+
-+  numAvail = p->numAvail;
-+  *backRes = (UInt32)-1;
-+  if (numAvail < 2)
-+    return 1;
-+  if (numAvail > LZMA_MATCH_LEN_MAX)
-+    numAvail = LZMA_MATCH_LEN_MAX;
-+  data = p->matchFinder.GetPointerToCurrentPos(p->matchFinderObj) - 1;
-+
-+  repLen = repIndex = 0;
-+  for (i = 0; i < LZMA_NUM_REPS; i++)
-+  {
-+    UInt32 len;
-+    const Byte *data2 = data - (p->reps[i] + 1);
-+    if (data[0] != data2[0] || data[1] != data2[1])
-+      continue;
-+    for (len = 2; len < numAvail && data[len] == data2[len]; len++);
-+    if (len >= p->numFastBytes)
-+    {
-+      *backRes = i;
-+      MovePos(p, len - 1);
-+      return len;
-+    }
-+    if (len > repLen)
-+    {
-+      repIndex = i;
-+      repLen = len;
-+    }
-+  }
-+
-+  matches = p->matches;
-+  if (mainLen >= p->numFastBytes)
-+  {
-+    *backRes = matches[numPairs - 1] + LZMA_NUM_REPS;
-+    MovePos(p, mainLen - 1);
-+    return mainLen;
-+  }
-+
-+  mainDist = 0; /* for GCC */
-+  if (mainLen >= 2)
-+  {
-+    mainDist = matches[numPairs - 1];
-+    while (numPairs > 2 && mainLen == matches[numPairs - 4] + 1)
-+    {
-+      if (!ChangePair(matches[numPairs - 3], mainDist))
-+        break;
-+      numPairs -= 2;
-+      mainLen = matches[numPairs - 2];
-+      mainDist = matches[numPairs - 1];
-+    }
-+    if (mainLen == 2 && mainDist >= 0x80)
-+      mainLen = 1;
-+  }
-+
-+  if (repLen >= 2 && (
-+        (repLen + 1 >= mainLen) ||
-+        (repLen + 2 >= mainLen && mainDist >= (1 << 9)) ||
-+        (repLen + 3 >= mainLen && mainDist >= (1 << 15))))
-+  {
-+    *backRes = repIndex;
-+    MovePos(p, repLen - 1);
-+    return repLen;
-+  }
-+
-+  if (mainLen < 2 || numAvail <= 2)
-+    return 1;
-+
-+  p->longestMatchLength = ReadMatchDistances(p, &p->numPairs);
-+  if (p->longestMatchLength >= 2)
-+  {
-+    UInt32 newDistance = matches[p->numPairs - 1];
-+    if ((p->longestMatchLength >= mainLen && newDistance < mainDist) ||
-+        (p->longestMatchLength == mainLen + 1 && !ChangePair(mainDist, newDistance)) ||
-+        (p->longestMatchLength > mainLen + 1) ||
-+        (p->longestMatchLength + 1 >= mainLen && mainLen >= 3 && ChangePair(newDistance, mainDist)))
-+      return 1;
-+  }
-+
-+  data = p->matchFinder.GetPointerToCurrentPos(p->matchFinderObj) - 1;
-+  for (i = 0; i < LZMA_NUM_REPS; i++)
-+  {
-+    UInt32 len, limit;
-+    const Byte *data2 = data - (p->reps[i] + 1);
-+    if (data[0] != data2[0] || data[1] != data2[1])
-+      continue;
-+    limit = mainLen - 1;
-+    for (len = 2; len < limit && data[len] == data2[len]; len++);
-+    if (len >= limit)
-+      return 1;
-+  }
-+  *backRes = mainDist + LZMA_NUM_REPS;
-+  MovePos(p, mainLen - 2);
-+  return mainLen;
-+}
-+
-+static void WriteEndMarker(CLzmaEnc *p, UInt32 posState)
-+{
-+  UInt32 len;
-+  RangeEnc_EncodeBit(&p->rc, &p->isMatch[p->state][posState], 1);
-+  RangeEnc_EncodeBit(&p->rc, &p->isRep[p->state], 0);
-+  p->state = kMatchNextStates[p->state];
-+  len = LZMA_MATCH_LEN_MIN;
-+  LenEnc_Encode2(&p->lenEnc, &p->rc, len - LZMA_MATCH_LEN_MIN, posState, !p->fastMode, p->ProbPrices);
-+  RcTree_Encode(&p->rc, p->posSlotEncoder[GetLenToPosState(len)], kNumPosSlotBits, (1 << kNumPosSlotBits) - 1);
-+  RangeEnc_EncodeDirectBits(&p->rc, (((UInt32)1 << 30) - 1) >> kNumAlignBits, 30 - kNumAlignBits);
-+  RcTree_ReverseEncode(&p->rc, p->posAlignEncoder, kNumAlignBits, kAlignMask);
-+}
-+
-+static SRes CheckErrors(CLzmaEnc *p)
-+{
-+  if (p->result != SZ_OK)
-+    return p->result;
-+  if (p->rc.res != SZ_OK)
-+    p->result = SZ_ERROR_WRITE;
-+  if (p->matchFinderBase.result != SZ_OK)
-+    p->result = SZ_ERROR_READ;
-+  if (p->result != SZ_OK)
-+    p->finished = True;
-+  return p->result;
-+}
-+
-+static SRes Flush(CLzmaEnc *p, UInt32 nowPos)
-+{
-+  /* ReleaseMFStream(); */
-+  p->finished = True;
-+  if (p->writeEndMark)
-+    WriteEndMarker(p, nowPos & p->pbMask);
-+  RangeEnc_FlushData(&p->rc);
-+  RangeEnc_FlushStream(&p->rc);
-+  return CheckErrors(p);
-+}
-+
-+static void FillAlignPrices(CLzmaEnc *p)
-+{
-+  UInt32 i;
-+  for (i = 0; i < kAlignTableSize; i++)
-+    p->alignPrices[i] = RcTree_ReverseGetPrice(p->posAlignEncoder, kNumAlignBits, i, p->ProbPrices);
-+  p->alignPriceCount = 0;
-+}
-+
-+static void FillDistancesPrices(CLzmaEnc *p)
-+{
-+  UInt32 tempPrices[kNumFullDistances];
-+  UInt32 i, lenToPosState;
-+  for (i = kStartPosModelIndex; i < kNumFullDistances; i++)
-+  {
-+    UInt32 posSlot = GetPosSlot1(i);
-+    UInt32 footerBits = ((posSlot >> 1) - 1);
-+    UInt32 base = ((2 | (posSlot & 1)) << footerBits);
-+    tempPrices[i] = RcTree_ReverseGetPrice(p->posEncoders + base - posSlot - 1, footerBits, i - base, p->ProbPrices);
-+  }
-+
-+  for (lenToPosState = 0; lenToPosState < kNumLenToPosStates; lenToPosState++)
-+  {
-+    UInt32 posSlot;
-+    const CLzmaProb *encoder = p->posSlotEncoder[lenToPosState];
-+    UInt32 *posSlotPrices = p->posSlotPrices[lenToPosState];
-+    for (posSlot = 0; posSlot < p->distTableSize; posSlot++)
-+      posSlotPrices[posSlot] = RcTree_GetPrice(encoder, kNumPosSlotBits, posSlot, p->ProbPrices);
-+    for (posSlot = kEndPosModelIndex; posSlot < p->distTableSize; posSlot++)
-+      posSlotPrices[posSlot] += ((((posSlot >> 1) - 1) - kNumAlignBits) << kNumBitPriceShiftBits);
-+
-+    {
-+      UInt32 *distancesPrices = p->distancesPrices[lenToPosState];
-+      UInt32 i;
-+      for (i = 0; i < kStartPosModelIndex; i++)
-+        distancesPrices[i] = posSlotPrices[i];
-+      for (; i < kNumFullDistances; i++)
-+        distancesPrices[i] = posSlotPrices[GetPosSlot1(i)] + tempPrices[i];
-+    }
-+  }
-+  p->matchPriceCount = 0;
-+}
-+
-+static void LzmaEnc_Construct(CLzmaEnc *p)
-+{
-+  RangeEnc_Construct(&p->rc);
-+  MatchFinder_Construct(&p->matchFinderBase);
-+  #ifndef _7ZIP_ST
-+  MatchFinderMt_Construct(&p->matchFinderMt);
-+  p->matchFinderMt.MatchFinder = &p->matchFinderBase;
-+  #endif
-+
-+  {
-+    CLzmaEncProps props;
-+    LzmaEncProps_Init(&props);
-+    LzmaEnc_SetProps(p, &props);
-+  }
-+
-+  #ifndef LZMA_LOG_BSR
-+  LzmaEnc_FastPosInit(p->g_FastPos);
-+  #endif
-+
-+  LzmaEnc_InitPriceTables(p->ProbPrices);
-+  p->litProbs = 0;
-+  p->saveState.litProbs = 0;
-+}
-+
-+CLzmaEncHandle LzmaEnc_Create(ISzAlloc *alloc)
-+{
-+  void *p;
-+  p = alloc->Alloc(alloc, sizeof(CLzmaEnc));
-+  if (p != 0)
-+    LzmaEnc_Construct((CLzmaEnc *)p);
-+  return p;
-+}
-+
-+static void LzmaEnc_FreeLits(CLzmaEnc *p, ISzAlloc *alloc)
-+{
-+  alloc->Free(alloc, p->litProbs);
-+  alloc->Free(alloc, p->saveState.litProbs);
-+  p->litProbs = 0;
-+  p->saveState.litProbs = 0;
-+}
-+
-+static void LzmaEnc_Destruct(CLzmaEnc *p, ISzAlloc *alloc, ISzAlloc *allocBig)
-+{
-+  #ifndef _7ZIP_ST
-+  MatchFinderMt_Destruct(&p->matchFinderMt, allocBig);
-+  #endif
-+  MatchFinder_Free(&p->matchFinderBase, allocBig);
-+  LzmaEnc_FreeLits(p, alloc);
-+  RangeEnc_Free(&p->rc, alloc);
-+}
-+
-+void LzmaEnc_Destroy(CLzmaEncHandle p, ISzAlloc *alloc, ISzAlloc *allocBig)
-+{
-+  LzmaEnc_Destruct((CLzmaEnc *)p, alloc, allocBig);
-+  alloc->Free(alloc, p);
-+}
-+
-+static SRes LzmaEnc_CodeOneBlock(CLzmaEnc *p, Bool useLimits, UInt32 maxPackSize, UInt32 maxUnpackSize)
-+{
-+  UInt32 nowPos32, startPos32;
-+  if (p->needInit)
-+  {
-+    p->matchFinder.Init(p->matchFinderObj);
-+    p->needInit = 0;
-+  }
-+
-+  if (p->finished)
-+    return p->result;
-+  RINOK(CheckErrors(p));
-+
-+  nowPos32 = (UInt32)p->nowPos64;
-+  startPos32 = nowPos32;
-+
-+  if (p->nowPos64 == 0)
-+  {
-+    UInt32 numPairs;
-+    Byte curByte;
-+    if (p->matchFinder.GetNumAvailableBytes(p->matchFinderObj) == 0)
-+      return Flush(p, nowPos32);
-+    ReadMatchDistances(p, &numPairs);
-+    RangeEnc_EncodeBit(&p->rc, &p->isMatch[p->state][0], 0);
-+    p->state = kLiteralNextStates[p->state];
-+    curByte = p->matchFinder.GetIndexByte(p->matchFinderObj, 0 - p->additionalOffset);
-+    LitEnc_Encode(&p->rc, p->litProbs, curByte);
-+    p->additionalOffset--;
-+    nowPos32++;
-+  }
-+
-+  if (p->matchFinder.GetNumAvailableBytes(p->matchFinderObj) != 0)
-+  for (;;)
-+  {
-+    UInt32 pos, len, posState;
-+
-+    if (p->fastMode)
-+      len = GetOptimumFast(p, &pos);
-+    else
-+      len = GetOptimum(p, nowPos32, &pos);
-+
-+    #ifdef SHOW_STAT2
-+    printf("\n pos = %4X,   len = %d   pos = %d", nowPos32, len, pos);
-+    #endif
-+
-+    posState = nowPos32 & p->pbMask;
-+    if (len == 1 && pos == (UInt32)-1)
-+    {
-+      Byte curByte;
-+      CLzmaProb *probs;
-+      const Byte *data;
-+
-+      RangeEnc_EncodeBit(&p->rc, &p->isMatch[p->state][posState], 0);
-+      data = p->matchFinder.GetPointerToCurrentPos(p->matchFinderObj) - p->additionalOffset;
-+      curByte = *data;
-+      probs = LIT_PROBS(nowPos32, *(data - 1));
-+      if (IsCharState(p->state))
-+        LitEnc_Encode(&p->rc, probs, curByte);
-+      else
-+        LitEnc_EncodeMatched(&p->rc, probs, curByte, *(data - p->reps[0] - 1));
-+      p->state = kLiteralNextStates[p->state];
-+    }
-+    else
-+    {
-+      RangeEnc_EncodeBit(&p->rc, &p->isMatch[p->state][posState], 1);
-+      if (pos < LZMA_NUM_REPS)
-+      {
-+        RangeEnc_EncodeBit(&p->rc, &p->isRep[p->state], 1);
-+        if (pos == 0)
-+        {
-+          RangeEnc_EncodeBit(&p->rc, &p->isRepG0[p->state], 0);
-+          RangeEnc_EncodeBit(&p->rc, &p->isRep0Long[p->state][posState], ((len == 1) ? 0 : 1));
-+        }
-+        else
-+        {
-+          UInt32 distance = p->reps[pos];
-+          RangeEnc_EncodeBit(&p->rc, &p->isRepG0[p->state], 1);
-+          if (pos == 1)
-+            RangeEnc_EncodeBit(&p->rc, &p->isRepG1[p->state], 0);
-+          else
-+          {
-+            RangeEnc_EncodeBit(&p->rc, &p->isRepG1[p->state], 1);
-+            RangeEnc_EncodeBit(&p->rc, &p->isRepG2[p->state], pos - 2);
-+            if (pos == 3)
-+              p->reps[3] = p->reps[2];
-+            p->reps[2] = p->reps[1];
-+          }
-+          p->reps[1] = p->reps[0];
-+          p->reps[0] = distance;
-+        }
-+        if (len == 1)
-+          p->state = kShortRepNextStates[p->state];
-+        else
-+        {
-+          LenEnc_Encode2(&p->repLenEnc, &p->rc, len - LZMA_MATCH_LEN_MIN, posState, !p->fastMode, p->ProbPrices);
-+          p->state = kRepNextStates[p->state];
-+        }
-+      }
-+      else
-+      {
-+        UInt32 posSlot;
-+        RangeEnc_EncodeBit(&p->rc, &p->isRep[p->state], 0);
-+        p->state = kMatchNextStates[p->state];
-+        LenEnc_Encode2(&p->lenEnc, &p->rc, len - LZMA_MATCH_LEN_MIN, posState, !p->fastMode, p->ProbPrices);
-+        pos -= LZMA_NUM_REPS;
-+        GetPosSlot(pos, posSlot);
-+        RcTree_Encode(&p->rc, p->posSlotEncoder[GetLenToPosState(len)], kNumPosSlotBits, posSlot);
-+
-+        if (posSlot >= kStartPosModelIndex)
-+        {
-+          UInt32 footerBits = ((posSlot >> 1) - 1);
-+          UInt32 base = ((2 | (posSlot & 1)) << footerBits);
-+          UInt32 posReduced = pos - base;
-+
-+          if (posSlot < kEndPosModelIndex)
-+            RcTree_ReverseEncode(&p->rc, p->posEncoders + base - posSlot - 1, footerBits, posReduced);
-+          else
-+          {
-+            RangeEnc_EncodeDirectBits(&p->rc, posReduced >> kNumAlignBits, footerBits - kNumAlignBits);
-+            RcTree_ReverseEncode(&p->rc, p->posAlignEncoder, kNumAlignBits, posReduced & kAlignMask);
-+            p->alignPriceCount++;
-+          }
-+        }
-+        p->reps[3] = p->reps[2];
-+        p->reps[2] = p->reps[1];
-+        p->reps[1] = p->reps[0];
-+        p->reps[0] = pos;
-+        p->matchPriceCount++;
-+      }
-+    }
-+    p->additionalOffset -= len;
-+    nowPos32 += len;
-+    if (p->additionalOffset == 0)
-+    {
-+      UInt32 processed;
-+      if (!p->fastMode)
-+      {
-+        if (p->matchPriceCount >= (1 << 7))
-+          FillDistancesPrices(p);
-+        if (p->alignPriceCount >= kAlignTableSize)
-+          FillAlignPrices(p);
-+      }
-+      if (p->matchFinder.GetNumAvailableBytes(p->matchFinderObj) == 0)
-+        break;
-+      processed = nowPos32 - startPos32;
-+      if (useLimits)
-+      {
-+        if (processed + kNumOpts + 300 >= maxUnpackSize ||
-+            RangeEnc_GetProcessed(&p->rc) + kNumOpts * 2 >= maxPackSize)
-+          break;
-+      }
-+      else if (processed >= (1 << 15))
-+      {
-+        p->nowPos64 += nowPos32 - startPos32;
-+        return CheckErrors(p);
-+      }
-+    }
-+  }
-+  p->nowPos64 += nowPos32 - startPos32;
-+  return Flush(p, nowPos32);
-+}
-+
-+#define kBigHashDicLimit ((UInt32)1 << 24)
-+
-+static SRes LzmaEnc_Alloc(CLzmaEnc *p, UInt32 keepWindowSize, ISzAlloc *alloc, ISzAlloc *allocBig)
-+{
-+  UInt32 beforeSize = kNumOpts;
-+  Bool btMode;
-+  if (!RangeEnc_Alloc(&p->rc, alloc))
-+    return SZ_ERROR_MEM;
-+  btMode = (p->matchFinderBase.btMode != 0);
-+  #ifndef _7ZIP_ST
-+  p->mtMode = (p->multiThread && !p->fastMode && btMode);
-+  #endif
-+
-+  {
-+    unsigned lclp = p->lc + p->lp;
-+    if (p->litProbs == 0 || p->saveState.litProbs == 0 || p->lclp != lclp)
-+    {
-+      LzmaEnc_FreeLits(p, alloc);
-+      p->litProbs = (CLzmaProb *)alloc->Alloc(alloc, (0x300 << lclp) * sizeof(CLzmaProb));
-+      p->saveState.litProbs = (CLzmaProb *)alloc->Alloc(alloc, (0x300 << lclp) * sizeof(CLzmaProb));
-+      if (p->litProbs == 0 || p->saveState.litProbs == 0)
-+      {
-+        LzmaEnc_FreeLits(p, alloc);
-+        return SZ_ERROR_MEM;
-+      }
-+      p->lclp = lclp;
-+    }
-+  }
-+
-+  p->matchFinderBase.bigHash = (p->dictSize > kBigHashDicLimit);
-+
-+  if (beforeSize + p->dictSize < keepWindowSize)
-+    beforeSize = keepWindowSize - p->dictSize;
-+
-+  #ifndef _7ZIP_ST
-+  if (p->mtMode)
-+  {
-+    RINOK(MatchFinderMt_Create(&p->matchFinderMt, p->dictSize, beforeSize, p->numFastBytes, LZMA_MATCH_LEN_MAX, allocBig));
-+    p->matchFinderObj = &p->matchFinderMt;
-+    MatchFinderMt_CreateVTable(&p->matchFinderMt, &p->matchFinder);
-+  }
-+  else
-+  #endif
-+  {
-+    if (!MatchFinder_Create(&p->matchFinderBase, p->dictSize, beforeSize, p->numFastBytes, LZMA_MATCH_LEN_MAX, allocBig))
-+      return SZ_ERROR_MEM;
-+    p->matchFinderObj = &p->matchFinderBase;
-+    MatchFinder_CreateVTable(&p->matchFinderBase, &p->matchFinder);
-+  }
-+  return SZ_OK;
-+}
-+
-+static void LzmaEnc_Init(CLzmaEnc *p)
-+{
-+  UInt32 i;
-+  p->state = 0;
-+  for (i = 0 ; i < LZMA_NUM_REPS; i++)
-+    p->reps[i] = 0;
-+
-+  RangeEnc_Init(&p->rc);
-+
-+
-+  for (i = 0; i < kNumStates; i++)
-+  {
-+    UInt32 j;
-+    for (j = 0; j < LZMA_NUM_PB_STATES_MAX; j++)
-+    {
-+      p->isMatch[i][j] = kProbInitValue;
-+      p->isRep0Long[i][j] = kProbInitValue;
-+    }
-+    p->isRep[i] = kProbInitValue;
-+    p->isRepG0[i] = kProbInitValue;
-+    p->isRepG1[i] = kProbInitValue;
-+    p->isRepG2[i] = kProbInitValue;
-+  }
-+
-+  {
-+    UInt32 num = 0x300 << (p->lp + p->lc);
-+    for (i = 0; i < num; i++)
-+      p->litProbs[i] = kProbInitValue;
-+  }
-+
-+  {
-+    for (i = 0; i < kNumLenToPosStates; i++)
-+    {
-+      CLzmaProb *probs = p->posSlotEncoder[i];
-+      UInt32 j;
-+      for (j = 0; j < (1 << kNumPosSlotBits); j++)
-+        probs[j] = kProbInitValue;
-+    }
-+  }
-+  {
-+    for (i = 0; i < kNumFullDistances - kEndPosModelIndex; i++)
-+      p->posEncoders[i] = kProbInitValue;
-+  }
-+
-+  LenEnc_Init(&p->lenEnc.p);
-+  LenEnc_Init(&p->repLenEnc.p);
-+
-+  for (i = 0; i < (1 << kNumAlignBits); i++)
-+    p->posAlignEncoder[i] = kProbInitValue;
-+
-+  p->optimumEndIndex = 0;
-+  p->optimumCurrentIndex = 0;
-+  p->additionalOffset = 0;
-+
-+  p->pbMask = (1 << p->pb) - 1;
-+  p->lpMask = (1 << p->lp) - 1;
-+}
-+
-+static void LzmaEnc_InitPrices(CLzmaEnc *p)
-+{
-+  if (!p->fastMode)
-+  {
-+    FillDistancesPrices(p);
-+    FillAlignPrices(p);
-+  }
-+
-+  p->lenEnc.tableSize =
-+  p->repLenEnc.tableSize =
-+      p->numFastBytes + 1 - LZMA_MATCH_LEN_MIN;
-+  LenPriceEnc_UpdateTables(&p->lenEnc, 1 << p->pb, p->ProbPrices);
-+  LenPriceEnc_UpdateTables(&p->repLenEnc, 1 << p->pb, p->ProbPrices);
-+}
-+
-+static SRes LzmaEnc_AllocAndInit(CLzmaEnc *p, UInt32 keepWindowSize, ISzAlloc *alloc, ISzAlloc *allocBig)
-+{
-+  UInt32 i;
-+  for (i = 0; i < (UInt32)kDicLogSizeMaxCompress; i++)
-+    if (p->dictSize <= ((UInt32)1 << i))
-+      break;
-+  p->distTableSize = i * 2;
-+
-+  p->finished = False;
-+  p->result = SZ_OK;
-+  RINOK(LzmaEnc_Alloc(p, keepWindowSize, alloc, allocBig));
-+  LzmaEnc_Init(p);
-+  LzmaEnc_InitPrices(p);
-+  p->nowPos64 = 0;
-+  return SZ_OK;
-+}
-+
-+static void LzmaEnc_SetInputBuf(CLzmaEnc *p, const Byte *src, SizeT srcLen)
-+{
-+  p->matchFinderBase.directInput = 1;
-+  p->matchFinderBase.bufferBase = (Byte *)src;
-+  p->matchFinderBase.directInputRem = srcLen;
-+}
-+
-+static SRes LzmaEnc_MemPrepare(CLzmaEncHandle pp, const Byte *src, SizeT srcLen,
-+    UInt32 keepWindowSize, ISzAlloc *alloc, ISzAlloc *allocBig)
-+{
-+  CLzmaEnc *p = (CLzmaEnc *)pp;
-+  LzmaEnc_SetInputBuf(p, src, srcLen);
-+  p->needInit = 1;
-+
-+  return LzmaEnc_AllocAndInit(p, keepWindowSize, alloc, allocBig);
-+}
-+
-+static void LzmaEnc_Finish(CLzmaEncHandle pp)
-+{
-+  #ifndef _7ZIP_ST
-+  CLzmaEnc *p = (CLzmaEnc *)pp;
-+  if (p->mtMode)
-+    MatchFinderMt_ReleaseStream(&p->matchFinderMt);
-+  #else
-+  pp = pp;
-+  #endif
-+}
-+
-+typedef struct
-+{
-+  ISeqOutStream funcTable;
-+  Byte *data;
-+  SizeT rem;
-+  Bool overflow;
-+} CSeqOutStreamBuf;
-+
-+static size_t MyWrite(void *pp, const void *data, size_t size)
-+{
-+  CSeqOutStreamBuf *p = (CSeqOutStreamBuf *)pp;
-+  if (p->rem < size)
-+  {
-+    size = p->rem;
-+    p->overflow = True;
-+  }
-+  memcpy(p->data, data, size);
-+  p->rem -= size;
-+  p->data += size;
-+  return size;
-+}
-+
-+static SRes LzmaEnc_Encode2(CLzmaEnc *p, ICompressProgress *progress)
-+{
-+  SRes res = SZ_OK;
-+
-+  #ifndef _7ZIP_ST
-+  Byte allocaDummy[0x300];
-+  int i = 0;
-+  for (i = 0; i < 16; i++)
-+    allocaDummy[i] = (Byte)i;
-+  #endif
-+
-+  for (;;)
-+  {
-+    res = LzmaEnc_CodeOneBlock(p, False, 0, 0);
-+    if (res != SZ_OK || p->finished != 0)
-+      break;
-+    if (progress != 0)
-+    {
-+      res = progress->Progress(progress, p->nowPos64, RangeEnc_GetProcessed(&p->rc));
-+      if (res != SZ_OK)
-+      {
-+        res = SZ_ERROR_PROGRESS;
-+        break;
-+      }
-+    }
-+  }
-+  LzmaEnc_Finish(p);
-+  return res;
-+}
-+
-+SRes LzmaEnc_WriteProperties(CLzmaEncHandle pp, Byte *props, SizeT *size)
-+{
-+  CLzmaEnc *p = (CLzmaEnc *)pp;
-+  int i;
-+  UInt32 dictSize = p->dictSize;
-+  if (*size < LZMA_PROPS_SIZE)
-+    return SZ_ERROR_PARAM;
-+  *size = LZMA_PROPS_SIZE;
-+  props[0] = (Byte)((p->pb * 5 + p->lp) * 9 + p->lc);
-+
-+  for (i = 11; i <= 30; i++)
-+  {
-+    if (dictSize <= ((UInt32)2 << i))
-+    {
-+      dictSize = (2 << i);
-+      break;
-+    }
-+    if (dictSize <= ((UInt32)3 << i))
-+    {
-+      dictSize = (3 << i);
-+      break;
-+    }
-+  }
-+
-+  for (i = 0; i < 4; i++)
-+    props[1 + i] = (Byte)(dictSize >> (8 * i));
-+  return SZ_OK;
-+}
-+
-+SRes LzmaEnc_MemEncode(CLzmaEncHandle pp, Byte *dest, SizeT *destLen, const Byte *src, SizeT srcLen,
-+    int writeEndMark, ICompressProgress *progress, ISzAlloc *alloc, ISzAlloc *allocBig)
-+{
-+  SRes res;
-+  CLzmaEnc *p = (CLzmaEnc *)pp;
-+
-+  CSeqOutStreamBuf outStream;
-+
-+  LzmaEnc_SetInputBuf(p, src, srcLen);
-+
-+  outStream.funcTable.Write = MyWrite;
-+  outStream.data = dest;
-+  outStream.rem = *destLen;
-+  outStream.overflow = False;
-+
-+  p->writeEndMark = writeEndMark;
-+
-+  p->rc.outStream = &outStream.funcTable;
-+  res = LzmaEnc_MemPrepare(pp, src, srcLen, 0, alloc, allocBig);
-+  if (res == SZ_OK)
-+    res = LzmaEnc_Encode2(p, progress);
-+
-+  *destLen -= outStream.rem;
-+  if (outStream.overflow)
-+    return SZ_ERROR_OUTPUT_EOF;
-+  return res;
-+}
---- /dev/null
-+++ b/lib/lzma/Makefile
-@@ -0,0 +1,7 @@
-+lzma_compress-objs := LzFind.o LzmaEnc.o
-+lzma_decompress-objs := LzmaDec.o
-+
-+obj-$(CONFIG_LZMA_COMPRESS) += lzma_compress.o
-+obj-$(CONFIG_LZMA_DECOMPRESS) += lzma_decompress.o
-+
-+EXTRA_CFLAGS += -Iinclude/linux -Iinclude/linux/lzma -include types.h
diff --git a/target/linux/generic/pending-5.15/532-jffs2_eofdetect.patch b/target/linux/generic/pending-5.15/532-jffs2_eofdetect.patch
deleted file mode 100644 (file)
index 744fbd0..0000000
+++ /dev/null
@@ -1,65 +0,0 @@
-From: Felix Fietkau <[email protected]>
-Subject: fs: jffs2: EOF marker
-
-Signed-off-by: Felix Fietkau <[email protected]>
----
- fs/jffs2/build.c | 10 ++++++++++
- fs/jffs2/scan.c  | 21 +++++++++++++++++++--
- 2 files changed, 29 insertions(+), 2 deletions(-)
-
---- a/fs/jffs2/build.c
-+++ b/fs/jffs2/build.c
-@@ -117,6 +117,16 @@ static int jffs2_build_filesystem(struct
-       dbg_fsbuild("scanned flash completely\n");
-       jffs2_dbg_dump_block_lists_nolock(c);
-+      if (c->flags & (1 << 7)) {
-+              printk("%s(): unlocking the mtd device... ", __func__);
-+              mtd_unlock(c->mtd, 0, c->mtd->size);
-+              printk("done.\n");
-+
-+              printk("%s(): erasing all blocks after the end marker... ", __func__);
-+              jffs2_erase_pending_blocks(c, -1);
-+              printk("done.\n");
-+      }
-+
-       dbg_fsbuild("pass 1 starting\n");
-       c->flags |= JFFS2_SB_FLAG_BUILDING;
-       /* Now scan the directory tree, increasing nlink according to every dirent found. */
---- a/fs/jffs2/scan.c
-+++ b/fs/jffs2/scan.c
-@@ -148,8 +148,14 @@ int jffs2_scan_medium(struct jffs2_sb_in
-               /* reset summary info for next eraseblock scan */
-               jffs2_sum_reset_collected(s);
--              ret = jffs2_scan_eraseblock(c, jeb, buf_size?flashbuf:(flashbuf+jeb->offset),
--                                              buf_size, s);
-+              if (c->flags & (1 << 7)) {
-+                      if (mtd_block_isbad(c->mtd, jeb->offset))
-+                              ret = BLK_STATE_BADBLOCK;
-+                      else
-+                              ret = BLK_STATE_ALLFF;
-+              } else
-+                      ret = jffs2_scan_eraseblock(c, jeb, buf_size?flashbuf:(flashbuf+jeb->offset),
-+                                                      buf_size, s);
-               if (ret < 0)
-                       goto out;
-@@ -567,6 +573,17 @@ full_scan:
-                       return err;
-       }
-+      if ((buf[0] == 0xde) &&
-+              (buf[1] == 0xad) &&
-+              (buf[2] == 0xc0) &&
-+              (buf[3] == 0xde)) {
-+              /* end of filesystem. erase everything after this point */
-+              printk("%s(): End of filesystem marker found at 0x%x\n", __func__, jeb->offset);
-+              c->flags |= (1 << 7);
-+
-+              return BLK_STATE_ALLFF;
-+      }
-+
-       /* We temporarily use 'ofs' as a pointer into the buffer/jeb */
-       ofs = 0;
-       max_ofs = EMPTY_SCAN_SIZE(c->sector_size);
diff --git a/target/linux/generic/pending-5.15/600-netfilter_conntrack_flush.patch b/target/linux/generic/pending-5.15/600-netfilter_conntrack_flush.patch
deleted file mode 100644 (file)
index a88e3d7..0000000
+++ /dev/null
@@ -1,88 +0,0 @@
-From: Felix Fietkau <[email protected]>
-Subject: netfilter: add support for flushing conntrack via /proc
-
-lede-commit 8193bbe59a74d34d6a26d4a8cb857b1952905314
-Signed-off-by: Felix Fietkau <[email protected]>
----
- net/netfilter/nf_conntrack_standalone.c | 59 ++++++++++++++++++++++++++++++++-
- 1 file changed, 58 insertions(+), 1 deletion(-)
-
---- a/net/netfilter/nf_conntrack_standalone.c
-+++ b/net/netfilter/nf_conntrack_standalone.c
-@@ -9,6 +9,7 @@
- #include <linux/percpu.h>
- #include <linux/netdevice.h>
- #include <linux/security.h>
-+#include <linux/inet.h>
- #include <net/net_namespace.h>
- #ifdef CONFIG_SYSCTL
- #include <linux/sysctl.h>
-@@ -462,6 +463,56 @@ static int ct_cpu_seq_show(struct seq_fi
-       return 0;
- }
-+struct kill_request {
-+      u16 family;
-+      union nf_inet_addr addr;
-+};
-+
-+static int kill_matching(struct nf_conn *i, void *data)
-+{
-+      struct kill_request *kr = data;
-+      struct nf_conntrack_tuple *t1 = &i->tuplehash[IP_CT_DIR_ORIGINAL].tuple;
-+      struct nf_conntrack_tuple *t2 = &i->tuplehash[IP_CT_DIR_REPLY].tuple;
-+
-+      if (!kr->family)
-+              return 1;
-+
-+      if (t1->src.l3num != kr->family)
-+              return 0;
-+
-+      return (nf_inet_addr_cmp(&kr->addr, &t1->src.u3) ||
-+              nf_inet_addr_cmp(&kr->addr, &t1->dst.u3) ||
-+              nf_inet_addr_cmp(&kr->addr, &t2->src.u3) ||
-+              nf_inet_addr_cmp(&kr->addr, &t2->dst.u3));
-+}
-+
-+static int ct_file_write(struct file *file, char *buf, size_t count)
-+{
-+      struct seq_file *seq = file->private_data;
-+      struct net *net = seq_file_net(seq);
-+      struct kill_request kr = { };
-+
-+      if (count == 0)
-+              return 0;
-+
-+      if (count >= INET6_ADDRSTRLEN)
-+              count = INET6_ADDRSTRLEN - 1;
-+
-+      if (strnchr(buf, count, ':')) {
-+              kr.family = AF_INET6;
-+              if (!in6_pton(buf, count, (void *)&kr.addr, '\n', NULL))
-+                      return -EINVAL;
-+      } else if (strnchr(buf, count, '.')) {
-+              kr.family = AF_INET;
-+              if (!in4_pton(buf, count, (void *)&kr.addr, '\n', NULL))
-+                      return -EINVAL;
-+      }
-+
-+      nf_ct_iterate_cleanup_net(net, kill_matching, &kr, 0, 0);
-+
-+      return 0;
-+}
-+
- static const struct seq_operations ct_cpu_seq_ops = {
-       .start  = ct_cpu_seq_start,
-       .next   = ct_cpu_seq_next,
-@@ -475,8 +526,9 @@ static int nf_conntrack_standalone_init_
-       kuid_t root_uid;
-       kgid_t root_gid;
--      pde = proc_create_net("nf_conntrack", 0440, net->proc_net, &ct_seq_ops,
--                      sizeof(struct ct_iter_state));
-+      pde = proc_create_net_data_write("nf_conntrack", 0440, net->proc_net,
-+                                       &ct_seq_ops, &ct_file_write,
-+                                       sizeof(struct ct_iter_state), NULL);
-       if (!pde)
-               goto out_nf_conntrack;
diff --git a/target/linux/generic/pending-5.15/610-netfilter_match_bypass_default_checks.patch b/target/linux/generic/pending-5.15/610-netfilter_match_bypass_default_checks.patch
deleted file mode 100644 (file)
index 8b1e70b..0000000
+++ /dev/null
@@ -1,110 +0,0 @@
-From: Felix Fietkau <[email protected]>
-Subject: kernel: add a new version of my netfilter speedup patches for linux 2.6.39 and 3.0
-
-Signed-off-by: Felix Fietkau <[email protected]>
----
- include/uapi/linux/netfilter_ipv4/ip_tables.h |  1 +
- net/ipv4/netfilter/ip_tables.c                | 37 +++++++++++++++++++++++++++
- 2 files changed, 38 insertions(+)
-
---- a/include/uapi/linux/netfilter_ipv4/ip_tables.h
-+++ b/include/uapi/linux/netfilter_ipv4/ip_tables.h
-@@ -89,6 +89,7 @@ struct ipt_ip {
- #define IPT_F_FRAG            0x01    /* Set if rule is a fragment rule */
- #define IPT_F_GOTO            0x02    /* Set if jump is a goto */
- #define IPT_F_MASK            0x03    /* All possible flag bits mask. */
-+#define IPT_F_NO_DEF_MATCH    0x80    /* Internal: no default match rules present */
- /* Values for "inv" field in struct ipt_ip. */
- #define IPT_INV_VIA_IN                0x01    /* Invert the sense of IN IFACE. */
---- a/net/ipv4/netfilter/ip_tables.c
-+++ b/net/ipv4/netfilter/ip_tables.c
-@@ -50,6 +50,9 @@ ip_packet_match(const struct iphdr *ip,
- {
-       unsigned long ret;
-+      if (ipinfo->flags & IPT_F_NO_DEF_MATCH)
-+              return true;
-+
-       if (NF_INVF(ipinfo, IPT_INV_SRCIP,
-                   (ip->saddr & ipinfo->smsk.s_addr) != ipinfo->src.s_addr) ||
-           NF_INVF(ipinfo, IPT_INV_DSTIP,
-@@ -80,6 +83,29 @@ ip_packet_match(const struct iphdr *ip,
-       return true;
- }
-+static void
-+ip_checkdefault(struct ipt_ip *ip)
-+{
-+      static const char iface_mask[IFNAMSIZ] = {};
-+
-+      if (ip->invflags || ip->flags & IPT_F_FRAG)
-+              return;
-+
-+      if (memcmp(ip->iniface_mask, iface_mask, IFNAMSIZ) != 0)
-+              return;
-+
-+      if (memcmp(ip->outiface_mask, iface_mask, IFNAMSIZ) != 0)
-+              return;
-+
-+      if (ip->smsk.s_addr || ip->dmsk.s_addr)
-+              return;
-+
-+      if (ip->proto)
-+              return;
-+
-+      ip->flags |= IPT_F_NO_DEF_MATCH;
-+}
-+
- static bool
- ip_checkentry(const struct ipt_ip *ip)
- {
-@@ -524,6 +550,8 @@ find_check_entry(struct ipt_entry *e, st
-       struct xt_mtchk_param mtpar;
-       struct xt_entry_match *ematch;
-+      ip_checkdefault(&e->ip);
-+
-       if (!xt_percpu_counter_alloc(alloc_state, &e->counters))
-               return -ENOMEM;
-@@ -818,6 +846,7 @@ copy_entries_to_user(unsigned int total_
-       const struct xt_table_info *private = table->private;
-       int ret = 0;
-       const void *loc_cpu_entry;
-+      u8 flags;
-       counters = alloc_counters(table);
-       if (IS_ERR(counters))
-@@ -845,6 +874,14 @@ copy_entries_to_user(unsigned int total_
-                       goto free_counters;
-               }
-+              flags = e->ip.flags & IPT_F_MASK;
-+              if (copy_to_user(userptr + off
-+                               + offsetof(struct ipt_entry, ip.flags),
-+                               &flags, sizeof(flags)) != 0) {
-+                      ret = -EFAULT;
-+                      goto free_counters;
-+              }
-+
-               for (i = sizeof(struct ipt_entry);
-                    i < e->target_offset;
-                    i += m->u.match_size) {
-@@ -1226,12 +1263,15 @@ compat_copy_entry_to_user(struct ipt_ent
-       compat_uint_t origsize;
-       const struct xt_entry_match *ematch;
-       int ret = 0;
-+      u8 flags = e->ip.flags & IPT_F_MASK;
-       origsize = *size;
-       ce = *dstptr;
-       if (copy_to_user(ce, e, sizeof(struct ipt_entry)) != 0 ||
-           copy_to_user(&ce->counters, &counters[i],
--          sizeof(counters[i])) != 0)
-+          sizeof(counters[i])) != 0 ||
-+          copy_to_user(&ce->ip.flags, &flags,
-+          sizeof(flags)) != 0)
-               return -EFAULT;
-       *dstptr += sizeof(struct compat_ipt_entry);
diff --git a/target/linux/generic/pending-5.15/611-netfilter_match_bypass_default_table.patch b/target/linux/generic/pending-5.15/611-netfilter_match_bypass_default_table.patch
deleted file mode 100644 (file)
index baf738a..0000000
+++ /dev/null
@@ -1,106 +0,0 @@
-From: Felix Fietkau <[email protected]>
-Subject: netfilter: match bypass default table
-
-Signed-off-by: Felix Fietkau <[email protected]>
----
- net/ipv4/netfilter/ip_tables.c | 79 +++++++++++++++++++++++++++++++-----------
- 1 file changed, 58 insertions(+), 21 deletions(-)
-
---- a/net/ipv4/netfilter/ip_tables.c
-+++ b/net/ipv4/netfilter/ip_tables.c
-@@ -246,6 +246,33 @@ struct ipt_entry *ipt_next_entry(const s
-       return (void *)entry + entry->next_offset;
- }
-+static bool
-+ipt_handle_default_rule(struct ipt_entry *e, unsigned int *verdict)
-+{
-+      struct xt_entry_target *t;
-+      struct xt_standard_target *st;
-+
-+      if (e->target_offset != sizeof(struct ipt_entry))
-+              return false;
-+
-+      if (!(e->ip.flags & IPT_F_NO_DEF_MATCH))
-+              return false;
-+
-+      t = ipt_get_target(e);
-+      if (t->u.kernel.target->target)
-+              return false;
-+
-+      st = (struct xt_standard_target *) t;
-+      if (st->verdict == XT_RETURN)
-+              return false;
-+
-+      if (st->verdict >= 0)
-+              return false;
-+
-+      *verdict = (unsigned)(-st->verdict) - 1;
-+      return true;
-+}
-+
- /* Returns one of the generic firewall policies, like NF_ACCEPT. */
- unsigned int
- ipt_do_table(struct sk_buff *skb,
-@@ -266,27 +293,28 @@ ipt_do_table(struct sk_buff *skb,
-       unsigned int addend;
-       /* Initialization */
-+      WARN_ON(!(table->valid_hooks & (1 << hook)));
-+      local_bh_disable();
-+      private = READ_ONCE(table->private); /* Address dependency. */
-+      cpu        = smp_processor_id();
-+      table_base = private->entries;
-+
-+      e = get_entry(table_base, private->hook_entry[hook]);
-+      if (ipt_handle_default_rule(e, &verdict)) {
-+              struct xt_counters *counter;
-+
-+              counter = xt_get_this_cpu_counter(&e->counters);
-+              ADD_COUNTER(*counter, skb->len, 1);
-+              local_bh_enable();
-+              return verdict;
-+      }
-+
-       stackidx = 0;
-       ip = ip_hdr(skb);
-       indev = state->in ? state->in->name : nulldevname;
-       outdev = state->out ? state->out->name : nulldevname;
--      /* We handle fragments by dealing with the first fragment as
--       * if it was a normal packet.  All other fragments are treated
--       * normally, except that they will NEVER match rules that ask
--       * things we don't know, ie. tcp syn flag or ports).  If the
--       * rule is also a fragment-specific rule, non-fragments won't
--       * match it. */
--      acpar.fragoff = ntohs(ip->frag_off) & IP_OFFSET;
--      acpar.thoff   = ip_hdrlen(skb);
--      acpar.hotdrop = false;
--      acpar.state   = state;
--      WARN_ON(!(table->valid_hooks & (1 << hook)));
--      local_bh_disable();
-       addend = xt_write_recseq_begin();
--      private = READ_ONCE(table->private); /* Address dependency. */
--      cpu        = smp_processor_id();
--      table_base = private->entries;
-       jumpstack  = (struct ipt_entry **)private->jumpstack[cpu];
-       /* Switch to alternate jumpstack if we're being invoked via TEE.
-@@ -299,7 +327,16 @@ ipt_do_table(struct sk_buff *skb,
-       if (static_key_false(&xt_tee_enabled))
-               jumpstack += private->stacksize * __this_cpu_read(nf_skb_duplicated);
--      e = get_entry(table_base, private->hook_entry[hook]);
-+      /* We handle fragments by dealing with the first fragment as
-+       * if it was a normal packet.  All other fragments are treated
-+       * normally, except that they will NEVER match rules that ask
-+       * things we don't know, ie. tcp syn flag or ports).  If the
-+       * rule is also a fragment-specific rule, non-fragments won't
-+       * match it. */
-+      acpar.fragoff = ntohs(ip->frag_off) & IP_OFFSET;
-+      acpar.thoff   = ip_hdrlen(skb);
-+      acpar.hotdrop = false;
-+      acpar.state   = state;
-       do {
-               const struct xt_entry_target *t;
diff --git a/target/linux/generic/pending-5.15/612-netfilter_match_reduce_memory_access.patch b/target/linux/generic/pending-5.15/612-netfilter_match_reduce_memory_access.patch
deleted file mode 100644 (file)
index 79da677..0000000
+++ /dev/null
@@ -1,22 +0,0 @@
-From: Felix Fietkau <[email protected]>
-Subject: netfilter: reduce match memory access
-
-Signed-off-by: Felix Fietkau <[email protected]>
----
- net/ipv4/netfilter/ip_tables.c | 4 ++--
- 1 file changed, 2 insertions(+), 2 deletions(-)
-
---- a/net/ipv4/netfilter/ip_tables.c
-+++ b/net/ipv4/netfilter/ip_tables.c
-@@ -53,9 +53,9 @@ ip_packet_match(const struct iphdr *ip,
-       if (ipinfo->flags & IPT_F_NO_DEF_MATCH)
-               return true;
--      if (NF_INVF(ipinfo, IPT_INV_SRCIP,
-+      if (NF_INVF(ipinfo, IPT_INV_SRCIP, ipinfo->smsk.s_addr &&
-                   (ip->saddr & ipinfo->smsk.s_addr) != ipinfo->src.s_addr) ||
--          NF_INVF(ipinfo, IPT_INV_DSTIP,
-+          NF_INVF(ipinfo, IPT_INV_DSTIP, ipinfo->dmsk.s_addr &&
-                   (ip->daddr & ipinfo->dmsk.s_addr) != ipinfo->dst.s_addr))
-               return false;
diff --git a/target/linux/generic/pending-5.15/620-net_sched-codel-do-not-defer-queue-length-update.patch b/target/linux/generic/pending-5.15/620-net_sched-codel-do-not-defer-queue-length-update.patch
deleted file mode 100644 (file)
index 4b4825a..0000000
+++ /dev/null
@@ -1,86 +0,0 @@
-From: Konstantin Khlebnikov <[email protected]>
-Date: Mon, 21 Aug 2017 11:14:14 +0300
-Subject: [PATCH] net_sched/codel: do not defer queue length update
-
-When codel wants to drop last packet in ->dequeue() it cannot call
-qdisc_tree_reduce_backlog() right away - it will notify parent qdisc
-about zero qlen and HTB/HFSC will deactivate class. The same class will
-be deactivated second time by caller of ->dequeue(). Currently codel and
-fq_codel defer update. This triggers warning in HFSC when it's qlen != 0
-but there is no active classes.
-
-This patch update parent queue length immediately: just temporary increase
-qlen around qdisc_tree_reduce_backlog() to prevent first class deactivation
-if we have skb to return.
-
-This might open another problem in HFSC - now operation peek could fail and
-deactivate parent class.
-
-Signed-off-by: Konstantin Khlebnikov <[email protected]>
-Link: https://bugzilla.kernel.org/show_bug.cgi?id=109581
----
-
---- a/net/sched/sch_codel.c
-+++ b/net/sched/sch_codel.c
-@@ -95,11 +95,17 @@ static struct sk_buff *codel_qdisc_deque
-                           &q->stats, qdisc_pkt_len, codel_get_enqueue_time,
-                           drop_func, dequeue_func);
--      /* We cant call qdisc_tree_reduce_backlog() if our qlen is 0,
--       * or HTB crashes. Defer it for next round.
-+      /* If our qlen is 0 qdisc_tree_reduce_backlog() will deactivate
-+       * parent class, dequeue in parent qdisc will do the same if we
-+       * return skb. Temporary increment qlen if we have skb.
-        */
--      if (q->stats.drop_count && sch->q.qlen) {
--              qdisc_tree_reduce_backlog(sch, q->stats.drop_count, q->stats.drop_len);
-+      if (q->stats.drop_count) {
-+              if (skb)
-+                      sch->q.qlen++;
-+              qdisc_tree_reduce_backlog(sch, q->stats.drop_count,
-+                                        q->stats.drop_len);
-+              if (skb)
-+                      sch->q.qlen--;
-               q->stats.drop_count = 0;
-               q->stats.drop_len = 0;
-       }
---- a/net/sched/sch_fq_codel.c
-+++ b/net/sched/sch_fq_codel.c
-@@ -304,6 +304,21 @@ begin:
-                           &flow->cvars, &q->cstats, qdisc_pkt_len,
-                           codel_get_enqueue_time, drop_func, dequeue_func);
-+      /* If our qlen is 0 qdisc_tree_reduce_backlog() will deactivate
-+       * parent class, dequeue in parent qdisc will do the same if we
-+       * return skb. Temporary increment qlen if we have skb.
-+       */
-+      if (q->cstats.drop_count) {
-+              if (skb)
-+                      sch->q.qlen++;
-+              qdisc_tree_reduce_backlog(sch, q->cstats.drop_count,
-+                                        q->cstats.drop_len);
-+              if (skb)
-+                      sch->q.qlen--;
-+              q->cstats.drop_count = 0;
-+              q->cstats.drop_len = 0;
-+      }
-+
-       if (!skb) {
-               /* force a pass through old_flows to prevent starvation */
-               if ((head == &q->new_flows) && !list_empty(&q->old_flows))
-@@ -314,15 +329,6 @@ begin:
-       }
-       qdisc_bstats_update(sch, skb);
-       flow->deficit -= qdisc_pkt_len(skb);
--      /* We cant call qdisc_tree_reduce_backlog() if our qlen is 0,
--       * or HTB crashes. Defer it for next round.
--       */
--      if (q->cstats.drop_count && sch->q.qlen) {
--              qdisc_tree_reduce_backlog(sch, q->cstats.drop_count,
--                                        q->cstats.drop_len);
--              q->cstats.drop_count = 0;
--              q->cstats.drop_len = 0;
--      }
-       return skb;
- }
diff --git a/target/linux/generic/pending-5.15/630-packet_socket_type.patch b/target/linux/generic/pending-5.15/630-packet_socket_type.patch
deleted file mode 100644 (file)
index 486ba9d..0000000
+++ /dev/null
@@ -1,138 +0,0 @@
-From: Felix Fietkau <[email protected]>
-Subject: net: add an optimization for dealing with raw sockets
-
-lede-commit: 4898039703d7315f0f3431c860123338ec3be0f6
-Signed-off-by: Felix Fietkau <[email protected]>
----
- include/uapi/linux/if_packet.h |  3 +++
- net/packet/af_packet.c         | 34 +++++++++++++++++++++++++++-------
- net/packet/internal.h          |  1 +
- 3 files changed, 31 insertions(+), 7 deletions(-)
-
---- a/include/uapi/linux/if_packet.h
-+++ b/include/uapi/linux/if_packet.h
-@@ -33,6 +33,8 @@ struct sockaddr_ll {
- #define PACKET_KERNEL         7               /* To kernel space      */
- /* Unused, PACKET_FASTROUTE and PACKET_LOOPBACK are invisible to user space */
- #define PACKET_FASTROUTE      6               /* Fastrouted frame     */
-+#define PACKET_MASK_ANY               0xffffffff      /* mask for packet type bits */
-+
- /* Packet socket options */
-@@ -59,6 +61,7 @@ struct sockaddr_ll {
- #define PACKET_ROLLOVER_STATS         21
- #define PACKET_FANOUT_DATA            22
- #define PACKET_IGNORE_OUTGOING                23
-+#define PACKET_RECV_TYPE              24
- #define PACKET_FANOUT_HASH            0
- #define PACKET_FANOUT_LB              1
---- a/net/packet/af_packet.c
-+++ b/net/packet/af_packet.c
-@@ -1830,6 +1830,7 @@ static int packet_rcv_spkt(struct sk_buf
- {
-       struct sock *sk;
-       struct sockaddr_pkt *spkt;
-+      struct packet_sock *po;
-       /*
-        *      When we registered the protocol we saved the socket in the data
-@@ -1837,6 +1838,7 @@ static int packet_rcv_spkt(struct sk_buf
-        */
-       sk = pt->af_packet_priv;
-+      po = pkt_sk(sk);
-       /*
-        *      Yank back the headers [hope the device set this
-@@ -1849,7 +1851,7 @@ static int packet_rcv_spkt(struct sk_buf
-        *      so that this procedure is noop.
-        */
--      if (skb->pkt_type == PACKET_LOOPBACK)
-+      if (!(po->pkt_type & (1 << skb->pkt_type)))
-               goto out;
-       if (!net_eq(dev_net(dev), sock_net(sk)))
-@@ -2095,12 +2097,12 @@ static int packet_rcv(struct sk_buff *sk
-       unsigned int snaplen, res;
-       bool is_drop_n_account = false;
--      if (skb->pkt_type == PACKET_LOOPBACK)
--              goto drop;
--
-       sk = pt->af_packet_priv;
-       po = pkt_sk(sk);
-+      if (!(po->pkt_type & (1 << skb->pkt_type)))
-+              goto drop;
-+
-       if (!net_eq(dev_net(dev), sock_net(sk)))
-               goto drop;
-@@ -2226,12 +2228,12 @@ static int tpacket_rcv(struct sk_buff *s
-       BUILD_BUG_ON(TPACKET_ALIGN(sizeof(*h.h2)) != 32);
-       BUILD_BUG_ON(TPACKET_ALIGN(sizeof(*h.h3)) != 48);
--      if (skb->pkt_type == PACKET_LOOPBACK)
--              goto drop;
--
-       sk = pt->af_packet_priv;
-       po = pkt_sk(sk);
-+      if (!(po->pkt_type & (1 << skb->pkt_type)))
-+              goto drop;
-+
-       if (!net_eq(dev_net(dev), sock_net(sk)))
-               goto drop;
-@@ -3345,6 +3347,7 @@ static int packet_create(struct net *net
-       mutex_init(&po->pg_vec_lock);
-       po->rollover = NULL;
-       po->prot_hook.func = packet_rcv;
-+      po->pkt_type = PACKET_MASK_ANY & ~(1 << PACKET_LOOPBACK);
-       if (sock->type == SOCK_PACKET)
-               po->prot_hook.func = packet_rcv_spkt;
-@@ -3982,6 +3985,16 @@ packet_setsockopt(struct socket *sock, i
-               WRITE_ONCE(po->xmit, val ? packet_direct_xmit : dev_queue_xmit);
-               return 0;
-       }
-+      case PACKET_RECV_TYPE:
-+      {
-+              unsigned int val;
-+              if (optlen != sizeof(val))
-+                      return -EINVAL;
-+              if (copy_from_sockptr(&val, optval, sizeof(val)))
-+                      return -EFAULT;
-+              po->pkt_type = val & ~BIT(PACKET_LOOPBACK);
-+              return 0;
-+      }
-       default:
-               return -ENOPROTOOPT;
-       }
-@@ -4038,6 +4051,13 @@ static int packet_getsockopt(struct sock
-       case PACKET_VNET_HDR:
-               val = po->has_vnet_hdr;
-               break;
-+      case PACKET_RECV_TYPE:
-+              if (len > sizeof(unsigned int))
-+                      len = sizeof(unsigned int);
-+              val = po->pkt_type;
-+
-+              data = &val;
-+              break;
-       case PACKET_VERSION:
-               val = po->tp_version;
-               break;
---- a/net/packet/internal.h
-+++ b/net/packet/internal.h
-@@ -136,6 +136,7 @@ struct packet_sock {
-       int                     (*xmit)(struct sk_buff *skb);
-       struct packet_type      prot_hook ____cacheline_aligned_in_smp;
-       atomic_t                tp_drops ____cacheline_aligned_in_smp;
-+      unsigned int            pkt_type;
- };
- static inline struct packet_sock *pkt_sk(struct sock *sk)
diff --git a/target/linux/generic/pending-5.15/655-increase_skb_pad.patch b/target/linux/generic/pending-5.15/655-increase_skb_pad.patch
deleted file mode 100644 (file)
index e9075f4..0000000
+++ /dev/null
@@ -1,20 +0,0 @@
-From: Felix Fietkau <[email protected]>
-Subject: kernel: add a few patches for avoiding unnecessary skb reallocations - significantly improves ethernet<->wireless performance
-
-lede-commit: 6f89cffc9add6939d44a6b54cf9a5e77849aa7fd
-Signed-off-by: Felix Fietkau <[email protected]>
----
- include/linux/skbuff.h | 2 +-
- 1 file changed, 1 insertion(+), 1 deletion(-)
-
---- a/include/linux/skbuff.h
-+++ b/include/linux/skbuff.h
-@@ -2836,7 +2836,7 @@ static inline int pskb_network_may_pull(
-  * NET_IP_ALIGN(2) + ethernet_header(14) + IP_header(20/40) + ports(8)
-  */
- #ifndef NET_SKB_PAD
--#define NET_SKB_PAD   max(32, L1_CACHE_BYTES)
-+#define NET_SKB_PAD   max(64, L1_CACHE_BYTES)
- #endif
- int ___pskb_trim(struct sk_buff *skb, unsigned int len);
diff --git a/target/linux/generic/pending-5.15/666-Add-support-for-MAP-E-FMRs-mesh-mode.patch b/target/linux/generic/pending-5.15/666-Add-support-for-MAP-E-FMRs-mesh-mode.patch
deleted file mode 100644 (file)
index 3931278..0000000
+++ /dev/null
@@ -1,511 +0,0 @@
-From: Steven Barth <[email protected]>
-Subject: Add support for MAP-E FMRs (mesh mode)
-
-MAP-E FMRs (draft-ietf-softwire-map-10) are rules for IPv4-communication
-between MAP CEs (mesh mode) without the need to forward such data to a
-border relay. This is similar to how 6rd works but for IPv4 over IPv6.
-
-Signed-off-by: Steven Barth <[email protected]>
----
- include/net/ip6_tunnel.h       |  13 ++
- include/uapi/linux/if_tunnel.h |  13 ++
- net/ipv6/ip6_tunnel.c          | 276 +++++++++++++++++++++++++++++++++++++++--
- 3 files changed, 291 insertions(+), 11 deletions(-)
-
---- a/include/net/ip6_tunnel.h
-+++ b/include/net/ip6_tunnel.h
-@@ -18,6 +18,18 @@
- /* determine capability on a per-packet basis */
- #define IP6_TNL_F_CAP_PER_PACKET 0x40000
-+/* IPv6 tunnel FMR */
-+struct __ip6_tnl_fmr {
-+      struct __ip6_tnl_fmr *next; /* next fmr in list */
-+      struct in6_addr ip6_prefix;
-+      struct in_addr ip4_prefix;
-+
-+      __u8 ip6_prefix_len;
-+      __u8 ip4_prefix_len;
-+      __u8 ea_len;
-+      __u8 offset;
-+};
-+
- struct __ip6_tnl_parm {
-       char name[IFNAMSIZ];    /* name of tunnel device */
-       int link;               /* ifindex of underlying L2 interface */
-@@ -29,6 +41,7 @@ struct __ip6_tnl_parm {
-       __u32 flags;            /* tunnel flags */
-       struct in6_addr laddr;  /* local tunnel end-point address */
-       struct in6_addr raddr;  /* remote tunnel end-point address */
-+      struct __ip6_tnl_fmr *fmrs;     /* FMRs */
-       __be16                  i_flags;
-       __be16                  o_flags;
---- a/include/uapi/linux/if_tunnel.h
-+++ b/include/uapi/linux/if_tunnel.h
-@@ -77,10 +77,23 @@ enum {
-       IFLA_IPTUN_ENCAP_DPORT,
-       IFLA_IPTUN_COLLECT_METADATA,
-       IFLA_IPTUN_FWMARK,
-+      IFLA_IPTUN_FMRS,
-       __IFLA_IPTUN_MAX,
- };
- #define IFLA_IPTUN_MAX        (__IFLA_IPTUN_MAX - 1)
-+enum {
-+      IFLA_IPTUN_FMR_UNSPEC,
-+      IFLA_IPTUN_FMR_IP6_PREFIX,
-+      IFLA_IPTUN_FMR_IP4_PREFIX,
-+      IFLA_IPTUN_FMR_IP6_PREFIX_LEN,
-+      IFLA_IPTUN_FMR_IP4_PREFIX_LEN,
-+      IFLA_IPTUN_FMR_EA_LEN,
-+      IFLA_IPTUN_FMR_OFFSET,
-+      __IFLA_IPTUN_FMR_MAX,
-+};
-+#define IFLA_IPTUN_FMR_MAX (__IFLA_IPTUN_FMR_MAX - 1)
-+
- enum tunnel_encap_types {
-       TUNNEL_ENCAP_NONE,
-       TUNNEL_ENCAP_FOU,
---- a/net/ipv6/ip6_tunnel.c
-+++ b/net/ipv6/ip6_tunnel.c
-@@ -11,6 +11,9 @@
-  *      linux/net/ipv6/sit.c and linux/net/ipv4/ipip.c
-  *
-  *      RFC 2473
-+ *
-+ *      Changes:
-+ *      Steven Barth <[email protected]>:           MAP-E FMR support
-  */
- #define pr_fmt(fmt) KBUILD_MODNAME ": " fmt
-@@ -67,9 +70,9 @@ static bool log_ecn_error = true;
- module_param(log_ecn_error, bool, 0644);
- MODULE_PARM_DESC(log_ecn_error, "Log packets received with corrupted ECN");
--static u32 HASH(const struct in6_addr *addr1, const struct in6_addr *addr2)
-+static u32 HASH(const struct in6_addr *addr)
- {
--      u32 hash = ipv6_addr_hash(addr1) ^ ipv6_addr_hash(addr2);
-+      u32 hash = ipv6_addr_hash(addr);
-       return hash_32(hash, IP6_TUNNEL_HASH_SIZE_SHIFT);
- }
-@@ -114,17 +117,33 @@ static struct ip6_tnl *
- ip6_tnl_lookup(struct net *net, int link,
-              const struct in6_addr *remote, const struct in6_addr *local)
- {
--      unsigned int hash = HASH(remote, local);
-+      unsigned int hash = HASH(local);
-       struct ip6_tnl *t, *cand = NULL;
-       struct ip6_tnl_net *ip6n = net_generic(net, ip6_tnl_net_id);
-       struct in6_addr any;
-       for_each_ip6_tunnel_rcu(ip6n->tnls_r_l[hash]) {
-               if (!ipv6_addr_equal(local, &t->parms.laddr) ||
--                  !ipv6_addr_equal(remote, &t->parms.raddr) ||
-                   !(t->dev->flags & IFF_UP))
-                       continue;
-+              if (!ipv6_addr_equal(remote, &t->parms.raddr)) {
-+                      struct __ip6_tnl_fmr *fmr;
-+                      bool found = false;
-+
-+                      for (fmr = t->parms.fmrs; fmr; fmr = fmr->next) {
-+                              if (!ipv6_prefix_equal(remote, &fmr->ip6_prefix,
-+                                                     fmr->ip6_prefix_len))
-+                                      continue;
-+
-+                              found = true;
-+                              break;
-+                      }
-+
-+                      if (!found)
-+                              continue;
-+              }
-+
-               if (link == t->parms.link)
-                       return t;
-               else
-@@ -132,7 +151,7 @@ ip6_tnl_lookup(struct net *net, int link
-       }
-       memset(&any, 0, sizeof(any));
--      hash = HASH(&any, local);
-+      hash = HASH(local);
-       for_each_ip6_tunnel_rcu(ip6n->tnls_r_l[hash]) {
-               if (!ipv6_addr_equal(local, &t->parms.laddr) ||
-                   !ipv6_addr_any(&t->parms.raddr) ||
-@@ -145,7 +164,7 @@ ip6_tnl_lookup(struct net *net, int link
-                       cand = t;
-       }
--      hash = HASH(remote, &any);
-+      hash = HASH(&any);
-       for_each_ip6_tunnel_rcu(ip6n->tnls_r_l[hash]) {
-               if (!ipv6_addr_equal(remote, &t->parms.raddr) ||
-                   !ipv6_addr_any(&t->parms.laddr) ||
-@@ -194,7 +213,7 @@ ip6_tnl_bucket(struct ip6_tnl_net *ip6n,
-       if (!ipv6_addr_any(remote) || !ipv6_addr_any(local)) {
-               prio = 1;
--              h = HASH(remote, local);
-+              h = HASH(local);
-       }
-       return &ip6n->tnls[prio][h];
- }
-@@ -378,6 +397,12 @@ ip6_tnl_dev_uninit(struct net_device *de
-       struct net *net = t->net;
-       struct ip6_tnl_net *ip6n = net_generic(net, ip6_tnl_net_id);
-+      while (t->parms.fmrs) {
-+              struct __ip6_tnl_fmr *next = t->parms.fmrs->next;
-+              kfree(t->parms.fmrs);
-+              t->parms.fmrs = next;
-+      }
-+
-       if (dev == ip6n->fb_tnl_dev)
-               RCU_INIT_POINTER(ip6n->tnls_wc[0], NULL);
-       else
-@@ -790,6 +815,107 @@ int ip6_tnl_rcv_ctl(struct ip6_tnl *t,
- }
- EXPORT_SYMBOL_GPL(ip6_tnl_rcv_ctl);
-+/**
-+ * ip4ip6_fmr_calc - calculate target / source IPv6-address based on FMR
-+ *   @dest: destination IPv6 address buffer
-+ *   @skb: received socket buffer
-+ *   @fmr: MAP FMR
-+ *   @xmit: Calculate for xmit or rcv
-+ **/
-+static void ip4ip6_fmr_calc(struct in6_addr *dest,
-+              const struct iphdr *iph, const uint8_t *end,
-+              const struct __ip6_tnl_fmr *fmr, bool xmit)
-+{
-+      int psidlen = fmr->ea_len - (32 - fmr->ip4_prefix_len);
-+      u8 *portp = NULL;
-+      bool use_dest_addr;
-+      const struct iphdr *dsth = iph;
-+
-+      if ((u8*)dsth >= end)
-+              return;
-+
-+      /* find significant IP header */
-+      if (iph->protocol == IPPROTO_ICMP) {
-+              struct icmphdr *ih = (struct icmphdr*)(((u8*)dsth) + dsth->ihl * 4);
-+              if (ih && ((u8*)&ih[1]) <= end && (
-+                      ih->type == ICMP_DEST_UNREACH ||
-+                      ih->type == ICMP_SOURCE_QUENCH ||
-+                      ih->type == ICMP_TIME_EXCEEDED ||
-+                      ih->type == ICMP_PARAMETERPROB ||
-+                      ih->type == ICMP_REDIRECT))
-+                              dsth = (const struct iphdr*)&ih[1];
-+      }
-+
-+      /* in xmit-path use dest port by default and source port only if
-+              this is an ICMP reply to something else; vice versa in rcv-path */
-+      use_dest_addr = (xmit && dsth == iph) || (!xmit && dsth != iph);
-+
-+      /* get dst port */
-+      if (((u8*)&dsth[1]) <= end && (
-+              dsth->protocol == IPPROTO_UDP ||
-+              dsth->protocol == IPPROTO_TCP ||
-+              dsth->protocol == IPPROTO_SCTP ||
-+              dsth->protocol == IPPROTO_DCCP)) {
-+                      /* for UDP, TCP, SCTP and DCCP source and dest port
-+                      follow IPv4 header directly */
-+                      portp = ((u8*)dsth) + dsth->ihl * 4;
-+
-+                      if (use_dest_addr)
-+                              portp += sizeof(u16);
-+      } else if (iph->protocol == IPPROTO_ICMP) {
-+              struct icmphdr *ih = (struct icmphdr*)(((u8*)dsth) + dsth->ihl * 4);
-+
-+              /* use icmp identifier as port */
-+              if (((u8*)&ih) <= end && (
-+                  (use_dest_addr && (
-+                  ih->type == ICMP_ECHOREPLY ||
-+                      ih->type == ICMP_TIMESTAMPREPLY ||
-+                      ih->type == ICMP_INFO_REPLY ||
-+                      ih->type == ICMP_ADDRESSREPLY)) ||
-+                      (!use_dest_addr && (
-+                      ih->type == ICMP_ECHO ||
-+                      ih->type == ICMP_TIMESTAMP ||
-+                      ih->type == ICMP_INFO_REQUEST ||
-+                      ih->type == ICMP_ADDRESS)
-+                      )))
-+                              portp = (u8*)&ih->un.echo.id;
-+      }
-+
-+      if ((portp && &portp[2] <= end) || psidlen == 0) {
-+              int frombyte = fmr->ip6_prefix_len / 8;
-+              int fromrem = fmr->ip6_prefix_len % 8;
-+              int bytes = sizeof(struct in6_addr) - frombyte;
-+              const u32 *addr = (use_dest_addr) ? &iph->daddr : &iph->saddr;
-+              u64 eabits = ((u64)ntohl(*addr)) << (32 + fmr->ip4_prefix_len);
-+              u64 t = 0;
-+
-+              /* extract PSID from port and add it to eabits */
-+              u16 psidbits = 0;
-+              if (psidlen > 0) {
-+                      psidbits = ((u16)portp[0]) << 8 | ((u16)portp[1]);
-+                      psidbits >>= 16 - psidlen - fmr->offset;
-+                      psidbits = (u16)(psidbits << (16 - psidlen));
-+                      eabits |= ((u64)psidbits) << (48 - (fmr->ea_len - psidlen));
-+              }
-+
-+              /* rewrite destination address */
-+              *dest = fmr->ip6_prefix;
-+              memcpy(&dest->s6_addr[10], addr, sizeof(*addr));
-+              dest->s6_addr16[7] = htons(psidbits >> (16 - psidlen));
-+
-+              if (bytes > sizeof(u64))
-+                      bytes = sizeof(u64);
-+
-+              /* insert eabits */
-+              memcpy(&t, &dest->s6_addr[frombyte], bytes);
-+              t = be64_to_cpu(t) & ~(((((u64)1) << fmr->ea_len) - 1)
-+                      << (64 - fmr->ea_len - fromrem));
-+              t = cpu_to_be64(t | (eabits >> fromrem));
-+              memcpy(&dest->s6_addr[frombyte], &t, bytes);
-+      }
-+}
-+
-+
- static int __ip6_tnl_rcv(struct ip6_tnl *tunnel, struct sk_buff *skb,
-                        const struct tnl_ptk_info *tpi,
-                        struct metadata_dst *tun_dst,
-@@ -857,6 +983,27 @@ static int __ip6_tnl_rcv(struct ip6_tnl
-       memset(skb->cb, 0, sizeof(struct inet6_skb_parm));
-+      if (tpi->proto == htons(ETH_P_IP) && tunnel->parms.fmrs &&
-+              !ipv6_addr_equal(&ipv6h->saddr, &tunnel->parms.raddr)) {
-+                      /* Packet didn't come from BR, so lookup FMR */
-+                      struct __ip6_tnl_fmr *fmr;
-+                      struct in6_addr expected = tunnel->parms.raddr;
-+                      for (fmr = tunnel->parms.fmrs; fmr; fmr = fmr->next)
-+                              if (ipv6_prefix_equal(&ipv6h->saddr,
-+                                      &fmr->ip6_prefix, fmr->ip6_prefix_len))
-+                                              break;
-+
-+                      /* Check that IPv6 matches IPv4 source to prevent spoofing */
-+                      if (fmr)
-+                              ip4ip6_fmr_calc(&expected, ip_hdr(skb),
-+                                              skb_tail_pointer(skb), fmr, false);
-+
-+                      if (!ipv6_addr_equal(&ipv6h->saddr, &expected)) {
-+                              rcu_read_unlock();
-+                              goto drop;
-+                      }
-+      }
-+
-       __skb_tunnel_rx(skb, tunnel->dev, tunnel->net);
-       err = dscp_ecn_decapsulate(tunnel, ipv6h, skb);
-@@ -1004,6 +1151,7 @@ static void init_tel_txopt(struct ipv6_t
-       opt->ops.opt_nflen = 8;
- }
-+
- /**
-  * ip6_tnl_addr_conflict - compare packet addresses to tunnel's own
-  *   @t: the outgoing tunnel device
-@@ -1284,6 +1432,7 @@ ipxip6_tnl_xmit(struct sk_buff *skb, str
-               u8 protocol)
- {
-       struct ip6_tnl *t = netdev_priv(dev);
-+      struct __ip6_tnl_fmr *fmr;
-       struct ipv6hdr *ipv6h;
-       const struct iphdr  *iph;
-       int encap_limit = -1;
-@@ -1383,6 +1532,18 @@ ipxip6_tnl_xmit(struct sk_buff *skb, str
-       fl6.flowi6_uid = sock_net_uid(dev_net(dev), NULL);
-       dsfield = INET_ECN_encapsulate(dsfield, orig_dsfield);
-+      /* try to find matching FMR */
-+      for (fmr = t->parms.fmrs; fmr; fmr = fmr->next) {
-+              unsigned mshift = 32 - fmr->ip4_prefix_len;
-+              if (ntohl(fmr->ip4_prefix.s_addr) >> mshift ==
-+                              ntohl(ip_hdr(skb)->daddr) >> mshift)
-+                      break;
-+      }
-+
-+      /* change dstaddr according to FMR */
-+      if (fmr)
-+              ip4ip6_fmr_calc(&fl6.daddr, ip_hdr(skb), skb_tail_pointer(skb), fmr, true);
-+
-       if (iptunnel_handle_offloads(skb, SKB_GSO_IPXIP6))
-               return -1;
-@@ -1536,6 +1697,14 @@ ip6_tnl_change(struct ip6_tnl *t, const
-       t->parms.link = p->link;
-       t->parms.proto = p->proto;
-       t->parms.fwmark = p->fwmark;
-+
-+      while (t->parms.fmrs) {
-+              struct __ip6_tnl_fmr *next = t->parms.fmrs->next;
-+              kfree(t->parms.fmrs);
-+              t->parms.fmrs = next;
-+      }
-+      t->parms.fmrs = p->fmrs;
-+
-       dst_cache_reset(&t->dst_cache);
-       ip6_tnl_link_config(t);
-       return 0;
-@@ -1574,6 +1743,7 @@ ip6_tnl_parm_from_user(struct __ip6_tnl_
-       p->flowinfo = u->flowinfo;
-       p->link = u->link;
-       p->proto = u->proto;
-+      p->fmrs = NULL;
-       memcpy(p->name, u->name, sizeof(u->name));
- }
-@@ -1960,6 +2130,15 @@ static int ip6_tnl_validate(struct nlatt
-       return 0;
- }
-+static const struct nla_policy ip6_tnl_fmr_policy[IFLA_IPTUN_FMR_MAX + 1] = {
-+      [IFLA_IPTUN_FMR_IP6_PREFIX] = { .len = sizeof(struct in6_addr) },
-+      [IFLA_IPTUN_FMR_IP4_PREFIX] = { .len = sizeof(struct in_addr) },
-+      [IFLA_IPTUN_FMR_IP6_PREFIX_LEN] = { .type = NLA_U8 },
-+      [IFLA_IPTUN_FMR_IP4_PREFIX_LEN] = { .type = NLA_U8 },
-+      [IFLA_IPTUN_FMR_EA_LEN] = { .type = NLA_U8 },
-+      [IFLA_IPTUN_FMR_OFFSET] = { .type = NLA_U8 }
-+};
-+
- static void ip6_tnl_netlink_parms(struct nlattr *data[],
-                                 struct __ip6_tnl_parm *parms)
- {
-@@ -1997,6 +2176,46 @@ static void ip6_tnl_netlink_parms(struct
-       if (data[IFLA_IPTUN_FWMARK])
-               parms->fwmark = nla_get_u32(data[IFLA_IPTUN_FWMARK]);
-+
-+      if (data[IFLA_IPTUN_FMRS]) {
-+              unsigned rem;
-+              struct nlattr *fmr;
-+              nla_for_each_nested(fmr, data[IFLA_IPTUN_FMRS], rem) {
-+                      struct nlattr *fmrd[IFLA_IPTUN_FMR_MAX + 1], *c;
-+                      struct __ip6_tnl_fmr *nfmr;
-+
-+                      nla_parse_nested(fmrd, IFLA_IPTUN_FMR_MAX,
-+                              fmr, ip6_tnl_fmr_policy, NULL);
-+
-+                      if (!(nfmr = kzalloc(sizeof(*nfmr), GFP_KERNEL)))
-+                              continue;
-+
-+                      nfmr->offset = 6;
-+
-+                      if ((c = fmrd[IFLA_IPTUN_FMR_IP6_PREFIX]))
-+                              nla_memcpy(&nfmr->ip6_prefix, fmrd[IFLA_IPTUN_FMR_IP6_PREFIX],
-+                                      sizeof(nfmr->ip6_prefix));
-+
-+                      if ((c = fmrd[IFLA_IPTUN_FMR_IP4_PREFIX]))
-+                              nla_memcpy(&nfmr->ip4_prefix, fmrd[IFLA_IPTUN_FMR_IP4_PREFIX],
-+                                      sizeof(nfmr->ip4_prefix));
-+
-+                      if ((c = fmrd[IFLA_IPTUN_FMR_IP6_PREFIX_LEN]))
-+                              nfmr->ip6_prefix_len = nla_get_u8(c);
-+
-+                      if ((c = fmrd[IFLA_IPTUN_FMR_IP4_PREFIX_LEN]))
-+                              nfmr->ip4_prefix_len = nla_get_u8(c);
-+
-+                      if ((c = fmrd[IFLA_IPTUN_FMR_EA_LEN]))
-+                              nfmr->ea_len = nla_get_u8(c);
-+
-+                      if ((c = fmrd[IFLA_IPTUN_FMR_OFFSET]))
-+                              nfmr->offset = nla_get_u8(c);
-+
-+                      nfmr->next = parms->fmrs;
-+                      parms->fmrs = nfmr;
-+              }
-+      }
- }
- static bool ip6_tnl_netlink_encap_parms(struct nlattr *data[],
-@@ -2112,6 +2331,12 @@ static void ip6_tnl_dellink(struct net_d
- static size_t ip6_tnl_get_size(const struct net_device *dev)
- {
-+      const struct ip6_tnl *t = netdev_priv(dev);
-+      struct __ip6_tnl_fmr *c;
-+      int fmrs = 0;
-+      for (c = t->parms.fmrs; c; c = c->next)
-+              ++fmrs;
-+
-       return
-               /* IFLA_IPTUN_LINK */
-               nla_total_size(4) +
-@@ -2141,6 +2366,24 @@ static size_t ip6_tnl_get_size(const str
-               nla_total_size(0) +
-               /* IFLA_IPTUN_FWMARK */
-               nla_total_size(4) +
-+              /* IFLA_IPTUN_FMRS */
-+              nla_total_size(0) +
-+              (
-+                      /* nest */
-+                      nla_total_size(0) +
-+                      /* IFLA_IPTUN_FMR_IP6_PREFIX */
-+                      nla_total_size(sizeof(struct in6_addr)) +
-+                      /* IFLA_IPTUN_FMR_IP4_PREFIX */
-+                      nla_total_size(sizeof(struct in_addr)) +
-+                      /* IFLA_IPTUN_FMR_EA_LEN */
-+                      nla_total_size(1) +
-+                      /* IFLA_IPTUN_FMR_IP6_PREFIX_LEN */
-+                      nla_total_size(1) +
-+                      /* IFLA_IPTUN_FMR_IP4_PREFIX_LEN */
-+                      nla_total_size(1) +
-+                      /* IFLA_IPTUN_FMR_OFFSET */
-+                      nla_total_size(1)
-+              ) * fmrs +
-               0;
- }
-@@ -2148,6 +2391,9 @@ static int ip6_tnl_fill_info(struct sk_b
- {
-       struct ip6_tnl *tunnel = netdev_priv(dev);
-       struct __ip6_tnl_parm *parm = &tunnel->parms;
-+      struct __ip6_tnl_fmr *c;
-+      int fmrcnt = 0;
-+      struct nlattr *fmrs;
-       if (nla_put_u32(skb, IFLA_IPTUN_LINK, parm->link) ||
-           nla_put_in6_addr(skb, IFLA_IPTUN_LOCAL, &parm->laddr) ||
-@@ -2157,9 +2403,27 @@ static int ip6_tnl_fill_info(struct sk_b
-           nla_put_be32(skb, IFLA_IPTUN_FLOWINFO, parm->flowinfo) ||
-           nla_put_u32(skb, IFLA_IPTUN_FLAGS, parm->flags) ||
-           nla_put_u8(skb, IFLA_IPTUN_PROTO, parm->proto) ||
--          nla_put_u32(skb, IFLA_IPTUN_FWMARK, parm->fwmark))
-+          nla_put_u32(skb, IFLA_IPTUN_FWMARK, parm->fwmark) ||
-+          !(fmrs = nla_nest_start(skb, IFLA_IPTUN_FMRS)))
-               goto nla_put_failure;
-+      for (c = parm->fmrs; c; c = c->next) {
-+              struct nlattr *fmr = nla_nest_start(skb, ++fmrcnt);
-+              if (!fmr ||
-+                      nla_put(skb, IFLA_IPTUN_FMR_IP6_PREFIX,
-+                              sizeof(c->ip6_prefix), &c->ip6_prefix) ||
-+                      nla_put(skb, IFLA_IPTUN_FMR_IP4_PREFIX,
-+                              sizeof(c->ip4_prefix), &c->ip4_prefix) ||
-+                      nla_put_u8(skb, IFLA_IPTUN_FMR_IP6_PREFIX_LEN, c->ip6_prefix_len) ||
-+                      nla_put_u8(skb, IFLA_IPTUN_FMR_IP4_PREFIX_LEN, c->ip4_prefix_len) ||
-+                      nla_put_u8(skb, IFLA_IPTUN_FMR_EA_LEN, c->ea_len) ||
-+                      nla_put_u8(skb, IFLA_IPTUN_FMR_OFFSET, c->offset))
-+                              goto nla_put_failure;
-+
-+              nla_nest_end(skb, fmr);
-+      }
-+      nla_nest_end(skb, fmrs);
-+
-       if (nla_put_u16(skb, IFLA_IPTUN_ENCAP_TYPE, tunnel->encap.type) ||
-           nla_put_be16(skb, IFLA_IPTUN_ENCAP_SPORT, tunnel->encap.sport) ||
-           nla_put_be16(skb, IFLA_IPTUN_ENCAP_DPORT, tunnel->encap.dport) ||
-@@ -2199,6 +2463,7 @@ static const struct nla_policy ip6_tnl_p
-       [IFLA_IPTUN_ENCAP_DPORT]        = { .type = NLA_U16 },
-       [IFLA_IPTUN_COLLECT_METADATA]   = { .type = NLA_FLAG },
-       [IFLA_IPTUN_FWMARK]             = { .type = NLA_U32 },
-+      [IFLA_IPTUN_FMRS]               = { .type = NLA_NESTED },
- };
- static struct rtnl_link_ops ip6_link_ops __read_mostly = {
diff --git a/target/linux/generic/pending-5.15/670-ipv6-allow-rejecting-with-source-address-failed-policy.patch b/target/linux/generic/pending-5.15/670-ipv6-allow-rejecting-with-source-address-failed-policy.patch
deleted file mode 100644 (file)
index d4e274e..0000000
+++ /dev/null
@@ -1,263 +0,0 @@
-From: Jonas Gorski <[email protected]>
-Subject: ipv6: allow rejecting with "source address failed policy"
-
-RFC6204 L-14 requires rejecting traffic from invalid addresses with
-ICMPv6 Destination Unreachable, Code 5 (Source address failed ingress/
-egress policy) on the LAN side, so add an appropriate rule for that.
-
-Signed-off-by: Jonas Gorski <[email protected]>
----
- include/net/netns/ipv6.h       |  1 +
- include/uapi/linux/fib_rules.h |  4 +++
- include/uapi/linux/rtnetlink.h |  1 +
- net/ipv4/fib_semantics.c       |  4 +++
- net/ipv4/fib_trie.c            |  1 +
- net/ipv4/ipmr.c                |  1 +
- net/ipv6/fib6_rules.c          |  4 +++
- net/ipv6/ip6mr.c               |  2 ++
- net/ipv6/route.c               | 58 +++++++++++++++++++++++++++++++++++++++++-
- 9 files changed, 75 insertions(+), 1 deletion(-)
-
---- a/include/net/netns/ipv6.h
-+++ b/include/net/netns/ipv6.h
-@@ -85,6 +85,7 @@ struct netns_ipv6 {
-       unsigned int            fib6_routes_require_src;
- #endif
-       struct rt6_info         *ip6_prohibit_entry;
-+      struct rt6_info         *ip6_policy_failed_entry;
-       struct rt6_info         *ip6_blk_hole_entry;
-       struct fib6_table       *fib6_local_tbl;
-       struct fib_rules_ops    *fib6_rules_ops;
---- a/include/uapi/linux/fib_rules.h
-+++ b/include/uapi/linux/fib_rules.h
-@@ -82,6 +82,10 @@ enum {
-       FR_ACT_BLACKHOLE,       /* Drop without notification */
-       FR_ACT_UNREACHABLE,     /* Drop with ENETUNREACH */
-       FR_ACT_PROHIBIT,        /* Drop with EACCES */
-+      FR_ACT_RES9,
-+      FR_ACT_RES10,
-+      FR_ACT_RES11,
-+      FR_ACT_POLICY_FAILED,   /* Drop with EACCES */
-       __FR_ACT_MAX,
- };
---- a/include/uapi/linux/rtnetlink.h
-+++ b/include/uapi/linux/rtnetlink.h
-@@ -256,6 +256,7 @@ enum {
-       RTN_THROW,              /* Not in this table            */
-       RTN_NAT,                /* Translate this address       */
-       RTN_XRESOLVE,           /* Use external resolver        */
-+      RTN_POLICY_FAILED,      /* Failed ingress/egress policy */
-       __RTN_MAX
- };
---- a/net/ipv4/fib_semantics.c
-+++ b/net/ipv4/fib_semantics.c
-@@ -143,6 +143,10 @@ const struct fib_prop fib_props[RTN_MAX
-               .error  = -EINVAL,
-               .scope  = RT_SCOPE_NOWHERE,
-       },
-+      [RTN_POLICY_FAILED] = {
-+              .error  = -EACCES,
-+              .scope  = RT_SCOPE_UNIVERSE,
-+      },
- };
- static void rt_fibinfo_free(struct rtable __rcu **rtp)
---- a/net/ipv4/fib_trie.c
-+++ b/net/ipv4/fib_trie.c
-@@ -2777,6 +2777,7 @@ static const char *const rtn_type_names[
-       [RTN_THROW] = "THROW",
-       [RTN_NAT] = "NAT",
-       [RTN_XRESOLVE] = "XRESOLVE",
-+      [RTN_POLICY_FAILED] = "POLICY_FAILED",
- };
- static inline const char *rtn_type(char *buf, size_t len, unsigned int t)
---- a/net/ipv4/ipmr.c
-+++ b/net/ipv4/ipmr.c
-@@ -175,6 +175,7 @@ static int ipmr_rule_action(struct fib_r
-       case FR_ACT_UNREACHABLE:
-               return -ENETUNREACH;
-       case FR_ACT_PROHIBIT:
-+      case FR_ACT_POLICY_FAILED:
-               return -EACCES;
-       case FR_ACT_BLACKHOLE:
-       default:
---- a/net/ipv6/fib6_rules.c
-+++ b/net/ipv6/fib6_rules.c
-@@ -220,6 +220,10 @@ static int __fib6_rule_action(struct fib
-               err = -EACCES;
-               rt = net->ipv6.ip6_prohibit_entry;
-               goto discard_pkt;
-+      case FR_ACT_POLICY_FAILED:
-+              err = -EACCES;
-+              rt = net->ipv6.ip6_policy_failed_entry;
-+              goto discard_pkt;
-       }
-       tb_id = fib_rule_get_table(rule, arg);
---- a/net/ipv6/ip6mr.c
-+++ b/net/ipv6/ip6mr.c
-@@ -163,6 +163,8 @@ static int ip6mr_rule_action(struct fib_
-               return -ENETUNREACH;
-       case FR_ACT_PROHIBIT:
-               return -EACCES;
-+      case FR_ACT_POLICY_FAILED:
-+              return -EACCES;
-       case FR_ACT_BLACKHOLE:
-       default:
-               return -EINVAL;
---- a/net/ipv6/route.c
-+++ b/net/ipv6/route.c
-@@ -98,6 +98,8 @@ static int           ip6_pkt_discard(struct sk_bu
- static int            ip6_pkt_discard_out(struct net *net, struct sock *sk, struct sk_buff *skb);
- static int            ip6_pkt_prohibit(struct sk_buff *skb);
- static int            ip6_pkt_prohibit_out(struct net *net, struct sock *sk, struct sk_buff *skb);
-+static int            ip6_pkt_policy_failed(struct sk_buff *skb);
-+static int            ip6_pkt_policy_failed_out(struct net *net, struct sock *sk, struct sk_buff *skb);
- static void           ip6_link_failure(struct sk_buff *skb);
- static void           ip6_rt_update_pmtu(struct dst_entry *dst, struct sock *sk,
-                                          struct sk_buff *skb, u32 mtu,
-@@ -313,6 +315,18 @@ static const struct rt6_info ip6_prohibi
-       .rt6i_flags     = (RTF_REJECT | RTF_NONEXTHOP),
- };
-+static const struct rt6_info ip6_policy_failed_entry_template = {
-+      .dst = {
-+              .__refcnt       = ATOMIC_INIT(1),
-+              .__use          = 1,
-+              .obsolete       = DST_OBSOLETE_FORCE_CHK,
-+              .error          = -EACCES,
-+              .input          = ip6_pkt_policy_failed,
-+              .output         = ip6_pkt_policy_failed_out,
-+      },
-+      .rt6i_flags     = (RTF_REJECT | RTF_NONEXTHOP),
-+};
-+
- static const struct rt6_info ip6_blk_hole_entry_template = {
-       .dst = {
-               .__refcnt       = ATOMIC_INIT(1),
-@@ -1034,6 +1048,7 @@ static const int fib6_prop[RTN_MAX + 1]
-       [RTN_BLACKHOLE] = -EINVAL,
-       [RTN_UNREACHABLE] = -EHOSTUNREACH,
-       [RTN_PROHIBIT]  = -EACCES,
-+      [RTN_POLICY_FAILED] = -EACCES,
-       [RTN_THROW]     = -EAGAIN,
-       [RTN_NAT]       = -EINVAL,
-       [RTN_XRESOLVE]  = -EINVAL,
-@@ -1069,6 +1084,10 @@ static void ip6_rt_init_dst_reject(struc
-               rt->dst.output = ip6_pkt_prohibit_out;
-               rt->dst.input = ip6_pkt_prohibit;
-               break;
-+      case RTN_POLICY_FAILED:
-+              rt->dst.output = ip6_pkt_policy_failed_out;
-+              rt->dst.input = ip6_pkt_policy_failed;
-+              break;
-       case RTN_THROW:
-       case RTN_UNREACHABLE:
-       default:
-@@ -4561,6 +4580,17 @@ static int ip6_pkt_prohibit_out(struct n
-       return ip6_pkt_drop(skb, ICMPV6_ADM_PROHIBITED, IPSTATS_MIB_OUTNOROUTES);
- }
-+static int ip6_pkt_policy_failed(struct sk_buff *skb)
-+{
-+      return ip6_pkt_drop(skb, ICMPV6_POLICY_FAIL, IPSTATS_MIB_INNOROUTES);
-+}
-+
-+static int ip6_pkt_policy_failed_out(struct net *net, struct sock *sk, struct sk_buff *skb)
-+{
-+      skb->dev = skb_dst(skb)->dev;
-+      return ip6_pkt_drop(skb, ICMPV6_POLICY_FAIL, IPSTATS_MIB_OUTNOROUTES);
-+}
-+
- /*
-  *    Allocate a dst for local (unicast / anycast) address.
-  */
-@@ -5048,7 +5078,8 @@ static int rtm_to_fib6_config(struct sk_
-       if (rtm->rtm_type == RTN_UNREACHABLE ||
-           rtm->rtm_type == RTN_BLACKHOLE ||
-           rtm->rtm_type == RTN_PROHIBIT ||
--          rtm->rtm_type == RTN_THROW)
-+          rtm->rtm_type == RTN_THROW ||
-+          rtm->rtm_type == RTN_POLICY_FAILED)
-               cfg->fc_flags |= RTF_REJECT;
-       if (rtm->rtm_type == RTN_LOCAL)
-@@ -6295,6 +6326,8 @@ static int ip6_route_dev_notify(struct n
- #ifdef CONFIG_IPV6_MULTIPLE_TABLES
-               net->ipv6.ip6_prohibit_entry->dst.dev = dev;
-               net->ipv6.ip6_prohibit_entry->rt6i_idev = in6_dev_get(dev);
-+              net->ipv6.ip6_policy_failed_entry->dst.dev = dev;
-+              net->ipv6.ip6_policy_failed_entry->rt6i_idev = in6_dev_get(dev);
-               net->ipv6.ip6_blk_hole_entry->dst.dev = dev;
-               net->ipv6.ip6_blk_hole_entry->rt6i_idev = in6_dev_get(dev);
- #endif
-@@ -6306,6 +6339,7 @@ static int ip6_route_dev_notify(struct n
-               in6_dev_put_clear(&net->ipv6.ip6_null_entry->rt6i_idev);
- #ifdef CONFIG_IPV6_MULTIPLE_TABLES
-               in6_dev_put_clear(&net->ipv6.ip6_prohibit_entry->rt6i_idev);
-+              in6_dev_put_clear(&net->ipv6.ip6_policy_failed_entry->rt6i_idev);
-               in6_dev_put_clear(&net->ipv6.ip6_blk_hole_entry->rt6i_idev);
- #endif
-       }
-@@ -6497,6 +6531,8 @@ static int __net_init ip6_route_net_init
- #ifdef CONFIG_IPV6_MULTIPLE_TABLES
-       net->ipv6.fib6_has_custom_rules = false;
-+
-+
-       net->ipv6.ip6_prohibit_entry = kmemdup(&ip6_prohibit_entry_template,
-                                              sizeof(*net->ipv6.ip6_prohibit_entry),
-                                              GFP_KERNEL);
-@@ -6507,11 +6543,21 @@ static int __net_init ip6_route_net_init
-                        ip6_template_metrics, true);
-       INIT_LIST_HEAD(&net->ipv6.ip6_prohibit_entry->rt6i_uncached);
-+      net->ipv6.ip6_policy_failed_entry =
-+                              kmemdup(&ip6_policy_failed_entry_template,
-+                              sizeof(*net->ipv6.ip6_policy_failed_entry), GFP_KERNEL);
-+      if (!net->ipv6.ip6_policy_failed_entry)
-+              goto out_ip6_prohibit_entry;
-+      net->ipv6.ip6_policy_failed_entry->dst.ops = &net->ipv6.ip6_dst_ops;
-+      dst_init_metrics(&net->ipv6.ip6_policy_failed_entry->dst,
-+                       ip6_template_metrics, true);
-+      INIT_LIST_HEAD(&net->ipv6.ip6_policy_failed_entry->rt6i_uncached);
-+
-       net->ipv6.ip6_blk_hole_entry = kmemdup(&ip6_blk_hole_entry_template,
-                                              sizeof(*net->ipv6.ip6_blk_hole_entry),
-                                              GFP_KERNEL);
-       if (!net->ipv6.ip6_blk_hole_entry)
--              goto out_ip6_prohibit_entry;
-+              goto out_ip6_policy_failed_entry;
-       net->ipv6.ip6_blk_hole_entry->dst.ops = &net->ipv6.ip6_dst_ops;
-       dst_init_metrics(&net->ipv6.ip6_blk_hole_entry->dst,
-                        ip6_template_metrics, true);
-@@ -6538,6 +6584,8 @@ out:
-       return ret;
- #ifdef CONFIG_IPV6_MULTIPLE_TABLES
-+out_ip6_policy_failed_entry:
-+      kfree(net->ipv6.ip6_policy_failed_entry);
- out_ip6_prohibit_entry:
-       kfree(net->ipv6.ip6_prohibit_entry);
- out_ip6_null_entry:
-@@ -6557,6 +6605,7 @@ static void __net_exit ip6_route_net_exi
-       kfree(net->ipv6.ip6_null_entry);
- #ifdef CONFIG_IPV6_MULTIPLE_TABLES
-       kfree(net->ipv6.ip6_prohibit_entry);
-+      kfree(net->ipv6.ip6_policy_failed_entry);
-       kfree(net->ipv6.ip6_blk_hole_entry);
- #endif
-       dst_entries_destroy(&net->ipv6.ip6_dst_ops);
-@@ -6640,6 +6689,9 @@ void __init ip6_route_init_special_entri
-       init_net.ipv6.ip6_prohibit_entry->rt6i_idev = in6_dev_get(init_net.loopback_dev);
-       init_net.ipv6.ip6_blk_hole_entry->dst.dev = init_net.loopback_dev;
-       init_net.ipv6.ip6_blk_hole_entry->rt6i_idev = in6_dev_get(init_net.loopback_dev);
-+      init_net.ipv6.ip6_policy_failed_entry->dst.dev = init_net.loopback_dev;
-+      init_net.ipv6.ip6_policy_failed_entry->rt6i_idev =
-+              in6_dev_get(init_net.loopback_dev);
-   #endif
- }
diff --git a/target/linux/generic/pending-5.15/671-net-provide-defines-for-_POLICY_FAILED-until-all-cod.patch b/target/linux/generic/pending-5.15/671-net-provide-defines-for-_POLICY_FAILED-until-all-cod.patch
deleted file mode 100644 (file)
index bea43b2..0000000
+++ /dev/null
@@ -1,50 +0,0 @@
-From: Jonas Gorski <[email protected]>
-Subject: net: provide defines for _POLICY_FAILED until all code is updated
-
-Upstream introduced ICMPV6_POLICY_FAIL for code 5 of destination
-unreachable, conflicting with our name.
-
-Add appropriate defines to allow our code to build with the new
-name until we have updated our local patches for older kernels
-and userspace packages.
-
-Signed-off-by: Jonas Gorski <[email protected]>
----
- include/uapi/linux/fib_rules.h | 2 ++
- include/uapi/linux/icmpv6.h    | 2 ++
- include/uapi/linux/rtnetlink.h | 2 ++
- 3 files changed, 6 insertions(+)
-
---- a/include/uapi/linux/fib_rules.h
-+++ b/include/uapi/linux/fib_rules.h
-@@ -89,6 +89,8 @@ enum {
-       __FR_ACT_MAX,
- };
-+#define FR_ACT_FAILED_POLICY FR_ACT_POLICY_FAILED
-+
- #define FR_ACT_MAX (__FR_ACT_MAX - 1)
- #endif
---- a/include/uapi/linux/icmpv6.h
-+++ b/include/uapi/linux/icmpv6.h
-@@ -126,6 +126,8 @@ struct icmp6hdr {
- #define ICMPV6_POLICY_FAIL            5
- #define ICMPV6_REJECT_ROUTE           6
-+#define ICMPV6_FAILED_POLICY          ICMPV6_POLICY_FAIL
-+
- /*
-  *    Codes for Time Exceeded
-  */
---- a/include/uapi/linux/rtnetlink.h
-+++ b/include/uapi/linux/rtnetlink.h
-@@ -260,6 +260,8 @@ enum {
-       __RTN_MAX
- };
-+#define RTN_FAILED_POLICY RTN_POLICY_FAILED
-+
- #define RTN_MAX (__RTN_MAX - 1)
diff --git a/target/linux/generic/pending-5.15/680-NET-skip-GRO-for-foreign-MAC-addresses.patch b/target/linux/generic/pending-5.15/680-NET-skip-GRO-for-foreign-MAC-addresses.patch
deleted file mode 100644 (file)
index 6eb72ab..0000000
+++ /dev/null
@@ -1,149 +0,0 @@
-From: Felix Fietkau <[email protected]>
-Subject: net: replace GRO optimization patch with a new one that supports VLANs/bridges with different MAC addresses
-
-Signed-off-by: Felix Fietkau <[email protected]>
----
- include/linux/netdevice.h |  2 ++
- include/linux/skbuff.h    |  3 ++-
- net/core/dev.c            | 48 +++++++++++++++++++++++++++++++++++++++++++++++
- net/ethernet/eth.c        | 18 +++++++++++++++++-
- 4 files changed, 69 insertions(+), 2 deletions(-)
-
---- a/include/linux/netdevice.h
-+++ b/include/linux/netdevice.h
-@@ -2099,6 +2099,8 @@ struct net_device {
-       struct netdev_hw_addr_list      mc;
-       struct netdev_hw_addr_list      dev_addrs;
-+      unsigned char           local_addr_mask[MAX_ADDR_LEN];
-+
- #ifdef CONFIG_SYSFS
-       struct kset             *queues_kset;
- #endif
---- a/include/linux/skbuff.h
-+++ b/include/linux/skbuff.h
-@@ -893,6 +893,7 @@ struct sk_buff {
- #ifdef CONFIG_IPV6_NDISC_NODETYPE
-       __u8                    ndisc_nodetype:2;
- #endif
-+      __u8                    gro_skip:1;
-       __u8                    ipvs_property:1;
-       __u8                    inner_protocol_type:1;
---- a/net/core/dev.c
-+++ b/net/core/dev.c
-@@ -6077,6 +6077,9 @@ static enum gro_result dev_gro_receive(s
-       int same_flow;
-       int grow;
-+      if (skb->gro_skip)
-+              goto normal;
-+
-       if (netif_elide_gro(skb->dev))
-               goto normal;
-@@ -8094,6 +8097,48 @@ static void __netdev_adjacent_dev_unlink
-                                          &upper_dev->adj_list.lower);
- }
-+static void __netdev_addr_mask(unsigned char *mask, const unsigned char *addr,
-+                             struct net_device *dev)
-+{
-+      int i;
-+
-+      for (i = 0; i < dev->addr_len; i++)
-+              mask[i] |= addr[i] ^ dev->dev_addr[i];
-+}
-+
-+static void __netdev_upper_mask(unsigned char *mask, struct net_device *dev,
-+                              struct net_device *lower)
-+{
-+      struct net_device *cur;
-+      struct list_head *iter;
-+
-+      netdev_for_each_upper_dev_rcu(dev, cur, iter) {
-+              __netdev_addr_mask(mask, cur->dev_addr, lower);
-+              __netdev_upper_mask(mask, cur, lower);
-+      }
-+}
-+
-+static void __netdev_update_addr_mask(struct net_device *dev)
-+{
-+      unsigned char mask[MAX_ADDR_LEN];
-+      struct net_device *cur;
-+      struct list_head *iter;
-+
-+      memset(mask, 0, sizeof(mask));
-+      __netdev_upper_mask(mask, dev, dev);
-+      memcpy(dev->local_addr_mask, mask, dev->addr_len);
-+
-+      netdev_for_each_lower_dev(dev, cur, iter)
-+              __netdev_update_addr_mask(cur);
-+}
-+
-+static void netdev_update_addr_mask(struct net_device *dev)
-+{
-+      rcu_read_lock();
-+      __netdev_update_addr_mask(dev);
-+      rcu_read_unlock();
-+}
-+
- static int __netdev_upper_dev_link(struct net_device *dev,
-                                  struct net_device *upper_dev, bool master,
-                                  void *upper_priv, void *upper_info,
-@@ -8145,6 +8190,7 @@ static int __netdev_upper_dev_link(struc
-       if (ret)
-               return ret;
-+      netdev_update_addr_mask(dev);
-       ret = call_netdevice_notifiers_info(NETDEV_CHANGEUPPER,
-                                           &changeupper_info.info);
-       ret = notifier_to_errno(ret);
-@@ -8241,6 +8287,7 @@ static void __netdev_upper_dev_unlink(st
-       __netdev_adjacent_dev_unlink_neighbour(dev, upper_dev);
-+      netdev_update_addr_mask(dev);
-       call_netdevice_notifiers_info(NETDEV_CHANGEUPPER,
-                                     &changeupper_info.info);
-@@ -9060,6 +9107,7 @@ int dev_set_mac_address(struct net_devic
-       if (err)
-               return err;
-       dev->addr_assign_type = NET_ADDR_SET;
-+      netdev_update_addr_mask(dev);
-       call_netdevice_notifiers(NETDEV_CHANGEADDR, dev);
-       add_device_randomness(dev->dev_addr, dev->addr_len);
-       return 0;
---- a/net/ethernet/eth.c
-+++ b/net/ethernet/eth.c
-@@ -142,6 +142,18 @@ u32 eth_get_headlen(const struct net_dev
- }
- EXPORT_SYMBOL(eth_get_headlen);
-+static inline bool
-+eth_check_local_mask(const void *addr1, const void *addr2, const void *mask)
-+{
-+      const u16 *a1 = addr1;
-+      const u16 *a2 = addr2;
-+      const u16 *m = mask;
-+
-+      return (((a1[0] ^ a2[0]) & ~m[0]) |
-+              ((a1[1] ^ a2[1]) & ~m[1]) |
-+              ((a1[2] ^ a2[2]) & ~m[2]));
-+}
-+
- /**
-  * eth_type_trans - determine the packet's protocol ID.
-  * @skb: received socket data
-@@ -165,6 +177,10 @@ __be16 eth_type_trans(struct sk_buff *sk
-       eth_skb_pkt_type(skb, dev);
-+      if (unlikely(!ether_addr_equal_64bits(eth->h_dest, dev->dev_addr)) &&
-+          eth_check_local_mask(eth->h_dest, dev->dev_addr, dev->local_addr_mask))
-+              skb->gro_skip = 1;
-+
-       /*
-        * Some variants of DSA tagging don't have an ethertype field
-        * at all, so we check here whether one of those tagging
diff --git a/target/linux/generic/pending-5.15/683-of_net-add-mac-address-to-of-tree.patch b/target/linux/generic/pending-5.15/683-of_net-add-mac-address-to-of-tree.patch
deleted file mode 100644 (file)
index 03ee537..0000000
+++ /dev/null
@@ -1,75 +0,0 @@
-From 8585756342caa6d27008d1ad0c18023e4211a40a Mon Sep 17 00:00:00 2001
-From: OpenWrt community <[email protected]>
-Date: Wed, 13 Jul 2022 12:22:48 +0200
-Subject: [PATCH] of/of_net: write back netdev MAC-address to device-tree
-
-The label-mac logic relies on the mac-address property of a netdev
-devices of-node. However, the mac address can also be stored as a
-different property or read from e.g. an mtd device.
-
-Create this node when reading a mac-address from OF if it does not
-already exist and copy the mac-address used for the device to this
-property. This way, the MAC address can be accessed using procfs.
-
----
- net/core/of_net.c | 22 ++++++++++++++++++++++
- 1 file changed, 22 insertions(+)
-
---- a/net/core/of_net.c
-+++ b/net/core/of_net.c
-@@ -95,6 +95,27 @@ static int of_get_mac_addr_nvmem(struct
-       return 0;
- }
-+static int of_add_mac_address(struct device_node *np, u8* addr)
-+{
-+      struct property *prop;
-+
-+      prop = kzalloc(sizeof(*prop), GFP_KERNEL);
-+      if (!prop)
-+              return -ENOMEM;
-+
-+      prop->name = "mac-address";
-+      prop->length = ETH_ALEN;
-+      prop->value = kmemdup(addr, ETH_ALEN, GFP_KERNEL);
-+      if (!prop->value || of_update_property(np, prop))
-+              goto free;
-+
-+      return 0;
-+free:
-+      kfree(prop->value);
-+      kfree(prop);
-+      return -ENOMEM;
-+}
-+
- /**
-  * of_get_mac_address()
-  * @np:               Caller's Device Node
-@@ -130,17 +151,23 @@ int of_get_mac_address(struct device_nod
-       ret = of_get_mac_addr(np, "mac-address", addr);
-       if (!ret)
--              return 0;
-+              goto found;
-       ret = of_get_mac_addr(np, "local-mac-address", addr);
-       if (!ret)
--              return 0;
-+              goto found;
-       ret = of_get_mac_addr(np, "address", addr);
-       if (!ret)
--              return 0;
-+              goto found;
--      return of_get_mac_addr_nvmem(np, addr);
-+      ret = of_get_mac_addr_nvmem(np, addr);
-+      if (ret)
-+              return ret;
-+
-+found:
-+      ret = of_add_mac_address(np, addr);
-+      return ret;
- }
- EXPORT_SYMBOL(of_get_mac_address);
diff --git a/target/linux/generic/pending-5.15/700-netfilter-nft_flow_offload-handle-netdevice-events-f.patch b/target/linux/generic/pending-5.15/700-netfilter-nft_flow_offload-handle-netdevice-events-f.patch
deleted file mode 100644 (file)
index ba75e4a..0000000
+++ /dev/null
@@ -1,110 +0,0 @@
-From: Pablo Neira Ayuso <[email protected]>
-Date: Thu, 25 Jan 2018 12:58:55 +0100
-Subject: [PATCH] netfilter: nft_flow_offload: handle netdevice events from
- nf_flow_table
-
-Move the code that deals with device events to the core.
-
-Signed-off-by: Pablo Neira Ayuso <[email protected]>
----
-
---- a/net/netfilter/nf_flow_table_core.c
-+++ b/net/netfilter/nf_flow_table_core.c
-@@ -651,6 +651,23 @@ static struct pernet_operations nf_flow_
-       .exit_batch = nf_flow_table_pernet_exit,
- };
-+static int nf_flow_table_netdev_event(struct notifier_block *this,
-+                                    unsigned long event, void *ptr)
-+{
-+      struct net_device *dev = netdev_notifier_info_to_dev(ptr);
-+
-+      if (event != NETDEV_DOWN)
-+              return NOTIFY_DONE;
-+
-+      nf_flow_table_cleanup(dev);
-+
-+      return NOTIFY_DONE;
-+}
-+
-+static struct notifier_block flow_offload_netdev_notifier = {
-+      .notifier_call  = nf_flow_table_netdev_event,
-+};
-+
- static int __init nf_flow_table_module_init(void)
- {
-       int ret;
-@@ -663,8 +680,14 @@ static int __init nf_flow_table_module_i
-       if (ret)
-               goto out_offload;
-+      ret = register_netdevice_notifier(&flow_offload_netdev_notifier);
-+      if (ret)
-+              goto out_offload_init;
-+
-       return 0;
-+out_offload_init:
-+      nf_flow_table_offload_exit();
- out_offload:
-       unregister_pernet_subsys(&nf_flow_table_net_ops);
-       return ret;
-@@ -672,6 +695,7 @@ out_offload:
- static void __exit nf_flow_table_module_exit(void)
- {
-+      unregister_netdevice_notifier(&flow_offload_netdev_notifier);
-       nf_flow_table_offload_exit();
-       unregister_pernet_subsys(&nf_flow_table_net_ops);
- }
---- a/net/netfilter/nft_flow_offload.c
-+++ b/net/netfilter/nft_flow_offload.c
-@@ -455,47 +455,14 @@ static struct nft_expr_type nft_flow_off
-       .owner          = THIS_MODULE,
- };
--static int flow_offload_netdev_event(struct notifier_block *this,
--                                   unsigned long event, void *ptr)
--{
--      struct net_device *dev = netdev_notifier_info_to_dev(ptr);
--
--      if (event != NETDEV_DOWN)
--              return NOTIFY_DONE;
--
--      nf_flow_table_cleanup(dev);
--
--      return NOTIFY_DONE;
--}
--
--static struct notifier_block flow_offload_netdev_notifier = {
--      .notifier_call  = flow_offload_netdev_event,
--};
--
- static int __init nft_flow_offload_module_init(void)
- {
--      int err;
--
--      err = register_netdevice_notifier(&flow_offload_netdev_notifier);
--      if (err)
--              goto err;
--
--      err = nft_register_expr(&nft_flow_offload_type);
--      if (err < 0)
--              goto register_expr;
--
--      return 0;
--
--register_expr:
--      unregister_netdevice_notifier(&flow_offload_netdev_notifier);
--err:
--      return err;
-+      return nft_register_expr(&nft_flow_offload_type);
- }
- static void __exit nft_flow_offload_module_exit(void)
- {
-       nft_unregister_expr(&nft_flow_offload_type);
--      unregister_netdevice_notifier(&flow_offload_netdev_notifier);
- }
- module_init(nft_flow_offload_module_init);
diff --git a/target/linux/generic/pending-5.15/701-netfilter-nf_tables-ignore-EOPNOTSUPP-on-flowtable-d.patch b/target/linux/generic/pending-5.15/701-netfilter-nf_tables-ignore-EOPNOTSUPP-on-flowtable-d.patch
deleted file mode 100644 (file)
index 3037a72..0000000
+++ /dev/null
@@ -1,29 +0,0 @@
-From: Felix Fietkau <[email protected]>
-Date: Thu, 31 Aug 2023 21:48:38 +0200
-Subject: [PATCH] netfilter: nf_tables: ignore -EOPNOTSUPP on flowtable device
- offload setup
-
-On many embedded devices, it is common to configure flowtable offloading for
-a mix of different devices, some of which have hardware offload support and
-some of which don't.
-The current code limits the ability of user space to properly set up such a
-configuration by only allowing adding devices with hardware offload support to
-a offload-enabled flowtable.
-Given that offload-enabled flowtables also imply fallback to pure software
-offloading, this limitation makes little sense.
-Fix it by not bailing out when the offload setup returns -EOPNOTSUPP
-
-Signed-off-by: Felix Fietkau <[email protected]>
----
-
---- a/net/netfilter/nf_tables_api.c
-+++ b/net/netfilter/nf_tables_api.c
-@@ -7811,7 +7811,7 @@ static int nft_register_flowtable_net_ho
-               err = flowtable->data.type->setup(&flowtable->data,
-                                                 hook->ops.dev,
-                                                 FLOW_BLOCK_BIND);
--              if (err < 0)
-+              if (err < 0 && err != -EOPNOTSUPP)
-                       goto err_unregister_net_hooks;
-               err = nf_register_net_hook(net, &hook->ops);
diff --git a/target/linux/generic/pending-5.15/702-net-ethernet-mtk_eth_soc-enable-threaded-NAPI.patch b/target/linux/generic/pending-5.15/702-net-ethernet-mtk_eth_soc-enable-threaded-NAPI.patch
deleted file mode 100644 (file)
index 67cff4d..0000000
+++ /dev/null
@@ -1,41 +0,0 @@
-From: Felix Fietkau <[email protected]>
-Date: Mon, 21 Mar 2022 20:39:59 +0100
-Subject: [PATCH] net: ethernet: mtk_eth_soc: enable threaded NAPI
-
-This can improve performance under load by ensuring that NAPI processing is
-not pinned on CPU 0.
-
-Signed-off-by: Felix Fietkau <[email protected]>
----
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-@@ -3099,8 +3099,8 @@ static irqreturn_t mtk_handle_irq_rx(int
-       eth->rx_events++;
-       if (likely(napi_schedule_prep(&eth->rx_napi))) {
--              __napi_schedule(&eth->rx_napi);
-               mtk_rx_irq_disable(eth, eth->soc->txrx.rx_irq_done_mask);
-+              __napi_schedule(&eth->rx_napi);
-       }
-       return IRQ_HANDLED;
-@@ -3112,8 +3112,8 @@ static irqreturn_t mtk_handle_irq_tx(int
-       eth->tx_events++;
-       if (likely(napi_schedule_prep(&eth->tx_napi))) {
--              __napi_schedule(&eth->tx_napi);
-               mtk_tx_irq_disable(eth, MTK_TX_DONE_INT);
-+              __napi_schedule(&eth->tx_napi);
-       }
-       return IRQ_HANDLED;
-@@ -4887,6 +4887,8 @@ static int mtk_probe(struct platform_dev
-        * for NAPI to work
-        */
-       init_dummy_netdev(&eth->dummy_dev);
-+      eth->dummy_dev.threaded = 1;
-+      strcpy(eth->dummy_dev.name, "mtk_eth");
-       netif_napi_add(&eth->dummy_dev, &eth->tx_napi, mtk_napi_tx,
-                      NAPI_POLL_WEIGHT);
-       netif_napi_add(&eth->dummy_dev, &eth->rx_napi, mtk_napi_rx,
diff --git a/target/linux/generic/pending-5.15/703-phy-add-detach-callback-to-struct-phy_driver.patch b/target/linux/generic/pending-5.15/703-phy-add-detach-callback-to-struct-phy_driver.patch
deleted file mode 100644 (file)
index f93dca6..0000000
+++ /dev/null
@@ -1,38 +0,0 @@
-From: Gabor Juhos <[email protected]>
-Subject: generic: add detach callback to struct phy_driver
-
-lede-commit: fe61fc2d7d0b3fb348b502f68f98243b3ddf5867
-
-Signed-off-by: Gabor Juhos <[email protected]>
----
- drivers/net/phy/phy_device.c | 3 +++
- include/linux/phy.h          | 6 ++++++
- 2 files changed, 9 insertions(+)
-
---- a/drivers/net/phy/phy_device.c
-+++ b/drivers/net/phy/phy_device.c
-@@ -1751,6 +1751,9 @@ void phy_detach(struct phy_device *phyde
-       struct module *ndev_owner = NULL;
-       struct mii_bus *bus;
-+      if (phydev->drv && phydev->drv->detach)
-+              phydev->drv->detach(phydev);
-+
-       if (phydev->sysfs_links) {
-               if (dev)
-                       sysfs_remove_link(&dev->dev.kobj, "phydev");
---- a/include/linux/phy.h
-+++ b/include/linux/phy.h
-@@ -868,6 +868,12 @@ struct phy_driver {
-       /** @handle_interrupt: Override default interrupt handling */
-       irqreturn_t (*handle_interrupt)(struct phy_device *phydev);
-+      /*
-+       * Called before an ethernet device is detached
-+       * from the PHY.
-+       */
-+      void (*detach)(struct phy_device *phydev);
-+
-       /** @remove: Clears up any memory if needed */
-       void (*remove)(struct phy_device *phydev);
diff --git a/target/linux/generic/pending-5.15/704-01-v6.4-net-mvneta-fix-transmit-path-dma-unmapping-on-error.patch b/target/linux/generic/pending-5.15/704-01-v6.4-net-mvneta-fix-transmit-path-dma-unmapping-on-error.patch
deleted file mode 100644 (file)
index 287728b..0000000
+++ /dev/null
@@ -1,111 +0,0 @@
-From d6d80269cf5c79f9dfe7d69f8b41a72015c89748 Mon Sep 17 00:00:00 2001
-From: "Russell King (Oracle)" <[email protected]>
-Date: Mon, 3 Apr 2023 19:30:20 +0100
-Subject: [PATCH 1/5] net: mvneta: fix transmit path dma-unmapping on error
-
-The transmit code assumes that the transmit descriptors that are used
-begin with the first descriptor in the ring, but this may not be the
-case. Fix this by providing a new function that dma-unmaps a range of
-numbered descriptor entries, and use that to do the unmapping.
-
-Signed-off-by: Russell King (Oracle) <[email protected]>
----
- drivers/net/ethernet/marvell/mvneta.c | 53 +++++++++++++++++----------
- 1 file changed, 33 insertions(+), 20 deletions(-)
-
---- a/drivers/net/ethernet/marvell/mvneta.c
-+++ b/drivers/net/ethernet/marvell/mvneta.c
-@@ -2647,14 +2647,40 @@ mvneta_tso_put_data(struct net_device *d
-       return 0;
- }
-+static void mvneta_release_descs(struct mvneta_port *pp,
-+                               struct mvneta_tx_queue *txq,
-+                               int first, int num)
-+{
-+      int desc_idx, i;
-+
-+      desc_idx = first + num;
-+      if (desc_idx >= txq->size)
-+              desc_idx -= txq->size;
-+
-+      for (i = num; i >= 0; i--) {
-+              struct mvneta_tx_desc *tx_desc = txq->descs + desc_idx;
-+
-+              if (!IS_TSO_HEADER(txq, tx_desc->buf_phys_addr))
-+                      dma_unmap_single(pp->dev->dev.parent,
-+                                       tx_desc->buf_phys_addr,
-+                                       tx_desc->data_size,
-+                                       DMA_TO_DEVICE);
-+
-+              mvneta_txq_desc_put(txq);
-+
-+              if (desc_idx == 0)
-+                      desc_idx = txq->size;
-+              desc_idx -= 1;
-+      }
-+}
-+
- static int mvneta_tx_tso(struct sk_buff *skb, struct net_device *dev,
-                        struct mvneta_tx_queue *txq)
- {
-       int hdr_len, total_len, data_left;
--      int desc_count = 0;
-+      int first_desc, desc_count = 0;
-       struct mvneta_port *pp = netdev_priv(dev);
-       struct tso_t tso;
--      int i;
-       /* Count needed descriptors */
-       if ((txq->count + tso_count_descs(skb)) >= txq->size)
-@@ -2665,6 +2691,8 @@ static int mvneta_tx_tso(struct sk_buff
-               return 0;
-       }
-+      first_desc = txq->txq_put_index;
-+
-       /* Initialize the TSO handler, and prepare the first payload */
-       hdr_len = tso_start(skb, &tso);
-@@ -2705,15 +2733,7 @@ err_release:
-       /* Release all used data descriptors; header descriptors must not
-        * be DMA-unmapped.
-        */
--      for (i = desc_count - 1; i >= 0; i--) {
--              struct mvneta_tx_desc *tx_desc = txq->descs + i;
--              if (!IS_TSO_HEADER(txq, tx_desc->buf_phys_addr))
--                      dma_unmap_single(pp->dev->dev.parent,
--                                       tx_desc->buf_phys_addr,
--                                       tx_desc->data_size,
--                                       DMA_TO_DEVICE);
--              mvneta_txq_desc_put(txq);
--      }
-+      mvneta_release_descs(pp, txq, first_desc, desc_count - 1);
-       return 0;
- }
-@@ -2723,6 +2743,7 @@ static int mvneta_tx_frag_process(struct
- {
-       struct mvneta_tx_desc *tx_desc;
-       int i, nr_frags = skb_shinfo(skb)->nr_frags;
-+      int first_desc = txq->txq_put_index;
-       for (i = 0; i < nr_frags; i++) {
-               struct mvneta_tx_buf *buf = &txq->buf[txq->txq_put_index];
-@@ -2761,15 +2782,7 @@ error:
-       /* Release all descriptors that were used to map fragments of
-        * this packet, as well as the corresponding DMA mappings
-        */
--      for (i = i - 1; i >= 0; i--) {
--              tx_desc = txq->descs + i;
--              dma_unmap_single(pp->dev->dev.parent,
--                               tx_desc->buf_phys_addr,
--                               tx_desc->data_size,
--                               DMA_TO_DEVICE);
--              mvneta_txq_desc_put(txq);
--      }
--
-+      mvneta_release_descs(pp, txq, first_desc, i - 1);
-       return -ENOMEM;
- }
diff --git a/target/linux/generic/pending-5.15/704-02-v6.4-net-mvneta-mark-mapped-and-tso-buffers-separately.patch b/target/linux/generic/pending-5.15/704-02-v6.4-net-mvneta-mark-mapped-and-tso-buffers-separately.patch
deleted file mode 100644 (file)
index 4db3ffe..0000000
+++ /dev/null
@@ -1,42 +0,0 @@
-From e3c77d0a1b635d114c147fd2078afb57ed558b81 Mon Sep 17 00:00:00 2001
-From: "Russell King (Oracle)" <[email protected]>
-Date: Mon, 3 Apr 2023 19:30:25 +0100
-Subject: [PATCH 2/5] net: mvneta: mark mapped and tso buffers separately
-
-Mark dma-mapped skbs and TSO buffers separately, so we can use
-buf->type to identify their differences.
-
-Signed-off-by: Russell King (Oracle) <[email protected]>
----
- drivers/net/ethernet/marvell/mvneta.c | 6 ++++--
- 1 file changed, 4 insertions(+), 2 deletions(-)
-
---- a/drivers/net/ethernet/marvell/mvneta.c
-+++ b/drivers/net/ethernet/marvell/mvneta.c
-@@ -607,6 +607,7 @@ struct mvneta_rx_desc {
- #endif
- enum mvneta_tx_buf_type {
-+      MVNETA_TYPE_TSO,
-       MVNETA_TYPE_SKB,
-       MVNETA_TYPE_XDP_TX,
-       MVNETA_TYPE_XDP_NDO,
-@@ -1852,7 +1853,8 @@ static void mvneta_txq_bufs_free(struct
-                       dma_unmap_single(pp->dev->dev.parent,
-                                        tx_desc->buf_phys_addr,
-                                        tx_desc->data_size, DMA_TO_DEVICE);
--              if (buf->type == MVNETA_TYPE_SKB && buf->skb) {
-+              if ((buf->type == MVNETA_TYPE_TSO ||
-+                   buf->type == MVNETA_TYPE_SKB) && buf->skb) {
-                       bytes_compl += buf->skb->len;
-                       pkts_compl++;
-                       dev_kfree_skb_any(buf->skb);
-@@ -2607,7 +2609,7 @@ mvneta_tso_put_hdr(struct sk_buff *skb,
-       tx_desc->command |= MVNETA_TXD_F_DESC;
-       tx_desc->buf_phys_addr = txq->tso_hdrs_phys +
-                                txq->txq_put_index * TSO_HEADER_SIZE;
--      buf->type = MVNETA_TYPE_SKB;
-+      buf->type = MVNETA_TYPE_TSO;
-       buf->skb = NULL;
-       mvneta_txq_inc_put(txq);
diff --git a/target/linux/generic/pending-5.15/704-03-v6.4-net-mvneta-use-buf-type-to-determine-whether-to-dma-.patch b/target/linux/generic/pending-5.15/704-03-v6.4-net-mvneta-use-buf-type-to-determine-whether-to-dma-.patch
deleted file mode 100644 (file)
index 37511ff..0000000
+++ /dev/null
@@ -1,59 +0,0 @@
-From fe2abc1abc0dfc6c13fe8f189216f00dbbb33044 Mon Sep 17 00:00:00 2001
-From: "Russell King (Oracle)" <[email protected]>
-Date: Mon, 3 Apr 2023 19:30:30 +0100
-Subject: [PATCH 3/5] net: mvneta: use buf->type to determine whether to
- dma-unmap
-
-Now that we use a different buffer type for TSO headers, we can use
-buf->type to determine whether the original buffer was DMA-mapped or
-not. The rules are:
-
-       MVNETA_TYPE_XDP_TX - from a DMA pool, no unmap is required
-       MVNETA_TYPE_XDP_NDO - dma_map_single()'d
-       MVNETA_TYPE_SKB - normal skbuff, dma_map_single()'d
-       MVNETA_TYPE_TSO - from the TSO buffer area
-
-This means we only need to call dma_unmap_single() on the XDP_NDO and
-SKB types of buffer, and we no longer need the private IS_TSO_HEADER()
-which relies on the TSO region being contiguously allocated.
-
-Signed-off-by: Russell King (Oracle) <[email protected]>
----
- drivers/net/ethernet/marvell/mvneta.c | 11 ++++-------
- 1 file changed, 4 insertions(+), 7 deletions(-)
-
---- a/drivers/net/ethernet/marvell/mvneta.c
-+++ b/drivers/net/ethernet/marvell/mvneta.c
-@@ -334,10 +334,6 @@
-                        MVNETA_SKB_HEADROOM))
- #define MVNETA_MAX_RX_BUF_SIZE        (PAGE_SIZE - MVNETA_SKB_PAD)
--#define IS_TSO_HEADER(txq, addr) \
--      ((addr >= txq->tso_hdrs_phys) && \
--       (addr < txq->tso_hdrs_phys + txq->size * TSO_HEADER_SIZE))
--
- #define MVNETA_RX_GET_BM_POOL_ID(rxd) \
-       (((rxd)->status & MVNETA_RXD_BM_POOL_MASK) >> MVNETA_RXD_BM_POOL_SHIFT)
-@@ -1848,8 +1844,8 @@ static void mvneta_txq_bufs_free(struct
-               mvneta_txq_inc_get(txq);
--              if (!IS_TSO_HEADER(txq, tx_desc->buf_phys_addr) &&
--                  buf->type != MVNETA_TYPE_XDP_TX)
-+              if (buf->type == MVNETA_TYPE_XDP_NDO ||
-+                  buf->type == MVNETA_TYPE_SKB)
-                       dma_unmap_single(pp->dev->dev.parent,
-                                        tx_desc->buf_phys_addr,
-                                        tx_desc->data_size, DMA_TO_DEVICE);
-@@ -2661,8 +2657,9 @@ static void mvneta_release_descs(struct
-       for (i = num; i >= 0; i--) {
-               struct mvneta_tx_desc *tx_desc = txq->descs + desc_idx;
-+              struct mvneta_tx_buf *buf = &txq->buf[desc_idx];
--              if (!IS_TSO_HEADER(txq, tx_desc->buf_phys_addr))
-+              if (buf->type == MVNETA_TYPE_SKB)
-                       dma_unmap_single(pp->dev->dev.parent,
-                                        tx_desc->buf_phys_addr,
-                                        tx_desc->data_size,
diff --git a/target/linux/generic/pending-5.15/704-04-v6.4-net-mvneta-move-tso_build_hdr-into-mvneta_tso_put_hd.patch b/target/linux/generic/pending-5.15/704-04-v6.4-net-mvneta-move-tso_build_hdr-into-mvneta_tso_put_hd.patch
deleted file mode 100644 (file)
index 444b60f..0000000
+++ /dev/null
@@ -1,65 +0,0 @@
-From 210ca75d4949f1ace8ea53a75148806cc28224a0 Mon Sep 17 00:00:00 2001
-From: "Russell King (Oracle)" <[email protected]>
-Date: Mon, 3 Apr 2023 19:30:35 +0100
-Subject: [PATCH 4/5] net: mvneta: move tso_build_hdr() into
- mvneta_tso_put_hdr()
-
-Move tso_build_hdr() into mvneta_tso_put_hdr() so that all the TSO
-header building code is in one place.
-
-Signed-off-by: Russell King (Oracle) <[email protected]>
----
- drivers/net/ethernet/marvell/mvneta.c | 22 +++++++++++-----------
- 1 file changed, 11 insertions(+), 11 deletions(-)
-
---- a/drivers/net/ethernet/marvell/mvneta.c
-+++ b/drivers/net/ethernet/marvell/mvneta.c
-@@ -2592,19 +2592,24 @@ err_drop_frame:
-       return rx_done;
- }
--static inline void
--mvneta_tso_put_hdr(struct sk_buff *skb, struct mvneta_tx_queue *txq)
-+static void mvneta_tso_put_hdr(struct sk_buff *skb, struct mvneta_tx_queue *txq,
-+                             struct tso_t *tso, int size, bool is_last)
- {
--      int hdr_len = skb_transport_offset(skb) + tcp_hdrlen(skb);
-+      int tso_offset, hdr_len = skb_transport_offset(skb) + tcp_hdrlen(skb);
-       struct mvneta_tx_buf *buf = &txq->buf[txq->txq_put_index];
-       struct mvneta_tx_desc *tx_desc;
-+      char *hdr;
-+
-+      tso_offset = txq->txq_put_index * TSO_HEADER_SIZE;
-+
-+      hdr = txq->tso_hdrs + tso_offset;
-+      tso_build_hdr(skb, hdr, tso, size, is_last);
-       tx_desc = mvneta_txq_next_desc_get(txq);
-       tx_desc->data_size = hdr_len;
-       tx_desc->command = mvneta_skb_tx_csum(skb);
-       tx_desc->command |= MVNETA_TXD_F_DESC;
--      tx_desc->buf_phys_addr = txq->tso_hdrs_phys +
--                               txq->txq_put_index * TSO_HEADER_SIZE;
-+      tx_desc->buf_phys_addr = txq->tso_hdrs_phys + tso_offset;
-       buf->type = MVNETA_TYPE_TSO;
-       buf->skb = NULL;
-@@ -2697,17 +2702,12 @@ static int mvneta_tx_tso(struct sk_buff
-       total_len = skb->len - hdr_len;
-       while (total_len > 0) {
--              char *hdr;
--
-               data_left = min_t(int, skb_shinfo(skb)->gso_size, total_len);
-               total_len -= data_left;
-               desc_count++;
-               /* prepare packet headers: MAC + IP + TCP */
--              hdr = txq->tso_hdrs + txq->txq_put_index * TSO_HEADER_SIZE;
--              tso_build_hdr(skb, hdr, &tso, data_left, total_len == 0);
--
--              mvneta_tso_put_hdr(skb, txq);
-+              mvneta_tso_put_hdr(skb, txq, &tso, data_left, total_len == 0);
-               while (data_left > 0) {
-                       int size;
diff --git a/target/linux/generic/pending-5.15/704-05-v6.4-net-mvneta-allocate-TSO-header-DMA-memory-in-chunks.patch b/target/linux/generic/pending-5.15/704-05-v6.4-net-mvneta-allocate-TSO-header-DMA-memory-in-chunks.patch
deleted file mode 100644 (file)
index 395a0bf..0000000
+++ /dev/null
@@ -1,179 +0,0 @@
-From 58d50fb089da553023df5a05f5ae86feaacc7f24 Mon Sep 17 00:00:00 2001
-From: "Russell King (Oracle)" <[email protected]>
-Date: Mon, 3 Apr 2023 19:30:40 +0100
-Subject: [PATCH 5/5] net: mvneta: allocate TSO header DMA memory in chunks
-
-Now that we no longer need to check whether the DMA address is within
-the TSO header DMA memory range for the queue, we can allocate the TSO
-header DMA memory in chunks rather than one contiguous order-6 chunk,
-which can stress the kernel's memory subsystems to allocate.
-
-Instead, use order-1 (8k) allocations, which will result in 32 order-1
-pages containing 32 TSO headers.
-
-Signed-off-by: Russell King (Oracle) <[email protected]>
----
- drivers/net/ethernet/marvell/mvneta.c | 88 +++++++++++++++++++++------
- 1 file changed, 70 insertions(+), 18 deletions(-)
-
---- a/drivers/net/ethernet/marvell/mvneta.c
-+++ b/drivers/net/ethernet/marvell/mvneta.c
-@@ -314,6 +314,15 @@
- #define MVNETA_MAX_SKB_DESCS (MVNETA_MAX_TSO_SEGS * 2 + MAX_SKB_FRAGS)
-+/* The size of a TSO header page */
-+#define MVNETA_TSO_PAGE_SIZE (2 * PAGE_SIZE)
-+
-+/* Number of TSO headers per page. This should be a power of 2 */
-+#define MVNETA_TSO_PER_PAGE (MVNETA_TSO_PAGE_SIZE / TSO_HEADER_SIZE)
-+
-+/* Maximum number of TSO header pages */
-+#define MVNETA_MAX_TSO_PAGES (MVNETA_MAX_TXD / MVNETA_TSO_PER_PAGE)
-+
- /* descriptor aligned size */
- #define MVNETA_DESC_ALIGNED_SIZE      32
-@@ -656,10 +665,10 @@ struct mvneta_tx_queue {
-       int next_desc_to_proc;
-       /* DMA buffers for TSO headers */
--      char *tso_hdrs;
-+      char *tso_hdrs[MVNETA_MAX_TSO_PAGES];
-       /* DMA address of TSO headers */
--      dma_addr_t tso_hdrs_phys;
-+      dma_addr_t tso_hdrs_phys[MVNETA_MAX_TSO_PAGES];
-       /* Affinity mask for CPUs*/
-       cpumask_t affinity_mask;
-@@ -2592,24 +2601,71 @@ err_drop_frame:
-       return rx_done;
- }
-+static void mvneta_free_tso_hdrs(struct mvneta_port *pp,
-+                               struct mvneta_tx_queue *txq)
-+{
-+      struct device *dev = pp->dev->dev.parent;
-+      int i;
-+
-+      for (i = 0; i < MVNETA_MAX_TSO_PAGES; i++) {
-+              if (txq->tso_hdrs[i]) {
-+                      dma_free_coherent(dev, MVNETA_TSO_PAGE_SIZE,
-+                                        txq->tso_hdrs[i],
-+                                        txq->tso_hdrs_phys[i]);
-+                      txq->tso_hdrs[i] = NULL;
-+              }
-+      }
-+}
-+
-+static int mvneta_alloc_tso_hdrs(struct mvneta_port *pp,
-+                               struct mvneta_tx_queue *txq)
-+{
-+      struct device *dev = pp->dev->dev.parent;
-+      int i, num;
-+
-+      num = DIV_ROUND_UP(txq->size, MVNETA_TSO_PER_PAGE);
-+      for (i = 0; i < num; i++) {
-+              txq->tso_hdrs[i] = dma_alloc_coherent(dev, MVNETA_TSO_PAGE_SIZE,
-+                                                    &txq->tso_hdrs_phys[i],
-+                                                    GFP_KERNEL);
-+              if (!txq->tso_hdrs[i]) {
-+                      mvneta_free_tso_hdrs(pp, txq);
-+                      return -ENOMEM;
-+              }
-+      }
-+
-+      return 0;
-+}
-+
-+static char *mvneta_get_tso_hdr(struct mvneta_tx_queue *txq, dma_addr_t *dma)
-+{
-+      int index, offset;
-+
-+      index = txq->txq_put_index / MVNETA_TSO_PER_PAGE;
-+      offset = (txq->txq_put_index % MVNETA_TSO_PER_PAGE) * TSO_HEADER_SIZE;
-+
-+      *dma = txq->tso_hdrs_phys[index] + offset;
-+
-+      return txq->tso_hdrs[index] + offset;
-+}
-+
- static void mvneta_tso_put_hdr(struct sk_buff *skb, struct mvneta_tx_queue *txq,
-                              struct tso_t *tso, int size, bool is_last)
- {
--      int tso_offset, hdr_len = skb_transport_offset(skb) + tcp_hdrlen(skb);
-+      int hdr_len = skb_transport_offset(skb) + tcp_hdrlen(skb);
-       struct mvneta_tx_buf *buf = &txq->buf[txq->txq_put_index];
-       struct mvneta_tx_desc *tx_desc;
-+      dma_addr_t hdr_phys;
-       char *hdr;
--      tso_offset = txq->txq_put_index * TSO_HEADER_SIZE;
--
--      hdr = txq->tso_hdrs + tso_offset;
-+      hdr = mvneta_get_tso_hdr(txq, &hdr_phys);
-       tso_build_hdr(skb, hdr, tso, size, is_last);
-       tx_desc = mvneta_txq_next_desc_get(txq);
-       tx_desc->data_size = hdr_len;
-       tx_desc->command = mvneta_skb_tx_csum(skb);
-       tx_desc->command |= MVNETA_TXD_F_DESC;
--      tx_desc->buf_phys_addr = txq->tso_hdrs_phys + tso_offset;
-+      tx_desc->buf_phys_addr = hdr_phys;
-       buf->type = MVNETA_TYPE_TSO;
-       buf->skb = NULL;
-@@ -3401,7 +3457,7 @@ static void mvneta_rxq_deinit(struct mvn
- static int mvneta_txq_sw_init(struct mvneta_port *pp,
-                             struct mvneta_tx_queue *txq)
- {
--      int cpu;
-+      int cpu, err;
-       txq->size = pp->tx_ring_size;
-@@ -3426,11 +3482,9 @@ static int mvneta_txq_sw_init(struct mvn
-               return -ENOMEM;
-       /* Allocate DMA buffers for TSO MAC/IP/TCP headers */
--      txq->tso_hdrs = dma_alloc_coherent(pp->dev->dev.parent,
--                                         txq->size * TSO_HEADER_SIZE,
--                                         &txq->tso_hdrs_phys, GFP_KERNEL);
--      if (!txq->tso_hdrs)
--              return -ENOMEM;
-+      err = mvneta_alloc_tso_hdrs(pp, txq);
-+      if (err)
-+              return err;
-       /* Setup XPS mapping */
-       if (pp->neta_armada3700)
-@@ -3482,10 +3536,7 @@ static void mvneta_txq_sw_deinit(struct
-       kfree(txq->buf);
--      if (txq->tso_hdrs)
--              dma_free_coherent(pp->dev->dev.parent,
--                                txq->size * TSO_HEADER_SIZE,
--                                txq->tso_hdrs, txq->tso_hdrs_phys);
-+      mvneta_free_tso_hdrs(pp, txq);
-       if (txq->descs)
-               dma_free_coherent(pp->dev->dev.parent,
-                                 txq->size * MVNETA_DESC_ALIGNED_SIZE,
-@@ -3494,7 +3545,6 @@ static void mvneta_txq_sw_deinit(struct
-       netdev_tx_reset_queue(nq);
-       txq->buf               = NULL;
--      txq->tso_hdrs          = NULL;
-       txq->descs             = NULL;
-       txq->last_desc         = 0;
-       txq->next_desc_to_proc = 0;
-@@ -5543,6 +5593,8 @@ static int __init mvneta_driver_init(voi
- {
-       int ret;
-+      BUILD_BUG_ON_NOT_POWER_OF_2(MVNETA_TSO_PER_PAGE);
-+
-       ret = cpuhp_setup_state_multi(CPUHP_AP_ONLINE_DYN, "net/mvneta:online",
-                                     mvneta_cpu_online,
-                                     mvneta_cpu_down_prepare);
diff --git a/target/linux/generic/pending-5.15/705-net-dsa-tag_mtk-add-padding-for-tx-packets.patch b/target/linux/generic/pending-5.15/705-net-dsa-tag_mtk-add-padding-for-tx-packets.patch
deleted file mode 100644 (file)
index d444b20..0000000
+++ /dev/null
@@ -1,28 +0,0 @@
-From: Felix Fietkau <[email protected]>
-Date: Fri, 6 May 2022 21:38:42 +0200
-Subject: [PATCH] net: dsa: tag_mtk: add padding for tx packets
-
-Padding for transmitted packets needs to account for the special tag.
-With not enough padding, garbage bytes are inserted by the switch at the
-end of small packets.
-
-Fixes: 5cd8985a1909 ("net-next: dsa: add Mediatek tag RX/TX handler")
-Signed-off-by: Felix Fietkau <[email protected]>
----
-
---- a/net/dsa/tag_mtk.c
-+++ b/net/dsa/tag_mtk.c
-@@ -27,6 +27,13 @@ static struct sk_buff *mtk_tag_xmit(stru
-       skb_set_queue_mapping(skb, dp->index);
-+      /* The Ethernet switch we are interfaced with needs packets to be at
-+       * least 64 bytes (including FCS) otherwise their padding might be
-+       * corrupted. With tags enabled, we need to make sure that packets are
-+       * at least 68 bytes (including FCS and tag).
-+       */
-+      eth_skb_pad(skb);
-+
-       /* Build the special tag after the MAC Source Address. If VLAN header
-        * is present, it's required that VLAN header and special tag is
-        * being combined. Only in this way we can allow the switch can parse
diff --git a/target/linux/generic/pending-5.15/710-bridge-add-knob-for-filtering-rx-tx-BPDU-pack.patch b/target/linux/generic/pending-5.15/710-bridge-add-knob-for-filtering-rx-tx-BPDU-pack.patch
deleted file mode 100644 (file)
index fd1b79c..0000000
+++ /dev/null
@@ -1,174 +0,0 @@
-From: Felix Fietkau <[email protected]>
-Date: Fri, 27 Aug 2021 12:22:32 +0200
-Subject: [PATCH] bridge: add knob for filtering rx/tx BPDU packets on a port
-
-Some devices (e.g. wireless APs) can't have devices behind them be part of
-a bridge topology with redundant links, due to address limitations.
-Additionally, broadcast traffic on these devices is somewhat expensive, due to
-the low data rate and wakeups of clients in powersave mode.
-This knob can be used to ensure that BPDU packets are never sent or forwarded
-to/from these devices
-
-Signed-off-by: Felix Fietkau <[email protected]>
----
-
---- a/include/linux/if_bridge.h
-+++ b/include/linux/if_bridge.h
-@@ -58,6 +58,7 @@ struct br_ip_list {
- #define BR_MRP_LOST_CONT      BIT(18)
- #define BR_MRP_LOST_IN_CONT   BIT(19)
- #define BR_TX_FWD_OFFLOAD     BIT(20)
-+#define BR_BPDU_FILTER                BIT(21)
- #define BR_DEFAULT_AGEING_TIME        (300 * HZ)
---- a/net/bridge/br_forward.c
-+++ b/net/bridge/br_forward.c
-@@ -199,6 +199,7 @@ out:
- void br_flood(struct net_bridge *br, struct sk_buff *skb,
-             enum br_pkt_type pkt_type, bool local_rcv, bool local_orig)
- {
-+      const unsigned char *dest = eth_hdr(skb)->h_dest;
-       struct net_bridge_port *prev = NULL;
-       struct net_bridge_port *p;
-@@ -214,6 +215,10 @@ void br_flood(struct net_bridge *br, str
-               case BR_PKT_MULTICAST:
-                       if (!(p->flags & BR_MCAST_FLOOD) && skb->dev != br->dev)
-                               continue;
-+                      if ((p->flags & BR_BPDU_FILTER) &&
-+                          unlikely(is_link_local_ether_addr(dest) &&
-+                                   dest[5] == 0))
-+                              continue;
-                       break;
-               case BR_PKT_BROADCAST:
-                       if (!(p->flags & BR_BCAST_FLOOD) && skb->dev != br->dev)
---- a/net/bridge/br_input.c
-+++ b/net/bridge/br_input.c
-@@ -331,6 +331,8 @@ static rx_handler_result_t br_handle_fra
-               fwd_mask |= p->group_fwd_mask;
-               switch (dest[5]) {
-               case 0x00:      /* Bridge Group Address */
-+                      if (p->flags & BR_BPDU_FILTER)
-+                              goto drop;
-                       /* If STP is turned off,
-                          then must forward to keep loop detection */
-                       if (p->br->stp_enabled == BR_NO_STP ||
---- a/net/bridge/br_sysfs_if.c
-+++ b/net/bridge/br_sysfs_if.c
-@@ -240,6 +240,7 @@ BRPORT_ATTR_FLAG(multicast_flood, BR_MCA
- BRPORT_ATTR_FLAG(broadcast_flood, BR_BCAST_FLOOD);
- BRPORT_ATTR_FLAG(neigh_suppress, BR_NEIGH_SUPPRESS);
- BRPORT_ATTR_FLAG(isolated, BR_ISOLATED);
-+BRPORT_ATTR_FLAG(bpdu_filter, BR_BPDU_FILTER);
- #ifdef CONFIG_BRIDGE_IGMP_SNOOPING
- static ssize_t show_multicast_router(struct net_bridge_port *p, char *buf)
-@@ -292,6 +293,7 @@ static const struct brport_attribute *br
-       &brport_attr_group_fwd_mask,
-       &brport_attr_neigh_suppress,
-       &brport_attr_isolated,
-+      &brport_attr_bpdu_filter,
-       &brport_attr_backup_port,
-       NULL
- };
---- a/net/bridge/br_stp_bpdu.c
-+++ b/net/bridge/br_stp_bpdu.c
-@@ -80,7 +80,8 @@ void br_send_config_bpdu(struct net_brid
- {
-       unsigned char buf[35];
--      if (p->br->stp_enabled != BR_KERNEL_STP)
-+      if (p->br->stp_enabled != BR_KERNEL_STP ||
-+          (p->flags & BR_BPDU_FILTER))
-               return;
-       buf[0] = 0;
-@@ -127,7 +128,8 @@ void br_send_tcn_bpdu(struct net_bridge_
- {
-       unsigned char buf[4];
--      if (p->br->stp_enabled != BR_KERNEL_STP)
-+      if (p->br->stp_enabled != BR_KERNEL_STP ||
-+          (p->flags & BR_BPDU_FILTER))
-               return;
-       buf[0] = 0;
-@@ -172,6 +174,9 @@ void br_stp_rcv(const struct stp_proto *
-       if (!(br->dev->flags & IFF_UP))
-               goto out;
-+      if (p->flags & BR_BPDU_FILTER)
-+              goto out;
-+
-       if (p->state == BR_STATE_DISABLED)
-               goto out;
---- a/include/uapi/linux/if_link.h
-+++ b/include/uapi/linux/if_link.h
-@@ -536,6 +536,7 @@ enum {
-       IFLA_BRPORT_MRP_IN_OPEN,
-       IFLA_BRPORT_MCAST_EHT_HOSTS_LIMIT,
-       IFLA_BRPORT_MCAST_EHT_HOSTS_CNT,
-+      IFLA_BRPORT_BPDU_FILTER,
-       __IFLA_BRPORT_MAX
- };
- #define IFLA_BRPORT_MAX (__IFLA_BRPORT_MAX - 1)
---- a/net/bridge/br_netlink.c
-+++ b/net/bridge/br_netlink.c
-@@ -184,6 +184,7 @@ static inline size_t br_port_info_size(v
-               + nla_total_size(1)     /* IFLA_BRPORT_VLAN_TUNNEL */
-               + nla_total_size(1)     /* IFLA_BRPORT_NEIGH_SUPPRESS */
-               + nla_total_size(1)     /* IFLA_BRPORT_ISOLATED */
-+              + nla_total_size(1)     /* IFLA_BRPORT_BPDU_FILTER */
-               + nla_total_size(sizeof(struct ifla_bridge_id)) /* IFLA_BRPORT_ROOT_ID */
-               + nla_total_size(sizeof(struct ifla_bridge_id)) /* IFLA_BRPORT_BRIDGE_ID */
-               + nla_total_size(sizeof(u16))   /* IFLA_BRPORT_DESIGNATED_PORT */
-@@ -269,7 +270,8 @@ static int br_port_fill_attrs(struct sk_
-                                                         BR_MRP_LOST_CONT)) ||
-           nla_put_u8(skb, IFLA_BRPORT_MRP_IN_OPEN,
-                      !!(p->flags & BR_MRP_LOST_IN_CONT)) ||
--          nla_put_u8(skb, IFLA_BRPORT_ISOLATED, !!(p->flags & BR_ISOLATED)))
-+          nla_put_u8(skb, IFLA_BRPORT_ISOLATED, !!(p->flags & BR_ISOLATED)) ||
-+          nla_put_u8(skb, IFLA_BRPORT_BPDU_FILTER, !!(p->flags & BR_BPDU_FILTER)))
-               return -EMSGSIZE;
-       timerval = br_timer_value(&p->message_age_timer);
-@@ -829,6 +831,7 @@ static const struct nla_policy br_port_p
-       [IFLA_BRPORT_ISOLATED]  = { .type = NLA_U8 },
-       [IFLA_BRPORT_BACKUP_PORT] = { .type = NLA_U32 },
-       [IFLA_BRPORT_MCAST_EHT_HOSTS_LIMIT] = { .type = NLA_U32 },
-+      [IFLA_BRPORT_BPDU_FILTER] = { .type = NLA_U8 },
- };
- /* Change the state of the port and notify spanning tree */
-@@ -893,6 +896,7 @@ static int br_setport(struct net_bridge_
-       br_set_port_flag(p, tb, IFLA_BRPORT_VLAN_TUNNEL, BR_VLAN_TUNNEL);
-       br_set_port_flag(p, tb, IFLA_BRPORT_NEIGH_SUPPRESS, BR_NEIGH_SUPPRESS);
-       br_set_port_flag(p, tb, IFLA_BRPORT_ISOLATED, BR_ISOLATED);
-+      br_set_port_flag(p, tb, IFLA_BRPORT_BPDU_FILTER, BR_BPDU_FILTER);
-       changed_mask = old_flags ^ p->flags;
---- a/net/core/rtnetlink.c
-+++ b/net/core/rtnetlink.c
-@@ -55,7 +55,7 @@
- #include <net/net_namespace.h>
- #define RTNL_MAX_TYPE         50
--#define RTNL_SLAVE_MAX_TYPE   40
-+#define RTNL_SLAVE_MAX_TYPE   41
- struct rtnl_link {
-       rtnl_doit_func          doit;
-@@ -4739,7 +4739,9 @@ int ndo_dflt_bridge_getlink(struct sk_bu
-           brport_nla_put_flag(skb, flags, mask,
-                               IFLA_BRPORT_MCAST_FLOOD, BR_MCAST_FLOOD) ||
-           brport_nla_put_flag(skb, flags, mask,
--                              IFLA_BRPORT_BCAST_FLOOD, BR_BCAST_FLOOD)) {
-+                              IFLA_BRPORT_BCAST_FLOOD, BR_BCAST_FLOOD) ||
-+          brport_nla_put_flag(skb, flags, mask,
-+                              IFLA_BRPORT_BPDU_FILTER, BR_BPDU_FILTER)) {
-               nla_nest_cancel(skb, protinfo);
-               goto nla_put_failure;
-       }
diff --git a/target/linux/generic/pending-5.15/721-net-phy-realtek-rtl8221-allow-to-configure-SERDES-mo.patch b/target/linux/generic/pending-5.15/721-net-phy-realtek-rtl8221-allow-to-configure-SERDES-mo.patch
deleted file mode 100644 (file)
index c93fe42..0000000
+++ /dev/null
@@ -1,106 +0,0 @@
-From ace6abaa0f9203083fe4c0a6a74da2d96410b625 Mon Sep 17 00:00:00 2001
-From: Alexander Couzens <[email protected]>
-Date: Sat, 13 Aug 2022 12:49:33 +0200
-Subject: [PATCH 01/10] net: phy: realtek: rtl8221: allow to configure SERDES
- mode
-
-The rtl8221 supports multiple SERDES modes:
-- SGMII
-- 2500base-x
-- HiSGMII
-
-Further it supports rate adaption on SERDES links to allow
-slow ethernet speeds (10/100/1000mbit) to work on 2500base-x/HiSGMII
-links without reducing the SERDES speed.
-
-When operating without rate adapters the SERDES link will follow the
-ethernet speed.
-
-Signed-off-by: Alexander Couzens <[email protected]>
----
- drivers/net/phy/realtek.c | 48 +++++++++++++++++++++++++++++++++++++++
- 1 file changed, 48 insertions(+)
-
---- a/drivers/net/phy/realtek.c
-+++ b/drivers/net/phy/realtek.c
-@@ -53,6 +53,15 @@
-                                                RTL8201F_ISR_LINK)
- #define RTL8201F_IER                          0x13
-+#define RTL8221B_MMD_SERDES_CTRL              MDIO_MMD_VEND1
-+#define RTL8221B_MMD_PHY_CTRL                 MDIO_MMD_VEND2
-+#define RTL8221B_SERDES_OPTION                        0x697a
-+#define RTL8221B_SERDES_OPTION_MODE_MASK      GENMASK(5, 0)
-+#define RTL8221B_SERDES_OPTION_MODE_2500BASEX_SGMII   0
-+#define RTL8221B_SERDES_OPTION_MODE_HISGMII_SGMII     1
-+#define RTL8221B_SERDES_OPTION_MODE_2500BASEX         2
-+#define RTL8221B_SERDES_OPTION_MODE_HISGMII           3
-+
- #define RTL8366RB_POWER_SAVE                  0x15
- #define RTL8366RB_POWER_SAVE_ON                       BIT(12)
-@@ -841,6 +850,48 @@ static irqreturn_t rtl9000a_handle_inter
-       return IRQ_HANDLED;
- }
-+static int rtl8221b_config_init(struct phy_device *phydev)
-+{
-+      u16 option_mode;
-+
-+      switch (phydev->interface) {
-+      case PHY_INTERFACE_MODE_2500BASEX:
-+              if (!phydev->is_c45) {
-+                      option_mode = RTL8221B_SERDES_OPTION_MODE_2500BASEX;
-+                      break;
-+              }
-+              fallthrough;
-+      case PHY_INTERFACE_MODE_SGMII:
-+              option_mode = RTL8221B_SERDES_OPTION_MODE_2500BASEX_SGMII;
-+              break;
-+      default:
-+              return 0;
-+      }
-+
-+      phy_write_mmd(phydev, RTL8221B_MMD_SERDES_CTRL,
-+                    0x75f3, 0);
-+
-+      phy_modify_mmd_changed(phydev, RTL8221B_MMD_SERDES_CTRL,
-+                             RTL8221B_SERDES_OPTION,
-+                             RTL8221B_SERDES_OPTION_MODE_MASK, option_mode);
-+      switch (option_mode) {
-+      case RTL8221B_SERDES_OPTION_MODE_2500BASEX_SGMII:
-+      case RTL8221B_SERDES_OPTION_MODE_2500BASEX:
-+              phy_write_mmd(phydev, RTL8221B_MMD_SERDES_CTRL, 0x6a04, 0x0503);
-+              phy_write_mmd(phydev, RTL8221B_MMD_SERDES_CTRL, 0x6f10, 0xd455);
-+              phy_write_mmd(phydev, RTL8221B_MMD_SERDES_CTRL, 0x6f11, 0x8020);
-+              break;
-+      case RTL8221B_SERDES_OPTION_MODE_HISGMII_SGMII:
-+      case RTL8221B_SERDES_OPTION_MODE_HISGMII:
-+              phy_write_mmd(phydev, RTL8221B_MMD_SERDES_CTRL, 0x6a04, 0x0503);
-+              phy_write_mmd(phydev, RTL8221B_MMD_SERDES_CTRL, 0x6f10, 0xd433);
-+              phy_write_mmd(phydev, RTL8221B_MMD_SERDES_CTRL, 0x6f11, 0x8020);
-+              break;
-+      }
-+
-+      return 0;
-+}
-+
- static struct phy_driver realtek_drvs[] = {
-       {
-               PHY_ID_MATCH_EXACT(0x00008201),
-@@ -981,6 +1032,7 @@ static struct phy_driver realtek_drvs[]
-               PHY_ID_MATCH_EXACT(0x001cc849),
-               .name           = "RTL8221B-VB-CG 2.5Gbps PHY",
-               .get_features   = rtl822x_get_features,
-+              .config_init    = rtl8221b_config_init,
-               .config_aneg    = rtl822x_config_aneg,
-               .read_status    = rtl822x_read_status,
-               .suspend        = genphy_suspend,
-@@ -992,6 +1044,7 @@ static struct phy_driver realtek_drvs[]
-               .name           = "RTL8221B-VM-CG 2.5Gbps PHY",
-               .get_features   = rtl822x_get_features,
-               .config_aneg    = rtl822x_config_aneg,
-+              .config_init    = rtl8221b_config_init,
-               .read_status    = rtl822x_read_status,
-               .suspend        = genphy_suspend,
-               .resume         = rtlgen_resume,
diff --git a/target/linux/generic/pending-5.15/722-net-phy-realtek-support-switching-between-SGMII-and-.patch b/target/linux/generic/pending-5.15/722-net-phy-realtek-support-switching-between-SGMII-and-.patch
deleted file mode 100644 (file)
index 211a8ed..0000000
+++ /dev/null
@@ -1,61 +0,0 @@
-From 312753d0aadba0f58841ae513b80fdbabc887523 Mon Sep 17 00:00:00 2001
-From: Chukun Pan <[email protected]>
-Date: Wed, 8 Feb 2023 16:32:18 +0800
-Subject: [PATCH] net: phy: realtek: support switching between SGMII and
- 2500BASE-X for RTL822x series
-
-After commit ace6aba ("net: phy: realtek: rtl8221: allow to configure
-SERDES mode"), the rtl8221 phy can work in SGMII and 2500base-x modes
-respectively. So add interface automatic switching for rtl8221 phy to
-match various wire speeds.
-
-Signed-off-by: Chukun Pan <[email protected]>
----
- drivers/net/phy/realtek.c | 26 ++++++++++++++++++++++++--
- 1 file changed, 24 insertions(+), 2 deletions(-)
-
---- a/drivers/net/phy/realtek.c
-+++ b/drivers/net/phy/realtek.c
-@@ -676,6 +676,25 @@ static int rtl822x_config_aneg(struct ph
-       return __genphy_config_aneg(phydev, ret);
- }
-+static void rtl822x_update_interface(struct phy_device *phydev)
-+{
-+      /* Automatically switch SERDES interface between
-+       * SGMII and 2500-BaseX according to speed.
-+       */
-+      switch (phydev->speed) {
-+      case SPEED_2500:
-+              phydev->interface = PHY_INTERFACE_MODE_2500BASEX;
-+              break;
-+      case SPEED_1000:
-+      case SPEED_100:
-+      case SPEED_10:
-+              phydev->interface = PHY_INTERFACE_MODE_SGMII;
-+              break;
-+      default:
-+              break;
-+      }
-+}
-+
- static int rtl822x_read_status(struct phy_device *phydev)
- {
-       int ret;
-@@ -694,11 +713,14 @@ static int rtl822x_read_status(struct ph
-                       phydev->lp_advertising, lpadv & RTL_LPADV_2500FULL);
-       }
--      ret = genphy_read_status(phydev);
-+      ret = rtlgen_read_status(phydev);
-       if (ret < 0)
-               return ret;
--      return rtlgen_get_speed(phydev);
-+      if (phydev->is_c45 && phydev->link)
-+              rtl822x_update_interface(phydev);
-+
-+      return 0;
- }
- static bool rtlgen_supports_2_5gbps(struct phy_device *phydev)
diff --git a/target/linux/generic/pending-5.15/723-net-mt7531-ensure-all-MACs-are-powered-down-before-r.patch b/target/linux/generic/pending-5.15/723-net-mt7531-ensure-all-MACs-are-powered-down-before-r.patch
deleted file mode 100644 (file)
index 792135b..0000000
+++ /dev/null
@@ -1,28 +0,0 @@
-From 3fb8841513c4ec3a2e5d366df86230c45f239a57 Mon Sep 17 00:00:00 2001
-From: Alexander Couzens <[email protected]>
-Date: Sat, 13 Aug 2022 13:08:22 +0200
-Subject: [PATCH 03/10] net: mt7531: ensure all MACs are powered down before
- reset
-
-The datasheet [1] explicit describes it as requirement for a reset.
-
-[1] MT7531 Reference Manual for Development Board rev 1.0, page 735
-
-Signed-off-by: Alexander Couzens <[email protected]>
----
- drivers/net/dsa/mt7530.c | 6 +++++-
- 1 file changed, 5 insertions(+), 1 deletion(-)
-
---- a/drivers/net/dsa/mt7530.c
-+++ b/drivers/net/dsa/mt7530.c
-@@ -2680,6 +2680,10 @@ mt7531_setup(struct dsa_switch *ds)
-               return -ENODEV;
-       }
-+      /* all MACs must be forced link-down before sw reset */
-+      for (i = 0; i < MT7530_NUM_PORTS; i++)
-+              mt7530_write(priv, MT7530_PMCR_P(i), MT7531_FORCE_LNK);
-+
-       /* Reset the switch through internal reset */
-       mt7530_write(priv, MT7530_SYS_CTRL,
-                    SYS_CTRL_PHY_RST | SYS_CTRL_SW_RST |
diff --git a/target/linux/generic/pending-5.15/724-net-phy-realtek-use-genphy_soft_reset-for-2.5G-PHYs.patch b/target/linux/generic/pending-5.15/724-net-phy-realtek-use-genphy_soft_reset-for-2.5G-PHYs.patch
deleted file mode 100644 (file)
index 6941818..0000000
+++ /dev/null
@@ -1,65 +0,0 @@
-From 85cd45580f5e3b26068cccb7d6173f200e754dc0 Mon Sep 17 00:00:00 2001
-From: Daniel Golle <[email protected]>
-Date: Sun, 2 Apr 2023 23:56:16 +0100
-Subject: [PATCH 1/2] net: phy: realtek: use genphy_soft_reset for 2.5G PHYs
-
-Some vendor bootloaders do weird things with those PHYs which result in
-link modes being reported wrongly. Start from a clean sheet by resetting
-the PHY.
-
-Reported-by: Yevhen Kolomeiko <[email protected]>
-Signed-off-by: Daniel Golle <[email protected]>
----
- drivers/net/phy/realtek.c | 6 ++++++
- 1 file changed, 6 insertions(+)
-
---- a/drivers/net/phy/realtek.c
-+++ b/drivers/net/phy/realtek.c
-@@ -1018,6 +1018,7 @@ static struct phy_driver realtek_drvs[]
-               .write_page     = rtl821x_write_page,
-               .read_mmd       = rtl822x_read_mmd,
-               .write_mmd      = rtl822x_write_mmd,
-+              .soft_reset     = genphy_soft_reset,
-       }, {
-               PHY_ID_MATCH_EXACT(0x001cc840),
-               .name           = "RTL8226B_RTL8221B 2.5Gbps PHY",
-@@ -1030,6 +1031,7 @@ static struct phy_driver realtek_drvs[]
-               .write_page     = rtl821x_write_page,
-               .read_mmd       = rtl822x_read_mmd,
-               .write_mmd      = rtl822x_write_mmd,
-+              .soft_reset     = genphy_soft_reset,
-       }, {
-               PHY_ID_MATCH_EXACT(0x001cc838),
-               .name           = "RTL8226-CG 2.5Gbps PHY",
-@@ -1040,6 +1042,7 @@ static struct phy_driver realtek_drvs[]
-               .resume         = rtlgen_resume,
-               .read_page      = rtl821x_read_page,
-               .write_page     = rtl821x_write_page,
-+              .soft_reset     = genphy_soft_reset,
-       }, {
-               PHY_ID_MATCH_EXACT(0x001cc848),
-               .name           = "RTL8226B-CG_RTL8221B-CG 2.5Gbps PHY",
-@@ -1050,6 +1053,7 @@ static struct phy_driver realtek_drvs[]
-               .resume         = rtlgen_resume,
-               .read_page      = rtl821x_read_page,
-               .write_page     = rtl821x_write_page,
-+              .soft_reset     = genphy_soft_reset,
-       }, {
-               PHY_ID_MATCH_EXACT(0x001cc849),
-               .name           = "RTL8221B-VB-CG 2.5Gbps PHY",
-@@ -1061,6 +1065,7 @@ static struct phy_driver realtek_drvs[]
-               .resume         = rtlgen_resume,
-               .read_page      = rtl821x_read_page,
-               .write_page     = rtl821x_write_page,
-+              .soft_reset     = genphy_soft_reset,
-       }, {
-               PHY_ID_MATCH_EXACT(0x001cc84a),
-               .name           = "RTL8221B-VM-CG 2.5Gbps PHY",
-@@ -1072,6 +1077,7 @@ static struct phy_driver realtek_drvs[]
-               .resume         = rtlgen_resume,
-               .read_page      = rtl821x_read_page,
-               .write_page     = rtl821x_write_page,
-+              .soft_reset     = genphy_soft_reset,
-       }, {
-               PHY_ID_MATCH_EXACT(0x001cc961),
-               .name           = "RTL8366RB Gigabit Ethernet",
diff --git a/target/linux/generic/pending-5.15/725-net-phy-realtek-disable-SGMII-in-band-AN-for-2-5G-PHYs.patch b/target/linux/generic/pending-5.15/725-net-phy-realtek-disable-SGMII-in-band-AN-for-2-5G-PHYs.patch
deleted file mode 100644 (file)
index 1370c63..0000000
+++ /dev/null
@@ -1,43 +0,0 @@
-From 2b1b8c4c215af7988136401c902338d091d408a1 Mon Sep 17 00:00:00 2001
-From: Daniel Golle <[email protected]>
-Date: Mon, 3 Apr 2023 01:21:57 +0300
-Subject: [PATCH 2/2] net: phy: realtek: disable SGMII in-band AN for 2.5G PHYs
-
-MAC drivers don't use SGMII in-band autonegotiation unless told to do so
-in device tree using 'managed = "in-band-status"'. When using MDIO to
-access a PHY, in-band-status is unneeded as we have link-status via
-MDIO. Switch off SGMII in-band autonegotiation using magic values.
-
-Reported-by: Chen Minqiang <[email protected]>
-Reported-by: Chukun Pan <[email protected]>
-Reported-by: Yevhen Kolomeiko <[email protected]>
-Tested-by: Yevhen Kolomeiko <[email protected]>
-Signed-off-by: Daniel Golle <[email protected]>
----
- drivers/net/phy/realtek.c | 8 ++++++++
- 1 file changed, 8 insertions(+)
-
---- a/drivers/net/phy/realtek.c
-+++ b/drivers/net/phy/realtek.c
-@@ -875,6 +875,7 @@ static irqreturn_t rtl9000a_handle_inter
- static int rtl8221b_config_init(struct phy_device *phydev)
- {
-       u16 option_mode;
-+      int val;
-       switch (phydev->interface) {
-       case PHY_INTERFACE_MODE_2500BASEX:
-@@ -911,6 +912,13 @@ static int rtl8221b_config_init(struct p
-               break;
-       }
-+      /* Disable SGMII AN */
-+      phy_write_mmd(phydev, RTL8221B_MMD_SERDES_CTRL, 0x7588, 0x2);
-+      phy_write_mmd(phydev, RTL8221B_MMD_SERDES_CTRL, 0x7589, 0x71d0);
-+      phy_write_mmd(phydev, RTL8221B_MMD_SERDES_CTRL, 0x7587, 0x3);
-+      phy_read_mmd_poll_timeout(phydev, RTL8221B_MMD_SERDES_CTRL, 0x7587,
-+                                val, !(val & BIT(0)), 500, 100000, false);
-+
-       return 0;
- }
diff --git a/target/linux/generic/pending-5.15/726-net-phy-realtek-make-sure-paged-read-is-protected-by.patch b/target/linux/generic/pending-5.15/726-net-phy-realtek-make-sure-paged-read-is-protected-by.patch
deleted file mode 100644 (file)
index 31f0622..0000000
+++ /dev/null
@@ -1,35 +0,0 @@
-From 4dd2cc9b91ecb25f278a2c55e07e6455e9000e6b Mon Sep 17 00:00:00 2001
-From: Daniel Golle <[email protected]>
-Date: Sat, 22 Apr 2023 01:21:14 +0100
-Subject: [PATCH] net: phy: realtek: make sure paged read is protected by mutex
-
-As we cannot rely on phy_read_paged function before the PHY is
-identified, the paged read in rtlgen_supports_2_5gbps needs to be open
-coded as it is being called by the match_phy_device function, ie. before
-.read_page and .write_page have been populated.
-
-Make sure it is also protected by the MDIO bus mutex and use
-rtl821x_write_page instead of 3 individually locked MDIO bus operations.
-
-Signed-off-by: Daniel Golle <[email protected]>
----
- drivers/net/phy/realtek.c | 8 +++++---
- 1 file changed, 5 insertions(+), 3 deletions(-)
-
---- a/drivers/net/phy/realtek.c
-+++ b/drivers/net/phy/realtek.c
-@@ -727,9 +727,11 @@ static bool rtlgen_supports_2_5gbps(stru
- {
-       int val;
--      phy_write(phydev, RTL821x_PAGE_SELECT, 0xa61);
--      val = phy_read(phydev, 0x13);
--      phy_write(phydev, RTL821x_PAGE_SELECT, 0);
-+      mutex_lock(&phydev->mdio.bus->mdio_lock);
-+      rtl821x_write_page(phydev, 0xa61);
-+      val = __phy_read(phydev, 0x13);
-+      rtl821x_write_page(phydev, 0);
-+      mutex_unlock(&phydev->mdio.bus->mdio_lock);
-       return val >= 0 && val & RTL_SUPPORTS_2500FULL;
- }
diff --git a/target/linux/generic/pending-5.15/727-net-phy-realtek-use-inline-functions-for-10GbE-adver.patch b/target/linux/generic/pending-5.15/727-net-phy-realtek-use-inline-functions-for-10GbE-adver.patch
deleted file mode 100644 (file)
index a24b4dd..0000000
+++ /dev/null
@@ -1,60 +0,0 @@
-From 92c8b9d558160d94b981dd8a2b9c47657627ffdc Mon Sep 17 00:00:00 2001
-From: Daniel Golle <[email protected]>
-Date: Sat, 22 Apr 2023 01:23:08 +0100
-Subject: [PATCH 2/3] net: phy: realtek: use inline functions for 10GbE
- advertisement
-
-Use existing generic inline functions to encode local advertisement
-of 10GbE link modes as well as to decode link-partner advertisement.
-
-Signed-off-by: Daniel Golle <[email protected]>
----
- drivers/net/phy/realtek.c | 22 +++++-----------------
- 1 file changed, 5 insertions(+), 17 deletions(-)
-
---- a/drivers/net/phy/realtek.c
-+++ b/drivers/net/phy/realtek.c
-@@ -68,10 +68,6 @@
- #define RTL_SUPPORTS_5000FULL                 BIT(14)
- #define RTL_SUPPORTS_2500FULL                 BIT(13)
- #define RTL_SUPPORTS_10000FULL                        BIT(0)
--#define RTL_ADV_2500FULL                      BIT(7)
--#define RTL_LPADV_10000FULL                   BIT(11)
--#define RTL_LPADV_5000FULL                    BIT(6)
--#define RTL_LPADV_2500FULL                    BIT(5)
- #define RTL9000A_GINMR                                0x14
- #define RTL9000A_GINMR_LINK_STATUS            BIT(4)
-@@ -661,14 +657,11 @@ static int rtl822x_config_aneg(struct ph
-       int ret = 0;
-       if (phydev->autoneg == AUTONEG_ENABLE) {
--              u16 adv2500 = 0;
--
--              if (linkmode_test_bit(ETHTOOL_LINK_MODE_2500baseT_Full_BIT,
--                                    phydev->advertising))
--                      adv2500 = RTL_ADV_2500FULL;
--
-               ret = phy_modify_paged_changed(phydev, 0xa5d, 0x12,
--                                             RTL_ADV_2500FULL, adv2500);
-+                                             MDIO_AN_10GBT_CTRL_ADV10G |
-+                                             MDIO_AN_10GBT_CTRL_ADV5G |
-+                                             MDIO_AN_10GBT_CTRL_ADV2_5G,
-+                      linkmode_adv_to_mii_10gbt_adv_t(phydev->advertising));
-               if (ret < 0)
-                       return ret;
-       }
-@@ -705,12 +698,7 @@ static int rtl822x_read_status(struct ph
-               if (lpadv < 0)
-                       return lpadv;
--              linkmode_mod_bit(ETHTOOL_LINK_MODE_10000baseT_Full_BIT,
--                      phydev->lp_advertising, lpadv & RTL_LPADV_10000FULL);
--              linkmode_mod_bit(ETHTOOL_LINK_MODE_5000baseT_Full_BIT,
--                      phydev->lp_advertising, lpadv & RTL_LPADV_5000FULL);
--              linkmode_mod_bit(ETHTOOL_LINK_MODE_2500baseT_Full_BIT,
--                      phydev->lp_advertising, lpadv & RTL_LPADV_2500FULL);
-+              mii_10gbt_stat_mod_linkmode_lpa_t(phydev->lp_advertising, lpadv);
-       }
-       ret = rtlgen_read_status(phydev);
diff --git a/target/linux/generic/pending-5.15/728-net-phy-realtek-check-validity-of-10GbE-link-partner.patch b/target/linux/generic/pending-5.15/728-net-phy-realtek-check-validity-of-10GbE-link-partner.patch
deleted file mode 100644 (file)
index 084ee4b..0000000
+++ /dev/null
@@ -1,28 +0,0 @@
-From 929bb4d3cfbc7878326c0771a01a636d49c54b40 Mon Sep 17 00:00:00 2001
-From: Daniel Golle <[email protected]>
-Date: Sat, 22 Apr 2023 01:25:39 +0100
-Subject: [PATCH 3/3] net: phy: realtek: check validity of 10GbE link-partner
- advertisement
-
-Only use link-partner advertisement bits for 10GbE modes if they are
-actually valid. Check LOCALOK and REMOTEOK bits and clear 10GbE modes
-unless both of them are set.
-
-Signed-off-by: Daniel Golle <[email protected]>
----
- drivers/net/phy/realtek.c | 4 ++++
- 1 file changed, 4 insertions(+)
-
---- a/drivers/net/phy/realtek.c
-+++ b/drivers/net/phy/realtek.c
-@@ -698,6 +698,10 @@ static int rtl822x_read_status(struct ph
-               if (lpadv < 0)
-                       return lpadv;
-+              if (!(lpadv & MDIO_AN_10GBT_STAT_REMOK) ||
-+                  !(lpadv & MDIO_AN_10GBT_STAT_LOCOK))
-+                      lpadv = 0;
-+
-               mii_10gbt_stat_mod_linkmode_lpa_t(phydev->lp_advertising, lpadv);
-       }
diff --git a/target/linux/generic/pending-5.15/729-net-phy-realtek-introduce-rtl822x_probe.patch b/target/linux/generic/pending-5.15/729-net-phy-realtek-introduce-rtl822x_probe.patch
deleted file mode 100644 (file)
index cea3511..0000000
+++ /dev/null
@@ -1,84 +0,0 @@
-From 9155098547fb1172d4fa536f3f6bc9d42f59d08c Mon Sep 17 00:00:00 2001
-From: Daniel Golle <[email protected]>
-Date: Sat, 22 Apr 2023 03:26:01 +0100
-Subject: [PATCH] net: phy: realtek: setup ALDPS on RTL822x
-
-Setup Link Down Power Saving Mode according the DTS property
-just like for RTL821x 1GE PHYs.
-
-Signed-off-by: Daniel Golle <[email protected]>
----
- drivers/net/phy/realtek.c | 11 +++++++++++
- 1 file changed, 11 insertions(+)
-
---- a/drivers/net/phy/realtek.c
-+++ b/drivers/net/phy/realtek.c
-@@ -62,6 +62,10 @@
- #define RTL8221B_SERDES_OPTION_MODE_2500BASEX         2
- #define RTL8221B_SERDES_OPTION_MODE_HISGMII           3
-+#define RTL8221B_PHYCR1                               0xa430
-+#define RTL8221B_PHYCR1_ALDPS_EN              BIT(2)
-+#define RTL8221B_PHYCR1_ALDPS_XTAL_OFF_EN     BIT(12)
-+
- #define RTL8366RB_POWER_SAVE                  0x15
- #define RTL8366RB_POWER_SAVE_ON                       BIT(12)
-@@ -740,6 +744,25 @@ static int rtl8226_match_phy_device(stru
-              rtlgen_supports_2_5gbps(phydev);
- }
-+static int rtl822x_probe(struct phy_device *phydev)
-+{
-+      struct device *dev = &phydev->mdio.dev;
-+      int val;
-+
-+      val = phy_read_mmd(phydev, RTL8221B_MMD_SERDES_CTRL, RTL8221B_PHYCR1);
-+      if (val < 0)
-+              return val;
-+
-+      if (of_property_read_bool(dev->of_node, "realtek,aldps-enable"))
-+              val |= RTL8221B_PHYCR1_ALDPS_EN | RTL8221B_PHYCR1_ALDPS_XTAL_OFF_EN;
-+      else
-+              val &= ~(RTL8221B_PHYCR1_ALDPS_EN | RTL8221B_PHYCR1_ALDPS_XTAL_OFF_EN);
-+
-+      phy_write_mmd(phydev, RTL8221B_MMD_SERDES_CTRL, RTL8221B_PHYCR1, val);
-+
-+      return 0;
-+}
-+
- static int rtlgen_resume(struct phy_device *phydev)
- {
-       int ret = genphy_resume(phydev);
-@@ -1039,6 +1062,7 @@ static struct phy_driver realtek_drvs[]
-               .name           = "RTL8226-CG 2.5Gbps PHY",
-               .get_features   = rtl822x_get_features,
-               .config_aneg    = rtl822x_config_aneg,
-+              .probe          = rtl822x_probe,
-               .read_status    = rtl822x_read_status,
-               .suspend        = genphy_suspend,
-               .resume         = rtlgen_resume,
-@@ -1050,6 +1074,7 @@ static struct phy_driver realtek_drvs[]
-               .name           = "RTL8226B-CG_RTL8221B-CG 2.5Gbps PHY",
-               .get_features   = rtl822x_get_features,
-               .config_aneg    = rtl822x_config_aneg,
-+              .probe          = rtl822x_probe,
-               .read_status    = rtl822x_read_status,
-               .suspend        = genphy_suspend,
-               .resume         = rtlgen_resume,
-@@ -1062,6 +1087,7 @@ static struct phy_driver realtek_drvs[]
-               .get_features   = rtl822x_get_features,
-               .config_init    = rtl8221b_config_init,
-               .config_aneg    = rtl822x_config_aneg,
-+              .probe          = rtl822x_probe,
-               .read_status    = rtl822x_read_status,
-               .suspend        = genphy_suspend,
-               .resume         = rtlgen_resume,
-@@ -1074,6 +1100,7 @@ static struct phy_driver realtek_drvs[]
-               .get_features   = rtl822x_get_features,
-               .config_aneg    = rtl822x_config_aneg,
-               .config_init    = rtl8221b_config_init,
-+              .probe          = rtl822x_probe,
-               .read_status    = rtl822x_read_status,
-               .suspend        = genphy_suspend,
-               .resume         = rtlgen_resume,
diff --git a/target/linux/generic/pending-5.15/730-net-phy-realtek-detect-early-version-of-RTL8221B.patch b/target/linux/generic/pending-5.15/730-net-phy-realtek-detect-early-version-of-RTL8221B.patch
deleted file mode 100644 (file)
index e3edfa4..0000000
+++ /dev/null
@@ -1,71 +0,0 @@
-From 0de82310d2b32e78ff79d42c08b1122a6ede3778 Mon Sep 17 00:00:00 2001
-From: Daniel Golle <[email protected]>
-Date: Sun, 30 Apr 2023 00:15:41 +0100
-Subject: [PATCH] net: phy: realtek: detect early version of RTL8221B
-
-Early versions (?) of the RTL8221B PHY cannot be identified in a regular
-Clause-45 bus scan as the PHY doesn't report the implemented MMDs
-correctly but returns 0 instead.
-Implement custom identify function using the PKGID instead of iterating
-over the implemented MMDs.
-
-Signed-off-by: Daniel Golle <[email protected]>
-
---- a/drivers/net/phy/realtek.c
-+++ b/drivers/net/phy/realtek.c
-@@ -79,6 +79,7 @@
- #define RTLGEN_SPEED_MASK                     0x0630
- #define RTL_GENERIC_PHYID                     0x001cc800
-+#define RTL_8221B_VB_CG_PHYID                 0x001cc849
- MODULE_DESCRIPTION("Realtek PHY driver");
- MODULE_AUTHOR("Johnson Leung");
-@@ -744,6 +745,38 @@ static int rtl8226_match_phy_device(stru
-              rtlgen_supports_2_5gbps(phydev);
- }
-+static int rtl8221b_vb_cg_match_phy_device(struct phy_device *phydev)
-+{
-+      int val;
-+      u32 id;
-+
-+      if (phydev->mdio.bus->probe_capabilities >= MDIOBUS_C45) {
-+              val = phy_read_mmd(phydev, MDIO_MMD_PMAPMD, MDIO_PKGID1);
-+              if (val < 0)
-+                      return 0;
-+
-+              id = val << 16;
-+              val = phy_read_mmd(phydev, MDIO_MMD_PMAPMD, MDIO_PKGID2);
-+              if (val < 0)
-+                      return 0;
-+
-+              id |= val;
-+      } else {
-+              val = phy_read(phydev, MII_PHYSID1);
-+              if (val < 0)
-+                      return 0;
-+
-+              id = val << 16;
-+              val = phy_read(phydev, MII_PHYSID2);
-+              if (val < 0)
-+                      return 0;
-+
-+              id |= val;
-+      }
-+
-+      return (id == RTL_8221B_VB_CG_PHYID);
-+}
-+
- static int rtl822x_probe(struct phy_device *phydev)
- {
-       struct device *dev = &phydev->mdio.dev;
-@@ -1082,7 +1115,7 @@ static struct phy_driver realtek_drvs[]
-               .write_page     = rtl821x_write_page,
-               .soft_reset     = genphy_soft_reset,
-       }, {
--              PHY_ID_MATCH_EXACT(0x001cc849),
-+              .match_phy_device = rtl8221b_vb_cg_match_phy_device,
-               .name           = "RTL8221B-VB-CG 2.5Gbps PHY",
-               .get_features   = rtl822x_get_features,
-               .config_init    = rtl8221b_config_init,
diff --git a/target/linux/generic/pending-5.15/731-net-phy-realtek-support-interrupt-of-RTL8221B.patch b/target/linux/generic/pending-5.15/731-net-phy-realtek-support-interrupt-of-RTL8221B.patch
deleted file mode 100644 (file)
index 07d46d8..0000000
+++ /dev/null
@@ -1,75 +0,0 @@
-From d7943c31d57c11e1a517aa3ce2006fca44866870 Mon Sep 17 00:00:00 2001
-From: Jianhui Zhao <[email protected]>
-Date: Sun, 24 Sep 2023 22:15:00 +0800
-Subject: [PATCH] net: phy: realtek: add interrupt support for RTL8221B
-
-This commit introduces interrupt support for RTL8221B.
-
-Signed-off-by: Jianhui Zhao <[email protected]>
----
- drivers/net/phy/realtek.c | 47 +++++++++++++++++++++++++++++++++++++++
- 1 file changed, 47 insertions(+)
-
---- a/drivers/net/phy/realtek.c
-+++ b/drivers/net/phy/realtek.c
-@@ -972,6 +972,51 @@ static int rtl8221b_config_init(struct p
-       return 0;
- }
-+static int rtl8221b_ack_interrupt(struct phy_device *phydev)
-+{
-+      int err;
-+
-+      err = phy_read_mmd(phydev, RTL8221B_MMD_PHY_CTRL, 0xa4d4);
-+
-+      return (err < 0) ? err : 0;
-+}
-+
-+static int rtl8221b_config_intr(struct phy_device *phydev)
-+{
-+      int err;
-+
-+      if (phydev->interrupts == PHY_INTERRUPT_ENABLED) {
-+              err = rtl8221b_ack_interrupt(phydev);
-+              if (err)
-+                      return err;
-+
-+              err = phy_write_mmd(phydev, RTL8221B_MMD_PHY_CTRL, 0xa4d2, 0x7ff);
-+      } else {
-+              err = phy_write_mmd(phydev, RTL8221B_MMD_PHY_CTRL, 0xa4d2, 0x0);
-+              if (err)
-+                      return err;
-+
-+              err = rtl8221b_ack_interrupt(phydev);
-+      }
-+
-+      return err;
-+}
-+
-+static irqreturn_t rtl8221b_handle_interrupt(struct phy_device *phydev)
-+{
-+      int err;
-+
-+      err = rtl8221b_ack_interrupt(phydev);
-+      if (err) {
-+              phy_error(phydev);
-+              return IRQ_NONE;
-+      }
-+
-+      phy_trigger_machine(phydev);
-+
-+      return IRQ_HANDLED;
-+}
-+
- static struct phy_driver realtek_drvs[] = {
-       {
-               PHY_ID_MATCH_EXACT(0x00008201),
-@@ -1120,6 +1165,8 @@ static struct phy_driver realtek_drvs[]
-               .get_features   = rtl822x_get_features,
-               .config_init    = rtl8221b_config_init,
-               .config_aneg    = rtl822x_config_aneg,
-+              .config_intr    = rtl8221b_config_intr,
-+              .handle_interrupt = rtl8221b_handle_interrupt,
-               .probe          = rtl822x_probe,
-               .read_status    = rtl822x_read_status,
-               .suspend        = genphy_suspend,
diff --git a/target/linux/generic/pending-5.15/732-00-net-ethernet-mtk_eth_soc-compile-out-netsys-v2-code-.patch b/target/linux/generic/pending-5.15/732-00-net-ethernet-mtk_eth_soc-compile-out-netsys-v2-code-.patch
deleted file mode 100644 (file)
index 1d84ea9..0000000
+++ /dev/null
@@ -1,44 +0,0 @@
-From: Felix Fietkau <[email protected]>
-Date: Thu, 27 Oct 2022 23:39:52 +0200
-Subject: [PATCH] net: ethernet: mtk_eth_soc: compile out netsys v2 code
- on mt7621
-
-Avoid some branches in the hot path on low-end devices with limited CPU power,
-and reduce code size
-
-Signed-off-by: Felix Fietkau <[email protected]>
----
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-@@ -1323,6 +1323,22 @@ struct mtk_mac {
- /* the struct describing the SoC. these are declared in the soc_xyz.c files */
- extern const struct of_device_id of_mtk_match[];
-+#ifdef CONFIG_SOC_MT7621
-+static inline bool mtk_is_netsys_v1(struct mtk_eth *eth)
-+{
-+      return true;
-+}
-+
-+static inline bool mtk_is_netsys_v2_or_greater(struct mtk_eth *eth)
-+{
-+      return false;
-+}
-+
-+static inline bool mtk_is_netsys_v3_or_greater(struct mtk_eth *eth)
-+{
-+      return false;
-+}
-+#else
- static inline bool mtk_is_netsys_v1(struct mtk_eth *eth)
- {
-       return eth->soc->version == 1;
-@@ -1337,6 +1353,7 @@ static inline bool mtk_is_netsys_v3_or_g
- {
-       return eth->soc->version > 2;
- }
-+#endif
- static inline struct mtk_foe_entry *
- mtk_foe_get_entry(struct mtk_ppe *ppe, u16 hash)
diff --git a/target/linux/generic/pending-5.15/732-01-net-ethernet-mtk_eth_soc-work-around-issue-with-send.patch b/target/linux/generic/pending-5.15/732-01-net-ethernet-mtk_eth_soc-work-around-issue-with-send.patch
deleted file mode 100644 (file)
index 56edb63..0000000
+++ /dev/null
@@ -1,94 +0,0 @@
-From: Felix Fietkau <[email protected]>
-Date: Thu, 3 Nov 2022 12:38:49 +0100
-Subject: [PATCH] net: ethernet: mtk_eth_soc: work around issue with sending
- small fragments
-
-When lots of frames are sent with a number of very small fragments, an
-internal FIFO can overflow, causing the DMA engine to lock up lock up and
-transmit attempts time out.
-
-Fix this on MT7986 by increasing the reserved FIFO space.
-Fix this on older chips by detecting the presence of small fragments and use
-skb_gso_segment + skb_linearize to deal with them.
-
-Signed-off-by: Felix Fietkau <[email protected]>
----
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-@@ -1516,12 +1516,28 @@ static void mtk_wake_queue(struct mtk_et
-       }
- }
-+static bool mtk_skb_has_small_frag(struct sk_buff *skb)
-+{
-+      int min_size = 16;
-+      int i;
-+
-+      if (skb_headlen(skb) < min_size)
-+              return true;
-+
-+      for (i = 0; i < skb_shinfo(skb)->nr_frags; i++)
-+              if (skb_frag_size(&skb_shinfo(skb)->frags[i]) < min_size)
-+                      return true;
-+
-+      return false;
-+}
-+
- static netdev_tx_t mtk_start_xmit(struct sk_buff *skb, struct net_device *dev)
- {
-       struct mtk_mac *mac = netdev_priv(dev);
-       struct mtk_eth *eth = mac->hw;
-       struct mtk_tx_ring *ring = &eth->tx_ring;
-       struct net_device_stats *stats = &dev->stats;
-+      struct sk_buff *segs, *next;
-       bool gso = false;
-       int tx_num;
-@@ -1543,6 +1559,18 @@ static netdev_tx_t mtk_start_xmit(struct
-               return NETDEV_TX_BUSY;
-       }
-+      if (mtk_is_netsys_v1(eth) &&
-+          skb_is_gso(skb) && mtk_skb_has_small_frag(skb)) {
-+              segs = skb_gso_segment(skb, dev->features & ~NETIF_F_ALL_TSO);
-+              if (IS_ERR(segs))
-+                      goto drop;
-+
-+              if (segs) {
-+                      consume_skb(skb);
-+                      skb = segs;
-+              }
-+      }
-+
-       /* TSO: fill MSS info in tcp checksum field */
-       if (skb_is_gso(skb)) {
-               if (skb_cow_head(skb, 0)) {
-@@ -1558,8 +1586,14 @@ static netdev_tx_t mtk_start_xmit(struct
-               }
-       }
--      if (mtk_tx_map(skb, dev, tx_num, ring, gso) < 0)
--              goto drop;
-+      skb_list_walk_safe(skb, skb, next) {
-+              if ((mtk_is_netsys_v1(eth) &&
-+                   mtk_skb_has_small_frag(skb) && skb_linearize(skb)) ||
-+                  mtk_tx_map(skb, dev, tx_num, ring, gso) < 0) {
-+                              stats->tx_dropped++;
-+                              dev_kfree_skb_any(skb);
-+              }
-+      }
-       if (unlikely(atomic_read(&ring->free_count) <= ring->thresh))
-               netif_tx_stop_all_queues(dev);
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-@@ -268,7 +268,7 @@
- #define MTK_CHK_DDONE_EN      BIT(28)
- #define MTK_DMAD_WR_WDONE     BIT(26)
- #define MTK_WCOMP_EN          BIT(24)
--#define MTK_RESV_BUF          (0x40 << 16)
-+#define MTK_RESV_BUF          (0x80 << 16)
- #define MTK_MUTLI_CNT         (0x4 << 12)
- #define MTK_LEAKY_BUCKET_EN   BIT(11)
diff --git a/target/linux/generic/pending-5.15/732-02-net-ethernet-mtk_eth_soc-set-NETIF_F_ALL_TSO.patch b/target/linux/generic/pending-5.15/732-02-net-ethernet-mtk_eth_soc-set-NETIF_F_ALL_TSO.patch
deleted file mode 100644 (file)
index 11a81dd..0000000
+++ /dev/null
@@ -1,21 +0,0 @@
-From: Felix Fietkau <[email protected]>
-Date: Fri, 28 Oct 2022 12:54:48 +0200
-Subject: [PATCH] net: ethernet: mtk_eth_soc: set NETIF_F_ALL_TSO
-
-Significantly improves performance by avoiding unnecessary segmentation
-
-Signed-off-by: Felix Fietkau <[email protected]>
----
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-@@ -47,8 +47,7 @@
- #define MTK_HW_FEATURES               (NETIF_F_IP_CSUM | \
-                                NETIF_F_RXCSUM | \
-                                NETIF_F_HW_VLAN_CTAG_TX | \
--                               NETIF_F_SG | NETIF_F_TSO | \
--                               NETIF_F_TSO6 | \
-+                               NETIF_F_SG | NETIF_F_ALL_TSO | \
-                                NETIF_F_IPV6_CSUM |\
-                                NETIF_F_HW_TC)
- #define MTK_HW_FEATURES_MT7628        (NETIF_F_SG | NETIF_F_RXCSUM)
diff --git a/target/linux/generic/pending-5.15/732-03-net-ethernet-mtk_eth_soc-fix-remaining-throughput-re.patch b/target/linux/generic/pending-5.15/732-03-net-ethernet-mtk_eth_soc-fix-remaining-throughput-re.patch
deleted file mode 100644 (file)
index cc6c9e9..0000000
+++ /dev/null
@@ -1,42 +0,0 @@
-From: Felix Fietkau <[email protected]>
-Date: Wed, 29 Mar 2023 16:02:54 +0200
-Subject: [PATCH] net: ethernet: mtk_eth_soc: fix remaining throughput
- regression
-
-Based on further tests, it seems that the QDMA shaper is not able to
-perform shaping close to the MAC link rate without throughput loss.
-This cannot be compensated by increasing the shaping rate, so it seems
-to be an internal limit.
-
-Fix the remaining throughput regression by detecting that condition and
-limiting shaping to ports with lower link speed.
-
-This patch intentionally ignores link speed gain from TRGMII, because
-even on such links, shaping to 1000 Mbit/s incurs some throughput
-degradation.
-
-Fixes: f63959c7eec3 ("net: ethernet: mtk_eth_soc: implement multi-queue support for per-port queues")
-Reported-by: Frank Wunderlich <[email protected]>
-Signed-off-by: Felix Fietkau <[email protected]>
----
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-@@ -723,6 +723,7 @@ static void mtk_mac_link_up(struct phyli
-                MAC_MCR_FORCE_RX_FC);
-       /* Configure speed */
-+      mac->speed = speed;
-       switch (speed) {
-       case SPEED_2500:
-       case SPEED_1000:
-@@ -3292,6 +3293,9 @@ found:
-       if (dp->index >= MTK_QDMA_NUM_QUEUES)
-               return NOTIFY_DONE;
-+      if (mac->speed > 0 && mac->speed <= s.base.speed)
-+              s.base.speed = 0;
-+
-       mtk_set_queue_speed(eth, dp->index + 3, s.base.speed);
-       return NOTIFY_DONE;
diff --git a/target/linux/generic/pending-5.15/734-net-ethernet-mtk_eth_soc-ppe-fix-L2-offloading-with-.patch b/target/linux/generic/pending-5.15/734-net-ethernet-mtk_eth_soc-ppe-fix-L2-offloading-with-.patch
deleted file mode 100644 (file)
index ed0a544..0000000
+++ /dev/null
@@ -1,33 +0,0 @@
-From: Felix Fietkau <[email protected]>
-Date: Tue, 27 Dec 2022 15:02:51 +0100
-Subject: [PATCH] net: ethernet: mtk_eth_soc: ppe: fix L2 offloading with DSA
- untagging offload enabled
-
-Check for skb metadata in order to detect the case where the DSA header is not
-present.
-
-Fixes: 2d7605a72906 ("net: ethernet: mtk_eth_soc: enable hardware DSA untagging")
-Signed-off-by: Felix Fietkau <[email protected]>
----
-
---- a/drivers/net/ethernet/mediatek/mtk_ppe.c
-+++ b/drivers/net/ethernet/mediatek/mtk_ppe.c
-@@ -8,6 +8,7 @@
- #include <linux/platform_device.h>
- #include <linux/if_ether.h>
- #include <linux/if_vlan.h>
-+#include <net/dst_metadata.h>
- #include <net/dsa.h>
- #include "mtk_eth_soc.h"
- #include "mtk_ppe.h"
-@@ -835,7 +836,9 @@ void __mtk_ppe_check_skb(struct mtk_ppe
-                   skb->dev->dsa_ptr->tag_ops->proto != DSA_TAG_PROTO_MTK)
-                       goto out;
--              tag += 4;
-+              if (!skb_metadata_dst(skb))
-+                      tag += 4;
-+
-               if (get_unaligned_be16(tag) != ETH_P_8021Q)
-                       break;
diff --git a/target/linux/generic/pending-5.15/737-net-ethernet-mtk_eth_soc-add-paths-and-SerDes-modes-.patch b/target/linux/generic/pending-5.15/737-net-ethernet-mtk_eth_soc-add-paths-and-SerDes-modes-.patch
deleted file mode 100644 (file)
index 61c23da..0000000
+++ /dev/null
@@ -1,1605 +0,0 @@
-From 1e25ca1147579bda8b941be1b9851f5911d44eb0 Mon Sep 17 00:00:00 2001
-From: Daniel Golle <[email protected]>
-Date: Tue, 22 Aug 2023 19:04:42 +0100
-Subject: [PATCH 098/125] net: ethernet: mtk_eth_soc: add paths and SerDes
- modes for MT7988
-
-MT7988 comes with a built-in 2.5G PHY as well as SerDes lanes to
-connect external PHYs or transceivers in USXGMII, 10GBase-R, 5GBase-R,
-2500Base-X, 1000Base-X and Cisco SGMII interface modes.
-
-Implement support for configuring for the new paths to SerDes interfaces
-and the internal 2.5G PHY.
-
-Add USXGMII PCS driver for 10GBase-R, 5GBase-R and USXGMII mode, and
-setup the new PHYA on MT7988 to access the also still existing old
-LynxI PCS for 1000Base-X, 2500Base-X and Cisco SGMII PCS interface
-modes.
-
-Signed-off-by: Daniel Golle <[email protected]>
----
- drivers/net/ethernet/mediatek/Kconfig        |  16 +
- drivers/net/ethernet/mediatek/Makefile       |   1 +
- drivers/net/ethernet/mediatek/mtk_eth_path.c | 123 +++-
- drivers/net/ethernet/mediatek/mtk_eth_soc.c  | 182 ++++-
- drivers/net/ethernet/mediatek/mtk_eth_soc.h  | 232 ++++++-
- drivers/net/ethernet/mediatek/mtk_usxgmii.c  | 692 +++++++++++++++++++
- 6 files changed, 1215 insertions(+), 31 deletions(-)
- create mode 100644 drivers/net/ethernet/mediatek/mtk_usxgmii.c
-
---- a/drivers/net/ethernet/mediatek/Kconfig
-+++ b/drivers/net/ethernet/mediatek/Kconfig
-@@ -24,6 +24,22 @@ config NET_MEDIATEK_SOC
-         This driver supports the gigabit ethernet MACs in the
-         MediaTek SoC family.
-+config NET_MEDIATEK_SOC_USXGMII
-+      bool "Support USXGMII SerDes on MT7988"
-+      depends on (ARCH_MEDIATEK && ARM64) || COMPILE_TEST
-+      def_bool NET_MEDIATEK_SOC != n
-+      help
-+        Include support for 10GE SerDes which can be found on MT7988.
-+        If this kernel should run on SoCs with 10 GBit/s Ethernet you
-+        will need to select this option to use GMAC2 and GMAC3 with
-+        external PHYs, SFP(+) cages in 10GBase-R, 5GBase-R or USXGMII
-+        interface modes.
-+
-+        Note that as the 2500Base-X/1000Base-X/Cisco SGMII SerDes PCS
-+        unit (MediaTek LynxI) in MT7988 is connected via the new 10GE
-+        SerDes, you will also need to select this option in case you
-+        want to use any of those SerDes modes.
-+
- config NET_MEDIATEK_STAR_EMAC
-       tristate "MediaTek STAR Ethernet MAC support"
-       select PHYLIB
---- a/drivers/net/ethernet/mediatek/Makefile
-+++ b/drivers/net/ethernet/mediatek/Makefile
-@@ -5,6 +5,7 @@
- obj-$(CONFIG_NET_MEDIATEK_SOC) += mtk_eth.o
- mtk_eth-y := mtk_eth_soc.o mtk_eth_path.o mtk_ppe.o mtk_ppe_debugfs.o mtk_ppe_offload.o
-+mtk_eth-$(CONFIG_NET_MEDIATEK_SOC_USXGMII) += mtk_usxgmii.o
- mtk_eth-$(CONFIG_NET_MEDIATEK_SOC_WED) += mtk_wed.o mtk_wed_mcu.o mtk_wed_wo.o
- ifdef CONFIG_DEBUG_FS
- mtk_eth-$(CONFIG_NET_MEDIATEK_SOC_WED) += mtk_wed_debugfs.o
---- a/drivers/net/ethernet/mediatek/mtk_eth_path.c
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_path.c
-@@ -31,10 +31,20 @@ static const char *mtk_eth_path_name(u64
-               return "gmac2_rgmii";
-       case MTK_ETH_PATH_GMAC2_SGMII:
-               return "gmac2_sgmii";
-+      case MTK_ETH_PATH_GMAC2_2P5GPHY:
-+              return "gmac2_2p5gphy";
-       case MTK_ETH_PATH_GMAC2_GEPHY:
-               return "gmac2_gephy";
-+      case MTK_ETH_PATH_GMAC3_SGMII:
-+              return "gmac3_sgmii";
-       case MTK_ETH_PATH_GDM1_ESW:
-               return "gdm1_esw";
-+      case MTK_ETH_PATH_GMAC1_USXGMII:
-+              return "gmac1_usxgmii";
-+      case MTK_ETH_PATH_GMAC2_USXGMII:
-+              return "gmac2_usxgmii";
-+      case MTK_ETH_PATH_GMAC3_USXGMII:
-+              return "gmac3_usxgmii";
-       default:
-               return "unknown path";
-       }
-@@ -127,6 +137,27 @@ static int set_mux_u3_gmac2_to_qphy(stru
-       return 0;
- }
-+static int set_mux_gmac2_to_2p5gphy(struct mtk_eth *eth, u64 path)
-+{
-+      int ret;
-+
-+      if (path == MTK_ETH_PATH_GMAC2_2P5GPHY) {
-+              ret = regmap_clear_bits(eth->ethsys, ETHSYS_SYSCFG0, SYSCFG0_SGMII_GMAC2_V2);
-+              if (ret)
-+                      return ret;
-+
-+              /* Setup mux to 2p5g PHY */
-+              ret = regmap_clear_bits(eth->infra, TOP_MISC_NETSYS_PCS_MUX, MUX_G2_USXGMII_SEL);
-+              if (ret)
-+                      return ret;
-+
-+              dev_dbg(eth->dev, "path %s in %s updated\n",
-+                      mtk_eth_path_name(path), __func__);
-+      }
-+
-+      return 0;
-+}
-+
- static int set_mux_gmac1_gmac2_to_sgmii_rgmii(struct mtk_eth *eth, u64 path)
- {
-       unsigned int val = 0;
-@@ -165,7 +196,48 @@ static int set_mux_gmac1_gmac2_to_sgmii_
-       return 0;
- }
--static int set_mux_gmac12_to_gephy_sgmii(struct mtk_eth *eth, u64 path)
-+static int set_mux_gmac123_to_usxgmii(struct mtk_eth *eth, u64 path)
-+{
-+      unsigned int val = 0;
-+      bool updated = true;
-+      int mac_id = 0;
-+
-+      /* Disable SYSCFG1 SGMII */
-+      regmap_read(eth->ethsys, ETHSYS_SYSCFG0, &val);
-+
-+      switch (path) {
-+      case MTK_ETH_PATH_GMAC1_USXGMII:
-+              val &= ~(u32)SYSCFG0_SGMII_GMAC1_V2;
-+              mac_id = MTK_GMAC1_ID;
-+              break;
-+      case MTK_ETH_PATH_GMAC2_USXGMII:
-+              val &= ~(u32)SYSCFG0_SGMII_GMAC2_V2;
-+              mac_id = MTK_GMAC2_ID;
-+              break;
-+      case MTK_ETH_PATH_GMAC3_USXGMII:
-+              val &= ~(u32)SYSCFG0_SGMII_GMAC3_V2;
-+              mac_id = MTK_GMAC3_ID;
-+              break;
-+      default:
-+              updated = false;
-+      };
-+
-+      if (updated) {
-+              regmap_update_bits(eth->ethsys, ETHSYS_SYSCFG0,
-+                                 SYSCFG0_SGMII_MASK, val);
-+
-+              if (mac_id == MTK_GMAC2_ID)
-+                      regmap_set_bits(eth->infra, TOP_MISC_NETSYS_PCS_MUX,
-+                                      MUX_G2_USXGMII_SEL);
-+      }
-+
-+      dev_dbg(eth->dev, "path %s in %s updated = %d\n",
-+              mtk_eth_path_name(path), __func__, updated);
-+
-+      return 0;
-+}
-+
-+static int set_mux_gmac123_to_gephy_sgmii(struct mtk_eth *eth, u64 path)
- {
-       unsigned int val = 0;
-       bool updated = true;
-@@ -182,6 +254,9 @@ static int set_mux_gmac12_to_gephy_sgmii
-       case MTK_ETH_PATH_GMAC2_SGMII:
-               val |= SYSCFG0_SGMII_GMAC2_V2;
-               break;
-+      case MTK_ETH_PATH_GMAC3_SGMII:
-+              val |= SYSCFG0_SGMII_GMAC3_V2;
-+              break;
-       default:
-               updated = false;
-       }
-@@ -210,13 +285,25 @@ static const struct mtk_eth_muxc mtk_eth
-               .cap_bit = MTK_ETH_MUX_U3_GMAC2_TO_QPHY,
-               .set_path = set_mux_u3_gmac2_to_qphy,
-       }, {
-+              .name = "mux_gmac2_to_2p5gphy",
-+              .cap_bit = MTK_ETH_MUX_GMAC2_TO_2P5GPHY,
-+              .set_path = set_mux_gmac2_to_2p5gphy,
-+      }, {
-               .name = "mux_gmac1_gmac2_to_sgmii_rgmii",
-               .cap_bit = MTK_ETH_MUX_GMAC1_GMAC2_TO_SGMII_RGMII,
-               .set_path = set_mux_gmac1_gmac2_to_sgmii_rgmii,
-       }, {
-               .name = "mux_gmac12_to_gephy_sgmii",
-               .cap_bit = MTK_ETH_MUX_GMAC12_TO_GEPHY_SGMII,
--              .set_path = set_mux_gmac12_to_gephy_sgmii,
-+              .set_path = set_mux_gmac123_to_gephy_sgmii,
-+      }, {
-+              .name = "mux_gmac123_to_gephy_sgmii",
-+              .cap_bit = MTK_ETH_MUX_GMAC123_TO_GEPHY_SGMII,
-+              .set_path = set_mux_gmac123_to_gephy_sgmii,
-+      }, {
-+              .name = "mux_gmac123_to_usxgmii",
-+              .cap_bit = MTK_ETH_MUX_GMAC123_TO_USXGMII,
-+              .set_path = set_mux_gmac123_to_usxgmii,
-       },
- };
-@@ -249,12 +336,39 @@ out:
-       return err;
- }
-+int mtk_gmac_usxgmii_path_setup(struct mtk_eth *eth, int mac_id)
-+{
-+      u64 path;
-+
-+      path = (mac_id == MTK_GMAC1_ID) ?  MTK_ETH_PATH_GMAC1_USXGMII :
-+             (mac_id == MTK_GMAC2_ID) ?  MTK_ETH_PATH_GMAC2_USXGMII :
-+                                         MTK_ETH_PATH_GMAC3_USXGMII;
-+
-+      /* Setup proper MUXes along the path */
-+      return mtk_eth_mux_setup(eth, path);
-+}
-+
- int mtk_gmac_sgmii_path_setup(struct mtk_eth *eth, int mac_id)
- {
-       u64 path;
--      path = (mac_id == 0) ?  MTK_ETH_PATH_GMAC1_SGMII :
--                              MTK_ETH_PATH_GMAC2_SGMII;
-+      path = (mac_id == MTK_GMAC1_ID) ? MTK_ETH_PATH_GMAC1_SGMII :
-+             (mac_id == MTK_GMAC2_ID) ? MTK_ETH_PATH_GMAC2_SGMII :
-+                                        MTK_ETH_PATH_GMAC3_SGMII;
-+
-+      /* Setup proper MUXes along the path */
-+      return mtk_eth_mux_setup(eth, path);
-+}
-+
-+int mtk_gmac_2p5gphy_path_setup(struct mtk_eth *eth, int mac_id)
-+{
-+      u64 path = 0;
-+
-+      if (mac_id == MTK_GMAC2_ID)
-+              path = MTK_ETH_PATH_GMAC2_2P5GPHY;
-+
-+      if (!path)
-+              return -EINVAL;
-       /* Setup proper MUXes along the path */
-       return mtk_eth_mux_setup(eth, path);
-@@ -284,4 +398,3 @@ int mtk_gmac_rgmii_path_setup(struct mtk
-       /* Setup proper MUXes along the path */
-       return mtk_eth_mux_setup(eth, path);
- }
--
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-@@ -432,6 +432,30 @@ static void mtk_setup_bridge_switch(stru
-               MTK_GSW_CFG);
- }
-+static bool mtk_check_gmac23_idle(struct mtk_mac *mac)
-+{
-+      u32 mac_fsm, gdm_fsm;
-+
-+      mac_fsm = mtk_r32(mac->hw, MTK_MAC_FSM(mac->id));
-+
-+      switch (mac->id) {
-+      case MTK_GMAC2_ID:
-+              gdm_fsm = mtk_r32(mac->hw, MTK_FE_GDM2_FSM);
-+              break;
-+      case MTK_GMAC3_ID:
-+              gdm_fsm = mtk_r32(mac->hw, MTK_FE_GDM3_FSM);
-+              break;
-+      default:
-+              return true;
-+      };
-+
-+      if ((mac_fsm & 0xFFFF0000) == 0x01010000 &&
-+          (gdm_fsm & 0xFFFF0000) == 0x00000000)
-+              return true;
-+
-+      return false;
-+}
-+
- static struct phylink_pcs *mtk_mac_select_pcs(struct phylink_config *config,
-                                             phy_interface_t interface)
- {
-@@ -440,12 +464,20 @@ static struct phylink_pcs *mtk_mac_selec
-       struct mtk_eth *eth = mac->hw;
-       unsigned int sid;
--      if (interface == PHY_INTERFACE_MODE_SGMII ||
--          phy_interface_mode_is_8023z(interface)) {
--              sid = (MTK_HAS_CAPS(eth->soc->caps, MTK_SHARED_SGMII)) ?
--                     0 : mac->id;
--
--              return eth->sgmii_pcs[sid];
-+      if ((interface == PHY_INTERFACE_MODE_SGMII ||
-+           phy_interface_mode_is_8023z(interface)) &&
-+          MTK_HAS_CAPS(eth->soc->caps, MTK_SGMII)) {
-+              sid = mtk_mac2xgmii_id(eth, mac->id);
-+              if (MTK_HAS_CAPS(eth->soc->caps, MTK_USXGMII))
-+                      return mtk_sgmii_wrapper_select_pcs(eth, mac->id);
-+              else
-+                      return eth->sgmii_pcs[sid];
-+      } else if ((interface == PHY_INTERFACE_MODE_USXGMII ||
-+                  interface == PHY_INTERFACE_MODE_10GBASER ||
-+                  interface == PHY_INTERFACE_MODE_5GBASER) &&
-+                 MTK_HAS_CAPS(eth->soc->caps, MTK_USXGMII) &&
-+                 mac->id != MTK_GMAC1_ID) {
-+              return mtk_usxgmii_select_pcs(eth, mac->id);
-       }
-       return NULL;
-@@ -501,7 +533,22 @@ static void mtk_mac_config(struct phylin
-                                       goto init_err;
-                       }
-                       break;
-+              case PHY_INTERFACE_MODE_USXGMII:
-+              case PHY_INTERFACE_MODE_10GBASER:
-+              case PHY_INTERFACE_MODE_5GBASER:
-+                      if (MTK_HAS_CAPS(eth->soc->caps, MTK_USXGMII)) {
-+                              err = mtk_gmac_usxgmii_path_setup(eth, mac->id);
-+                              if (err)
-+                                      goto init_err;
-+                      }
-+                      break;
-               case PHY_INTERFACE_MODE_INTERNAL:
-+                      if (mac->id == MTK_GMAC2_ID &&
-+                          MTK_HAS_CAPS(eth->soc->caps, MTK_2P5GPHY)) {
-+                              err = mtk_gmac_2p5gphy_path_setup(eth, mac->id);
-+                              if (err)
-+                                      goto init_err;
-+                      }
-                       break;
-               default:
-                       goto err_phy;
-@@ -556,8 +603,6 @@ static void mtk_mac_config(struct phylin
-               val &= ~SYSCFG0_GE_MODE(SYSCFG0_GE_MASK, mac->id);
-               val |= SYSCFG0_GE_MODE(ge_mode, mac->id);
-               regmap_write(eth->ethsys, ETHSYS_SYSCFG0, val);
--
--              mac->interface = state->interface;
-       }
-       /* SGMII */
-@@ -574,21 +619,40 @@ static void mtk_mac_config(struct phylin
-               /* Save the syscfg0 value for mac_finish */
-               mac->syscfg0 = val;
--      } else if (phylink_autoneg_inband(mode)) {
-+      } else if (state->interface != PHY_INTERFACE_MODE_USXGMII &&
-+                 state->interface != PHY_INTERFACE_MODE_10GBASER &&
-+                 state->interface != PHY_INTERFACE_MODE_5GBASER &&
-+                 phylink_autoneg_inband(mode)) {
-               dev_err(eth->dev,
--                      "In-band mode not supported in non SGMII mode!\n");
-+                      "In-band mode not supported in non-SerDes modes!\n");
-               return;
-       }
-       /* Setup gmac */
--      if (mtk_is_netsys_v3_or_greater(eth) &&
--          mac->interface == PHY_INTERFACE_MODE_INTERNAL) {
--              mtk_w32(mac->hw, MTK_GDMA_XGDM_SEL, MTK_GDMA_EG_CTRL(mac->id));
--              mtk_w32(mac->hw, MAC_MCR_FORCE_LINK_DOWN, MTK_MAC_MCR(mac->id));
-+      if (mtk_is_netsys_v3_or_greater(eth)) {
-+              if (mtk_interface_mode_is_xgmii(state->interface)) {
-+                      mtk_w32(mac->hw, MTK_GDMA_XGDM_SEL, MTK_GDMA_EG_CTRL(mac->id));
-+                      mtk_w32(mac->hw, MAC_MCR_FORCE_LINK_DOWN, MTK_MAC_MCR(mac->id));
-+
-+                      if (mac->id == MTK_GMAC1_ID)
-+                              mtk_setup_bridge_switch(eth);
-+              } else {
-+                      mtk_w32(eth, 0, MTK_GDMA_EG_CTRL(mac->id));
--              mtk_setup_bridge_switch(eth);
-+                      /* FIXME: In current hardware design, we have to reset FE
-+                       * when swtiching XGDM to GDM. Therefore, here trigger an SER
-+                       * to let GDM go back to the initial state.
-+                       */
-+                      if ((mtk_interface_mode_is_xgmii(mac->interface) ||
-+                           mac->interface == PHY_INTERFACE_MODE_NA) &&
-+                          !mtk_check_gmac23_idle(mac) &&
-+                          !test_bit(MTK_RESETTING, &eth->state))
-+                              schedule_work(&eth->pending_work);
-+              }
-       }
-+      mac->interface = state->interface;
-+
-       return;
- err_phy:
-@@ -633,10 +697,14 @@ static void mtk_mac_link_down(struct phy
- {
-       struct mtk_mac *mac = container_of(config, struct mtk_mac,
-                                          phylink_config);
--      u32 mcr = mtk_r32(mac->hw, MTK_MAC_MCR(mac->id));
--      mcr &= ~(MAC_MCR_TX_EN | MAC_MCR_RX_EN | MAC_MCR_FORCE_LINK);
--      mtk_w32(mac->hw, mcr, MTK_MAC_MCR(mac->id));
-+      if (!mtk_interface_mode_is_xgmii(interface)) {
-+              mtk_m32(mac->hw, MAC_MCR_TX_EN | MAC_MCR_RX_EN | MAC_MCR_FORCE_LINK, 0, MTK_MAC_MCR(mac->id));
-+              if (mtk_is_netsys_v3_or_greater(eth))
-+                      mtk_m32(mac->hw, MTK_XGMAC_FORCE_LINK(mac->id), 0, MTK_XGMAC_STS(mac->id));
-+      } else if (mac->id != MTK_GMAC1_ID) {
-+              mtk_m32(mac->hw, XMAC_MCR_TRX_DISABLE, XMAC_MCR_TRX_DISABLE, MTK_XMAC_MCR(mac->id));
-+      }
- }
- static void mtk_set_queue_speed(struct mtk_eth *eth, unsigned int idx,
-@@ -708,13 +776,11 @@ static void mtk_set_queue_speed(struct m
-       mtk_w32(eth, val, soc->reg_map->qdma.qtx_sch + ofs);
- }
--static void mtk_mac_link_up(struct phylink_config *config,
--                          struct phy_device *phy,
--                          unsigned int mode, phy_interface_t interface,
--                          int speed, int duplex, bool tx_pause, bool rx_pause)
-+static void mtk_gdm_mac_link_up(struct mtk_mac *mac,
-+                              struct phy_device *phy,
-+                              unsigned int mode, phy_interface_t interface,
-+                              int speed, int duplex, bool tx_pause, bool rx_pause)
- {
--      struct mtk_mac *mac = container_of(config, struct mtk_mac,
--                                         phylink_config);
-       u32 mcr;
-       mcr = mtk_r32(mac->hw, MTK_MAC_MCR(mac->id));
-@@ -748,6 +814,55 @@ static void mtk_mac_link_up(struct phyli
-       mtk_w32(mac->hw, mcr, MTK_MAC_MCR(mac->id));
- }
-+static void mtk_xgdm_mac_link_up(struct mtk_mac *mac,
-+                               struct phy_device *phy,
-+                               unsigned int mode, phy_interface_t interface,
-+                               int speed, int duplex, bool tx_pause, bool rx_pause)
-+{
-+      u32 mcr, force_link = 0;
-+
-+      if (mac->id == MTK_GMAC1_ID)
-+              return;
-+
-+      /* Eliminate the interference(before link-up) caused by PHY noise */
-+      mtk_m32(mac->hw, XMAC_LOGIC_RST, 0, MTK_XMAC_LOGIC_RST(mac->id));
-+      mdelay(20);
-+      mtk_m32(mac->hw, XMAC_GLB_CNTCLR, XMAC_GLB_CNTCLR, MTK_XMAC_CNT_CTRL(mac->id));
-+
-+      if (mac->interface == PHY_INTERFACE_MODE_INTERNAL || mac->id == MTK_GMAC3_ID)
-+              force_link = MTK_XGMAC_FORCE_LINK(mac->id);
-+
-+      mtk_m32(mac->hw, MTK_XGMAC_FORCE_LINK(mac->id), force_link, MTK_XGMAC_STS(mac->id));
-+
-+      mcr = mtk_r32(mac->hw, MTK_XMAC_MCR(mac->id));
-+      mcr &= ~(XMAC_MCR_FORCE_TX_FC | XMAC_MCR_FORCE_RX_FC | XMAC_MCR_TRX_DISABLE);
-+      /* Configure pause modes -
-+       * phylink will avoid these for half duplex
-+       */
-+      if (tx_pause)
-+              mcr |= XMAC_MCR_FORCE_TX_FC;
-+      if (rx_pause)
-+              mcr |= XMAC_MCR_FORCE_RX_FC;
-+
-+      mtk_w32(mac->hw, mcr, MTK_XMAC_MCR(mac->id));
-+}
-+
-+static void mtk_mac_link_up(struct phylink_config *config,
-+                          struct phy_device *phy,
-+                          unsigned int mode, phy_interface_t interface,
-+                          int speed, int duplex, bool tx_pause, bool rx_pause)
-+{
-+      struct mtk_mac *mac = container_of(config, struct mtk_mac,
-+                                         phylink_config);
-+
-+      if (mtk_interface_mode_is_xgmii(interface))
-+              mtk_xgdm_mac_link_up(mac, phy, mode, interface, speed, duplex,
-+                                   tx_pause, rx_pause);
-+      else
-+              mtk_gdm_mac_link_up(mac, phy, mode, interface, speed, duplex,
-+                                  tx_pause, rx_pause);
-+}
-+
- static const struct phylink_mac_ops mtk_phylink_ops = {
-       .validate = phylink_generic_validate,
-       .mac_select_pcs = mtk_mac_select_pcs,
-@@ -4562,8 +4677,21 @@ static int mtk_add_mac(struct mtk_eth *e
-               phy_interface_zero(mac->phylink_config.supported_interfaces);
-               __set_bit(PHY_INTERFACE_MODE_INTERNAL,
-                         mac->phylink_config.supported_interfaces);
-+      } else if (MTK_HAS_CAPS(mac->hw->soc->caps, MTK_USXGMII)) {
-+              mac->phylink_config.mac_capabilities |= MAC_5000FD | MAC_10000FD;
-+              __set_bit(PHY_INTERFACE_MODE_5GBASER,
-+                        mac->phylink_config.supported_interfaces);
-+              __set_bit(PHY_INTERFACE_MODE_10GBASER,
-+                        mac->phylink_config.supported_interfaces);
-+              __set_bit(PHY_INTERFACE_MODE_USXGMII,
-+                        mac->phylink_config.supported_interfaces);
-       }
-+      if (MTK_HAS_CAPS(mac->hw->soc->caps, MTK_2P5GPHY) &&
-+          id == MTK_GMAC2_ID)
-+              __set_bit(PHY_INTERFACE_MODE_INTERNAL,
-+                        mac->phylink_config.supported_interfaces);
-+
-       phylink = phylink_create(&mac->phylink_config,
-                                of_fwnode_handle(mac->of_node),
-                                phy_mode, &mtk_phylink_ops);
-@@ -4756,6 +4884,13 @@ static int mtk_probe(struct platform_dev
-               if (err)
-                       return err;
-+      }
-+
-+      if (MTK_HAS_CAPS(eth->soc->caps, MTK_USXGMII)) {
-+              err = mtk_usxgmii_init(eth);
-+
-+              if (err)
-+                      return err;
-       }
-       if (eth->soc->required_pctl) {
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.h
-@@ -499,6 +499,21 @@
- #define INTF_MODE_RGMII_1000    (TRGMII_MODE | TRGMII_CENTRAL_ALIGNED)
- #define INTF_MODE_RGMII_10_100  0
-+/* XFI Mac control registers */
-+#define MTK_XMAC_BASE(x)      (0x12000 + (((x) - 1) * 0x1000))
-+#define MTK_XMAC_MCR(x)               (MTK_XMAC_BASE(x))
-+#define XMAC_MCR_TRX_DISABLE  0xf
-+#define XMAC_MCR_FORCE_TX_FC  BIT(5)
-+#define XMAC_MCR_FORCE_RX_FC  BIT(4)
-+
-+/* XFI Mac logic reset registers */
-+#define MTK_XMAC_LOGIC_RST(x) (MTK_XMAC_BASE(x) + 0x10)
-+#define XMAC_LOGIC_RST                BIT(0)
-+
-+/* XFI Mac count global control */
-+#define MTK_XMAC_CNT_CTRL(x)  (MTK_XMAC_BASE(x) + 0x100)
-+#define XMAC_GLB_CNTCLR               BIT(0)
-+
- /* GPIO port control registers for GMAC 2*/
- #define GPIO_OD33_CTRL8               0x4c0
- #define GPIO_BIAS_CTRL                0xed0
-@@ -524,6 +539,7 @@
- #define SYSCFG0_SGMII_GMAC2    ((3 << 8) & SYSCFG0_SGMII_MASK)
- #define SYSCFG0_SGMII_GMAC1_V2 BIT(9)
- #define SYSCFG0_SGMII_GMAC2_V2 BIT(8)
-+#define SYSCFG0_SGMII_GMAC3_V2 BIT(7)
- /* ethernet subsystem clock register */
-@@ -556,12 +572,74 @@
- #define ETHSYS_DMA_AG_MAP_QDMA        BIT(1)
- #define ETHSYS_DMA_AG_MAP_PPE BIT(2)
-+/* USXGMII subsystem config registers */
-+/* Register to control speed */
-+#define RG_PHY_TOP_SPEED_CTRL1        0x80C
-+#define USXGMII_RATE_UPDATE_MODE      BIT(31)
-+#define USXGMII_MAC_CK_GATED  BIT(29)
-+#define USXGMII_IF_FORCE_EN   BIT(28)
-+#define USXGMII_RATE_ADAPT_MODE       GENMASK(10, 8)
-+#define USXGMII_RATE_ADAPT_MODE_X1    0
-+#define USXGMII_RATE_ADAPT_MODE_X2    1
-+#define USXGMII_RATE_ADAPT_MODE_X4    2
-+#define USXGMII_RATE_ADAPT_MODE_X10   3
-+#define USXGMII_RATE_ADAPT_MODE_X100  4
-+#define USXGMII_RATE_ADAPT_MODE_X5    5
-+#define USXGMII_RATE_ADAPT_MODE_X50   6
-+#define USXGMII_XFI_RX_MODE   GENMASK(6, 4)
-+#define USXGMII_XFI_RX_MODE_10G       0
-+#define USXGMII_XFI_RX_MODE_5G        1
-+#define USXGMII_XFI_TX_MODE   GENMASK(2, 0)
-+#define USXGMII_XFI_TX_MODE_10G       0
-+#define USXGMII_XFI_TX_MODE_5G        1
-+
-+/* Register to control PCS AN */
-+#define RG_PCS_AN_CTRL0               0x810
-+#define USXGMII_AN_RESTART    BIT(31)
-+#define USXGMII_AN_SYNC_CNT   GENMASK(30, 11)
-+#define USXGMII_AN_ENABLE     BIT(0)
-+
-+#define RG_PCS_AN_CTRL2               0x818
-+#define USXGMII_LINK_TIMER_IDLE_DETECT        GENMASK(29, 20)
-+#define USXGMII_LINK_TIMER_COMP_ACK_DETECT    GENMASK(19, 10)
-+#define USXGMII_LINK_TIMER_AN_RESTART GENMASK(9, 0)
-+
-+/* Register to read PCS AN status */
-+#define RG_PCS_AN_STS0                0x81c
-+#define USXGMII_PCS_AN_WORD   GENMASK(15, 0)
-+#define USXGMII_LPA_LATCH     BIT(31)
-+
-+/* Register to control USXGMII XFI PLL digital */
-+#define XFI_PLL_DIG_GLB8      0x08
-+#define RG_XFI_PLL_EN         BIT(31)
-+
-+/* Register to control USXGMII XFI PLL analog */
-+#define XFI_PLL_ANA_GLB8      0x108
-+#define RG_XFI_PLL_ANA_SWWA   0x02283248
-+
- /* Infrasys subsystem config registers */
- #define INFRA_MISC2            0x70c
- #define CO_QPHY_SEL            BIT(0)
- #define GEPHY_MAC_SEL          BIT(1)
-+/* Toprgu subsystem config registers */
-+#define TOPRGU_SWSYSRST               0x18
-+#define SWSYSRST_UNLOCK_KEY   GENMASK(31, 24)
-+#define SWSYSRST_XFI_PLL_GRST BIT(16)
-+#define SWSYSRST_XFI_PEXPT1_GRST      BIT(15)
-+#define SWSYSRST_XFI_PEXPT0_GRST      BIT(14)
-+#define SWSYSRST_XFI1_GRST    BIT(13)
-+#define SWSYSRST_XFI0_GRST    BIT(12)
-+#define SWSYSRST_SGMII1_GRST  BIT(2)
-+#define SWSYSRST_SGMII0_GRST  BIT(1)
-+#define TOPRGU_SWSYSRST_EN            0xFC
-+
- /* Top misc registers */
-+#define TOP_MISC_NETSYS_PCS_MUX       0x84
-+#define NETSYS_PCS_MUX_MASK   GENMASK(1, 0)
-+#define       MUX_G2_USXGMII_SEL      BIT(1)
-+#define MUX_HSGMII1_G1_SEL    BIT(0)
-+
- #define USB_PHY_SWITCH_REG    0x218
- #define QPHY_SEL_MASK         GENMASK(1, 0)
- #define SGMII_QPHY_SEL                0x2
-@@ -586,6 +664,8 @@
- #define MT7628_SDM_RBCNT      (MT7628_SDM_OFFSET + 0x10c)
- #define MT7628_SDM_CS_ERR     (MT7628_SDM_OFFSET + 0x110)
-+/* Debug Purpose Register */
-+#define MTK_PSE_FQFC_CFG      0x100
- #define MTK_FE_CDM1_FSM               0x220
- #define MTK_FE_CDM2_FSM               0x224
- #define MTK_FE_CDM3_FSM               0x238
-@@ -594,6 +674,11 @@
- #define MTK_FE_CDM6_FSM               0x328
- #define MTK_FE_GDM1_FSM               0x228
- #define MTK_FE_GDM2_FSM               0x22C
-+#define MTK_FE_GDM3_FSM               0x23C
-+#define MTK_FE_PSE_FREE               0x240
-+#define MTK_FE_DROP_FQ                0x244
-+#define MTK_FE_DROP_FC                0x248
-+#define MTK_FE_DROP_PPE               0x24C
- #define MTK_MAC_FSM(x)                (0x1010C + ((x) * 0x100))
-@@ -940,6 +1025,8 @@ enum mkt_eth_capabilities {
-       MTK_RGMII_BIT = 0,
-       MTK_TRGMII_BIT,
-       MTK_SGMII_BIT,
-+      MTK_USXGMII_BIT,
-+      MTK_2P5GPHY_BIT,
-       MTK_ESW_BIT,
-       MTK_GEPHY_BIT,
-       MTK_MUX_BIT,
-@@ -960,8 +1047,11 @@ enum mkt_eth_capabilities {
-       MTK_ETH_MUX_GDM1_TO_GMAC1_ESW_BIT,
-       MTK_ETH_MUX_GMAC2_GMAC0_TO_GEPHY_BIT,
-       MTK_ETH_MUX_U3_GMAC2_TO_QPHY_BIT,
-+      MTK_ETH_MUX_GMAC2_TO_2P5GPHY_BIT,
-       MTK_ETH_MUX_GMAC1_GMAC2_TO_SGMII_RGMII_BIT,
-       MTK_ETH_MUX_GMAC12_TO_GEPHY_SGMII_BIT,
-+      MTK_ETH_MUX_GMAC123_TO_GEPHY_SGMII_BIT,
-+      MTK_ETH_MUX_GMAC123_TO_USXGMII_BIT,
-       /* PATH BITS */
-       MTK_ETH_PATH_GMAC1_RGMII_BIT,
-@@ -969,14 +1059,21 @@ enum mkt_eth_capabilities {
-       MTK_ETH_PATH_GMAC1_SGMII_BIT,
-       MTK_ETH_PATH_GMAC2_RGMII_BIT,
-       MTK_ETH_PATH_GMAC2_SGMII_BIT,
-+      MTK_ETH_PATH_GMAC2_2P5GPHY_BIT,
-       MTK_ETH_PATH_GMAC2_GEPHY_BIT,
-+      MTK_ETH_PATH_GMAC3_SGMII_BIT,
-       MTK_ETH_PATH_GDM1_ESW_BIT,
-+      MTK_ETH_PATH_GMAC1_USXGMII_BIT,
-+      MTK_ETH_PATH_GMAC2_USXGMII_BIT,
-+      MTK_ETH_PATH_GMAC3_USXGMII_BIT,
- };
- /* Supported hardware group on SoCs */
- #define MTK_RGMII             BIT_ULL(MTK_RGMII_BIT)
- #define MTK_TRGMII            BIT_ULL(MTK_TRGMII_BIT)
- #define MTK_SGMII             BIT_ULL(MTK_SGMII_BIT)
-+#define MTK_USXGMII           BIT_ULL(MTK_USXGMII_BIT)
-+#define MTK_2P5GPHY           BIT_ULL(MTK_2P5GPHY_BIT)
- #define MTK_ESW                       BIT_ULL(MTK_ESW_BIT)
- #define MTK_GEPHY             BIT_ULL(MTK_GEPHY_BIT)
- #define MTK_MUX                       BIT_ULL(MTK_MUX_BIT)
-@@ -999,10 +1096,16 @@ enum mkt_eth_capabilities {
-       BIT_ULL(MTK_ETH_MUX_GMAC2_GMAC0_TO_GEPHY_BIT)
- #define MTK_ETH_MUX_U3_GMAC2_TO_QPHY          \
-       BIT_ULL(MTK_ETH_MUX_U3_GMAC2_TO_QPHY_BIT)
-+#define MTK_ETH_MUX_GMAC2_TO_2P5GPHY          \
-+      BIT_ULL(MTK_ETH_MUX_GMAC2_TO_2P5GPHY_BIT)
- #define MTK_ETH_MUX_GMAC1_GMAC2_TO_SGMII_RGMII        \
-       BIT_ULL(MTK_ETH_MUX_GMAC1_GMAC2_TO_SGMII_RGMII_BIT)
- #define MTK_ETH_MUX_GMAC12_TO_GEPHY_SGMII     \
-       BIT_ULL(MTK_ETH_MUX_GMAC12_TO_GEPHY_SGMII_BIT)
-+#define MTK_ETH_MUX_GMAC123_TO_GEPHY_SGMII    \
-+      BIT_ULL(MTK_ETH_MUX_GMAC123_TO_GEPHY_SGMII_BIT)
-+#define MTK_ETH_MUX_GMAC123_TO_USXGMII        \
-+      BIT_ULL(MTK_ETH_MUX_GMAC123_TO_USXGMII_BIT)
- /* Supported path present on SoCs */
- #define MTK_ETH_PATH_GMAC1_RGMII      BIT_ULL(MTK_ETH_PATH_GMAC1_RGMII_BIT)
-@@ -1010,8 +1113,13 @@ enum mkt_eth_capabilities {
- #define MTK_ETH_PATH_GMAC1_SGMII      BIT_ULL(MTK_ETH_PATH_GMAC1_SGMII_BIT)
- #define MTK_ETH_PATH_GMAC2_RGMII      BIT_ULL(MTK_ETH_PATH_GMAC2_RGMII_BIT)
- #define MTK_ETH_PATH_GMAC2_SGMII      BIT_ULL(MTK_ETH_PATH_GMAC2_SGMII_BIT)
-+#define MTK_ETH_PATH_GMAC2_2P5GPHY    BIT_ULL(MTK_ETH_PATH_GMAC2_2P5GPHY_BIT)
- #define MTK_ETH_PATH_GMAC2_GEPHY      BIT_ULL(MTK_ETH_PATH_GMAC2_GEPHY_BIT)
-+#define MTK_ETH_PATH_GMAC3_SGMII      BIT_ULL(MTK_ETH_PATH_GMAC3_SGMII_BIT)
- #define MTK_ETH_PATH_GDM1_ESW         BIT_ULL(MTK_ETH_PATH_GDM1_ESW_BIT)
-+#define MTK_ETH_PATH_GMAC1_USXGMII    BIT_ULL(MTK_ETH_PATH_GMAC1_USXGMII_BIT)
-+#define MTK_ETH_PATH_GMAC2_USXGMII    BIT_ULL(MTK_ETH_PATH_GMAC2_USXGMII_BIT)
-+#define MTK_ETH_PATH_GMAC3_USXGMII    BIT_ULL(MTK_ETH_PATH_GMAC3_USXGMII_BIT)
- #define MTK_GMAC1_RGMII               (MTK_ETH_PATH_GMAC1_RGMII | MTK_RGMII)
- #define MTK_GMAC1_TRGMII      (MTK_ETH_PATH_GMAC1_TRGMII | MTK_TRGMII)
-@@ -1019,7 +1127,12 @@ enum mkt_eth_capabilities {
- #define MTK_GMAC2_RGMII               (MTK_ETH_PATH_GMAC2_RGMII | MTK_RGMII)
- #define MTK_GMAC2_SGMII               (MTK_ETH_PATH_GMAC2_SGMII | MTK_SGMII)
- #define MTK_GMAC2_GEPHY               (MTK_ETH_PATH_GMAC2_GEPHY | MTK_GEPHY)
-+#define MTK_GMAC2_2P5GPHY     (MTK_ETH_PATH_GMAC2_2P5GPHY | MTK_2P5GPHY)
-+#define MTK_GMAC3_SGMII               (MTK_ETH_PATH_GMAC3_SGMII | MTK_SGMII)
- #define MTK_GDM1_ESW          (MTK_ETH_PATH_GDM1_ESW | MTK_ESW)
-+#define MTK_GMAC1_USXGMII     (MTK_ETH_PATH_GMAC1_USXGMII | MTK_USXGMII)
-+#define MTK_GMAC2_USXGMII     (MTK_ETH_PATH_GMAC2_USXGMII | MTK_USXGMII)
-+#define MTK_GMAC3_USXGMII     (MTK_ETH_PATH_GMAC3_USXGMII | MTK_USXGMII)
- /* MUXes present on SoCs */
- /* 0: GDM1 -> GMAC1, 1: GDM1 -> ESW */
-@@ -1038,10 +1151,20 @@ enum mkt_eth_capabilities {
-       (MTK_ETH_MUX_GMAC1_GMAC2_TO_SGMII_RGMII | MTK_MUX | \
-       MTK_SHARED_SGMII)
-+/* 2: GMAC2 -> XGMII */
-+#define MTK_MUX_GMAC2_TO_2P5GPHY      \
-+      (MTK_ETH_MUX_GMAC2_TO_2P5GPHY | MTK_MUX | MTK_INFRA)
-+
- /* 0: GMACx -> GEPHY, 1: GMACx -> SGMII where x is 1 or 2 */
- #define MTK_MUX_GMAC12_TO_GEPHY_SGMII   \
-       (MTK_ETH_MUX_GMAC12_TO_GEPHY_SGMII | MTK_MUX)
-+#define MTK_MUX_GMAC123_TO_GEPHY_SGMII   \
-+      (MTK_ETH_MUX_GMAC123_TO_GEPHY_SGMII | MTK_MUX)
-+
-+#define MTK_MUX_GMAC123_TO_USXGMII   \
-+      (MTK_ETH_MUX_GMAC123_TO_USXGMII | MTK_MUX | MTK_INFRA)
-+
- #define MTK_HAS_CAPS(caps, _x)                (((caps) & (_x)) == (_x))
- #define MT7621_CAPS  (MTK_GMAC1_RGMII | MTK_GMAC1_TRGMII | \
-@@ -1073,8 +1196,12 @@ enum mkt_eth_capabilities {
-                     MTK_MUX_GMAC12_TO_GEPHY_SGMII | MTK_QDMA | \
-                     MTK_RSTCTRL_PPE1 | MTK_SRAM)
--#define MT7988_CAPS  (MTK_36BIT_DMA | MTK_GDM1_ESW | MTK_QDMA | \
--                    MTK_RSTCTRL_PPE1 | MTK_RSTCTRL_PPE2 | MTK_SRAM)
-+#define MT7988_CAPS  (MTK_36BIT_DMA | MTK_GDM1_ESW | MTK_GMAC1_SGMII | \
-+                    MTK_GMAC2_2P5GPHY | MTK_GMAC2_SGMII | MTK_GMAC2_USXGMII | \
-+                    MTK_GMAC3_SGMII | MTK_GMAC3_USXGMII | \
-+                    MTK_MUX_GMAC123_TO_GEPHY_SGMII | \
-+                    MTK_MUX_GMAC123_TO_USXGMII | MTK_MUX_GMAC2_TO_2P5GPHY | \
-+                    MTK_QDMA | MTK_RSTCTRL_PPE1 | MTK_RSTCTRL_PPE2 | MTK_SRAM)
- struct mtk_tx_dma_desc_info {
-       dma_addr_t      addr;
-@@ -1184,6 +1311,24 @@ struct mtk_soc_data {
- /* currently no SoC has more than 3 macs */
- #define MTK_MAX_DEVS  3
-+/* struct mtk_usxgmii_pcs - This structure holds each usxgmii regmap and
-+ *                    associated data
-+ * @regmap:           The register map pointing at the range used to setup
-+ *                    USXGMII modes
-+ * @interface:                Currently selected interface mode
-+ * @id:                       The element is used to record the index of PCS
-+ * @pcs:              Phylink PCS structure
-+ */
-+struct mtk_usxgmii_pcs {
-+      struct mtk_eth          *eth;
-+      struct regmap           *regmap;
-+      struct phylink_pcs      *wrapped_sgmii_pcs;
-+      phy_interface_t         interface;
-+      u8                      id;
-+      unsigned int            mode;
-+      struct phylink_pcs      pcs;
-+};
-+
- /* struct mtk_eth -   This is the main datasructure for holding the state
-  *                    of the driver
-  * @dev:              The device pointer
-@@ -1204,6 +1349,12 @@ struct mtk_soc_data {
-  * @infra:              The register map pointing at the range used to setup
-  *                      SGMII and GePHY path
-  * @sgmii_pcs:                Pointers to mtk-pcs-lynxi phylink_pcs instances
-+ * @sgmii_wrapped_pcs:        Pointers to NETSYSv3 wrapper PCS instances
-+ * @usxgmii_pll:      The register map pointing at the range used to control
-+ *                    the USXGMII SerDes PLL
-+ * @regmap_pextp:     The register map pointing at the range used to setup
-+ *                    PHYA
-+ * @usxgmii_pcs:      Pointer to array of pointers to struct for USXGMII PCS
-  * @pctl:             The register map pointing at the range used to setup
-  *                    GMAC port drive/slew values
-  * @dma_refcnt:               track how many netdevs are using the DMA engine
-@@ -1247,6 +1398,10 @@ struct mtk_eth {
-       struct regmap                   *ethsys;
-       struct regmap                   *infra;
-       struct phylink_pcs              *sgmii_pcs[MTK_MAX_DEVS];
-+      struct regmap                   *toprgu;
-+      struct regmap                   *usxgmii_pll;
-+      struct regmap                   *regmap_pextp[MTK_MAX_DEVS];
-+      struct mtk_usxgmii_pcs          *usxgmii_pcs[MTK_MAX_DEVS];
-       struct regmap                   *pctl;
-       bool                            hwlro;
-       refcount_t                      dma_refcnt;
-@@ -1434,6 +1589,19 @@ static inline u32 mtk_get_ib2_multicast_
-       return MTK_FOE_IB2_MULTICAST;
- }
-+static inline bool mtk_interface_mode_is_xgmii(phy_interface_t interface)
-+{
-+      switch (interface) {
-+      case PHY_INTERFACE_MODE_INTERNAL:
-+      case PHY_INTERFACE_MODE_USXGMII:
-+      case PHY_INTERFACE_MODE_10GBASER:
-+      case PHY_INTERFACE_MODE_5GBASER:
-+              return true;
-+      default:
-+              return false;
-+      }
-+}
-+
- /* read the hardware status register */
- void mtk_stats_update_mac(struct mtk_mac *mac);
-@@ -1442,8 +1610,10 @@ u32 mtk_r32(struct mtk_eth *eth, unsigne
- u32 mtk_m32(struct mtk_eth *eth, u32 mask, u32 set, unsigned int reg);
- int mtk_gmac_sgmii_path_setup(struct mtk_eth *eth, int mac_id);
-+int mtk_gmac_2p5gphy_path_setup(struct mtk_eth *eth, int mac_id);
- int mtk_gmac_gephy_path_setup(struct mtk_eth *eth, int mac_id);
- int mtk_gmac_rgmii_path_setup(struct mtk_eth *eth, int mac_id);
-+int mtk_gmac_usxgmii_path_setup(struct mtk_eth *eth, int mac_id);
- int mtk_eth_offload_init(struct mtk_eth *eth);
- int mtk_eth_setup_tc(struct net_device *dev, enum tc_setup_type type,
-@@ -1453,5 +1623,63 @@ int mtk_flow_offload_cmd(struct mtk_eth
- void mtk_flow_offload_cleanup(struct mtk_eth *eth, struct list_head *list);
- void mtk_eth_set_dma_device(struct mtk_eth *eth, struct device *dma_dev);
-+static inline int mtk_mac2xgmii_id(struct mtk_eth *eth, int mac_id)
-+{
-+      int xgmii_id = mac_id;
-+
-+      if (mtk_is_netsys_v3_or_greater(eth)) {
-+              switch (mac_id) {
-+              case MTK_GMAC1_ID:
-+              case MTK_GMAC2_ID:
-+                      xgmii_id = 1;
-+                      break;
-+              case MTK_GMAC3_ID:
-+                      xgmii_id = 0;
-+                      break;
-+              default:
-+                      xgmii_id = -1;
-+              }
-+      }
-+
-+      return MTK_HAS_CAPS(eth->soc->caps, MTK_SHARED_SGMII) ? 0 : xgmii_id;
-+}
-+
-+static inline int mtk_xgmii2mac_id(struct mtk_eth *eth, int xgmii_id)
-+{
-+      int mac_id = xgmii_id;
-+
-+      if (mtk_is_netsys_v3_or_greater(eth)) {
-+              switch (xgmii_id) {
-+              case 0:
-+                      mac_id = 2;
-+                      break;
-+              case 1:
-+                      mac_id = 1;
-+                      break;
-+              default:
-+                      mac_id = -1;
-+              }
-+      }
-+
-+      return mac_id;
-+}
-+
-+#ifdef CONFIG_NET_MEDIATEK_SOC_USXGMII
-+struct phylink_pcs *mtk_sgmii_wrapper_select_pcs(struct mtk_eth *eth, int id);
-+struct phylink_pcs *mtk_usxgmii_select_pcs(struct mtk_eth *eth, int id);
-+int mtk_usxgmii_init(struct mtk_eth *eth);
-+#else
-+static inline struct phylink_pcs *mtk_sgmii_wrapper_select_pcs(struct mtk_eth *eth, int id)
-+{
-+      return NULL;
-+}
-+
-+static inline struct phylink_pcs *mtk_usxgmii_select_pcs(struct mtk_eth *eth, int id)
-+{
-+      return NULL;
-+}
-+
-+static inline int mtk_usxgmii_init(struct mtk_eth *eth) { return 0; }
-+#endif /* NET_MEDIATEK_SOC_USXGMII */
- #endif /* MTK_ETH_H */
---- /dev/null
-+++ b/drivers/net/ethernet/mediatek/mtk_usxgmii.c
-@@ -0,0 +1,690 @@
-+// SPDX-License-Identifier: GPL-2.0
-+/*
-+ * Copyright (c) 2023 MediaTek Inc.
-+ * Author: Henry Yen <[email protected]>
-+ *         Daniel Golle <[email protected]>
-+ */
-+
-+#include <linux/mfd/syscon.h>
-+#include <linux/of.h>
-+#include <linux/regmap.h>
-+#include "mtk_eth_soc.h"
-+
-+static struct mtk_usxgmii_pcs *pcs_to_mtk_usxgmii_pcs(struct phylink_pcs *pcs)
-+{
-+      return container_of(pcs, struct mtk_usxgmii_pcs, pcs);
-+}
-+
-+static int mtk_xfi_pextp_init(struct mtk_eth *eth)
-+{
-+      struct device *dev = eth->dev;
-+      struct device_node *r = dev->of_node;
-+      struct device_node *np;
-+      int i;
-+
-+      for (i = 0; i < MTK_MAX_DEVS; i++) {
-+              np = of_parse_phandle(r, "mediatek,xfi-pextp", i);
-+              if (!np)
-+                      break;
-+
-+              eth->regmap_pextp[i] = syscon_node_to_regmap(np);
-+              if (IS_ERR(eth->regmap_pextp[i]))
-+                      return PTR_ERR(eth->regmap_pextp[i]);
-+      }
-+
-+      return 0;
-+}
-+
-+static int mtk_xfi_pll_init(struct mtk_eth *eth)
-+{
-+      struct device_node *r = eth->dev->of_node;
-+      struct device_node *np;
-+
-+      np = of_parse_phandle(r, "mediatek,xfi-pll", 0);
-+      if (!np)
-+              return -1;
-+
-+      eth->usxgmii_pll = syscon_node_to_regmap(np);
-+      if (IS_ERR(eth->usxgmii_pll))
-+              return PTR_ERR(eth->usxgmii_pll);
-+
-+      return 0;
-+}
-+
-+static int mtk_toprgu_init(struct mtk_eth *eth)
-+{
-+      struct device_node *r = eth->dev->of_node;
-+      struct device_node *np;
-+
-+      np = of_parse_phandle(r, "mediatek,toprgu", 0);
-+      if (!np)
-+              return -1;
-+
-+      eth->toprgu = syscon_node_to_regmap(np);
-+      if (IS_ERR(eth->toprgu))
-+              return PTR_ERR(eth->toprgu);
-+
-+      return 0;
-+}
-+
-+static int mtk_xfi_pll_enable(struct mtk_eth *eth)
-+{
-+      u32 val = 0;
-+
-+      if (!eth->usxgmii_pll)
-+              return -EINVAL;
-+
-+      /* Add software workaround for USXGMII PLL TCL issue */
-+      regmap_write(eth->usxgmii_pll, XFI_PLL_ANA_GLB8, RG_XFI_PLL_ANA_SWWA);
-+
-+      regmap_read(eth->usxgmii_pll, XFI_PLL_DIG_GLB8, &val);
-+      val |= RG_XFI_PLL_EN;
-+      regmap_write(eth->usxgmii_pll, XFI_PLL_DIG_GLB8, val);
-+
-+      return 0;
-+}
-+
-+static void mtk_usxgmii_setup_phya(struct regmap *pextp, phy_interface_t interface, int id)
-+{
-+      bool is_10g = (interface == PHY_INTERFACE_MODE_10GBASER ||
-+                     interface == PHY_INTERFACE_MODE_USXGMII);
-+      bool is_2p5g = (interface == PHY_INTERFACE_MODE_2500BASEX);
-+      bool is_5g = (interface == PHY_INTERFACE_MODE_5GBASER);
-+
-+      /* Setup operation mode */
-+      if (is_10g)
-+              regmap_write(pextp, 0x9024, 0x00C9071C);
-+      else
-+              regmap_write(pextp, 0x9024, 0x00D9071C);
-+
-+      if (is_5g)
-+              regmap_write(pextp, 0x2020, 0xAAA5A5AA);
-+      else
-+              regmap_write(pextp, 0x2020, 0xAA8585AA);
-+
-+      if (is_2p5g || is_5g || is_10g) {
-+              regmap_write(pextp, 0x2030, 0x0C020707);
-+              regmap_write(pextp, 0x2034, 0x0E050F0F);
-+              regmap_write(pextp, 0x2040, 0x00140032);
-+      } else {
-+              regmap_write(pextp, 0x2030, 0x0C020207);
-+              regmap_write(pextp, 0x2034, 0x0E05050F);
-+              regmap_write(pextp, 0x2040, 0x00200032);
-+      }
-+
-+      if (is_2p5g || is_10g)
-+              regmap_write(pextp, 0x50F0, 0x00C014AA);
-+      else if (is_5g)
-+              regmap_write(pextp, 0x50F0, 0x00C018AA);
-+      else
-+              regmap_write(pextp, 0x50F0, 0x00C014BA);
-+
-+      if (is_5g) {
-+              regmap_write(pextp, 0x50E0, 0x3777812B);
-+              regmap_write(pextp, 0x506C, 0x005C9CFF);
-+              regmap_write(pextp, 0x5070, 0x9DFAFAFA);
-+              regmap_write(pextp, 0x5074, 0x273F3F3F);
-+              regmap_write(pextp, 0x5078, 0xA8883868);
-+              regmap_write(pextp, 0x507C, 0x14661466);
-+      } else {
-+              regmap_write(pextp, 0x50E0, 0x3777C12B);
-+              regmap_write(pextp, 0x506C, 0x005F9CFF);
-+              regmap_write(pextp, 0x5070, 0x9D9DFAFA);
-+              regmap_write(pextp, 0x5074, 0x27273F3F);
-+              regmap_write(pextp, 0x5078, 0xA7883C68);
-+              regmap_write(pextp, 0x507C, 0x11661166);
-+      }
-+
-+      if (is_2p5g || is_10g) {
-+              regmap_write(pextp, 0x5080, 0x0E000AAF);
-+              regmap_write(pextp, 0x5084, 0x08080D0D);
-+              regmap_write(pextp, 0x5088, 0x02030909);
-+      } else if (is_5g) {
-+              regmap_write(pextp, 0x5080, 0x0E001ABF);
-+              regmap_write(pextp, 0x5084, 0x080B0D0D);
-+              regmap_write(pextp, 0x5088, 0x02050909);
-+      } else {
-+              regmap_write(pextp, 0x5080, 0x0E000EAF);
-+              regmap_write(pextp, 0x5084, 0x08080E0D);
-+              regmap_write(pextp, 0x5088, 0x02030B09);
-+      }
-+
-+      if (is_5g) {
-+              regmap_write(pextp, 0x50E4, 0x0C000000);
-+              regmap_write(pextp, 0x50E8, 0x04000000);
-+      } else {
-+              regmap_write(pextp, 0x50E4, 0x0C0C0000);
-+              regmap_write(pextp, 0x50E8, 0x04040000);
-+      }
-+
-+      if (is_2p5g || mtk_interface_mode_is_xgmii(interface))
-+              regmap_write(pextp, 0x50EC, 0x0F0F0C06);
-+      else
-+              regmap_write(pextp, 0x50EC, 0x0F0F0606);
-+
-+      if (is_5g) {
-+              regmap_write(pextp, 0x50A8, 0x50808C8C);
-+              regmap_write(pextp, 0x6004, 0x18000000);
-+      } else {
-+              regmap_write(pextp, 0x50A8, 0x506E8C8C);
-+              regmap_write(pextp, 0x6004, 0x18190000);
-+      }
-+
-+      if (is_10g)
-+              regmap_write(pextp, 0x00F8, 0x01423342);
-+      else if (is_5g)
-+              regmap_write(pextp, 0x00F8, 0x00A132A1);
-+      else if (is_2p5g)
-+              regmap_write(pextp, 0x00F8, 0x009C329C);
-+      else
-+              regmap_write(pextp, 0x00F8, 0x00FA32FA);
-+
-+      /* Force SGDT_OUT off and select PCS */
-+      if (mtk_interface_mode_is_xgmii(interface))
-+              regmap_write(pextp, 0x00F4, 0x80201F20);
-+      else
-+              regmap_write(pextp, 0x00F4, 0x80201F21);
-+
-+      /* Force GLB_CKDET_OUT */
-+      regmap_write(pextp, 0x0030, 0x00050C00);
-+
-+      /* Force AEQ on */
-+      regmap_write(pextp, 0x0070, 0x02002800);
-+      ndelay(1020);
-+
-+      /* Setup DA default value */
-+      regmap_write(pextp, 0x30B0, 0x00000020);
-+      regmap_write(pextp, 0x3028, 0x00008A01);
-+      regmap_write(pextp, 0x302C, 0x0000A884);
-+      regmap_write(pextp, 0x3024, 0x00083002);
-+      if (mtk_interface_mode_is_xgmii(interface)) {
-+              regmap_write(pextp, 0x3010, 0x00022220);
-+              regmap_write(pextp, 0x5064, 0x0F020A01);
-+              regmap_write(pextp, 0x50B4, 0x06100600);
-+              if (interface == PHY_INTERFACE_MODE_USXGMII)
-+                      regmap_write(pextp, 0x3048, 0x40704000);
-+              else
-+                      regmap_write(pextp, 0x3048, 0x47684100);
-+      } else {
-+              regmap_write(pextp, 0x3010, 0x00011110);
-+              regmap_write(pextp, 0x3048, 0x40704000);
-+      }
-+
-+      if (!mtk_interface_mode_is_xgmii(interface) && !is_2p5g)
-+              regmap_write(pextp, 0x3064, 0x0000C000);
-+
-+      if (interface == PHY_INTERFACE_MODE_USXGMII) {
-+              regmap_write(pextp, 0x3050, 0xA8000000);
-+              regmap_write(pextp, 0x3054, 0x000000AA);
-+      } else if (mtk_interface_mode_is_xgmii(interface)) {
-+              regmap_write(pextp, 0x3050, 0x00000000);
-+              regmap_write(pextp, 0x3054, 0x00000000);
-+      } else {
-+              regmap_write(pextp, 0x3050, 0xA8000000);
-+              regmap_write(pextp, 0x3054, 0x000000AA);
-+      }
-+
-+      if (mtk_interface_mode_is_xgmii(interface))
-+              regmap_write(pextp, 0x306C, 0x00000F00);
-+      else if (is_2p5g)
-+              regmap_write(pextp, 0x306C, 0x22000F00);
-+      else
-+              regmap_write(pextp, 0x306C, 0x20200F00);
-+
-+      if (interface == PHY_INTERFACE_MODE_10GBASER && id == 0)
-+              regmap_write(pextp, 0xA008, 0x0007B400);
-+
-+      if (mtk_interface_mode_is_xgmii(interface))
-+              regmap_write(pextp, 0xA060, 0x00040000);
-+      else
-+              regmap_write(pextp, 0xA060, 0x00050000);
-+
-+      if (is_10g)
-+              regmap_write(pextp, 0x90D0, 0x00000001);
-+      else if (is_5g)
-+              regmap_write(pextp, 0x90D0, 0x00000003);
-+      else if (is_2p5g)
-+              regmap_write(pextp, 0x90D0, 0x00000005);
-+      else
-+              regmap_write(pextp, 0x90D0, 0x00000007);
-+
-+      /* Release reset */
-+      regmap_write(pextp, 0x0070, 0x0200E800);
-+      usleep_range(150, 500);
-+
-+      /* Switch to P0 */
-+      regmap_write(pextp, 0x0070, 0x0200C111);
-+      ndelay(1020);
-+      regmap_write(pextp, 0x0070, 0x0200C101);
-+      usleep_range(15, 50);
-+
-+      if (mtk_interface_mode_is_xgmii(interface)) {
-+              /* Switch to Gen3 */
-+              regmap_write(pextp, 0x0070, 0x0202C111);
-+      } else {
-+              /* Switch to Gen2 */
-+              regmap_write(pextp, 0x0070, 0x0201C111);
-+      }
-+      ndelay(1020);
-+      if (mtk_interface_mode_is_xgmii(interface))
-+              regmap_write(pextp, 0x0070, 0x0202C101);
-+      else
-+              regmap_write(pextp, 0x0070, 0x0201C101);
-+      usleep_range(100, 500);
-+      regmap_write(pextp, 0x30B0, 0x00000030);
-+      if (mtk_interface_mode_is_xgmii(interface))
-+              regmap_write(pextp, 0x00F4, 0x80201F00);
-+      else
-+              regmap_write(pextp, 0x00F4, 0x80201F01);
-+
-+      regmap_write(pextp, 0x3040, 0x30000000);
-+      usleep_range(400, 1000);
-+}
-+
-+static void mtk_usxgmii_reset(struct mtk_eth *eth, int id)
-+{
-+      u32 toggle, val;
-+
-+      if (id >= MTK_MAX_DEVS || !eth->toprgu)
-+              return;
-+
-+      switch (id) {
-+      case 0:
-+              toggle = SWSYSRST_XFI_PEXPT0_GRST | SWSYSRST_XFI0_GRST |
-+                       SWSYSRST_SGMII0_GRST;
-+              break;
-+      case 1:
-+              toggle = SWSYSRST_XFI_PEXPT1_GRST | SWSYSRST_XFI1_GRST |
-+                       SWSYSRST_SGMII1_GRST;
-+              break;
-+      default:
-+              return;
-+      }
-+
-+      /* Enable software reset */
-+      regmap_set_bits(eth->toprgu, TOPRGU_SWSYSRST_EN, toggle);
-+
-+      /* Assert USXGMII reset */
-+      regmap_set_bits(eth->toprgu, TOPRGU_SWSYSRST,
-+                      FIELD_PREP(SWSYSRST_UNLOCK_KEY, 0x88) | toggle);
-+
-+      usleep_range(100, 500);
-+
-+      /* De-assert USXGMII reset */
-+      regmap_read(eth->toprgu, TOPRGU_SWSYSRST, &val);
-+      val |= FIELD_PREP(SWSYSRST_UNLOCK_KEY, 0x88);
-+      val &= ~toggle;
-+      regmap_write(eth->toprgu, TOPRGU_SWSYSRST, val);
-+
-+      /* Disable software reset */
-+      regmap_clear_bits(eth->toprgu, TOPRGU_SWSYSRST_EN, toggle);
-+
-+      mdelay(10);
-+}
-+
-+/* As the USXGMII PHYA is shared with the 1000Base-X/2500Base-X/Cisco SGMII unit
-+ * the psc-mtk-lynxi instance needs to be wrapped, so that calls to .pcs_config
-+ * also trigger an initial reset and subsequent configuration of the PHYA.
-+ */
-+struct mtk_sgmii_wrapper_pcs {
-+      struct mtk_eth          *eth;
-+      struct phylink_pcs      *wrapped_pcs;
-+      u8                      id;
-+      struct phylink_pcs      pcs;
-+};
-+
-+static int mtk_sgmii_wrapped_pcs_config(struct phylink_pcs *pcs,
-+                                      unsigned int mode,
-+                                      phy_interface_t interface,
-+                                      const unsigned long *advertising,
-+                                      bool permit_pause_to_mac)
-+{
-+      struct mtk_sgmii_wrapper_pcs *wp = container_of(pcs, struct mtk_sgmii_wrapper_pcs, pcs);
-+      bool full_reconf;
-+      int ret;
-+
-+      full_reconf = interface != wp->eth->usxgmii_pcs[wp->id]->interface;
-+      if (full_reconf) {
-+              mtk_xfi_pll_enable(wp->eth);
-+              mtk_usxgmii_reset(wp->eth, wp->id);
-+      }
-+
-+      ret = wp->wrapped_pcs->ops->pcs_config(wp->wrapped_pcs, mode, interface,
-+                                             advertising, permit_pause_to_mac);
-+
-+      if (full_reconf)
-+              mtk_usxgmii_setup_phya(wp->eth->regmap_pextp[wp->id], interface, wp->id);
-+
-+      wp->eth->usxgmii_pcs[wp->id]->interface = interface;
-+
-+      return ret;
-+}
-+
-+static void mtk_sgmii_wrapped_pcs_get_state(struct phylink_pcs *pcs,
-+                                          struct phylink_link_state *state)
-+{
-+      struct mtk_sgmii_wrapper_pcs *wp = container_of(pcs, struct mtk_sgmii_wrapper_pcs, pcs);
-+
-+      return wp->wrapped_pcs->ops->pcs_get_state(wp->wrapped_pcs, state);
-+}
-+
-+static void mtk_sgmii_wrapped_pcs_an_restart(struct phylink_pcs *pcs)
-+{
-+      struct mtk_sgmii_wrapper_pcs *wp = container_of(pcs, struct mtk_sgmii_wrapper_pcs, pcs);
-+
-+      wp->wrapped_pcs->ops->pcs_an_restart(wp->wrapped_pcs);
-+}
-+
-+static void mtk_sgmii_wrapped_pcs_link_up(struct phylink_pcs *pcs,
-+                                        unsigned int mode,
-+                                        phy_interface_t interface, int speed,
-+                                        int duplex)
-+{
-+      struct mtk_sgmii_wrapper_pcs *wp = container_of(pcs, struct mtk_sgmii_wrapper_pcs, pcs);
-+
-+      wp->wrapped_pcs->ops->pcs_link_up(wp->wrapped_pcs, mode, interface, speed, duplex);
-+}
-+
-+static void mtk_sgmii_wrapped_pcs_disable(struct phylink_pcs *pcs)
-+{
-+      struct mtk_sgmii_wrapper_pcs *wp = container_of(pcs, struct mtk_sgmii_wrapper_pcs, pcs);
-+
-+      wp->wrapped_pcs->ops->pcs_disable(wp->wrapped_pcs);
-+
-+      wp->eth->usxgmii_pcs[wp->id]->interface = PHY_INTERFACE_MODE_NA;
-+}
-+
-+static const struct phylink_pcs_ops mtk_sgmii_wrapped_pcs_ops = {
-+      .pcs_get_state = mtk_sgmii_wrapped_pcs_get_state,
-+      .pcs_config = mtk_sgmii_wrapped_pcs_config,
-+      .pcs_an_restart = mtk_sgmii_wrapped_pcs_an_restart,
-+      .pcs_link_up = mtk_sgmii_wrapped_pcs_link_up,
-+      .pcs_disable = mtk_sgmii_wrapped_pcs_disable,
-+};
-+
-+static int mtk_sgmii_wrapper_init(struct mtk_eth *eth)
-+{
-+      struct mtk_sgmii_wrapper_pcs *wp;
-+      int i;
-+
-+      for (i = 0; i < MTK_MAX_DEVS; i++) {
-+              if (!eth->sgmii_pcs[i])
-+                      continue;
-+
-+              if (!eth->usxgmii_pcs[i])
-+                      continue;
-+
-+              /* Make sure all PCS ops are supported by wrapped PCS */
-+              if (!eth->sgmii_pcs[i]->ops->pcs_get_state ||
-+                  !eth->sgmii_pcs[i]->ops->pcs_config ||
-+                  !eth->sgmii_pcs[i]->ops->pcs_an_restart ||
-+                  !eth->sgmii_pcs[i]->ops->pcs_link_up ||
-+                  !eth->sgmii_pcs[i]->ops->pcs_disable)
-+                      return -EOPNOTSUPP;
-+
-+              wp = devm_kzalloc(eth->dev, sizeof(*wp), GFP_KERNEL);
-+              if (!wp)
-+                      return -ENOMEM;
-+
-+              wp->wrapped_pcs = eth->sgmii_pcs[i];
-+              wp->id = i;
-+              wp->pcs.poll = true;
-+              wp->pcs.ops = &mtk_sgmii_wrapped_pcs_ops;
-+              wp->eth = eth;
-+
-+              eth->usxgmii_pcs[i]->wrapped_sgmii_pcs = &wp->pcs;
-+      }
-+
-+      return 0;
-+}
-+
-+struct phylink_pcs *mtk_sgmii_wrapper_select_pcs(struct mtk_eth *eth, int mac_id)
-+{
-+      u32 xgmii_id = mtk_mac2xgmii_id(eth, mac_id);
-+
-+      if (!eth->usxgmii_pcs[xgmii_id])
-+              return NULL;
-+
-+      return eth->usxgmii_pcs[xgmii_id]->wrapped_sgmii_pcs;
-+}
-+
-+static int mtk_usxgmii_pcs_config(struct phylink_pcs *pcs, unsigned int mode,
-+                                phy_interface_t interface,
-+                                const unsigned long *advertising,
-+                                bool permit_pause_to_mac)
-+{
-+      struct mtk_usxgmii_pcs *mpcs = pcs_to_mtk_usxgmii_pcs(pcs);
-+      struct mtk_eth *eth = mpcs->eth;
-+      struct regmap *pextp = eth->regmap_pextp[mpcs->id];
-+      unsigned int an_ctrl = 0, link_timer = 0, xfi_mode = 0, adapt_mode = 0;
-+      bool mode_changed = false;
-+
-+      if (!pextp)
-+              return -ENODEV;
-+
-+      if (interface == PHY_INTERFACE_MODE_USXGMII) {
-+              an_ctrl = FIELD_PREP(USXGMII_AN_SYNC_CNT, 0x1FF) | USXGMII_AN_ENABLE;
-+              link_timer = FIELD_PREP(USXGMII_LINK_TIMER_IDLE_DETECT, 0x7B) |
-+                           FIELD_PREP(USXGMII_LINK_TIMER_COMP_ACK_DETECT, 0x7B) |
-+                           FIELD_PREP(USXGMII_LINK_TIMER_AN_RESTART, 0x7B);
-+              xfi_mode = FIELD_PREP(USXGMII_XFI_RX_MODE, USXGMII_XFI_RX_MODE_10G) |
-+                         FIELD_PREP(USXGMII_XFI_TX_MODE, USXGMII_XFI_TX_MODE_10G);
-+      } else if (interface == PHY_INTERFACE_MODE_10GBASER) {
-+              an_ctrl = FIELD_PREP(USXGMII_AN_SYNC_CNT, 0x1FF);
-+              link_timer = FIELD_PREP(USXGMII_LINK_TIMER_IDLE_DETECT, 0x7B) |
-+                           FIELD_PREP(USXGMII_LINK_TIMER_COMP_ACK_DETECT, 0x7B) |
-+                           FIELD_PREP(USXGMII_LINK_TIMER_AN_RESTART, 0x7B);
-+              xfi_mode = FIELD_PREP(USXGMII_XFI_RX_MODE, USXGMII_XFI_RX_MODE_10G) |
-+                         FIELD_PREP(USXGMII_XFI_TX_MODE, USXGMII_XFI_TX_MODE_10G);
-+              adapt_mode = USXGMII_RATE_UPDATE_MODE;
-+      } else if (interface == PHY_INTERFACE_MODE_5GBASER) {
-+              an_ctrl = FIELD_PREP(USXGMII_AN_SYNC_CNT, 0xFF);
-+              link_timer = FIELD_PREP(USXGMII_LINK_TIMER_IDLE_DETECT, 0x3D) |
-+                           FIELD_PREP(USXGMII_LINK_TIMER_COMP_ACK_DETECT, 0x3D) |
-+                           FIELD_PREP(USXGMII_LINK_TIMER_AN_RESTART, 0x3D);
-+              xfi_mode = FIELD_PREP(USXGMII_XFI_RX_MODE, USXGMII_XFI_RX_MODE_5G) |
-+                         FIELD_PREP(USXGMII_XFI_TX_MODE, USXGMII_XFI_TX_MODE_5G);
-+              adapt_mode = USXGMII_RATE_UPDATE_MODE;
-+      } else {
-+              return -EINVAL;
-+      }
-+
-+      adapt_mode |= FIELD_PREP(USXGMII_RATE_ADAPT_MODE, USXGMII_RATE_ADAPT_MODE_X1);
-+
-+      if (mpcs->interface != interface) {
-+              mpcs->interface = interface;
-+              mode_changed = true;
-+      }
-+
-+      mtk_xfi_pll_enable(eth);
-+      mtk_usxgmii_reset(eth, mpcs->id);
-+
-+      /* Setup USXGMII AN ctrl */
-+      regmap_update_bits(mpcs->regmap, RG_PCS_AN_CTRL0,
-+                         USXGMII_AN_SYNC_CNT | USXGMII_AN_ENABLE,
-+                         an_ctrl);
-+
-+      regmap_update_bits(mpcs->regmap, RG_PCS_AN_CTRL2,
-+                         USXGMII_LINK_TIMER_IDLE_DETECT |
-+                         USXGMII_LINK_TIMER_COMP_ACK_DETECT |
-+                         USXGMII_LINK_TIMER_AN_RESTART,
-+                         link_timer);
-+
-+      mpcs->mode = mode;
-+
-+      /* Gated MAC CK */
-+      regmap_update_bits(mpcs->regmap, RG_PHY_TOP_SPEED_CTRL1,
-+                         USXGMII_MAC_CK_GATED, USXGMII_MAC_CK_GATED);
-+
-+      /* Enable interface force mode */
-+      regmap_update_bits(mpcs->regmap, RG_PHY_TOP_SPEED_CTRL1,
-+                         USXGMII_IF_FORCE_EN, USXGMII_IF_FORCE_EN);
-+
-+      /* Setup USXGMII adapt mode */
-+      regmap_update_bits(mpcs->regmap, RG_PHY_TOP_SPEED_CTRL1,
-+                         USXGMII_RATE_UPDATE_MODE | USXGMII_RATE_ADAPT_MODE,
-+                         adapt_mode);
-+
-+      /* Setup USXGMII speed */
-+      regmap_update_bits(mpcs->regmap, RG_PHY_TOP_SPEED_CTRL1,
-+                         USXGMII_XFI_RX_MODE | USXGMII_XFI_TX_MODE,
-+                         xfi_mode);
-+
-+      usleep_range(1, 10);
-+
-+      /* Un-gated MAC CK */
-+      regmap_update_bits(mpcs->regmap, RG_PHY_TOP_SPEED_CTRL1,
-+                         USXGMII_MAC_CK_GATED, 0);
-+
-+      usleep_range(1, 10);
-+
-+      /* Disable interface force mode for the AN mode */
-+      if (an_ctrl & USXGMII_AN_ENABLE)
-+              regmap_update_bits(mpcs->regmap, RG_PHY_TOP_SPEED_CTRL1,
-+                                 USXGMII_IF_FORCE_EN, 0);
-+
-+      /* Setup USXGMIISYS with the determined property */
-+      mtk_usxgmii_setup_phya(pextp, interface, mpcs->id);
-+
-+      return mode_changed;
-+}
-+
-+static void mtk_usxgmii_pcs_get_state(struct phylink_pcs *pcs,
-+                                    struct phylink_link_state *state)
-+{
-+      struct mtk_usxgmii_pcs *mpcs = pcs_to_mtk_usxgmii_pcs(pcs);
-+      struct mtk_eth *eth = mpcs->eth;
-+      struct mtk_mac *mac = eth->mac[mtk_xgmii2mac_id(eth, mpcs->id)];
-+      u32 val = 0;
-+
-+      regmap_read(mpcs->regmap, RG_PCS_AN_CTRL0, &val);
-+      if (FIELD_GET(USXGMII_AN_ENABLE, val)) {
-+              /* Refresh LPA by inverting LPA_LATCH */
-+              regmap_read(mpcs->regmap, RG_PCS_AN_STS0, &val);
-+              regmap_update_bits(mpcs->regmap, RG_PCS_AN_STS0,
-+                                 USXGMII_LPA_LATCH,
-+                                 !(val & USXGMII_LPA_LATCH));
-+
-+              regmap_read(mpcs->regmap, RG_PCS_AN_STS0, &val);
-+
-+              phylink_decode_usxgmii_word(state, FIELD_GET(USXGMII_PCS_AN_WORD,
-+                                                           val));
-+
-+              state->interface = mpcs->interface;
-+      } else {
-+              val = mtk_r32(mac->hw, MTK_XGMAC_STS(mac->id));
-+
-+              if (mac->id == MTK_GMAC2_ID)
-+                      val >>= 16;
-+
-+              switch (FIELD_GET(MTK_USXGMII_PCS_MODE, val)) {
-+              case 0:
-+                      state->speed = SPEED_10000;
-+                      break;
-+              case 1:
-+                      state->speed = SPEED_5000;
-+                      break;
-+              case 2:
-+                      state->speed = SPEED_2500;
-+                      break;
-+              case 3:
-+                      state->speed = SPEED_1000;
-+                      break;
-+              }
-+
-+              state->interface = mpcs->interface;
-+              state->link = FIELD_GET(MTK_USXGMII_PCS_LINK, val);
-+              state->duplex = DUPLEX_FULL;
-+      }
-+
-+      /* Continuously repeat re-configuration sequence until link comes up */
-+      if (state->link == 0)
-+              mtk_usxgmii_pcs_config(pcs, mpcs->mode,
-+                                     state->interface, NULL, false);
-+}
-+
-+static void mtk_usxgmii_pcs_restart_an(struct phylink_pcs *pcs)
-+{
-+      struct mtk_usxgmii_pcs *mpcs = pcs_to_mtk_usxgmii_pcs(pcs);
-+      unsigned int val = 0;
-+
-+      if (!mpcs->regmap)
-+              return;
-+
-+      regmap_read(mpcs->regmap, RG_PCS_AN_CTRL0, &val);
-+      val |= USXGMII_AN_RESTART;
-+      regmap_write(mpcs->regmap, RG_PCS_AN_CTRL0, val);
-+}
-+
-+static void mtk_usxgmii_pcs_link_up(struct phylink_pcs *pcs, unsigned int mode,
-+                                  phy_interface_t interface,
-+                                  int speed, int duplex)
-+{
-+      /* Reconfiguring USXGMII to ensure the quality of the RX signal
-+       * after the line side link up.
-+       */
-+      mtk_usxgmii_pcs_config(pcs, mode,
-+                             interface, NULL, false);
-+}
-+
-+static const struct phylink_pcs_ops mtk_usxgmii_pcs_ops = {
-+      .pcs_config = mtk_usxgmii_pcs_config,
-+      .pcs_get_state = mtk_usxgmii_pcs_get_state,
-+      .pcs_an_restart = mtk_usxgmii_pcs_restart_an,
-+      .pcs_link_up = mtk_usxgmii_pcs_link_up,
-+};
-+
-+int mtk_usxgmii_init(struct mtk_eth *eth)
-+{
-+      struct device_node *r = eth->dev->of_node;
-+      struct device *dev = eth->dev;
-+      struct device_node *np;
-+      int i, ret;
-+
-+      for (i = 0; i < MTK_MAX_DEVS; i++) {
-+              np = of_parse_phandle(r, "mediatek,usxgmiisys", i);
-+              if (!np)
-+                      break;
-+
-+              eth->usxgmii_pcs[i] = devm_kzalloc(dev, sizeof(*eth->usxgmii_pcs[i]), GFP_KERNEL);
-+              if (!eth->usxgmii_pcs[i])
-+                      return -ENOMEM;
-+
-+              eth->usxgmii_pcs[i]->id = i;
-+              eth->usxgmii_pcs[i]->eth = eth;
-+              eth->usxgmii_pcs[i]->regmap = syscon_node_to_regmap(np);
-+              if (IS_ERR(eth->usxgmii_pcs[i]->regmap))
-+                      return PTR_ERR(eth->usxgmii_pcs[i]->regmap);
-+
-+              eth->usxgmii_pcs[i]->pcs.ops = &mtk_usxgmii_pcs_ops;
-+              eth->usxgmii_pcs[i]->pcs.poll = true;
-+              eth->usxgmii_pcs[i]->interface = PHY_INTERFACE_MODE_NA;
-+              eth->usxgmii_pcs[i]->mode = -1;
-+
-+              of_node_put(np);
-+      }
-+
-+      ret = mtk_xfi_pextp_init(eth);
-+      if (ret)
-+              return ret;
-+
-+      ret = mtk_xfi_pll_init(eth);
-+      if (ret)
-+              return ret;
-+
-+      ret = mtk_toprgu_init(eth);
-+      if (ret)
-+              return ret;
-+
-+      return mtk_sgmii_wrapper_init(eth);
-+}
-+
-+struct phylink_pcs *mtk_usxgmii_select_pcs(struct mtk_eth *eth, int mac_id)
-+{
-+      u32 xgmii_id = mtk_mac2xgmii_id(eth, mac_id);
-+
-+      if (!eth->usxgmii_pcs[xgmii_id]->regmap)
-+              return NULL;
-+
-+      return &eth->usxgmii_pcs[xgmii_id]->pcs;
-+}
diff --git a/target/linux/generic/pending-5.15/738-net-ethernet-mtk_eth_soc-set-coherent-mask-to-get-PP.patch b/target/linux/generic/pending-5.15/738-net-ethernet-mtk_eth_soc-set-coherent-mask-to-get-PP.patch
deleted file mode 100644 (file)
index dda864a..0000000
+++ /dev/null
@@ -1,46 +0,0 @@
-From dee3f591103910c8d8b2a6d57879ccd2a4be4b10 Mon Sep 17 00:00:00 2001
-Message-ID: <dee3f591103910c8d8b2a6d57879ccd2a4be4b10.1706067287.git.daniel@makrotopia.org>
-From: Daniel Golle <[email protected]>
-Date: Wed, 24 Jan 2024 03:19:49 +0000
-Subject: [PATCH net] net: ethernet: mtk_eth_soc: set coherent mask to get PPE
- working
-To: Felix Fietkau <[email protected]>,
-    Sean Wang <[email protected]>,
-    Mark Lee <[email protected]>,
-    Lorenzo Bianconi <[email protected]>,
-    David S. Miller <[email protected]>,
-    Eric Dumazet <[email protected]>,
-    Jakub Kicinski <[email protected]>,
-    Paolo Abeni <[email protected]>,
-    Matthias Brugger <[email protected]>,
-    AngeloGioacchino Del Regno <[email protected]>,
-    Daniel Golle <[email protected]>,
-
-Set DMA coherent mask to 32-bit which makes PPE offloading engine start
-working on BPi-R4 which got 4 GiB of RAM.
-
-Fixes: 2d75891ebc09 ("net: ethernet: mtk_eth_soc: support 36-bit DMA addressing on MT7988")
-Suggested-by: Elad Yifee <[email protected]>
-Signed-off-by: Daniel Golle <[email protected]>
----
- drivers/net/ethernet/mediatek/mtk_eth_soc.c | 5 ++++-
- 1 file changed, 4 insertions(+), 1 deletion(-)
-
---- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
-@@ -4832,7 +4832,10 @@ static int mtk_probe(struct platform_dev
-       }
-       if (MTK_HAS_CAPS(eth->soc->caps, MTK_36BIT_DMA)) {
--              err = dma_set_mask_and_coherent(&pdev->dev, DMA_BIT_MASK(36));
-+              err = dma_set_mask(&pdev->dev, DMA_BIT_MASK(36));
-+              if (!err)
-+                      err = dma_set_coherent_mask(&pdev->dev, DMA_BIT_MASK(32));
-+
-               if (err) {
-                       dev_err(&pdev->dev, "Wrong DMA config\n");
-                       return -EINVAL;
diff --git a/target/linux/generic/pending-5.15/740-net-phy-motorcomm-Add-missing-include.patch b/target/linux/generic/pending-5.15/740-net-phy-motorcomm-Add-missing-include.patch
deleted file mode 100644 (file)
index 2a1f908..0000000
+++ /dev/null
@@ -1,22 +0,0 @@
-From 6f291aa7da199c6486cc229b055dcbcd5cee7a21 Mon Sep 17 00:00:00 2001
-From: Hauke Mehrtens <[email protected]>
-Date: Sun, 21 May 2023 22:24:56 +0200
-Subject: [PATCH] net: phy: motorcomm: Add missing include
-
-Directly include linux/bitfield.h which provides FIELD_PREP.
-
-Signed-off-by: Hauke Mehrtens <[email protected]>
----
- drivers/net/phy/motorcomm.c | 1 +
- 1 file changed, 1 insertion(+)
-
---- a/drivers/net/phy/motorcomm.c
-+++ b/drivers/net/phy/motorcomm.c
-@@ -6,6 +6,7 @@
-  * Author: Frank <[email protected]>
-  */
-+#include <linux/bitfield.h>
- #include <linux/etherdevice.h>
- #include <linux/kernel.h>
- #include <linux/module.h>
diff --git a/target/linux/generic/pending-5.15/750-skb-Do-mix-page-pool-and-page-referenced-frags-in-GR.patch b/target/linux/generic/pending-5.15/750-skb-Do-mix-page-pool-and-page-referenced-frags-in-GR.patch
deleted file mode 100644 (file)
index ec3e570..0000000
+++ /dev/null
@@ -1,35 +0,0 @@
-From: Alexander Duyck <[email protected]>
-Date: Thu, 26 Jan 2023 11:06:59 -0800
-Subject: [PATCH] skb: Do mix page pool and page referenced frags in GRO
-
-GSO should not merge page pool recycled frames with standard reference
-counted frames. Traditionally this didn't occur, at least not often.
-However as we start looking at adding support for wireless adapters there
-becomes the potential to mix the two due to A-MSDU repartitioning frames in
-the receive path. There are possibly other places where this may have
-occurred however I suspect they must be few and far between as we have not
-seen this issue until now.
-
-Fixes: 53e0961da1c7 ("page_pool: add frag page recycling support in page pool")
-Reported-by: Felix Fietkau <[email protected]>
-Signed-off-by: Alexander Duyck <[email protected]>
----
-
---- a/net/core/skbuff.c
-+++ b/net/core/skbuff.c
-@@ -4371,6 +4371,15 @@ int skb_gro_receive(struct sk_buff *p, s
-       if (unlikely(p->len + len >= 65536 || NAPI_GRO_CB(skb)->flush))
-               return -E2BIG;
-+      /* Do not splice page pool based packets w/ non-page pool
-+       * packets. This can result in reference count issues as page
-+       * pool pages will not decrement the reference count and will
-+       * instead be immediately returned to the pool or have frag
-+       * count decremented.
-+       */
-+      if (p->pp_recycle != skb->pp_recycle)
-+              return -ETOOMANYREFS;
-+
-       lp = NAPI_GRO_CB(p)->last;
-       pinfo = skb_shinfo(lp);
diff --git a/target/linux/generic/pending-5.15/760-net-core-add-optional-threading-for-backlog-processi.patch b/target/linux/generic/pending-5.15/760-net-core-add-optional-threading-for-backlog-processi.patch
deleted file mode 100644 (file)
index 1d1b168..0000000
+++ /dev/null
@@ -1,232 +0,0 @@
-From: Felix Fietkau <[email protected]>
-Date: Thu, 16 Feb 2023 18:39:04 +0100
-Subject: [PATCH] net/core: add optional threading for backlog processing
-
-When dealing with few flows or an imbalance on CPU utilization, static RPS
-CPU assignment can be too inflexible. Add support for enabling threaded NAPI
-for backlog processing in order to allow the scheduler to better balance
-processing. This helps better spread the load across idle CPUs.
-
-Signed-off-by: Felix Fietkau <[email protected]>
----
-
---- a/include/linux/netdevice.h
-+++ b/include/linux/netdevice.h
-@@ -502,6 +502,7 @@ static inline bool napi_complete(struct
- }
- int dev_set_threaded(struct net_device *dev, bool threaded);
-+int backlog_set_threaded(bool threaded);
- /**
-  *    napi_disable - prevent NAPI from scheduling
-@@ -3364,6 +3365,7 @@ struct softnet_data {
-       unsigned int            processed;
-       unsigned int            time_squeeze;
-       unsigned int            received_rps;
-+      unsigned int            process_queue_empty;
- #ifdef CONFIG_RPS
-       struct softnet_data     *rps_ipi_list;
- #endif
---- a/net/core/dev.c
-+++ b/net/core/dev.c
-@@ -4586,7 +4586,7 @@ static int rps_ipi_queued(struct softnet
- #ifdef CONFIG_RPS
-       struct softnet_data *mysd = this_cpu_ptr(&softnet_data);
--      if (sd != mysd) {
-+      if (sd != mysd && !test_bit(NAPI_STATE_THREADED, &sd->backlog.state)) {
-               sd->rps_ipi_next = mysd->rps_ipi_list;
-               mysd->rps_ipi_list = sd;
-@@ -5767,6 +5767,8 @@ static DEFINE_PER_CPU(struct work_struct
- /* Network device is going away, flush any packets still pending */
- static void flush_backlog(struct work_struct *work)
- {
-+      unsigned int process_queue_empty;
-+      bool threaded, flush_processq;
-       struct sk_buff *skb, *tmp;
-       struct softnet_data *sd;
-@@ -5782,9 +5784,18 @@ static void flush_backlog(struct work_st
-                       input_queue_head_incr(sd);
-               }
-       }
-+
-+      threaded = test_bit(NAPI_STATE_THREADED, &sd->backlog.state);
-+      flush_processq = threaded &&
-+                       !skb_queue_empty_lockless(&sd->process_queue);
-+      if (flush_processq)
-+              process_queue_empty = sd->process_queue_empty;
-       rps_unlock(sd);
-       local_irq_enable();
-+      if (threaded)
-+              goto out;
-+
-       skb_queue_walk_safe(&sd->process_queue, skb, tmp) {
-               if (skb->dev->reg_state == NETREG_UNREGISTERING) {
-                       __skb_unlink(skb, &sd->process_queue);
-@@ -5792,7 +5803,18 @@ static void flush_backlog(struct work_st
-                       input_queue_head_incr(sd);
-               }
-       }
-+
-+out:
-       local_bh_enable();
-+
-+      while (flush_processq) {
-+              msleep(1);
-+              local_irq_disable();
-+              rps_lock(sd);
-+              flush_processq = process_queue_empty == sd->process_queue_empty;
-+              rps_unlock(sd);
-+              local_irq_enable();
-+      }
- }
- static bool flush_required(int cpu)
-@@ -6475,6 +6497,7 @@ static int process_backlog(struct napi_s
-               local_irq_disable();
-               rps_lock(sd);
-+              sd->process_queue_empty++;
-               if (skb_queue_empty(&sd->input_pkt_queue)) {
-                       /*
-                        * Inline a custom version of __napi_complete().
-@@ -6484,7 +6507,8 @@ static int process_backlog(struct napi_s
-                        * We can use a plain write instead of clear_bit(),
-                        * and we dont need an smp_mb() memory barrier.
-                        */
--                      napi->state = 0;
-+                      napi->state &= ~(NAPIF_STATE_SCHED |
-+                                       NAPIF_STATE_SCHED_THREADED);
-                       again = false;
-               } else {
-                       skb_queue_splice_tail_init(&sd->input_pkt_queue,
-@@ -6901,6 +6925,57 @@ int dev_set_threaded(struct net_device *
- }
- EXPORT_SYMBOL(dev_set_threaded);
-+int backlog_set_threaded(bool threaded)
-+{
-+      static bool backlog_threaded;
-+      int err = 0;
-+      int i;
-+
-+      if (backlog_threaded == threaded)
-+              return 0;
-+
-+      for_each_possible_cpu(i) {
-+              struct softnet_data *sd = &per_cpu(softnet_data, i);
-+              struct napi_struct *n = &sd->backlog;
-+
-+              if (n->thread)
-+                      continue;
-+              n->thread = kthread_run(napi_threaded_poll, n, "napi/backlog-%d", i);
-+              if (IS_ERR(n->thread)) {
-+                      err = PTR_ERR(n->thread);
-+                      pr_err("kthread_run failed with err %d\n", err);
-+                      n->thread = NULL;
-+                      threaded = false;
-+                      break;
-+              }
-+
-+      }
-+
-+      backlog_threaded = threaded;
-+
-+      /* Make sure kthread is created before THREADED bit
-+       * is set.
-+       */
-+      smp_mb__before_atomic();
-+
-+      for_each_possible_cpu(i) {
-+              struct softnet_data *sd = &per_cpu(softnet_data, i);
-+              struct napi_struct *n = &sd->backlog;
-+              unsigned long flags;
-+
-+              local_irq_save(flags);
-+              rps_lock(sd);
-+              if (threaded)
-+                      n->state |= NAPIF_STATE_THREADED;
-+              else
-+                      n->state &= ~NAPIF_STATE_THREADED;
-+              rps_unlock(sd);
-+              local_irq_restore(flags);
-+      }
-+
-+      return err;
-+}
-+
- void netif_napi_add(struct net_device *dev, struct napi_struct *napi,
-                   int (*poll)(struct napi_struct *, int), int weight)
- {
-@@ -11385,6 +11460,9 @@ static int dev_cpu_dead(unsigned int old
-       raise_softirq_irqoff(NET_TX_SOFTIRQ);
-       local_irq_enable();
-+      if (test_bit(NAPI_STATE_THREADED, &oldsd->backlog.state))
-+              return 0;
-+
- #ifdef CONFIG_RPS
-       remsd = oldsd->rps_ipi_list;
-       oldsd->rps_ipi_list = NULL;
-@@ -11724,6 +11802,7 @@ static int __init net_dev_init(void)
-               sd->cpu = i;
- #endif
-+              INIT_LIST_HEAD(&sd->backlog.poll_list);
-               init_gro_hash(&sd->backlog);
-               sd->backlog.poll = process_backlog;
-               sd->backlog.weight = weight_p;
---- a/net/core/sysctl_net_core.c
-+++ b/net/core/sysctl_net_core.c
-@@ -28,6 +28,7 @@ static int int_3600 = 3600;
- static int min_sndbuf = SOCK_MIN_SNDBUF;
- static int min_rcvbuf = SOCK_MIN_RCVBUF;
- static int max_skb_frags = MAX_SKB_FRAGS;
-+static int backlog_threaded;
- static long long_one __maybe_unused = 1;
- static long long_max __maybe_unused = LONG_MAX;
-@@ -114,6 +115,23 @@ static int rps_sock_flow_sysctl(struct c
- }
- #endif /* CONFIG_RPS */
-+static int backlog_threaded_sysctl(struct ctl_table *table, int write,
-+                             void *buffer, size_t *lenp, loff_t *ppos)
-+{
-+      static DEFINE_MUTEX(backlog_threaded_mutex);
-+      int ret;
-+
-+      mutex_lock(&backlog_threaded_mutex);
-+
-+      ret = proc_dointvec_minmax(table, write, buffer, lenp, ppos);
-+      if (write && !ret)
-+              ret = backlog_set_threaded(backlog_threaded);
-+
-+      mutex_unlock(&backlog_threaded_mutex);
-+
-+      return ret;
-+}
-+
- #ifdef CONFIG_NET_FLOW_LIMIT
- static DEFINE_MUTEX(flow_limit_update_mutex);
-@@ -470,6 +488,15 @@ static struct ctl_table net_core_table[]
-               .proc_handler   = rps_sock_flow_sysctl
-       },
- #endif
-+      {
-+              .procname       = "backlog_threaded",
-+              .data           = &backlog_threaded,
-+              .maxlen         = sizeof(unsigned int),
-+              .mode           = 0644,
-+              .proc_handler   = backlog_threaded_sysctl,
-+              .extra1         = SYSCTL_ZERO,
-+              .extra2         = SYSCTL_ONE
-+      },
- #ifdef CONFIG_NET_FLOW_LIMIT
-       {
-               .procname       = "flow_limit_cpu_bitmap",
diff --git a/target/linux/generic/pending-5.15/768-net-dsa-mv88e6xxx-Request-assisted-learning-on-CPU-port.patch b/target/linux/generic/pending-5.15/768-net-dsa-mv88e6xxx-Request-assisted-learning-on-CPU-port.patch
deleted file mode 100644 (file)
index 4f322da..0000000
+++ /dev/null
@@ -1,27 +0,0 @@
-From:   Tobias Waldekranz <[email protected]>
-Subject: [RFC net-next 7/7] net: dsa: mv88e6xxx: Request assisted learning on CPU port
-Date:   Sat, 16 Jan 2021 02:25:15 +0100
-Archived-At: <https://lore.kernel.org/netdev/[email protected]/>
-
-While the hardware is capable of performing learning on the CPU port,
-it requires alot of additions to the bridge's forwarding path in order
-to handle multi-destination traffic correctly.
-
-Until that is in place, opt for the next best thing and let DSA sync
-the relevant addresses down to the hardware FDB.
-
-Signed-off-by: Tobias Waldekranz <[email protected]>
----
- drivers/net/dsa/mv88e6xxx/chip.c | 1 +
- 1 file changed, 1 insertion(+)
-
---- a/drivers/net/dsa/mv88e6xxx/chip.c
-+++ b/drivers/net/dsa/mv88e6xxx/chip.c
-@@ -6435,6 +6435,7 @@ static int mv88e6xxx_register_switch(str
-       ds->ops = &mv88e6xxx_switch_ops;
-       ds->ageing_time_min = chip->info->age_time_coeff;
-       ds->ageing_time_max = chip->info->age_time_coeff * U8_MAX;
-+      ds->assisted_learning_on_cpu_port = true;
-       /* Some chips support up to 32, but that requires enabling the
-        * 5-bit port mode, which we do not support. 640k^W16 ought to
diff --git a/target/linux/generic/pending-5.15/772-net-dsa-b53-add-support-for-BCM63xx-RGMIIs.patch b/target/linux/generic/pending-5.15/772-net-dsa-b53-add-support-for-BCM63xx-RGMIIs.patch
deleted file mode 100644 (file)
index ca963d1..0000000
+++ /dev/null
@@ -1,174 +0,0 @@
-From patchwork Sun Mar 19 22:08:05 2023
-Content-Type: text/plain; charset="utf-8"
-MIME-Version: 1.0
-Content-Transfer-Encoding: 8bit
-X-Patchwork-Submitter: =?utf-8?q?=C3=81lvaro_Fern=C3=A1ndez_Rojas?=
-X-Patchwork-Id: 13180645
-X-Patchwork-Delegate: [email protected]
-Return-Path: <[email protected]>
-X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on
-       aws-us-west-2-korg-lkml-1.web.codeaurora.org
-Received: from vger.kernel.org (vger.kernel.org [23.128.96.18])
-       by smtp.lore.kernel.org (Postfix) with ESMTP id A7A46C6FD1F
-       for <[email protected]>; Sun, 19 Mar 2023 22:08:15 +0000 (UTC)
-Received: ([email protected]) by vger.kernel.org via listexpand
-        id S230223AbjCSWIN (ORCPT <rfc822;[email protected]>);
-        Sun, 19 Mar 2023 18:08:13 -0400
-Received: from lindbergh.monkeyblade.net ([23.128.96.19]:32878 "EHLO
-        lindbergh.monkeyblade.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org
-        with ESMTP id S229565AbjCSWIM (ORCPT
-        <rfc822;[email protected]>); Sun, 19 Mar 2023 18:08:12 -0400
-Received: from mail-wr1-x42e.google.com (mail-wr1-x42e.google.com
- [IPv6:2a00:1450:4864:20::42e])
-        by lindbergh.monkeyblade.net (Postfix) with ESMTPS id 605D3E062;
-        Sun, 19 Mar 2023 15:08:10 -0700 (PDT)
-Received: by mail-wr1-x42e.google.com with SMTP id h17so8695188wrt.8;
-        Sun, 19 Mar 2023 15:08:10 -0700 (PDT)
-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed;
-        d=gmail.com; s=20210112; t=1679263689;
-        h=content-transfer-encoding:mime-version:references:in-reply-to
-         :message-id:date:subject:cc:to:from:from:to:cc:subject:date
-         :message-id:reply-to;
-        bh=GmPK75Q9ZD3h3IYflWYuDwS99V2e532KgDlnNucAoJg=;
-        b=PSdrywW48P4Lq8z9wOSPXFB/ZdO/JfuyiGlw3Gz1Iriy+Smo/cBnJ0Ve9zKkX3AKTO
-         Tr7/g8xhSQX8sU5WAOEPC13uVjKpO4VZsamXHTmMKL4mmfII3K/piAsQcMQkkNpgouab
-         Ci9yr+7ASSmqEUHIbYTM6sl6a47rPwqk3b3DcTIE2CwJsPPNXnpQ/aSVbJAcEdhcZICc
-         X4rAmjrYjcsl8coFIGHHPlrMH9ShekQWxB84vEb6bO1nXOORNPizOHuY1vJ3wa3WgXsx
-         YwlvutMFVIUXfgL2ZwCmQAKWJPiAaFk+CCk3oxSeOYoAzkjcbMyapz9VnooStfvR2aV3
-         k+2g==
-X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed;
-        d=1e100.net; s=20210112; t=1679263689;
-        h=content-transfer-encoding:mime-version:references:in-reply-to
-         :message-id:date:subject:cc:to:from:x-gm-message-state:from:to:cc
-         :subject:date:message-id:reply-to;
-        bh=GmPK75Q9ZD3h3IYflWYuDwS99V2e532KgDlnNucAoJg=;
-        b=NGjqrGERyaxRwINtevHaY97h9X9W+1UY62YYwotqwv5+cfvB8myjBbD3WH2WzaqMes
-         o9MMER9RE8/arW3jIVlBv4ORDUuEZ7AeGgy5UbFyQZIPHlp+hJ/sxFrGvYUwamg4Qrr9
-         ojargh8ORsEiMeqaf+5AkmEagNhrrV3ax0pUuWDzbJ3vXGoHjfCetHz5xyNL46dvXBfb
-         l/OZqjv9IYob552uUoUmCy/TbEQDqvmjkFrROFK9gtBNxgxUJkwbyiWIOVsf6RR8OarP
-         f7bbvSJYkvTvzx2u/g0Up7NW5ZyihMGBmDs377M3yW6AnSxW6jlfl30QmMU1aEigYXvy
-         v3mA==
-X-Gm-Message-State: AO0yUKUm1PYmYa4xlHuVD23mZcZm83a+xbhcbs0Xryi3yF/+UnjM4Cho
-        GAfqSh5MZ/rlOAm3Vnpn//9hOG5Lc8vLYg==
-X-Google-Smtp-Source: 
- AK7set+5pTahGGgk1hF/mHGkGBhsMf0//oQjZd4QFHx+HaeSgP5f6q7g0bRUcTX8kRtgHH0T7l1/hQ==
-X-Received: by 2002:a5d:474f:0:b0:2d6:2ae8:70d with SMTP id
- o15-20020a5d474f000000b002d62ae8070dmr2382593wrs.39.1679263688549;
-        Sun, 19 Mar 2023 15:08:08 -0700 (PDT)
-Received: from atlantis.lan (255.red-79-146-124.dynamicip.rima-tde.net.
- [79.146.124.255])
-        by smtp.gmail.com with ESMTPSA id
- d6-20020a5d6dc6000000b002c53f6c7599sm7354727wrz.29.2023.03.19.15.08.07
-        (version=TLS1_3 cipher=TLS_AES_256_GCM_SHA384 bits=256/256);
-        Sun, 19 Mar 2023 15:08:07 -0700 (PDT)
-From: =?utf-8?q?=C3=81lvaro_Fern=C3=A1ndez_Rojas?=  <[email protected]>
-        [email protected]
-Cc: =?utf-8?q?=C3=81lvaro_Fern=C3=A1ndez_Rojas?=  <[email protected]>
-Subject: [PATCH v2] net: dsa: b53: add support for BCM63xx RGMIIs
-Date: Sun, 19 Mar 2023 23:08:05 +0100
-Message-Id: <[email protected]>
-X-Mailer: git-send-email 2.30.2
-In-Reply-To: <[email protected]>
-References: <[email protected]>
-MIME-Version: 1.0
-Precedence: bulk
-List-ID: <netdev.vger.kernel.org>
-X-Mailing-List: [email protected]
-X-Patchwork-Delegate: [email protected]
-
-BCM63xx RGMII ports require additional configuration in order to work.
-
-Signed-off-by: Álvaro Fernández Rojas <[email protected]>
-Reviewed-by: Andrew Lunn <[email protected]>
----
- v2: add changes suggested by Andrew:
-  - Use a switch statement.
-  - Use dev_dbg() instead of dev_info().
-
- drivers/net/dsa/b53/b53_common.c | 46 ++++++++++++++++++++++++++++++++
- drivers/net/dsa/b53/b53_priv.h   |  1 +
- 2 files changed, 47 insertions(+)
-
---- a/drivers/net/dsa/b53/b53_common.c
-+++ b/drivers/net/dsa/b53/b53_common.c
-@@ -1209,6 +1209,46 @@ static void b53_force_port_config(struct
-       b53_write8(dev, B53_CTRL_PAGE, off, reg);
- }
-+static void b53_adjust_63xx_rgmii(struct dsa_switch *ds, int port,
-+                                phy_interface_t interface)
-+{
-+      struct b53_device *dev = ds->priv;
-+      u8 rgmii_ctrl = 0, off;
-+
-+      if (port == dev->imp_port)
-+              off = B53_RGMII_CTRL_IMP;
-+      else
-+              off = B53_RGMII_CTRL_P(port);
-+
-+      b53_read8(dev, B53_CTRL_PAGE, off, &rgmii_ctrl);
-+
-+      switch (interface) {
-+      case PHY_INTERFACE_MODE_RGMII_ID:
-+              rgmii_ctrl |= (RGMII_CTRL_DLL_RXC | RGMII_CTRL_DLL_TXC);
-+              break;
-+      case PHY_INTERFACE_MODE_RGMII_RXID:
-+              rgmii_ctrl &= ~(RGMII_CTRL_DLL_TXC);
-+              rgmii_ctrl |= RGMII_CTRL_DLL_RXC;
-+              break;
-+      case PHY_INTERFACE_MODE_RGMII_TXID:
-+              rgmii_ctrl &= ~(RGMII_CTRL_DLL_RXC);
-+              rgmii_ctrl |= RGMII_CTRL_DLL_TXC;
-+              break;
-+      case PHY_INTERFACE_MODE_RGMII:
-+      default:
-+              rgmii_ctrl &= ~(RGMII_CTRL_DLL_RXC | RGMII_CTRL_DLL_TXC);
-+              break;
-+      }
-+
-+      if (port != dev->imp_port)
-+              rgmii_ctrl |= RGMII_CTRL_ENABLE_GMII;
-+
-+      b53_write8(dev, B53_CTRL_PAGE, off, rgmii_ctrl);
-+
-+      dev_dbg(ds->dev, "Configured port %d for %s\n", port,
-+              phy_modes(interface));
-+}
-+
- static void b53_adjust_link(struct dsa_switch *ds, int port,
-                           struct phy_device *phydev)
- {
-@@ -1235,6 +1275,9 @@ static void b53_adjust_link(struct dsa_s
-                             tx_pause, rx_pause);
-       b53_force_link(dev, port, phydev->link);
-+      if (is63xx(dev) && port >= B53_63XX_RGMII0)
-+              b53_adjust_63xx_rgmii(ds, port, phydev->interface);
-+
-       if (is531x5(dev) && phy_interface_is_rgmii(phydev)) {
-               if (port == dev->imp_port)
-                       off = B53_RGMII_CTRL_IMP;
-@@ -1419,6 +1462,9 @@ void b53_phylink_mac_link_up(struct dsa_
- {
-       struct b53_device *dev = ds->priv;
-+      if (is63xx(dev) && port >= B53_63XX_RGMII0)
-+              b53_adjust_63xx_rgmii(ds, port, interface);
-+
-       if (mode == MLO_AN_PHY)
-               return;
---- a/drivers/net/dsa/b53/b53_priv.h
-+++ b/drivers/net/dsa/b53/b53_priv.h
-@@ -206,6 +206,7 @@ static inline int is58xx(struct b53_devi
-               dev->chip_id == BCM7278_DEVICE_ID;
- }
-+#define B53_63XX_RGMII0       4
- #define B53_CPU_PORT_25       5
- #define B53_CPU_PORT  8
diff --git a/target/linux/generic/pending-5.15/773-net-dsa-b53-mmap-add-more-63xx-SoCs.patch b/target/linux/generic/pending-5.15/773-net-dsa-b53-mmap-add-more-63xx-SoCs.patch
deleted file mode 100644 (file)
index e2da4e7..0000000
+++ /dev/null
@@ -1,108 +0,0 @@
-From patchwork Tue Mar 21 17:33:57 2023
-Content-Type: text/plain; charset="utf-8"
-MIME-Version: 1.0
-Content-Transfer-Encoding: 8bit
-X-Patchwork-Submitter: =?utf-8?q?=C3=81lvaro_Fern=C3=A1ndez_Rojas?=
-X-Patchwork-Id: 13183003
-X-Patchwork-Delegate: [email protected]
-Return-Path: <[email protected]>
-X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on
-       aws-us-west-2-korg-lkml-1.web.codeaurora.org
-Received: from vger.kernel.org (vger.kernel.org [23.128.96.18])
-       by smtp.lore.kernel.org (Postfix) with ESMTP id 823A1C761AF
-       for <[email protected]>; Tue, 21 Mar 2023 17:35:06 +0000 (UTC)
-Received: ([email protected]) by vger.kernel.org via listexpand
-        id S230490AbjCURfE (ORCPT <rfc822;[email protected]>);
-        Tue, 21 Mar 2023 13:35:04 -0400
-Received: from lindbergh.monkeyblade.net ([23.128.96.19]:47440 "EHLO
-        lindbergh.monkeyblade.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org
-        with ESMTP id S230357AbjCURex (ORCPT
-        <rfc822;[email protected]>); Tue, 21 Mar 2023 13:34:53 -0400
-Received: from mail-wr1-x430.google.com (mail-wr1-x430.google.com
- [IPv6:2a00:1450:4864:20::430])
-        by lindbergh.monkeyblade.net (Postfix) with ESMTPS id C9A45559D8;
-        Tue, 21 Mar 2023 10:34:26 -0700 (PDT)
-Received: by mail-wr1-x430.google.com with SMTP id m2so14547588wrh.6;
-        Tue, 21 Mar 2023 10:34:26 -0700 (PDT)
-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed;
-        d=gmail.com; s=20210112; t=1679420063;
-        h=content-transfer-encoding:mime-version:references:in-reply-to
-         :message-id:date:subject:cc:to:from:from:to:cc:subject:date
-         :message-id:reply-to;
-        bh=cUvnluVaZPzfEQB9fMRuYo+4/361t/7po7nyUBBJfxc=;
-        b=F0pa8JmQZ1FeXVtdpCygur8UmLrgKwxCcjaMn312u5zNvsXsEPeCAIDqP2tvNNTwv/
-         UYjaNaoZ77HSvv/gSqeG808AXGyNs1PvLuHZYuUTJRNuLaMixKtkNFi4ypheCdk0WCiE
-         IWz0DIm6ojmdwMqafDUKQ6Qwkv5R0vo8Wh5vpjimEmCelOyMvfuLZNqubsiGqpnCguBp
-         uWlmKh95/VubCGgiGG2xK1IXQayL14ENuWseDds7nVpVK50NycrFgJbL17Bd6qJKYkbo
-         m70IC+9jM0hjwKXpyi6ipCBNcW+1E6JIwILVC04Xi+BTpOGhbUAQ59Yn2hyq7tQM7dzs
-         4PLg==
-X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed;
-        d=1e100.net; s=20210112; t=1679420063;
-        h=content-transfer-encoding:mime-version:references:in-reply-to
-         :message-id:date:subject:cc:to:from:x-gm-message-state:from:to:cc
-         :subject:date:message-id:reply-to;
-        bh=cUvnluVaZPzfEQB9fMRuYo+4/361t/7po7nyUBBJfxc=;
-        b=SCX78yTuGjdnE5nuL0p7+kxGnOzsCExsigLdaV+x/JswmwxSpZvxn223i1yM95klj9
-         Rk0RnXqATLF1wZA7L1YmbeZ66zxUwW/osnCjJHPeEF8AGgjK/qawtLl/HJQHN67NaRNQ
-         bDsRn2nWQ2GRTRFpvD+iGRy4uyQCDu9HFxLbn43fBsBmRnXWGPQP5cEb90tL83/Onp4D
-         Lx/XcyZOh9QRfJNhj+G1BAeRCLRA/sdA0W3Ecu5SCFs+LtS6uvLVGWDKEDfnZhYY8Xqf
-         Mx9evWzdW2OorEN2FI6+xTglvnEBcVhHIJ7XEGAhCG6ocgMZeck++774S8RWumWl8xpy
-         /K9Q==
-X-Gm-Message-State: AO0yUKUORAlGfbkNwnYmQnTWcGPqW6sp4g9WfgQmRZGCV+9tCB0OebSP
-        ICq6v4YPmUPNRl/WNnVCbps=
-X-Google-Smtp-Source: 
- AK7set8pFDl8fHRwGPhAguqxIfqnQ4PY+b57IHEsybIaQ/HPNwdJ1cs1+IPBGHe3TL14dTS4aVNpHA==
-X-Received: by 2002:a5d:6991:0:b0:2ce:aab5:f96b with SMTP id
- g17-20020a5d6991000000b002ceaab5f96bmr2965175wru.67.1679420062764;
-        Tue, 21 Mar 2023 10:34:22 -0700 (PDT)
-Received: from atlantis.lan (255.red-79-146-124.dynamicip.rima-tde.net.
- [79.146.124.255])
-        by smtp.gmail.com with ESMTPSA id
- b13-20020a056000054d00b002da1261aa44sm184775wrf.48.2023.03.21.10.34.21
-        (version=TLS1_3 cipher=TLS_AES_256_GCM_SHA384 bits=256/256);
-        Tue, 21 Mar 2023 10:34:21 -0700 (PDT)
-From: =?utf-8?q?=C3=81lvaro_Fern=C3=A1ndez_Rojas?=  <[email protected]>
-Cc: =?utf-8?q?=C3=81lvaro_Fern=C3=A1ndez_Rojas?=  <[email protected]>
-Subject: [PATCH v2 2/4] net: dsa: b53: mmap: add more 63xx SoCs
-Date: Tue, 21 Mar 2023 18:33:57 +0100
-Message-Id: <[email protected]>
-X-Mailer: git-send-email 2.30.2
-In-Reply-To: <[email protected]>
-References: <[email protected]>
-MIME-Version: 1.0
-Precedence: bulk
-List-ID: <netdev.vger.kernel.org>
-X-Mailing-List: [email protected]
-X-Patchwork-Delegate: [email protected]
-
-BCM6318, BCM6362 and BCM63268 are SoCs with a B53 MMAP switch.
-
-Signed-off-by: Álvaro Fernández Rojas <[email protected]>
-Reviewed-by: Florian Fainelli <[email protected]>
----
- v2: no changes.
-
- drivers/net/dsa/b53/b53_mmap.c | 3 +++
- 1 file changed, 3 insertions(+)
-
---- a/drivers/net/dsa/b53/b53_mmap.c
-+++ b/drivers/net/dsa/b53/b53_mmap.c
-@@ -347,8 +347,11 @@ static void b53_mmap_shutdown(struct pla
- static const struct of_device_id b53_mmap_of_table[] = {
-       { .compatible = "brcm,bcm3384-switch" },
-+      { .compatible = "brcm,bcm6318-switch" },
-       { .compatible = "brcm,bcm6328-switch" },
-+      { .compatible = "brcm,bcm6362-switch" },
-       { .compatible = "brcm,bcm6368-switch" },
-+      { .compatible = "brcm,bcm63268-switch" },
-       { .compatible = "brcm,bcm63xx-switch" },
-       { /* sentinel */ },
- };
diff --git a/target/linux/generic/pending-5.15/774-net-dsa-b53-mmap-allow-passing-a-chip-ID.patch b/target/linux/generic/pending-5.15/774-net-dsa-b53-mmap-allow-passing-a-chip-ID.patch
deleted file mode 100644 (file)
index 456643f..0000000
+++ /dev/null
@@ -1,195 +0,0 @@
-From patchwork Tue Mar 21 17:33:58 2023
-Content-Type: text/plain; charset="utf-8"
-MIME-Version: 1.0
-Content-Transfer-Encoding: 8bit
-X-Patchwork-Submitter: =?utf-8?q?=C3=81lvaro_Fern=C3=A1ndez_Rojas?=
-X-Patchwork-Id: 13183004
-X-Patchwork-Delegate: [email protected]
-Return-Path: <[email protected]>
-X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on
-       aws-us-west-2-korg-lkml-1.web.codeaurora.org
-Received: from vger.kernel.org (vger.kernel.org [23.128.96.18])
-       by smtp.lore.kernel.org (Postfix) with ESMTP id B2B12C74A5B
-       for <[email protected]>; Tue, 21 Mar 2023 17:35:12 +0000 (UTC)
-Received: ([email protected]) by vger.kernel.org via listexpand
-        id S230297AbjCURfK (ORCPT <rfc822;[email protected]>);
-        Tue, 21 Mar 2023 13:35:10 -0400
-Received: from lindbergh.monkeyblade.net ([23.128.96.19]:47438 "EHLO
-        lindbergh.monkeyblade.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org
-        with ESMTP id S230374AbjCURex (ORCPT
-        <rfc822;[email protected]>); Tue, 21 Mar 2023 13:34:53 -0400
-Received: from mail-wr1-x432.google.com (mail-wr1-x432.google.com
- [IPv6:2a00:1450:4864:20::432])
-        by lindbergh.monkeyblade.net (Postfix) with ESMTPS id C906B5550A;
-        Tue, 21 Mar 2023 10:34:26 -0700 (PDT)
-Received: by mail-wr1-x432.google.com with SMTP id y14so14546846wrq.4;
-        Tue, 21 Mar 2023 10:34:26 -0700 (PDT)
-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed;
-        d=gmail.com; s=20210112; t=1679420064;
-        h=content-transfer-encoding:mime-version:references:in-reply-to
-         :message-id:date:subject:cc:to:from:from:to:cc:subject:date
-         :message-id:reply-to;
-        bh=vnvnwWc5Tmg09HBQo/m9RbRM6yM8KLx8r1VA+Abfg3k=;
-        b=eFv+mwe94Y2YZMiJP5gydXVrGlbIAR5HCrY0rdcoGoMPzQUHLFckZeYCgEKudI55I7
-         gMLZYCtLwvDXvKeHM2AUigsq2YuJSeF5QwICPrhTnMwUGBg4yyyltrc3+J0lSd6/4kQv
-         h0yM1Oo4v0d8CuqjBU6bXienIk34AFVJfsPq+vWQTjAbUL7ht4WHZ2Ez2MFoTvZpkIJA
-         5iWMyVoMbugZl6eqNRjvDHFmtBtrZIv8AFs10r2Ca6+Yxm+aq0v33DRkbSVVqgFPNEzy
-         q5QOXOeLBPL6BvyovOpmVSWGoHf1zFV7lrzcqi+uc+FuYxQ9dyN3ND73DrrhWSkLaSg9
-         r8yA==
-X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed;
-        d=1e100.net; s=20210112; t=1679420064;
-        h=content-transfer-encoding:mime-version:references:in-reply-to
-         :message-id:date:subject:cc:to:from:x-gm-message-state:from:to:cc
-         :subject:date:message-id:reply-to;
-        bh=vnvnwWc5Tmg09HBQo/m9RbRM6yM8KLx8r1VA+Abfg3k=;
-        b=jIRB8pIlrLA/ovhnEoePs/6SX8fn6l7l4fY2CxX2pLrTbP1JI8AAetPavvrNVQTr2M
-         Vm0iLbKyL/VpTq9+bSN1SMjaoi4lAMj0pgafoHrwABMVZpFauYvtCfSYTstZ2pw4Dr1j
-         wYQGj3BUSpFIYHtSIDMkb5449WA3T3TONhaQLRFAUCBD6gAFyEky5fY+DIHrGaj352B6
-         9ST/tkqHgPpuFlmromr42KQWoTFU+Pj0Uhyp7ru4BsnF7tTshWroZZIHUJmSACudEadr
-         fBPiuurX9jgp9zNqj8Oy0HjiVUnULFCapj8yICGp5s44uDAK/XFqFXpOuJ8ptS6uPazU
-         xUwg==
-X-Gm-Message-State: AO0yUKX2w6QZfaGDHtlZAlY/U8F8VuJa3HwlgXbxgGChgdgvIoFThawv
-        oDyFAhWbVfe4DxwXTwxgJ/I=
-X-Google-Smtp-Source: 
- AK7set+sH60XiJYup7bqrZTzFJVNe1YGcX/UTfjWV9xfGwNyodc34cHvKpqNagw5J+vEpv6CKvNHaA==
-X-Received: by 2002:adf:f344:0:b0:2cd:de25:1c76 with SMTP id
- e4-20020adff344000000b002cdde251c76mr12989754wrp.17.1679420064464;
-        Tue, 21 Mar 2023 10:34:24 -0700 (PDT)
-Received: from atlantis.lan (255.red-79-146-124.dynamicip.rima-tde.net.
- [79.146.124.255])
-        by smtp.gmail.com with ESMTPSA id
- b13-20020a056000054d00b002da1261aa44sm184775wrf.48.2023.03.21.10.34.22
-        (version=TLS1_3 cipher=TLS_AES_256_GCM_SHA384 bits=256/256);
-        Tue, 21 Mar 2023 10:34:23 -0700 (PDT)
-From: =?utf-8?q?=C3=81lvaro_Fern=C3=A1ndez_Rojas?=  <[email protected]>
-Cc: =?utf-8?q?=C3=81lvaro_Fern=C3=A1ndez_Rojas?=  <[email protected]>
-Subject: [PATCH v2 3/4] net: dsa: b53: mmap: allow passing a chip ID
-Date: Tue, 21 Mar 2023 18:33:58 +0100
-Message-Id: <[email protected]>
-X-Mailer: git-send-email 2.30.2
-In-Reply-To: <[email protected]>
-References: <[email protected]>
-MIME-Version: 1.0
-Precedence: bulk
-List-ID: <netdev.vger.kernel.org>
-X-Mailing-List: [email protected]
-X-Patchwork-Delegate: [email protected]
-
-BCM6318 and BCM63268 SoCs require a special handling for their RGMIIs, so we
-should be able to identify them as a special BCM63xx switch.
-
-Signed-off-by: Álvaro Fernández Rojas <[email protected]>
----
- v2:
-  - Add missing chip to b53_switch_chips[].
-  - Fix device_get_match_data() casting warning.
-  - Add BCM63268_DEVICE_ID to BCM6318 too.
-  - Add BCM6318 in commit description.
-
- drivers/net/dsa/b53/b53_common.c | 13 +++++++++++++
- drivers/net/dsa/b53/b53_mmap.c   | 32 +++++++++++++++++++++++---------
- drivers/net/dsa/b53/b53_priv.h   |  9 ++++++++-
- 3 files changed, 44 insertions(+), 10 deletions(-)
-
---- a/drivers/net/dsa/b53/b53_common.c
-+++ b/drivers/net/dsa/b53/b53_common.c
-@@ -2461,6 +2461,19 @@ static const struct b53_chip_data b53_sw
-               .jumbo_size_reg = B53_JUMBO_MAX_SIZE_63XX,
-       },
-       {
-+              .chip_id = BCM63268_DEVICE_ID,
-+              .dev_name = "BCM63268",
-+              .vlans = 4096,
-+              .enabled_ports = 0, /* pdata must provide them */
-+              .arl_bins = 4,
-+              .arl_buckets = 1024,
-+              .imp_port = 8,
-+              .vta_regs = B53_VTA_REGS_63XX,
-+              .duplex_reg = B53_DUPLEX_STAT_63XX,
-+              .jumbo_pm_reg = B53_JUMBO_PORT_MASK_63XX,
-+              .jumbo_size_reg = B53_JUMBO_MAX_SIZE_63XX,
-+      },
-+      {
-               .chip_id = BCM53010_DEVICE_ID,
-               .dev_name = "BCM53010",
-               .vlans = 4096,
---- a/drivers/net/dsa/b53/b53_mmap.c
-+++ b/drivers/net/dsa/b53/b53_mmap.c
-@@ -262,7 +262,7 @@ static int b53_mmap_probe_of(struct plat
-               return -ENOMEM;
-       pdata->regs = mem;
--      pdata->chip_id = BCM63XX_DEVICE_ID;
-+      pdata->chip_id = (u32)(unsigned long)device_get_match_data(dev);
-       pdata->big_endian = of_property_read_bool(np, "big-endian");
-       of_ports = of_get_child_by_name(np, "ports");
-@@ -346,14 +346,28 @@ static void b53_mmap_shutdown(struct pla
- }
- static const struct of_device_id b53_mmap_of_table[] = {
--      { .compatible = "brcm,bcm3384-switch" },
--      { .compatible = "brcm,bcm6318-switch" },
--      { .compatible = "brcm,bcm6328-switch" },
--      { .compatible = "brcm,bcm6362-switch" },
--      { .compatible = "brcm,bcm6368-switch" },
--      { .compatible = "brcm,bcm63268-switch" },
--      { .compatible = "brcm,bcm63xx-switch" },
--      { /* sentinel */ },
-+      {
-+              .compatible = "brcm,bcm3384-switch",
-+              .data = (void *)BCM63XX_DEVICE_ID,
-+      }, {
-+              .compatible = "brcm,bcm6318-switch",
-+              .data = (void *)BCM63268_DEVICE_ID,
-+      }, {
-+              .compatible = "brcm,bcm6328-switch",
-+              .data = (void *)BCM63XX_DEVICE_ID,
-+      }, {
-+              .compatible = "brcm,bcm6362-switch",
-+              .data = (void *)BCM63XX_DEVICE_ID,
-+      }, {
-+              .compatible = "brcm,bcm6368-switch",
-+              .data = (void *)BCM63XX_DEVICE_ID,
-+      }, {
-+              .compatible = "brcm,bcm63268-switch",
-+              .data = (void *)BCM63268_DEVICE_ID,
-+      }, {
-+              .compatible = "brcm,bcm63xx-switch",
-+              .data = (void *)BCM63XX_DEVICE_ID,
-+      }, { /* sentinel */ }
- };
- MODULE_DEVICE_TABLE(of, b53_mmap_of_table);
---- a/drivers/net/dsa/b53/b53_priv.h
-+++ b/drivers/net/dsa/b53/b53_priv.h
-@@ -75,6 +75,7 @@ enum {
-       BCM53125_DEVICE_ID = 0x53125,
-       BCM53128_DEVICE_ID = 0x53128,
-       BCM63XX_DEVICE_ID = 0x6300,
-+      BCM63268_DEVICE_ID = 0x63268,
-       BCM53010_DEVICE_ID = 0x53010,
-       BCM53011_DEVICE_ID = 0x53011,
-       BCM53012_DEVICE_ID = 0x53012,
-@@ -186,7 +187,13 @@ static inline int is531x5(struct b53_dev
- static inline int is63xx(struct b53_device *dev)
- {
--      return dev->chip_id == BCM63XX_DEVICE_ID;
-+      return dev->chip_id == BCM63XX_DEVICE_ID ||
-+              dev->chip_id == BCM63268_DEVICE_ID;
-+}
-+
-+static inline int is63268(struct b53_device *dev)
-+{
-+      return dev->chip_id == BCM63268_DEVICE_ID;
- }
- static inline int is5301x(struct b53_device *dev)
diff --git a/target/linux/generic/pending-5.15/775-net-dsa-b53-add-BCM63268-RGMII-configuration.patch b/target/linux/generic/pending-5.15/775-net-dsa-b53-add-BCM63268-RGMII-configuration.patch
deleted file mode 100644 (file)
index d90d757..0000000
+++ /dev/null
@@ -1,123 +0,0 @@
-From patchwork Tue Mar 21 17:33:59 2023
-Content-Type: text/plain; charset="utf-8"
-MIME-Version: 1.0
-Content-Transfer-Encoding: 8bit
-X-Patchwork-Submitter: =?utf-8?q?=C3=81lvaro_Fern=C3=A1ndez_Rojas?=
-X-Patchwork-Id: 13183005
-X-Patchwork-Delegate: [email protected]
-Return-Path: <[email protected]>
-X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on
-       aws-us-west-2-korg-lkml-1.web.codeaurora.org
-Received: from vger.kernel.org (vger.kernel.org [23.128.96.18])
-       by smtp.lore.kernel.org (Postfix) with ESMTP id 31BE4C761A6
-       for <[email protected]>; Tue, 21 Mar 2023 17:35:16 +0000 (UTC)
-Received: ([email protected]) by vger.kernel.org via listexpand
-        id S229674AbjCURfN (ORCPT <rfc822;[email protected]>);
-        Tue, 21 Mar 2023 13:35:13 -0400
-Received: from lindbergh.monkeyblade.net ([23.128.96.19]:47684 "EHLO
-        lindbergh.monkeyblade.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org
-        with ESMTP id S230327AbjCURfB (ORCPT
-        <rfc822;[email protected]>); Tue, 21 Mar 2023 13:35:01 -0400
-Received: from mail-wr1-x436.google.com (mail-wr1-x436.google.com
- [IPv6:2a00:1450:4864:20::436])
-        by lindbergh.monkeyblade.net (Postfix) with ESMTPS id E1D855507D;
-        Tue, 21 Mar 2023 10:34:27 -0700 (PDT)
-Received: by mail-wr1-x436.google.com with SMTP id i9so14537769wrp.3;
-        Tue, 21 Mar 2023 10:34:27 -0700 (PDT)
-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed;
-        d=gmail.com; s=20210112; t=1679420066;
-        h=content-transfer-encoding:mime-version:references:in-reply-to
-         :message-id:date:subject:cc:to:from:from:to:cc:subject:date
-         :message-id:reply-to;
-        bh=asmFs22xWYwR1Ql9m/IrNv+MPUNDn8hSjmwDRYvO7mE=;
-        b=Cqj2C6aG5vEOlhh9N3ybvDA0CV38nhQODnfdnr7utNddd323iDagoJty1Wmi3MAzj1
-         5ORmYT5fQvUnild7C4RhcCNTBn+MoYZ+wDZwZYelu6BKHkW11YFK949ax5B50by+ASR2
-         z+rGI3wR5fVXd4VDgmcsT6zF5x69wKyhbhqIfrhG9BVFTctfaBgDS/l+bX1C56kSqv82
-         bQkKSSAehSLGpFoCU3q62OGoZVi3jDe6HDb5M1Dp2mgHhqsW19otZpJ57DjtZ1CmtPai
-         o7T/ew6WoIYSl6whBmV36jeNaDJ3TItOBrKc4nMJBDWaCg4DNzUSe0ei5Xz7Oik5lb3p
-         y9ew==
-X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed;
-        d=1e100.net; s=20210112; t=1679420066;
-        h=content-transfer-encoding:mime-version:references:in-reply-to
-         :message-id:date:subject:cc:to:from:x-gm-message-state:from:to:cc
-         :subject:date:message-id:reply-to;
-        bh=asmFs22xWYwR1Ql9m/IrNv+MPUNDn8hSjmwDRYvO7mE=;
-        b=UdI2iQNBYwRf40ivf3ROR132t95BU/p3RUzXdZLCyz6c6JWtECQ5byyGeEwoX10n5u
-         HlepoNTJxMFLYrAHGvNLDPpWPuLXMa645S1mCVZ7NyWp8W96XzSynNZPeXHuJdb464QU
-         A7UTRSW3mlvKe9OR3EcB2CfBZv0yHWR0ldbnxcxGUFw8z78PNqpOVnITtjBdfpGesJ9c
-         VJw+fiM6hCcahor4nk9LLcAryPm8xmhDLxBKaLILO8wyTUiHY8G9hsXnFCtcpetnF5wS
-         pW13beAE+odb7ZZaXZUYpWGYhCe/hLzNjbo8YpgzHwadZthxPrT5YvNIYwyrvoViLM0n
-         KDRQ==
-X-Gm-Message-State: AO0yUKW+9H/kqcAUyWeZhZJhiJjsBcYn1THmZaSDrPrk/pNuGXJXGtJd
-        NgsGZW8iSqLEv81yK+U5Os8=
-X-Google-Smtp-Source: 
- AK7set/lzQZwCSxVaOe5dZ+7TR3xaQty/vg5xvZDpRW8TwTiPQblIbw5kJJTPLp67RySehrPIlCqSg==
-X-Received: by 2002:a5d:65c9:0:b0:2ce:ac31:54ff with SMTP id
- e9-20020a5d65c9000000b002ceac3154ffmr2776515wrw.2.1679420066191;
-        Tue, 21 Mar 2023 10:34:26 -0700 (PDT)
-Received: from atlantis.lan (255.red-79-146-124.dynamicip.rima-tde.net.
- [79.146.124.255])
-        by smtp.gmail.com with ESMTPSA id
- b13-20020a056000054d00b002da1261aa44sm184775wrf.48.2023.03.21.10.34.24
-        (version=TLS1_3 cipher=TLS_AES_256_GCM_SHA384 bits=256/256);
-        Tue, 21 Mar 2023 10:34:25 -0700 (PDT)
-From: =?utf-8?q?=C3=81lvaro_Fern=C3=A1ndez_Rojas?=  <[email protected]>
-Cc: =?utf-8?q?=C3=81lvaro_Fern=C3=A1ndez_Rojas?=  <[email protected]>,
- Simon Horman <[email protected]>
-Subject: [PATCH v2 4/4] net: dsa: b53: add BCM63268 RGMII configuration
-Date: Tue, 21 Mar 2023 18:33:59 +0100
-Message-Id: <[email protected]>
-X-Mailer: git-send-email 2.30.2
-In-Reply-To: <[email protected]>
-References: <[email protected]>
-MIME-Version: 1.0
-Precedence: bulk
-List-ID: <netdev.vger.kernel.org>
-X-Mailing-List: [email protected]
-X-Patchwork-Delegate: [email protected]
-
-BCM63268 requires special RGMII configuration to work.
-
-Signed-off-by: Álvaro Fernández Rojas <[email protected]>
-Reviewed-by: Florian Fainelli <[email protected]>
-Reviewed-by: Simon Horman <[email protected]>
----
- v2: no changes.
-
- drivers/net/dsa/b53/b53_common.c | 6 +++++-
- drivers/net/dsa/b53/b53_regs.h   | 1 +
- 2 files changed, 6 insertions(+), 1 deletion(-)
-
---- a/drivers/net/dsa/b53/b53_common.c
-+++ b/drivers/net/dsa/b53/b53_common.c
-@@ -1240,8 +1240,12 @@ static void b53_adjust_63xx_rgmii(struct
-               break;
-       }
--      if (port != dev->imp_port)
-+      if (port != dev->imp_port) {
-+              if (is63268(dev))
-+                      rgmii_ctrl |= RGMII_CTRL_MII_OVERRIDE;
-+
-               rgmii_ctrl |= RGMII_CTRL_ENABLE_GMII;
-+      }
-       b53_write8(dev, B53_CTRL_PAGE, off, rgmii_ctrl);
---- a/drivers/net/dsa/b53/b53_regs.h
-+++ b/drivers/net/dsa/b53/b53_regs.h
-@@ -138,6 +138,7 @@
- #define B53_RGMII_CTRL_IMP            0x60
- #define   RGMII_CTRL_ENABLE_GMII      BIT(7)
-+#define   RGMII_CTRL_MII_OVERRIDE     BIT(6)
- #define   RGMII_CTRL_TIMING_SEL               BIT(2)
- #define   RGMII_CTRL_DLL_RXC          BIT(1)
- #define   RGMII_CTRL_DLL_TXC          BIT(0)
diff --git a/target/linux/generic/pending-5.15/777-net-dsa-b53-mdio-add-support-for-BCM53134.patch b/target/linux/generic/pending-5.15/777-net-dsa-b53-mdio-add-support-for-BCM53134.patch
deleted file mode 100644 (file)
index 53494ec..0000000
+++ /dev/null
@@ -1,189 +0,0 @@
-From patchwork Fri Mar 24 08:41:38 2023
-Content-Type: text/plain; charset="utf-8"
-MIME-Version: 1.0
-Content-Transfer-Encoding: 8bit
-X-Patchwork-Submitter: =?utf-8?q?=C3=81lvaro_Fern=C3=A1ndez_Rojas?=
-X-Patchwork-Id: 13186549
-X-Patchwork-Delegate: [email protected]
-Return-Path: <[email protected]>
-X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on
-       aws-us-west-2-korg-lkml-1.web.codeaurora.org
-Received: from vger.kernel.org (vger.kernel.org [23.128.96.18])
-       by smtp.lore.kernel.org (Postfix) with ESMTP id EF744C76195
-       for <[email protected]>; Fri, 24 Mar 2023 08:42:01 +0000 (UTC)
-Received: ([email protected]) by vger.kernel.org via listexpand
-        id S231807AbjCXImA (ORCPT <rfc822;[email protected]>);
-        Fri, 24 Mar 2023 04:42:00 -0400
-Received: from lindbergh.monkeyblade.net ([23.128.96.19]:32956 "EHLO
-        lindbergh.monkeyblade.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org
-        with ESMTP id S231272AbjCXIly (ORCPT
-        <rfc822;[email protected]>); Fri, 24 Mar 2023 04:41:54 -0400
-Received: from mail-ed1-x535.google.com (mail-ed1-x535.google.com
- [IPv6:2a00:1450:4864:20::535])
-        by lindbergh.monkeyblade.net (Postfix) with ESMTPS id 113A517CF3;
-        Fri, 24 Mar 2023 01:41:46 -0700 (PDT)
-Received: by mail-ed1-x535.google.com with SMTP id ek18so4877175edb.6;
-        Fri, 24 Mar 2023 01:41:45 -0700 (PDT)
-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed;
-        d=gmail.com; s=20210112; t=1679647304;
-        h=content-transfer-encoding:mime-version:references:in-reply-to
-         :message-id:date:subject:cc:to:from:from:to:cc:subject:date
-         :message-id:reply-to;
-        bh=OfUWRaFIQIQw/lRivER+LHryfdLliXzvabGrcmkQVEU=;
-        b=JMrl6Eay1FS0JZqgPHsbcVzuNAbFELc0SLNGyzYtOVQXcI+YwKDM9Ls7I9PsQVEPoZ
-         CthomCTYoz5G9DU7uBuia207rnjOhssZJRu0syrCoU+O/ZiQyGLJDvq61z5oZJxC2S40
-         kzRsUsC6MRjn64DKPWmxhsSTMKLzn2+P233LKNFbHtfi3NWF5Qu/85sUkxMurnfUgja0
-         qQhl25qYY7ZIvmlFHYefaI5UkITQFuiybrqJW9tztCdHf/gS+f33YkkvQ8njmMQa1DW0
-         ppedfOUotX+6kmHZGX1yea2V5ezEGGvRourZtYMoecTiD0E5d1J1bKhktKslVLIDm0ig
-         oc2g==
-X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed;
-        d=1e100.net; s=20210112; t=1679647304;
-        h=content-transfer-encoding:mime-version:references:in-reply-to
-         :message-id:date:subject:cc:to:from:x-gm-message-state:from:to:cc
-         :subject:date:message-id:reply-to;
-        bh=OfUWRaFIQIQw/lRivER+LHryfdLliXzvabGrcmkQVEU=;
-        b=b3Gmga5ZDbnmQfnw1GCz+eU2JwgsVzfciZuSmfYAiVxpW4c6cur3MHbpzDPhi99wzA
-         ZYAM7ryLv88rXl/tQB5g2Nte5rvMfxUeHXsT/JpsRcSSocFRbRrk0QJyiA/Xj86NiD5N
-         C1sKz50Im190FmrvPcBh6OHQbv/3MQyE+1fQx+9q3jW5rQiAWQaYk4Ng8GlWA7gtG3jB
-         fHO6Fuoenn32pgkveJbQLYL/2t2f53wGf3QLQ3IeKW7jdfIHNThwrwqBMxdHoIDaTBT9
-         UWMeJuiYtylIibo/3zbORbWOgIERlWxZRf3BCOFpnzUn4eBzio4LgjtNxZ77ITRxsmbk
-         3+Hg==
-X-Gm-Message-State: AAQBX9dfyBfbR7Sdd5wqxMiAv3Yhk47pK1XzD87MZyAF3AxyoFyKcMaF
-        EbwJLyRvTGQEFdVWCGw1eMU=
-X-Google-Smtp-Source: 
- AKy350bpDVLq7k1FxG2Mek/VIobZL4KhufiKx8qfmpxpcWmLI3bLg8wfQKEAKJRNJBleo/7CZuCL5g==
-X-Received: by 2002:aa7:c711:0:b0:4a2:588f:b3c5 with SMTP id
- i17-20020aa7c711000000b004a2588fb3c5mr2261236edq.21.1679647304260;
-        Fri, 24 Mar 2023 01:41:44 -0700 (PDT)
-Received: from atlantis.lan (255.red-79-146-124.dynamicip.rima-tde.net.
- [79.146.124.255])
-        by smtp.gmail.com with ESMTPSA id
- z21-20020a50cd15000000b004acbda55f6bsm10323728edi.27.2023.03.24.01.41.43
-        (version=TLS1_3 cipher=TLS_AES_256_GCM_SHA384 bits=256/256);
-        Fri, 24 Mar 2023 01:41:43 -0700 (PDT)
-From: =?utf-8?q?=C3=81lvaro_Fern=C3=A1ndez_Rojas?=  <[email protected]>
-Cc: =?utf-8?q?=C3=81lvaro_Fern=C3=A1ndez_Rojas?=  <[email protected]>
-Subject: [PATCH v2 2/2] net: dsa: b53: mdio: add support for BCM53134
-Date: Fri, 24 Mar 2023 09:41:38 +0100
-Message-Id: <[email protected]>
-X-Mailer: git-send-email 2.30.2
-In-Reply-To: <[email protected]>
-References: <[email protected]>
-MIME-Version: 1.0
-Precedence: bulk
-List-ID: <netdev.vger.kernel.org>
-X-Mailing-List: [email protected]
-X-Patchwork-Delegate: [email protected]
-
-From: Paul Geurts <[email protected]>
-
-Add support for the BCM53134 Ethernet switch in the existing b53 dsa driver.
-BCM53134 is very similar to the BCM58XX series.
-
-Signed-off-by: Paul Geurts <[email protected]>
-Signed-off-by: Álvaro Fernández Rojas <[email protected]>
----
- v2: add BCM53134 to is531x5() and remove special RGMII config
-
- drivers/net/dsa/b53/b53_common.c | 15 +++++++++++++++
- drivers/net/dsa/b53/b53_mdio.c   |  5 ++++-
- drivers/net/dsa/b53/b53_priv.h   |  7 +++++--
- 3 files changed, 24 insertions(+), 3 deletions(-)
-
---- a/drivers/net/dsa/b53/b53_common.c
-+++ b/drivers/net/dsa/b53/b53_common.c
-@@ -2609,6 +2609,20 @@ static const struct b53_chip_data b53_sw
-               .jumbo_pm_reg = B53_JUMBO_PORT_MASK,
-               .jumbo_size_reg = B53_JUMBO_MAX_SIZE,
-       },
-+      {
-+              .chip_id = BCM53134_DEVICE_ID,
-+              .dev_name = "BCM53134",
-+              .vlans = 4096,
-+              .enabled_ports = 0x12f,
-+              .imp_port = 8,
-+              .cpu_port = B53_CPU_PORT,
-+              .vta_regs = B53_VTA_REGS,
-+              .arl_bins = 4,
-+              .arl_buckets = 1024,
-+              .duplex_reg = B53_DUPLEX_STAT_GE,
-+              .jumbo_pm_reg = B53_JUMBO_PORT_MASK,
-+              .jumbo_size_reg = B53_JUMBO_MAX_SIZE,
-+      },
- };
- static int b53_switch_init(struct b53_device *dev)
-@@ -2785,6 +2799,7 @@ int b53_switch_detect(struct b53_device
-               case BCM53012_DEVICE_ID:
-               case BCM53018_DEVICE_ID:
-               case BCM53019_DEVICE_ID:
-+              case BCM53134_DEVICE_ID:
-                       dev->chip_id = id32;
-                       break;
-               default:
---- a/drivers/net/dsa/b53/b53_mdio.c
-+++ b/drivers/net/dsa/b53/b53_mdio.c
-@@ -286,6 +286,7 @@ static const struct b53_io_ops b53_mdio_
- #define B53_BRCM_OUI_2        0x03625c00
- #define B53_BRCM_OUI_3        0x00406000
- #define B53_BRCM_OUI_4        0x01410c00
-+#define B53_BRCM_OUI_5        0xae025000
- static int b53_mdio_probe(struct mdio_device *mdiodev)
- {
-@@ -313,7 +314,8 @@ static int b53_mdio_probe(struct mdio_de
-       if ((phy_id & 0xfffffc00) != B53_BRCM_OUI_1 &&
-           (phy_id & 0xfffffc00) != B53_BRCM_OUI_2 &&
-           (phy_id & 0xfffffc00) != B53_BRCM_OUI_3 &&
--          (phy_id & 0xfffffc00) != B53_BRCM_OUI_4) {
-+          (phy_id & 0xfffffc00) != B53_BRCM_OUI_4 &&
-+          (phy_id & 0xfffffc00) != B53_BRCM_OUI_5) {
-               dev_err(&mdiodev->dev, "Unsupported device: 0x%08x\n", phy_id);
-               return -ENODEV;
-       }
-@@ -377,6 +379,7 @@ static const struct of_device_id b53_of_
-       { .compatible = "brcm,bcm53115" },
-       { .compatible = "brcm,bcm53125" },
-       { .compatible = "brcm,bcm53128" },
-+      { .compatible = "brcm,bcm53134" },
-       { .compatible = "brcm,bcm5365" },
-       { .compatible = "brcm,bcm5389" },
-       { .compatible = "brcm,bcm5395" },
---- a/drivers/net/dsa/b53/b53_priv.h
-+++ b/drivers/net/dsa/b53/b53_priv.h
-@@ -85,6 +85,7 @@ enum {
-       BCM583XX_DEVICE_ID = 0x58300,
-       BCM7445_DEVICE_ID = 0x7445,
-       BCM7278_DEVICE_ID = 0x7278,
-+      BCM53134_DEVICE_ID = 0x5075,
- };
- #define B53_N_PORTS   9
-@@ -182,7 +183,8 @@ static inline int is531x5(struct b53_dev
- {
-       return dev->chip_id == BCM53115_DEVICE_ID ||
-               dev->chip_id == BCM53125_DEVICE_ID ||
--              dev->chip_id == BCM53128_DEVICE_ID;
-+              dev->chip_id == BCM53128_DEVICE_ID ||
-+              dev->chip_id == BCM53134_DEVICE_ID;
- }
- static inline int is63xx(struct b53_device *dev)
-@@ -210,7 +212,8 @@ static inline int is58xx(struct b53_devi
-       return dev->chip_id == BCM58XX_DEVICE_ID ||
-               dev->chip_id == BCM583XX_DEVICE_ID ||
-               dev->chip_id == BCM7445_DEVICE_ID ||
--              dev->chip_id == BCM7278_DEVICE_ID;
-+              dev->chip_id == BCM7278_DEVICE_ID ||
-+              dev->chip_id == BCM53134_DEVICE_ID;
- }
- #define B53_63XX_RGMII0       4
diff --git a/target/linux/generic/pending-5.15/779-net-vxlan-don-t-learn-non-unicast-L2-destinations.patch b/target/linux/generic/pending-5.15/779-net-vxlan-don-t-learn-non-unicast-L2-destinations.patch
deleted file mode 100644 (file)
index 6c1f596..0000000
+++ /dev/null
@@ -1,30 +0,0 @@
-From 3f1a227cb071f65f6ecc4db9f399649869735a7c Mon Sep 17 00:00:00 2001
-From: David Bauer <[email protected]>
-Date: Sat, 17 Feb 2024 22:34:59 +0100
-Subject: [PATCH] net vxlan: don't learn non-unicast L2 destinations
-
-This patch avoids learning non-unicast targets in the vxlan FDB.
-They are non-unicast and thus should be sent to the broadcast-IPv6
-instead of a unicast address.
-
-Link: https://lore.kernel.org/netdev/[email protected]/
-Link: https://github.com/freifunk-gluon/gluon/issues/3191
-
-Signed-off-by: David Bauer <[email protected]>
----
- drivers/net/vxlan.c | 4 ++++
- 1 file changed, 4 insertions(+)
-
---- a/drivers/net/vxlan/vxlan_core.c
-+++ b/drivers/net/vxlan/vxlan_core.c
-@@ -1493,6 +1493,10 @@ static bool vxlan_snoop(struct net_devic
-       struct vxlan_fdb *f;
-       u32 ifindex = 0;
-+      /* Don't learn broadcast packets */
-+      if (is_multicast_ether_addr(src_mac) || is_zero_ether_addr(src_mac))
-+              return false;
-+
- #if IS_ENABLED(CONFIG_IPV6)
-       if (src_ip->sa.sa_family == AF_INET6 &&
-           (ipv6_addr_type(&src_ip->sin6.sin6_addr) & IPV6_ADDR_LINKLOCAL))
diff --git a/target/linux/generic/pending-5.15/780-ARM-kirkwood-add-missing-linux-if_ether.h-for-ETH_AL.patch b/target/linux/generic/pending-5.15/780-ARM-kirkwood-add-missing-linux-if_ether.h-for-ETH_AL.patch
deleted file mode 100644 (file)
index 39ba716..0000000
+++ /dev/null
@@ -1,61 +0,0 @@
-From patchwork Thu Aug  5 22:23:30 2021
-Content-Type: text/plain; charset="utf-8"
-MIME-Version: 1.0
-Content-Transfer-Encoding: 7bit
-X-Patchwork-Submitter: Daniel Golle <[email protected]>
-X-Patchwork-Id: 12422209
-Date: Thu, 5 Aug 2021 23:23:30 +0100
-From: Daniel Golle <[email protected]>
-Cc: "David S. Miller" <[email protected]>, Andrew Lunn <[email protected]>,
- Michael Walle <[email protected]>
-Subject: [PATCH] ARM: kirkwood: add missing <linux/if_ether.h> for ETH_ALEN
-Message-ID: <[email protected]>
-MIME-Version: 1.0
-Content-Disposition: inline
-X-BeenThere: [email protected]
-X-Mailman-Version: 2.1.34
-Precedence: list
-List-Id: <linux-arm-kernel.lists.infradead.org>
-List-Archive: <http://lists.infradead.org/pipermail/linux-arm-kernel/>
-Sender: "linux-arm-kernel" <[email protected]>
-
-After commit 83216e3988cd1 ("of: net: pass the dst buffer to
-of_get_mac_address()") build fails for kirkwood as ETH_ALEN is not
-defined.
-
-arch/arm/mach-mvebu/kirkwood.c: In function 'kirkwood_dt_eth_fixup':
-arch/arm/mach-mvebu/kirkwood.c:87:13: error: 'ETH_ALEN' undeclared (first use in this function); did you mean 'ESTALE'?
-   u8 tmpmac[ETH_ALEN];
-             ^~~~~~~~
-             ESTALE
-arch/arm/mach-mvebu/kirkwood.c:87:13: note: each undeclared identifier is reported only once for each function it appears in
-arch/arm/mach-mvebu/kirkwood.c:87:6: warning: unused variable 'tmpmac' [-Wunused-variable]
-   u8 tmpmac[ETH_ALEN];
-      ^~~~~~
-make[5]: *** [scripts/Makefile.build:262: arch/arm/mach-mvebu/kirkwood.o] Error 1
-make[5]: *** Waiting for unfinished jobs....
-
-Add missing #include <linux/if_ether.h> to fix this.
-
-Cc: David S. Miller <[email protected]>
-Cc: Andrew Lunn <[email protected]>
-Cc: Michael Walle <[email protected]>
-Reported-by: https://buildbot.openwrt.org/master/images/#/builders/56/builds/220/steps/44/logs/stdio
-Fixes: 83216e3988cd1 ("of: net: pass the dst buffer to of_get_mac_address()")
-Signed-off-by: Daniel Golle <[email protected]>
----
- arch/arm/mach-mvebu/kirkwood.c | 1 +
- 1 file changed, 1 insertion(+)
-
---- a/arch/arm/mach-mvebu/kirkwood.c
-+++ b/arch/arm/mach-mvebu/kirkwood.c
-@@ -11,6 +11,7 @@
- #include <linux/kernel.h>
- #include <linux/init.h>
- #include <linux/mbus.h>
-+#include <linux/if_ether.h>
- #include <linux/of.h>
- #include <linux/of_address.h>
- #include <linux/of_net.h>
diff --git a/target/linux/generic/pending-5.15/790-bus-mhi-core-add-SBL-state-callback.patch b/target/linux/generic/pending-5.15/790-bus-mhi-core-add-SBL-state-callback.patch
deleted file mode 100644 (file)
index 6402dd9..0000000
+++ /dev/null
@@ -1,48 +0,0 @@
-From 5f7c5e1c0d7a79be144e5efc1f24728ddd7fc25c Mon Sep 17 00:00:00 2001
-From: Robert Marko <[email protected]>
-Date: Sat, 5 Nov 2022 20:02:56 +0100
-Subject: [PATCH 1/2] bus: mhi: core: add SBL state callback
-
-Add support for SBL state callback in MHI core.
-
-It is required for ath11k MHI devices in order to be able to set QRTR
-instance ID in the SBL state so that QRTR instance ID-s dont conflict in
-case of multiple PCI/MHI cards or AHB + PCI/MHI card.
-Setting QRTR instance ID is only possible in SBL state and there is
-currently no way to ensure that we are in that state, so provide a
-callback that the controller can trigger off.
-
-Signed-off-by: Robert Marko <[email protected]>
----
- drivers/bus/mhi/host/main.c | 1 +
- include/linux/mhi.h         | 2 ++
- 2 files changed, 3 insertions(+)
-
---- a/drivers/bus/mhi/host/main.c
-+++ b/drivers/bus/mhi/host/main.c
-@@ -896,6 +896,7 @@ int mhi_process_ctrl_ev_ring(struct mhi_
-                       switch (event) {
-                       case MHI_EE_SBL:
-                               st = DEV_ST_TRANSITION_SBL;
-+                              mhi_cntrl->status_cb(mhi_cntrl, MHI_CB_EE_SBL_MODE);
-                               break;
-                       case MHI_EE_WFW:
-                       case MHI_EE_AMSS:
---- a/include/linux/mhi.h
-+++ b/include/linux/mhi.h
-@@ -34,6 +34,7 @@ struct mhi_buf_info;
-  * @MHI_CB_SYS_ERROR: MHI device entered error state (may recover)
-  * @MHI_CB_FATAL_ERROR: MHI device entered fatal error state
-  * @MHI_CB_BW_REQ: Received a bandwidth switch request from device
-+ * @MHI_CB_EE_SBL_MODE: MHI device entered SBL mode
-  */
- enum mhi_callback {
-       MHI_CB_IDLE,
-@@ -45,6 +46,7 @@ enum mhi_callback {
-       MHI_CB_SYS_ERROR,
-       MHI_CB_FATAL_ERROR,
-       MHI_CB_BW_REQ,
-+      MHI_CB_EE_SBL_MODE,
- };
- /**
diff --git a/target/linux/generic/pending-5.15/795-mt7530-register-OF-node-for-internal-MDIO-bus.patch b/target/linux/generic/pending-5.15/795-mt7530-register-OF-node-for-internal-MDIO-bus.patch
deleted file mode 100644 (file)
index 609e03d..0000000
+++ /dev/null
@@ -1,43 +0,0 @@
-From 1d81e51d6d79d9098013b2e8cdd677bae998c5d8 Mon Sep 17 00:00:00 2001
-From: David Bauer <[email protected]>
-Date: Fri, 28 Apr 2023 02:22:59 +0200
-Subject: [PATCH 1/2] mt7530: register OF node for internal MDIO bus
-
-The MT753x switches provide a switch-internal MDIO bus for the embedded
-PHYs.
-
-Register a OF sub-node on the switch OF-node for this internal MDIO bus.
-This allows to configure the embedded PHYs using device-tree.
-
-Signed-off-by: David Bauer <[email protected]>
----
- drivers/net/dsa/mt7530.c | 7 ++++++-
- 1 file changed, 6 insertions(+), 1 deletion(-)
-
---- a/drivers/net/dsa/mt7530.c
-+++ b/drivers/net/dsa/mt7530.c
-@@ -2356,10 +2356,13 @@ mt7530_setup_mdio(struct mt7530_priv *pr
- {
-       struct dsa_switch *ds = priv->ds;
-       struct device *dev = priv->dev;
-+      struct device_node *np, *mnp;
-       struct mii_bus *bus;
-       static int idx;
-       int ret;
-+      np = priv->dev->of_node;
-+
-       bus = devm_mdiobus_alloc(dev);
-       if (!bus)
-               return -ENOMEM;
-@@ -2376,7 +2379,9 @@ mt7530_setup_mdio(struct mt7530_priv *pr
-       if (priv->irq)
-               mt7530_setup_mdio_irq(priv);
--      ret = devm_mdiobus_register(dev, bus);
-+      mnp = of_get_child_by_name(np, "mdio");
-+      ret = devm_of_mdiobus_register(dev, bus, mnp);
-+      of_node_put(mnp);
-       if (ret) {
-               dev_err(dev, "failed to register MDIO bus: %d\n", ret);
-               if (priv->irq)
diff --git a/target/linux/generic/pending-5.15/796-net-dsa-mt7530-fix-10M-100M-speed-on-MT7988-switch.patch b/target/linux/generic/pending-5.15/796-net-dsa-mt7530-fix-10M-100M-speed-on-MT7988-switch.patch
deleted file mode 100644 (file)
index 1697347..0000000
+++ /dev/null
@@ -1,45 +0,0 @@
-From a444877c10a665cd8a869e6d37facdb89fd95f79 Mon Sep 17 00:00:00 2001
-Message-ID: <a444877c10a665cd8a869e6d37facdb89fd95f79.1706070008.git.daniel@makrotopia.org>
-From: Daniel Golle <[email protected]>
-Date: Wed, 24 Jan 2024 04:17:11 +0000
-Subject: [PATCH net] net: dsa: mt7530: fix 10M/100M speed on MT7988 switch
-To: Arınç ÜNAL <[email protected]>,
-    Daniel Golle <[email protected]>,
-    DENG Qingfang <[email protected]>,
-    Sean Wang <[email protected]>,
-    Andrew Lunn <[email protected]>,
-    Florian Fainelli <[email protected]>,
-    Vladimir Oltean <[email protected]>,
-    David S. Miller <[email protected]>,
-    Eric Dumazet <[email protected]>,
-    Jakub Kicinski <[email protected]>,
-    Paolo Abeni <[email protected]>,
-    Matthias Brugger <[email protected]>,
-    AngeloGioacchino Del Regno <[email protected]>,
-
-Setup PMCR port register for actual speed and duplex on internally
-connected PHYs of the MT7988 built-in switch. This fixes links with
-speeds other than 1000M.
-
-Fixes: ("110c18bfed414 net: dsa: mt7530: introduce driver for MT7988 built-in switch")
-Signed-off-by: Daniel Golle <[email protected]>
----
- drivers/net/dsa/mt7530.c | 3 +--
- 1 file changed, 1 insertion(+), 2 deletions(-)
-
---- a/drivers/net/dsa/mt7530.c
-+++ b/drivers/net/dsa/mt7530.c
-@@ -3065,8 +3065,7 @@ static void mt753x_phylink_mac_link_up(s
-       /* MT753x MAC works in 1G full duplex mode for all up-clocked
-        * variants.
-        */
--      if (interface == PHY_INTERFACE_MODE_INTERNAL ||
--          interface == PHY_INTERFACE_MODE_TRGMII ||
-+      if (interface == PHY_INTERFACE_MODE_TRGMII ||
-           (phy_interface_mode_is_8023z(interface))) {
-               speed = SPEED_1000;
-               duplex = DUPLEX_FULL;
diff --git a/target/linux/generic/pending-5.15/800-bcma-get-SoC-device-struct-copy-its-DMA-params-to-th.patch b/target/linux/generic/pending-5.15/800-bcma-get-SoC-device-struct-copy-its-DMA-params-to-th.patch
deleted file mode 100644 (file)
index 478a2cb..0000000
+++ /dev/null
@@ -1,73 +0,0 @@
-From: =?UTF-8?q?Rafa=C5=82=20Mi=C5=82ecki?= <[email protected]>
-Subject: [PATCH] bcma: get SoC device struct & copy its DMA params to the
- subdevices
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-For bus devices to be fully usable it's required to set their DMA
-parameters.
-
-For years it has been missing and remained unnoticed because of
-mips_dma_alloc_coherent() silently handling the empty coherent_dma_mask.
-Kernel 4.19 came with a lot of DMA changes and caused a regression on
-the bcm47xx. Starting with the commit f8c55dc6e828 ("MIPS: use generic
-dma noncoherent ops for simple noncoherent platforms") DMA coherent
-allocations just fail. Example:
-[    1.114914] bgmac_bcma bcma0:2: Allocation of TX ring 0x200 failed
-[    1.121215] bgmac_bcma bcma0:2: Unable to alloc memory for DMA
-[    1.127626] bgmac_bcma: probe of bcma0:2 failed with error -12
-[    1.133838] bgmac_bcma: Broadcom 47xx GBit MAC driver loaded
-
-This change fixes above regression in addition to the MIPS bcm47xx
-commit 321c46b91550 ("MIPS: BCM47XX: Setup struct device for the SoC").
-
-It also fixes another *old* GPIO regression caused by a parent pointing
-to the NULL:
-[    0.157054] missing gpiochip .dev parent pointer
-[    0.157287] bcma: bus0: Error registering GPIO driver: -22
-introduced by the commit 74f4e0cc6108 ("bcma: switch GPIO portions to
-use GPIOLIB_IRQCHIP").
-
-Fixes: f8c55dc6e828 ("MIPS: use generic dma noncoherent ops for simple noncoherent platforms")
-Fixes: 74f4e0cc6108 ("bcma: switch GPIO portions to use GPIOLIB_IRQCHIP")
-Cc: Christoph Hellwig <[email protected]>
-Cc: Linus Walleij <[email protected]>
-Signed-off-by: Rafał Miłecki <[email protected]>
----
-
---- a/drivers/bcma/host_soc.c
-+++ b/drivers/bcma/host_soc.c
-@@ -191,6 +191,8 @@ int __init bcma_host_soc_init(struct bcm
-       struct bcma_bus *bus = &soc->bus;
-       int err;
-+      bus->dev = soc->dev;
-+
-       /* Scan bus and initialize it */
-       err = bcma_bus_early_register(bus);
-       if (err)
---- a/drivers/bcma/main.c
-+++ b/drivers/bcma/main.c
-@@ -236,13 +236,17 @@ EXPORT_SYMBOL(bcma_core_irq);
- void bcma_prepare_core(struct bcma_bus *bus, struct bcma_device *core)
- {
--      device_initialize(&core->dev);
-+      struct device *dev = &core->dev;
-+
-+      device_initialize(dev);
-       core->dev.release = bcma_release_core_dev;
-       core->dev.bus = &bcma_bus_type;
--      dev_set_name(&core->dev, "bcma%d:%d", bus->num, core->core_index);
-+      dev_set_name(dev, "bcma%d:%d", bus->num, core->core_index);
-       core->dev.parent = bus->dev;
--      if (bus->dev)
-+      if (bus->dev) {
-               bcma_of_fill_device(bus->dev, core);
-+              dma_coerce_mask_and_coherent(dev, bus->dev->coherent_dma_mask);
-+      }
-       switch (bus->hosttype) {
-       case BCMA_HOSTTYPE_PCI:
diff --git a/target/linux/generic/pending-5.15/801-gpio-gpio-cascade-add-generic-GPIO-cascade.patch b/target/linux/generic/pending-5.15/801-gpio-gpio-cascade-add-generic-GPIO-cascade.patch
deleted file mode 100644 (file)
index c1e14b9..0000000
+++ /dev/null
@@ -1,222 +0,0 @@
-From fc23ea48ba52c24f201fe5ca0132ee1a3de5a70a Mon Sep 17 00:00:00 2001
-From: Mauri Sandberg <[email protected]>
-Date: Thu, 25 Mar 2021 11:48:05 +0200
-Subject: [PATCH 2/2] gpio: gpio-cascade: add generic GPIO cascade
-
-Adds support for building cascades of GPIO lines. That is, it allows
-setups when there is one upstream line and multiple cascaded lines, out
-of which one can be chosen at a time. The status of the upstream line
-can be conveyed to the selected cascaded line or, vice versa, the status
-of the cascaded line can be conveyed to the upstream line.
-
-A multiplexer is being used to select, which cascaded GPIO line is being
-used at any given time.
-
-At the moment only input direction is supported. In future it should be
-possible to add support for output direction, too.
-
-Signed-off-by: Mauri Sandberg <[email protected]>
-Reviewed-by: Linus Walleij <[email protected]>
-Reviewed-by: Andy Shevchenko <[email protected]>
----
-v7 -> v8:
- - rearrange members in struct gpio_cascade
- - cosmetic changes in file header and in one function declaration
- - added Reviewed-by tags by Linus and Andy
-v6 -> v7:
- - In Kconfig add info about module name
- - adhere to new convention that allows lines longer than 80 chars
- - use dev_probe_err with upstream gpio line too
- - refactor for cleaner exit of probe function.
-v5 -> v6:
- - In Kconfig, remove dependency to OF_GPIO and select only MULTIPLEXER
- - refactor code preferring one-liners
- - clean up prints, removing them from success-path.
- - don't explicitly set gpio_chip.of_node as it's done in the GPIO library
- - use devm_gpiochip_add_data instead of gpiochip_add
-v4 -> v5:
- - renamed gpio-mux-input -> gpio-cascade. refactored code accordingly
-   here and there and changed to use new bindings and compatible string
-   - ambigious and vague 'pin' was rename to 'upstream_line'
- - dropped Tested-by and Reviewed-by due to changes in bindings
- - dropped Reported-by suggested by an automatic bot as it was not really
-   appropriate to begin with
- - functionally it's the same as v4
-v3 -> v4:
- - Changed author email
- - Included Tested-by and Reviewed-by from Drew
-v2 -> v3:
- - use managed device resources
- - update Kconfig description
-v1 -> v2:
- - removed .owner from platform_driver as per test bot's instruction
- - added MODULE_AUTHOR, MODULE_DESCRIPTION, MODULE_LICENSE
- - added gpio_mux_input_get_direction as it's recommended for all chips
- - removed because this is input only chip: gpio_mux_input_set_value
- - removed because they are not needed for input/output only chips:
-     gpio_mux_input_direction_input
-     gpio_mux_input_direction_output
- - fixed typo in an error message
- - added info message about successful registration
- - removed can_sleep flag as this does not sleep while getting GPIO value
-   like I2C or SPI do
- - Updated description in Kconfig
----
- drivers/gpio/Kconfig        |  15 +++++
- drivers/gpio/Makefile       |   1 +
- drivers/gpio/gpio-cascade.c | 117 ++++++++++++++++++++++++++++++++++++
- 3 files changed, 133 insertions(+)
- create mode 100644 drivers/gpio/gpio-cascade.c
-
---- a/drivers/gpio/Kconfig
-+++ b/drivers/gpio/Kconfig
-@@ -1683,4 +1683,19 @@ config GPIO_VIRTIO
- endmenu
-+comment "Other GPIO expanders"
-+
-+config GPIO_CASCADE
-+      tristate "General GPIO cascade"
-+      select MULTIPLEXER
-+      help
-+        Say yes here to enable support for generic GPIO cascade.
-+
-+        This allows building one-to-many cascades of GPIO lines using
-+        different types of multiplexers readily available. At the
-+        moment only input lines are supported.
-+
-+        To build the driver as a module choose 'm' and the resulting module
-+        will be called 'gpio-cascade'.
-+
- endif
---- a/drivers/gpio/Makefile
-+++ b/drivers/gpio/Makefile
-@@ -45,6 +45,7 @@ obj-$(CONFIG_GPIO_BD9571MWV)         += gpio-bd
- obj-$(CONFIG_GPIO_BRCMSTB)            += gpio-brcmstb.o
- obj-$(CONFIG_GPIO_BT8XX)              += gpio-bt8xx.o
- obj-$(CONFIG_GPIO_CADENCE)            += gpio-cadence.o
-+obj-$(CONFIG_GPIO_CASCADE)            += gpio-cascade.o
- obj-$(CONFIG_GPIO_CLPS711X)           += gpio-clps711x.o
- obj-$(CONFIG_GPIO_SNPS_CREG)          += gpio-creg-snps.o
- obj-$(CONFIG_GPIO_CRYSTAL_COVE)               += gpio-crystalcove.o
---- /dev/null
-+++ b/drivers/gpio/gpio-cascade.c
-@@ -0,0 +1,117 @@
-+// SPDX-License-Identifier: GPL-2.0-only
-+/*
-+ *  A generic GPIO cascade driver
-+ *
-+ *  Copyright (C) 2021 Mauri Sandberg <[email protected]>
-+ *
-+ * This allows building cascades of GPIO lines in a manner illustrated
-+ * below:
-+ *
-+ *                 /|---- Cascaded GPIO line 0
-+ *  Upstream      | |---- Cascaded GPIO line 1
-+ *  GPIO line ----+ | .
-+ *                | | .
-+ *                 \|---- Cascaded GPIO line n
-+ *
-+ * A multiplexer is being used to select, which cascaded line is being
-+ * addressed at any given time.
-+ *
-+ * At the moment only input mode is supported due to lack of means for
-+ * testing output functionality. At least theoretically output should be
-+ * possible with open drain constructions.
-+ */
-+
-+#include <linux/module.h>
-+#include <linux/slab.h>
-+#include <linux/platform_device.h>
-+#include <linux/mux/consumer.h>
-+
-+#include <linux/gpio/consumer.h>
-+#include <linux/gpio/driver.h>
-+
-+struct gpio_cascade {
-+      struct gpio_chip        gpio_chip;
-+      struct device           *parent;
-+      struct mux_control      *mux_control;
-+      struct gpio_desc        *upstream_line;
-+};
-+
-+static struct gpio_cascade *chip_to_cascade(struct gpio_chip *gc)
-+{
-+      return container_of(gc, struct gpio_cascade, gpio_chip);
-+}
-+
-+static int gpio_cascade_get_direction(struct gpio_chip *gc, unsigned int offset)
-+{
-+      return GPIO_LINE_DIRECTION_IN;
-+}
-+
-+static int gpio_cascade_get_value(struct gpio_chip *gc, unsigned int offset)
-+{
-+      struct gpio_cascade *cas = chip_to_cascade(gc);
-+      int ret;
-+
-+      ret = mux_control_select(cas->mux_control, offset);
-+      if (ret)
-+              return ret;
-+
-+      ret = gpiod_get_value(cas->upstream_line);
-+      mux_control_deselect(cas->mux_control);
-+      return ret;
-+}
-+
-+static int gpio_cascade_probe(struct platform_device *pdev)
-+{
-+      struct device *dev = &pdev->dev;
-+      struct gpio_cascade *cas;
-+      struct mux_control *mc;
-+      struct gpio_desc *upstream;
-+      struct gpio_chip *gc;
-+
-+      cas = devm_kzalloc(dev, sizeof(*cas), GFP_KERNEL);
-+      if (!cas)
-+              return -ENOMEM;
-+
-+      mc = devm_mux_control_get(dev, NULL);
-+      if (IS_ERR(mc))
-+              return dev_err_probe(dev, PTR_ERR(mc), "unable to get mux-control\n");
-+
-+      cas->mux_control = mc;
-+      upstream = devm_gpiod_get(dev, "upstream",  GPIOD_IN);
-+      if (IS_ERR(upstream))
-+              return dev_err_probe(dev, PTR_ERR(upstream), "unable to claim upstream GPIO line\n");
-+
-+      cas->upstream_line = upstream;
-+      cas->parent = dev;
-+
-+      gc = &cas->gpio_chip;
-+      gc->get = gpio_cascade_get_value;
-+      gc->get_direction = gpio_cascade_get_direction;
-+      gc->base = -1;
-+      gc->ngpio = mux_control_states(mc);
-+      gc->label = dev_name(cas->parent);
-+      gc->parent = cas->parent;
-+      gc->owner = THIS_MODULE;
-+
-+      platform_set_drvdata(pdev, cas);
-+      return devm_gpiochip_add_data(dev, &cas->gpio_chip, NULL);
-+}
-+
-+static const struct of_device_id gpio_cascade_id[] = {
-+      { .compatible = "gpio-cascade" },
-+      { /* sentinel */ }
-+};
-+MODULE_DEVICE_TABLE(of, gpio_cascade_id);
-+
-+static struct platform_driver gpio_cascade_driver = {
-+      .driver = {
-+              .name           = "gpio-cascade",
-+              .of_match_table = gpio_cascade_id,
-+      },
-+      .probe  = gpio_cascade_probe,
-+};
-+module_platform_driver(gpio_cascade_driver);
-+
-+MODULE_AUTHOR("Mauri Sandberg <[email protected]>");
-+MODULE_DESCRIPTION("Generic GPIO cascade");
-+MODULE_LICENSE("GPL");
diff --git a/target/linux/generic/pending-5.15/802-nvmem-u-boot-env-align-endianness-of-crc32-values.patch b/target/linux/generic/pending-5.15/802-nvmem-u-boot-env-align-endianness-of-crc32-values.patch
deleted file mode 100644 (file)
index 29fe668..0000000
+++ /dev/null
@@ -1,45 +0,0 @@
-From 0e71cac033bb7689c4dfa2e6814191337ef770f5 Mon Sep 17 00:00:00 2001
-From: INAGAKI Hiroshi <[email protected]>
-Date: Thu, 13 Oct 2022 00:51:33 +0900
-Subject: [PATCH] nvmem: layouts: u-boot-env: align endianness of crc32 values
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-This patch fixes crc32 error on Big-Endianness system by conversion of
-calculated crc32 value.
-
-Little-Endianness system:
-
-  obtained crc32: Little
-calculated crc32: Little
-
-Big-Endianness system:
-
-  obtained crc32: Little
-calculated crc32: Big
-
-log (APRESIA ApresiaLightGS120GT-SS, RTL8382M, Big-Endianness):
-
-[    8.570000] u_boot_env 18001200.spi:flash@0:partitions:partition@c0000: Invalid calculated CRC32: 0x88cd6f09 (expected: 0x096fcd88)
-[    8.580000] u_boot_env: probe of 18001200.spi:flash@0:partitions:partition@c0000 failed with error -22
-
-Fixes: f955dc1445069 ("nvmem: add driver handling U-Boot environment variables")
-
-Signed-off-by: INAGAKI Hiroshi <[email protected]>
-Acked-by: Rafał Miłecki <[email protected]>
-Tested-by: Christian Lamparter <[email protected]>
-Signed-off-by: Srinivas Kandagatla <[email protected]>
----
-
---- a/drivers/nvmem/layouts/u-boot-env.c
-+++ b/drivers/nvmem/layouts/u-boot-env.c
-@@ -148,7 +148,7 @@ int u_boot_env_parse(struct device *dev,
-       crc32_data_len = dev_size - crc32_data_offset;
-       data_len = dev_size - data_offset;
--      calc = crc32(~0, buf + crc32_data_offset, crc32_data_len) ^ ~0L;
-+      calc = le32_to_cpu((__le32)crc32(~0, buf + crc32_data_offset, crc32_data_len) ^ ~0L);
-       if (calc != crc32) {
-               dev_err(dev, "Invalid calculated CRC32: 0x%08x (expected: 0x%08x)\n", calc, crc32);
-               err = -EINVAL;
diff --git a/target/linux/generic/pending-5.15/804-nvmem-core-support-mac-base-fixed-layout-cells.patch b/target/linux/generic/pending-5.15/804-nvmem-core-support-mac-base-fixed-layout-cells.patch
deleted file mode 100644 (file)
index 29cda18..0000000
+++ /dev/null
@@ -1,124 +0,0 @@
-From: =?UTF-8?q?Rafa=C5=82=20Mi=C5=82ecki?= <[email protected]>
-Date: Thu, 13 Jul 2023 18:29:19 +0200
-Subject: [PATCH] nvmem: core: support "mac-base" fixed layout cells
-
-Fixed layout binding allows specifying "mac-base" NVMEM cells. It's used
-for base MAC address (that can be used for calculating relative
-addresses). It can be stored in a raw binary format or as an ASCII
-string.
----
-
---- a/drivers/nvmem/Kconfig
-+++ b/drivers/nvmem/Kconfig
-@@ -1,6 +1,7 @@
- # SPDX-License-Identifier: GPL-2.0-only
- menuconfig NVMEM
-       bool "NVMEM Support"
-+      select GENERIC_NET_UTILS
-       imply NVMEM_LAYOUTS
-       help
-         Support for NVMEM(Non Volatile Memory) devices like EEPROM, EFUSES...
---- a/drivers/nvmem/core.c
-+++ b/drivers/nvmem/core.c
-@@ -7,9 +7,12 @@
-  */
- #include <linux/device.h>
-+#include <linux/ctype.h>
-+#include <linux/etherdevice.h>
- #include <linux/export.h>
- #include <linux/fs.h>
- #include <linux/idr.h>
-+#include <linux/if_ether.h>
- #include <linux/init.h>
- #include <linux/kref.h>
- #include <linux/module.h>
-@@ -797,6 +800,62 @@ static int nvmem_validate_keepouts(struc
-       return 0;
- }
-+static int nvmem_mac_base_raw_read(void *context, const char *id, int index, unsigned int offset,
-+                                 void *buf, size_t bytes)
-+{
-+      if (WARN_ON(bytes != ETH_ALEN))
-+              return -EINVAL;
-+
-+      if (index)
-+              eth_addr_add(buf, index);
-+
-+      return 0;
-+}
-+
-+static int nvmem_mac_base_ascii_read(void *context, const char *id, int index, unsigned int offset,
-+                                   void *buf, size_t bytes)
-+{
-+      u8 mac[ETH_ALEN];
-+
-+      if (WARN_ON(bytes != 3 * ETH_ALEN - 1))
-+              return -EINVAL;
-+
-+      if (!mac_pton(buf, mac))
-+              return -EINVAL;
-+
-+      if (index)
-+              eth_addr_add(mac, index);
-+
-+      ether_addr_copy(buf, mac);
-+
-+      return 0;
-+}
-+
-+static int nvmem_mac_base_hex_read(void *context, const char *id, int index, unsigned int offset,
-+                                 void *buf, size_t bytes)
-+{
-+      u8 mac[ETH_ALEN], *hexstr;
-+      int i;
-+
-+      if (WARN_ON(bytes != 2 * ETH_ALEN))
-+              return -EINVAL;
-+
-+      hexstr = (u8 *)buf;
-+      for (i = 0; i < ETH_ALEN; i++) {
-+              if (!isxdigit(hexstr[i * 2]) || !isxdigit(hexstr[i * 2 + 1]))
-+                      return -EINVAL;
-+
-+              mac[i] = (hex_to_bin(hexstr[i * 2]) << 4) | hex_to_bin(hexstr[i * 2 + 1]);
-+      }
-+
-+      if (index)
-+              eth_addr_add(mac, index);
-+
-+      ether_addr_copy(buf, mac);
-+
-+      return 0;
-+}
-+
- static int nvmem_add_cells_from_dt(struct nvmem_device *nvmem, struct device_node *np)
- {
-       struct device *dev = &nvmem->dev;
-@@ -836,6 +895,25 @@ static int nvmem_add_cells_from_dt(struc
-               if (nvmem->fixup_dt_cell_info)
-                       nvmem->fixup_dt_cell_info(nvmem, &info);
-+              if (of_device_is_compatible(np, "fixed-layout")) {
-+                      if (of_device_is_compatible(child, "mac-base")) {
-+                              if (info.bytes == ETH_ALEN) {
-+                                      info.raw_len = info.bytes;
-+                                      info.bytes = ETH_ALEN;
-+                                      info.read_post_process = nvmem_mac_base_raw_read;
-+                              } else if (info.bytes == 2 * ETH_ALEN) {
-+                                      info.raw_len = info.bytes;
-+                                      info.bytes = ETH_ALEN;
-+                                      info.read_post_process = nvmem_mac_base_hex_read;
-+                              } else if (info.bytes == 3 * ETH_ALEN - 1) {
-+                                      info.raw_len = info.bytes;
-+                                      info.bytes = ETH_ALEN;
-+                                      info.read_post_process = nvmem_mac_base_ascii_read;
-+                              }
-+
-+                      }
-+              }
-+
-               ret = nvmem_add_one_cell(nvmem, &info);
-               kfree(info.name);
-               if (ret) {
diff --git a/target/linux/generic/pending-5.15/810-pci_disable_common_quirks.patch b/target/linux/generic/pending-5.15/810-pci_disable_common_quirks.patch
deleted file mode 100644 (file)
index 302051c..0000000
+++ /dev/null
@@ -1,62 +0,0 @@
-From: Gabor Juhos <[email protected]>
-Subject: debloat: add kernel config option to disabling common PCI quirks
-
-Signed-off-by: Gabor Juhos <[email protected]>
----
- drivers/pci/Kconfig  | 6 ++++++
- drivers/pci/quirks.c | 6 ++++++
- 2 files changed, 12 insertions(+)
-
---- a/drivers/pci/Kconfig
-+++ b/drivers/pci/Kconfig
-@@ -118,6 +118,13 @@ config XEN_PCIDEV_FRONTEND
-         The PCI device frontend driver allows the kernel to import arbitrary
-         PCI devices from a PCI backend to support PCI driver domains.
-+config PCI_DISABLE_COMMON_QUIRKS
-+      bool "PCI disable common quirks"
-+      depends on PCI
-+      help
-+        If you don't know what to do here, say N.
-+
-+
- config PCI_ATS
-       bool
---- a/drivers/pci/quirks.c
-+++ b/drivers/pci/quirks.c
-@@ -207,6 +207,7 @@ static void quirk_mmio_always_on(struct
- DECLARE_PCI_FIXUP_CLASS_EARLY(PCI_ANY_ID, PCI_ANY_ID,
-                               PCI_CLASS_BRIDGE_HOST, 8, quirk_mmio_always_on);
-+#ifndef CONFIG_PCI_DISABLE_COMMON_QUIRKS
- /*
-  * The Mellanox Tavor device gives false positive parity errors.  Disable
-  * parity error reporting.
-@@ -3369,6 +3370,8 @@ DECLARE_PCI_FIXUP_HEADER(PCI_VENDOR_ID_I
- DECLARE_PCI_FIXUP_HEADER(PCI_VENDOR_ID_INTEL, 0x65f9, quirk_intel_mc_errata);
- DECLARE_PCI_FIXUP_HEADER(PCI_VENDOR_ID_INTEL, 0x65fa, quirk_intel_mc_errata);
-+#endif /* !CONFIG_PCI_DISABLE_COMMON_QUIRKS */
-+
- /*
-  * Ivytown NTB BAR sizes are misreported by the hardware due to an erratum.
-  * To work around this, query the size it should be configured to by the
-@@ -3394,6 +3397,8 @@ static void quirk_intel_ntb(struct pci_d
- DECLARE_PCI_FIXUP_HEADER(PCI_VENDOR_ID_INTEL, 0x0e08, quirk_intel_ntb);
- DECLARE_PCI_FIXUP_HEADER(PCI_VENDOR_ID_INTEL, 0x0e0d, quirk_intel_ntb);
-+#ifndef CONFIG_PCI_DISABLE_COMMON_QUIRKS
-+
- /*
-  * Some BIOS implementations leave the Intel GPU interrupts enabled, even
-  * though no one is handling them (e.g., if the i915 driver is never
-@@ -3432,6 +3437,8 @@ DECLARE_PCI_FIXUP_FINAL(PCI_VENDOR_ID_IN
- DECLARE_PCI_FIXUP_FINAL(PCI_VENDOR_ID_INTEL, 0x010a, disable_igfx_irq);
- DECLARE_PCI_FIXUP_FINAL(PCI_VENDOR_ID_INTEL, 0x0152, disable_igfx_irq);
-+#endif /* !CONFIG_PCI_DISABLE_COMMON_QUIRKS */
-+
- /*
-  * PCI devices which are on Intel chips can skip the 10ms delay
-  * before entering D3 mode.
diff --git a/target/linux/generic/pending-5.15/811-pci_disable_usb_common_quirks.patch b/target/linux/generic/pending-5.15/811-pci_disable_usb_common_quirks.patch
deleted file mode 100644 (file)
index b498d9f..0000000
+++ /dev/null
@@ -1,115 +0,0 @@
-From: Felix Fietkau <[email protected]>
-Subject: debloat: disable common USB quirks
-
-Signed-off-by: Felix Fietkau <[email protected]>
----
- drivers/usb/host/pci-quirks.c | 16 ++++++++++++++++
- drivers/usb/host/pci-quirks.h | 18 +++++++++++++++++-
- include/linux/usb/hcd.h       |  7 +++++++
- 3 files changed, 40 insertions(+), 1 deletion(-)
-
---- a/drivers/usb/host/pci-quirks.c
-+++ b/drivers/usb/host/pci-quirks.c
-@@ -128,6 +128,8 @@ struct amd_chipset_type {
-       u8 rev;
- };
-+#ifndef CONFIG_PCI_DISABLE_COMMON_QUIRKS
-+
- static struct amd_chipset_info {
-       struct pci_dev  *nb_dev;
-       struct pci_dev  *smbus_dev;
-@@ -633,6 +635,10 @@ bool usb_amd_pt_check_port(struct device
- }
- EXPORT_SYMBOL_GPL(usb_amd_pt_check_port);
-+#endif /* CONFIG_PCI_DISABLE_COMMON_QUIRKS */
-+
-+#if IS_ENABLED(CONFIG_USB_UHCI_HCD)
-+
- /*
-  * Make sure the controller is completely inactive, unable to
-  * generate interrupts or do DMA.
-@@ -712,8 +718,17 @@ reset_needed:
-       uhci_reset_hc(pdev, base);
-       return 1;
- }
-+#else
-+int uhci_check_and_reset_hc(struct pci_dev *pdev, unsigned long base)
-+{
-+      return 0;
-+}
-+
-+#endif
- EXPORT_SYMBOL_GPL(uhci_check_and_reset_hc);
-+#ifndef CONFIG_PCI_DISABLE_COMMON_QUIRKS
-+
- static inline int io_type_enabled(struct pci_dev *pdev, unsigned int mask)
- {
-       u16 cmd;
-@@ -1285,3 +1300,4 @@ static void quirk_usb_early_handoff(stru
- }
- DECLARE_PCI_FIXUP_CLASS_FINAL(PCI_ANY_ID, PCI_ANY_ID,
-                       PCI_CLASS_SERIAL_USB, 8, quirk_usb_early_handoff);
-+#endif
---- a/drivers/usb/host/pci-quirks.h
-+++ b/drivers/usb/host/pci-quirks.h
-@@ -5,6 +5,9 @@
- #ifdef CONFIG_USB_PCI
- void uhci_reset_hc(struct pci_dev *pdev, unsigned long base);
- int uhci_check_and_reset_hc(struct pci_dev *pdev, unsigned long base);
-+#endif  /* CONFIG_USB_PCI */
-+
-+#if defined(CONFIG_USB_PCI) && !defined(CONFIG_PCI_DISABLE_COMMON_QUIRKS)
- int usb_hcd_amd_remote_wakeup_quirk(struct pci_dev *pdev);
- bool usb_amd_hang_symptom_quirk(void);
- bool usb_amd_prefetch_quirk(void);
-@@ -19,6 +22,18 @@ void sb800_prefetch(struct device *dev,
- bool usb_amd_pt_check_port(struct device *device, int port);
- #else
- struct pci_dev;
-+static inline int usb_amd_quirk_pll_check(void)
-+{
-+      return 0;
-+}
-+static inline bool usb_amd_hang_symptom_quirk(void)
-+{
-+      return false;
-+}
-+static inline bool usb_amd_prefetch_quirk(void)
-+{
-+      return false;
-+}
- static inline void usb_amd_quirk_pll_disable(void) {}
- static inline void usb_amd_quirk_pll_enable(void) {}
- static inline void usb_asmedia_modifyflowcontrol(struct pci_dev *pdev) {}
-@@ -29,6 +44,11 @@ static inline bool usb_amd_pt_check_port
- {
-       return false;
- }
-+static inline void usb_enable_intel_xhci_ports(struct pci_dev *xhci_pdev) {}
-+static inline bool usb_xhci_needs_pci_reset(struct pci_dev *pdev)
-+{
-+      return false;
-+}
- #endif  /* CONFIG_USB_PCI */
- #endif  /*  __LINUX_USB_PCI_QUIRKS_H  */
---- a/include/linux/usb/hcd.h
-+++ b/include/linux/usb/hcd.h
-@@ -498,7 +498,14 @@ extern int usb_hcd_pci_probe(struct pci_
- extern void usb_hcd_pci_remove(struct pci_dev *dev);
- extern void usb_hcd_pci_shutdown(struct pci_dev *dev);
-+#ifndef CONFIG_PCI_DISABLE_COMMON_QUIRKS
- extern int usb_hcd_amd_remote_wakeup_quirk(struct pci_dev *dev);
-+#else
-+static inline int usb_hcd_amd_remote_wakeup_quirk(struct pci_dev *dev)
-+{
-+      return 0;
-+}
-+#endif
- #ifdef CONFIG_PM
- extern const struct dev_pm_ops usb_hcd_pci_pm_ops;
diff --git a/target/linux/generic/pending-5.15/820-w1-gpio-fix-problem-with-platfom-data-in-w1-gpio.patch b/target/linux/generic/pending-5.15/820-w1-gpio-fix-problem-with-platfom-data-in-w1-gpio.patch
deleted file mode 100644 (file)
index 33eb34c..0000000
+++ /dev/null
@@ -1,26 +0,0 @@
-From d9c8bc8c1408f3e8529db6e4e04017b4c579c342 Mon Sep 17 00:00:00 2001
-From: Pawel Dembicki <[email protected]>
-Date: Sun, 18 Feb 2018 17:08:04 +0100
-Subject: [PATCH] w1: gpio: fix problem with platfom data in w1-gpio
-
-In devices, where fdt is used, is impossible to apply platform data
-without proper fdt node.
-
-This patch allow to use platform data in devices with fdt.
-
-Signed-off-by: Pawel Dembicki <[email protected]>
----
- drivers/w1/masters/w1-gpio.c | 7 +++----
- 1 file changed, 3 insertions(+), 4 deletions(-)
-
---- a/drivers/w1/masters/w1-gpio.c
-+++ b/drivers/w1/masters/w1-gpio.c
-@@ -76,7 +76,7 @@ static int w1_gpio_probe(struct platform
-       enum gpiod_flags gflags = GPIOD_OUT_LOW_OPEN_DRAIN;
-       int err;
--      if (of_have_populated_dt()) {
-+      if (of_have_populated_dt() && !dev_get_platdata(&pdev->dev)) {
-               pdata = devm_kzalloc(&pdev->dev, sizeof(*pdata), GFP_KERNEL);
-               if (!pdata)
-                       return -ENOMEM;
diff --git a/target/linux/generic/pending-5.15/834-ledtrig-libata.patch b/target/linux/generic/pending-5.15/834-ledtrig-libata.patch
deleted file mode 100644 (file)
index d61e28b..0000000
+++ /dev/null
@@ -1,149 +0,0 @@
-From: Daniel Golle <[email protected]>
-Subject: libata: add ledtrig support
-
-This adds a LED trigger for each ATA port indicating disk activity.
-
-As this is needed only on specific platforms (NAS SoCs and such),
-these platforms should define ARCH_WANTS_LIBATA_LEDS if there
-are boards with LED(s) intended to indicate ATA disk activity and
-need the OS to take care of that.
-In that way, if not selected, LED trigger support not will be
-included in libata-core and both, codepaths and structures remain
-untouched.
-
-Signed-off-by: Daniel Golle <[email protected]>
----
- drivers/ata/Kconfig       | 16 ++++++++++++++++
- drivers/ata/libata-core.c | 41 +++++++++++++++++++++++++++++++++++++++++
- include/linux/libata.h    |  9 +++++++++
- 3 files changed, 66 insertions(+)
-
---- a/drivers/ata/Kconfig
-+++ b/drivers/ata/Kconfig
-@@ -67,6 +67,22 @@ config ATA_FORCE
-         If unsure, say Y.
-+config ARCH_WANT_LIBATA_LEDS
-+      bool
-+
-+config ATA_LEDS
-+      bool "support ATA port LED triggers"
-+      depends on ARCH_WANT_LIBATA_LEDS
-+      select NEW_LEDS
-+      select LEDS_CLASS
-+      select LEDS_TRIGGERS
-+      default y
-+      help
-+        This option adds a LED trigger for each registered ATA port.
-+        It is used to drive disk activity leds connected via GPIO.
-+
-+        If unsure, say N.
-+
- config ATA_ACPI
-       bool "ATA ACPI Support"
-       depends on ACPI
---- a/drivers/ata/libata-core.c
-+++ b/drivers/ata/libata-core.c
-@@ -656,6 +656,19 @@ u64 ata_tf_read_block(const struct ata_t
-       return block;
- }
-+#ifdef CONFIG_ATA_LEDS
-+#define LIBATA_BLINK_DELAY 20 /* ms */
-+static inline void ata_led_act(struct ata_port *ap)
-+{
-+      unsigned long led_delay = LIBATA_BLINK_DELAY;
-+
-+      if (unlikely(!ap->ledtrig))
-+              return;
-+
-+      led_trigger_blink_oneshot(ap->ledtrig, &led_delay, &led_delay, 0);
-+}
-+#endif
-+
- /**
-  *    ata_build_rw_tf - Build ATA taskfile for given read/write request
-  *    @tf: Target ATA taskfile
-@@ -4580,6 +4593,9 @@ struct ata_queued_cmd *ata_qc_new_init(s
-               if (tag < 0)
-                       return NULL;
-       }
-+#ifdef CONFIG_ATA_LEDS
-+      ata_led_act(ap);
-+#endif
-       qc = __ata_qc_from_tag(ap, tag);
-       qc->tag = qc->hw_tag = tag;
-@@ -5358,6 +5374,9 @@ struct ata_port *ata_port_alloc(struct a
-       ap->stats.unhandled_irq = 1;
-       ap->stats.idle_irq = 1;
- #endif
-+#ifdef CONFIG_ATA_LEDS
-+      ap->ledtrig = kzalloc(sizeof(struct led_trigger), GFP_KERNEL);
-+#endif
-       ata_sff_port_init(ap);
-       return ap;
-@@ -5393,6 +5412,12 @@ static void ata_host_release(struct kref
-               kfree(ap->pmp_link);
-               kfree(ap->slave_link);
-+#ifdef CONFIG_ATA_LEDS
-+              if (ap->ledtrig) {
-+                      led_trigger_unregister(ap->ledtrig);
-+                      kfree(ap->ledtrig);
-+              };
-+#endif
-               kfree(ap);
-               host->ports[i] = NULL;
-       }
-@@ -5799,7 +5824,23 @@ int ata_host_register(struct ata_host *h
-               host->ports[i]->print_id = atomic_inc_return(&ata_print_id);
-               host->ports[i]->local_port_no = i + 1;
-       }
-+#ifdef CONFIG_ATA_LEDS
-+      for (i = 0; i < host->n_ports; i++) {
-+              if (unlikely(!host->ports[i]->ledtrig))
-+                      continue;
-+              snprintf(host->ports[i]->ledtrig_name,
-+                      sizeof(host->ports[i]->ledtrig_name), "ata%u",
-+                      host->ports[i]->print_id);
-+
-+              host->ports[i]->ledtrig->name = host->ports[i]->ledtrig_name;
-+
-+              if (led_trigger_register(host->ports[i]->ledtrig)) {
-+                      kfree(host->ports[i]->ledtrig);
-+                      host->ports[i]->ledtrig = NULL;
-+              }
-+      }
-+#endif
-       /* Create associated sysfs transport objects  */
-       for (i = 0; i < host->n_ports; i++) {
-               rc = ata_tport_add(host->dev,host->ports[i]);
---- a/include/linux/libata.h
-+++ b/include/linux/libata.h
-@@ -23,6 +23,9 @@
- #include <linux/cdrom.h>
- #include <linux/sched.h>
- #include <linux/async.h>
-+#ifdef CONFIG_ATA_LEDS
-+#include <linux/leds.h>
-+#endif
- /*
-  * Define if arch has non-standard setup.  This is a _PCI_ standard
-@@ -898,6 +901,12 @@ struct ata_port {
- #ifdef CONFIG_ATA_ACPI
-       struct ata_acpi_gtm     __acpi_init_gtm; /* use ata_acpi_init_gtm() */
- #endif
-+
-+#ifdef CONFIG_ATA_LEDS
-+      struct led_trigger      *ledtrig;
-+      char                    ledtrig_name[8];
-+#endif
-+
-       /* owned by EH */
-       u8                      sector_buf[ATA_SECT_SIZE] ____cacheline_aligned;
- };
diff --git a/target/linux/generic/pending-5.15/840-hwrng-bcm2835-set-quality-to-1000.patch b/target/linux/generic/pending-5.15/840-hwrng-bcm2835-set-quality-to-1000.patch
deleted file mode 100644 (file)
index 5ca8933..0000000
+++ /dev/null
@@ -1,26 +0,0 @@
-From d6988cf1d16faac56899918bb2b1be8d85155e3f Mon Sep 17 00:00:00 2001
-From: =?UTF-8?q?=C3=81lvaro=20Fern=C3=A1ndez=20Rojas?= <[email protected]>
-Date: Sat, 20 Feb 2021 18:36:38 +0100
-Subject: [PATCH] hwrng: bcm2835: set quality to 1000
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-This allows devices without a high precission timer to reduce boot from >100s
-to <30s.
-
-Signed-off-by: Álvaro Fernández Rojas <[email protected]>
----
- drivers/char/hw_random/bcm2835-rng.c | 1 +
- 1 file changed, 1 insertion(+)
-
---- a/drivers/char/hw_random/bcm2835-rng.c
-+++ b/drivers/char/hw_random/bcm2835-rng.c
-@@ -170,6 +170,7 @@ static int bcm2835_rng_probe(struct plat
-       priv->rng.init = bcm2835_rng_init;
-       priv->rng.read = bcm2835_rng_read;
-       priv->rng.cleanup = bcm2835_rng_cleanup;
-+      priv->rng.quality = 1000;
-       if (dev_of_node(dev)) {
-               rng_id = of_match_node(bcm2835_rng_of_match, dev->of_node);
diff --git a/target/linux/generic/pending-5.15/850-0023-PCI-aardvark-Make-main-irq_chip-structure-a-static-d.patch b/target/linux/generic/pending-5.15/850-0023-PCI-aardvark-Make-main-irq_chip-structure-a-static-d.patch
deleted file mode 100644 (file)
index e180a38..0000000
+++ /dev/null
@@ -1,102 +0,0 @@
-From 663b9f99bb35dbc0c7b685f71ee3668a60d31320 Mon Sep 17 00:00:00 2001
-From: =?UTF-8?q?Marek=20Beh=C3=BAn?= <[email protected]>
-Date: Mon, 10 Jan 2022 02:02:00 +0100
-Subject: [PATCH] PCI: aardvark: Make main irq_chip structure a static driver
- structure
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-Marc Zyngier says [1] that we should use struct irq_chip as a global
-static struct in the driver. Even though the structure currently
-contains a dynamic member (parent_device), Marc says [2] that he plans
-to kill it and make the structure completely static.
-
-We have already converted others irq_chip structures in this driver in
-this way, but we omitted this one because the .name member is
-dynamically created from device's name, and the name is displayed in
-sysfs, so changing it would break sysfs ABI.
-
-The rationale for changing the name (to "advk-INT") in spite of sysfs
-ABI, and thus allowing to convert to a static structure, is that after
-the other changes we made in this series, the IRQ chip is basically
-something different: it no logner generates ERR and PME interrupts (they
-are generated by emulated bridge's rp_irq_chip).
-
-[1] https://lore.kernel.org/linux-pci/[email protected]/
-[2] https://lore.kernel.org/linux-pci/[email protected]/
-
-Signed-off-by: Marek Behún <[email protected]>
----
- drivers/pci/controller/pci-aardvark.c | 25 +++++++------------------
- 1 file changed, 7 insertions(+), 18 deletions(-)
-
---- a/drivers/pci/controller/pci-aardvark.c
-+++ b/drivers/pci/controller/pci-aardvark.c
-@@ -275,7 +275,6 @@ struct advk_pcie {
-       u8 wins_count;
-       struct irq_domain *rp_irq_domain;
-       struct irq_domain *irq_domain;
--      struct irq_chip irq_chip;
-       raw_spinlock_t irq_lock;
-       struct irq_domain *msi_domain;
-       struct irq_domain *msi_inner_domain;
-@@ -1345,14 +1344,19 @@ static void advk_pcie_irq_unmask(struct
-       raw_spin_unlock_irqrestore(&pcie->irq_lock, flags);
- }
-+static struct irq_chip advk_irq_chip = {
-+      .name           = "advk-INT",
-+      .irq_mask       = advk_pcie_irq_mask,
-+      .irq_unmask     = advk_pcie_irq_unmask,
-+};
-+
- static int advk_pcie_irq_map(struct irq_domain *h,
-                            unsigned int virq, irq_hw_number_t hwirq)
- {
-       struct advk_pcie *pcie = h->host_data;
-       irq_set_status_flags(virq, IRQ_LEVEL);
--      irq_set_chip_and_handler(virq, &pcie->irq_chip,
--                               handle_level_irq);
-+      irq_set_chip_and_handler(virq, &advk_irq_chip, handle_level_irq);
-       irq_set_chip_data(virq, pcie);
-       return 0;
-@@ -1411,7 +1415,6 @@ static int advk_pcie_init_irq_domain(str
-       struct device *dev = &pcie->pdev->dev;
-       struct device_node *node = dev->of_node;
-       struct device_node *pcie_intc_node;
--      struct irq_chip *irq_chip;
-       int ret = 0;
-       raw_spin_lock_init(&pcie->irq_lock);
-@@ -1422,28 +1425,14 @@ static int advk_pcie_init_irq_domain(str
-               return -ENODEV;
-       }
--      irq_chip = &pcie->irq_chip;
--
--      irq_chip->name = devm_kasprintf(dev, GFP_KERNEL, "%s-irq",
--                                      dev_name(dev));
--      if (!irq_chip->name) {
--              ret = -ENOMEM;
--              goto out_put_node;
--      }
--
--      irq_chip->irq_mask = advk_pcie_irq_mask;
--      irq_chip->irq_unmask = advk_pcie_irq_unmask;
--
-       pcie->irq_domain =
-               irq_domain_add_linear(pcie_intc_node, PCI_NUM_INTX,
-                                     &advk_pcie_irq_domain_ops, pcie);
-       if (!pcie->irq_domain) {
-               dev_err(dev, "Failed to get a INTx IRQ domain\n");
-               ret = -ENOMEM;
--              goto out_put_node;
-       }
--out_put_node:
-       of_node_put(pcie_intc_node);
-       return ret;
- }
diff --git a/target/linux/generic/pending-5.15/850-dt-bindings-clk-add-BCM63268-timer-clock-definitions.patch b/target/linux/generic/pending-5.15/850-dt-bindings-clk-add-BCM63268-timer-clock-definitions.patch
deleted file mode 100644 (file)
index cc6f1e0..0000000
+++ /dev/null
@@ -1,114 +0,0 @@
-From patchwork Wed Mar 22 17:15:12 2023
-Content-Type: text/plain; charset="utf-8"
-MIME-Version: 1.0
-Content-Transfer-Encoding: 8bit
-X-Patchwork-Submitter: =?utf-8?q?=C3=81lvaro_Fern=C3=A1ndez_Rojas?=
-X-Patchwork-Id: 13184389
-Return-Path: <[email protected]>
-X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on
-       aws-us-west-2-korg-lkml-1.web.codeaurora.org
-Received: from vger.kernel.org (vger.kernel.org [23.128.96.18])
-       by smtp.lore.kernel.org (Postfix) with ESMTP id 73F2DC6FD1C
-       for <[email protected]>; Wed, 22 Mar 2023 17:15:59 +0000 (UTC)
-Received: ([email protected]) by vger.kernel.org via listexpand
-        id S231363AbjCVRP5 (ORCPT <rfc822;[email protected]>);
-        Wed, 22 Mar 2023 13:15:57 -0400
-Received: from lindbergh.monkeyblade.net ([23.128.96.19]:58824 "EHLO
-        lindbergh.monkeyblade.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org
-        with ESMTP id S231408AbjCVRPy (ORCPT
-        <rfc822;[email protected]>); Wed, 22 Mar 2023 13:15:54 -0400
-Received: from mail-wm1-x32d.google.com (mail-wm1-x32d.google.com
- [IPv6:2a00:1450:4864:20::32d])
-        by lindbergh.monkeyblade.net (Postfix) with ESMTPS id 70E4C64B28;
-        Wed, 22 Mar 2023 10:15:24 -0700 (PDT)
-Received: by mail-wm1-x32d.google.com with SMTP id n19so1740892wms.0;
-        Wed, 22 Mar 2023 10:15:24 -0700 (PDT)
-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed;
-        d=gmail.com; s=20210112; t=1679505322;
-        h=content-transfer-encoding:mime-version:references:in-reply-to
-         :message-id:date:subject:cc:to:from:from:to:cc:subject:date
-         :message-id:reply-to;
-        bh=dEknM98Izmc8d/crPsoJ+ejZxfl78958Ei6SPYhYDHs=;
-        b=LTOQ75W3s5nYo+nEfiJAKqytSopONB4jCtU3zRygzPMasugVOrYFMsUR+WrpsAjuRT
-         v4HgWpJxEsIWeRXrUN9W21mFXhGgJLJXSxRnrio0CsZZBNMdkebbNOphgKXIWAdm+2iM
-         PzqAdGm5t38wT2mmm6V/9hCy90+12raHM82tNFdhhiezfg2cukVOKP3j/TeOVCwas0gQ
-         iFc+CuZB6y73zYXvMUMUpTsqI5vev4xJsSMHIQJVmUxJAwqhOBhN9JCRo7Ao+wayjn2d
-         Fxo6AV3A8v68nVfoQ0K0I+eWXG48nMCX45iWh/lVvVTOFcR99kn4va7NY1oVnPsh+WQz
-         WcLA==
-X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed;
-        d=1e100.net; s=20210112; t=1679505322;
-        h=content-transfer-encoding:mime-version:references:in-reply-to
-         :message-id:date:subject:cc:to:from:x-gm-message-state:from:to:cc
-         :subject:date:message-id:reply-to;
-        bh=dEknM98Izmc8d/crPsoJ+ejZxfl78958Ei6SPYhYDHs=;
-        b=wv2NSR1B5RnsdoEE7mgJSHAfSs1JHZbQ1HPMldyaGWAk1dcucqh/uDzM3Flz+ADRi1
-         19NoaB2Ur7QaWZejbuplnIOK/nte3PnmqJ9ZNw8HejmuS4eU8mB1V1aJUSKSPGsfUi4a
-         LYe3HSw87l0jrAC7ptdKvdUtzBoIkX0CeFvfguTQQkDhUTyAFIG144hY6uPXY9Mga96b
-         gnNe2dLCzHQLbEJpaDaavT7FEEcLDxaq7jNcR2xqEEZaIwfcew+Q05t4xL/3i8GAj9Ru
-         6ivQjIbBKfYQF88o7KnOW9o1wjrGsk+Nd4Iy0OLZix3JQasCJGrKV7ib5awI9J39upYV
-         fa4A==
-X-Gm-Message-State: AO0yUKWw75I1M5Vjrd4vXq4GTruQu0H84pycgyi2CT3bczTYRJpWmEWg
-        +bHDhvp1n5IWW85GI9vKWpbclB13a/S0RQ==
-X-Google-Smtp-Source: 
- AK7set9T/2oJsVetUb2L4mPEWu8YqDrnK8EzHK5bJf1ABIa1Et8f7BFJ7AA3j14ITZuf8cH0HqlRtg==
-X-Received: by 2002:a05:600c:2304:b0:3ed:2949:985b with SMTP id
- 4-20020a05600c230400b003ed2949985bmr206833wmo.23.1679505322457;
-        Wed, 22 Mar 2023 10:15:22 -0700 (PDT)
-Received: from atlantis.lan (255.red-79-146-124.dynamicip.rima-tde.net.
- [79.146.124.255])
-        by smtp.gmail.com with ESMTPSA id
- v10-20020a05600c470a00b003ee11ac2288sm8414333wmo.21.2023.03.22.10.15.21
-        (version=TLS1_3 cipher=TLS_AES_256_GCM_SHA384 bits=256/256);
-        Wed, 22 Mar 2023 10:15:22 -0700 (PDT)
-From: =?utf-8?q?=C3=81lvaro_Fern=C3=A1ndez_Rojas?=  <[email protected]>
-Cc: =?utf-8?q?=C3=81lvaro_Fern=C3=A1ndez_Rojas?=  <[email protected]>,
- Rob Herring <[email protected]>
-Subject: [PATCH v4 1/4] dt-bindings: clk: add BCM63268 timer clock definitions
-Date: Wed, 22 Mar 2023 18:15:12 +0100
-Message-Id: <[email protected]>
-X-Mailer: git-send-email 2.30.2
-In-Reply-To: <[email protected]>
-References: <[email protected]>
-MIME-Version: 1.0
-Precedence: bulk
-List-ID: <linux-clk.vger.kernel.org>
-X-Mailing-List: [email protected]
-
-Add missing timer clock definitions for BCM63268.
-
-Signed-off-by: Álvaro Fernández Rojas <[email protected]>
-Acked-by: Rob Herring <[email protected]>
----
- v4: no changes
- v3: no changes
- v2: change commit title, as suggested by Stephen Boyd
-
- include/dt-bindings/clock/bcm63268-clock.h | 13 +++++++++++++
- 1 file changed, 13 insertions(+)
-
---- a/include/dt-bindings/clock/bcm63268-clock.h
-+++ b/include/dt-bindings/clock/bcm63268-clock.h
-@@ -27,4 +27,17 @@
- #define BCM63268_CLK_TBUS     27
- #define BCM63268_CLK_ROBOSW250        31
-+#define BCM63268_TCLK_EPHY1           0
-+#define BCM63268_TCLK_EPHY2           1
-+#define BCM63268_TCLK_EPHY3           2
-+#define BCM63268_TCLK_GPHY1           3
-+#define BCM63268_TCLK_DSL             4
-+#define BCM63268_TCLK_WAKEON_EPHY     6
-+#define BCM63268_TCLK_WAKEON_DSL      7
-+#define BCM63268_TCLK_FAP1            11
-+#define BCM63268_TCLK_FAP2            15
-+#define BCM63268_TCLK_UTO_50          16
-+#define BCM63268_TCLK_UTO_EXTIN               17
-+#define BCM63268_TCLK_USB_REF         18
-+
- #endif /* __DT_BINDINGS_CLOCK_BCM63268_H */
diff --git a/target/linux/generic/pending-5.15/851-dt-bindings-reset-add-BCM63268-timer-reset-definitions.patch b/target/linux/generic/pending-5.15/851-dt-bindings-reset-add-BCM63268-timer-reset-definitions.patch
deleted file mode 100644 (file)
index 5f1be10..0000000
+++ /dev/null
@@ -1,107 +0,0 @@
-From patchwork Wed Mar 22 17:15:13 2023
-Content-Type: text/plain; charset="utf-8"
-MIME-Version: 1.0
-Content-Transfer-Encoding: 8bit
-X-Patchwork-Submitter: =?utf-8?q?=C3=81lvaro_Fern=C3=A1ndez_Rojas?=
-X-Patchwork-Id: 13184390
-Return-Path: <[email protected]>
-X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on
-       aws-us-west-2-korg-lkml-1.web.codeaurora.org
-Received: from vger.kernel.org (vger.kernel.org [23.128.96.18])
-       by smtp.lore.kernel.org (Postfix) with ESMTP id D0B1AC6FD1C
-       for <[email protected]>; Wed, 22 Mar 2023 17:16:08 +0000 (UTC)
-Received: ([email protected]) by vger.kernel.org via listexpand
-        id S231472AbjCVRQI (ORCPT <rfc822;[email protected]>);
-        Wed, 22 Mar 2023 13:16:08 -0400
-Received: from lindbergh.monkeyblade.net ([23.128.96.19]:58934 "EHLO
-        lindbergh.monkeyblade.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org
-        with ESMTP id S231435AbjCVRP5 (ORCPT
-        <rfc822;[email protected]>); Wed, 22 Mar 2023 13:15:57 -0400
-Received: from mail-wm1-x329.google.com (mail-wm1-x329.google.com
- [IPv6:2a00:1450:4864:20::329])
-        by lindbergh.monkeyblade.net (Postfix) with ESMTPS id 9655064863;
-        Wed, 22 Mar 2023 10:15:25 -0700 (PDT)
-Received: by mail-wm1-x329.google.com with SMTP id
- v4-20020a05600c470400b003ee4f06428fso2424553wmo.4;
-        Wed, 22 Mar 2023 10:15:25 -0700 (PDT)
-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed;
-        d=gmail.com; s=20210112; t=1679505324;
-        h=content-transfer-encoding:mime-version:references:in-reply-to
-         :message-id:date:subject:cc:to:from:from:to:cc:subject:date
-         :message-id:reply-to;
-        bh=C7ykhArT1dO7P8wtmI92eo4c7KtPZI9w182/5+cB3T0=;
-        b=WRZRU2SM9n1LfUj4SgTPfQczADC2pfvoIrOsNpBLTym2eOfmkTetb/WbGSla5kw2Wb
-         SH5MIC2fFeScJg6T5FFAUOOLmRVW9xvl8Q3T3NKb3z/9wvPHO767nrdIbffRWMJFs7gW
-         wT/kuTpn8GYdfY0sZ/dMTkq41DVusEkxfX6GxtG85O98ZP8xMHQog8aPs9fRfUvI5ZKB
-         eGYcRz/Wn1cHhjey9jtWzQEEmZ/BT3b0HQTF9Tl88oofhiEgbyjFXr91+vRsLbsJpGXH
-         /1FjjaLG5DnonKubV9rmbuCU8KzwH331gi2KuRjvLD2V+OMewqSa5i+GvgVv8x2zC8y+
-         /mLQ==
-X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed;
-        d=1e100.net; s=20210112; t=1679505324;
-        h=content-transfer-encoding:mime-version:references:in-reply-to
-         :message-id:date:subject:cc:to:from:x-gm-message-state:from:to:cc
-         :subject:date:message-id:reply-to;
-        bh=C7ykhArT1dO7P8wtmI92eo4c7KtPZI9w182/5+cB3T0=;
-        b=bhd0fNh0jDOMlGSC4F+p5igV8AUlGEPj2cXUwgdgqRfSSuUy9z+Li8cT0MbY/aWH5Z
-         qInRVA+R1cWV3ubrDyKag6oEc0LDU234bnMFcP9b7MRlrM8Dpit9TFSyqJU4sDUWNDs5
-         KOe2k/SNIdat6munC9VOuEBDO0eB/UDMN+repKwXNdHChp/Toq9qMvW4Uy8uHxosbQlD
-         8P88GbKFjynb1E8I8croGjfub7+y8PPsWB0xNUcafIv6xs3MnVOP1Mk4KwBCbqS509la
-         mfjsriXtIybO8XFqtn100ungjvbFWdogEplLdSPVdgAqdfF5J8gHxAoApoeYejYkL5/R
-         kOhQ==
-X-Gm-Message-State: AO0yUKWdzr3dMmjKhD8tF+ec4Dfdq9VGZ/WCU4d85npKQvxSwhNPZZ1J
-        5WYRIqivh0suFC1OqEidwenpiJYvXedYjw==
-X-Google-Smtp-Source: 
- AK7set87ew2/mKWeShXTTW/YBbBJNR2zeGFV0CfuqLXhiJEU6tqFuyKcW+vFEoKHIbNUS8wRy1SzLA==
-X-Received: by 2002:a05:600c:290:b0:3ee:6d88:774a with SMTP id
- 16-20020a05600c029000b003ee6d88774amr160734wmk.14.1679505323514;
-        Wed, 22 Mar 2023 10:15:23 -0700 (PDT)
-Received: from atlantis.lan (255.red-79-146-124.dynamicip.rima-tde.net.
- [79.146.124.255])
-        by smtp.gmail.com with ESMTPSA id
- v10-20020a05600c470a00b003ee11ac2288sm8414333wmo.21.2023.03.22.10.15.22
-        (version=TLS1_3 cipher=TLS_AES_256_GCM_SHA384 bits=256/256);
-        Wed, 22 Mar 2023 10:15:23 -0700 (PDT)
-From: =?utf-8?q?=C3=81lvaro_Fern=C3=A1ndez_Rojas?=  <[email protected]>
-Cc: =?utf-8?q?=C3=81lvaro_Fern=C3=A1ndez_Rojas?=  <[email protected]>,
- Rob Herring <[email protected]>
-Subject: [PATCH v4 2/4] dt-bindings: reset: add BCM63268 timer reset
- definitions
-Date: Wed, 22 Mar 2023 18:15:13 +0100
-Message-Id: <[email protected]>
-X-Mailer: git-send-email 2.30.2
-In-Reply-To: <[email protected]>
-References: <[email protected]>
-MIME-Version: 1.0
-Precedence: bulk
-List-ID: <linux-clk.vger.kernel.org>
-X-Mailing-List: [email protected]
-
-Add missing timer reset definitions for BCM63268.
-
-Signed-off-by: Álvaro Fernández Rojas <[email protected]>
-Acked-by: Rob Herring <[email protected]>
----
- v4: no changes
- v3: no changes
- v2: change commit title, as suggested by Stephen Boyd
-
- include/dt-bindings/reset/bcm63268-reset.h | 4 ++++
- 1 file changed, 4 insertions(+)
-
---- a/include/dt-bindings/reset/bcm63268-reset.h
-+++ b/include/dt-bindings/reset/bcm63268-reset.h
-@@ -23,4 +23,8 @@
- #define BCM63268_RST_PCIE_HARD        17
- #define BCM63268_RST_GPHY     18
-+#define BCM63268_TRST_SW      29
-+#define BCM63268_TRST_HW      30
-+#define BCM63268_TRST_POR     31
-+
- #endif /* __DT_BINDINGS_RESET_BCM63268_H */
diff --git a/target/linux/generic/pending-5.15/852-clk-bcm-Add-BCM63268-timer-clock-and-reset-driver.patch b/target/linux/generic/pending-5.15/852-clk-bcm-Add-BCM63268-timer-clock-and-reset-driver.patch
deleted file mode 100644 (file)
index 7e500cd..0000000
+++ /dev/null
@@ -1,345 +0,0 @@
-From patchwork Wed Mar 22 17:15:15 2023
-Content-Type: text/plain; charset="utf-8"
-MIME-Version: 1.0
-Content-Transfer-Encoding: 8bit
-X-Patchwork-Submitter: =?utf-8?q?=C3=81lvaro_Fern=C3=A1ndez_Rojas?=
-X-Patchwork-Id: 13184392
-Return-Path: <[email protected]>
-X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on
-       aws-us-west-2-korg-lkml-1.web.codeaurora.org
-Received: from vger.kernel.org (vger.kernel.org [23.128.96.18])
-       by smtp.lore.kernel.org (Postfix) with ESMTP id 199D9C76196
-       for <[email protected]>; Wed, 22 Mar 2023 17:16:11 +0000 (UTC)
-Received: ([email protected]) by vger.kernel.org via listexpand
-        id S231512AbjCVRQJ (ORCPT <rfc822;[email protected]>);
-        Wed, 22 Mar 2023 13:16:09 -0400
-Received: from lindbergh.monkeyblade.net ([23.128.96.19]:58942 "EHLO
-        lindbergh.monkeyblade.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org
-        with ESMTP id S231442AbjCVRP5 (ORCPT
-        <rfc822;[email protected]>); Wed, 22 Mar 2023 13:15:57 -0400
-Received: from mail-wm1-x32c.google.com (mail-wm1-x32c.google.com
- [IPv6:2a00:1450:4864:20::32c])
-        by lindbergh.monkeyblade.net (Postfix) with ESMTPS id 1DDB36487D;
-        Wed, 22 Mar 2023 10:15:27 -0700 (PDT)
-Received: by mail-wm1-x32c.google.com with SMTP id
- i5-20020a05600c354500b003edd24054e0so6717370wmq.4;
-        Wed, 22 Mar 2023 10:15:27 -0700 (PDT)
-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed;
-        d=gmail.com; s=20210112; t=1679505325;
-        h=content-transfer-encoding:mime-version:references:in-reply-to
-         :message-id:date:subject:cc:to:from:from:to:cc:subject:date
-         :message-id:reply-to;
-        bh=rkv/eZYA1ncHp5FnV2ZWc3hgYnAx28S86QA9vmcXFCY=;
-        b=Y1mva2Bt3sUbKxLgEUS331CJbGxUc4z8kTQW8qiHWGhYlFKtm+d5z4sT40E5BeZAnU
-         zmTbCI7jbroe9NYBxGUmSli6LNVDPjND80ChbhWTqbqMQTmeQFWut9KmeBWK6Oze2lC/
-         XMSOorUzowjcU2xtHNrzoq2KH2pstW573lsB8WnzFVfhMaRkE9DfRr6WNyA7zC8DyxM5
-         ezxlCQtCmgPfCqlyksbIDKrgrRf3GiUR0yUd6xRU+MssyvH1FkYGDCerPctDto6lGHBz
-         8Y15jT3l6OnQMT6dkekgpPF5/XrSUY93u9g0B4U8+0dhNj+K7vmDen+jqdess+tpLnq/
-         gFrA==
-X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed;
-        d=1e100.net; s=20210112; t=1679505325;
-        h=content-transfer-encoding:mime-version:references:in-reply-to
-         :message-id:date:subject:cc:to:from:x-gm-message-state:from:to:cc
-         :subject:date:message-id:reply-to;
-        bh=rkv/eZYA1ncHp5FnV2ZWc3hgYnAx28S86QA9vmcXFCY=;
-        b=Ym4+u8bbTQGNkewUBrLf+89vE0EFJBQp2f1crwUxZFboKTROF9ltZonY1CGepo7b0B
-         fkx3TbWQy5X65g3ScuieqtClCI8WanPeNBJ48+JipJYO3ODVNBxnVaTuW/0FOIcahfqe
-         sG5GvggHhzRz+Yeybsbnupmzxnw8Ez0BpMl3p7zcjHL7BGZDdOOX2Zbw3zfyYa5sg2nX
-         UXYJT36zy2h39gxUsy9QkhQ76CG3w6omniohZpYidpojpiDjbOy0nKFky4kUe+YyA1fF
-         4IBhjAm6mH+uh6wHSG1qj+NAXHs0xDDJps16PbJwAgL7Qt9K5WW+R/UAYPmHFgaRIHOw
-         /seA==
-X-Gm-Message-State: AO0yUKXRtoYO8Nfus6Ca8lhM39P1Xn6TGkhatEfoISd1YNOkTJJN2hW+
-        xRphLgxlzNfCLcVPlpGK9dk=
-X-Google-Smtp-Source: 
- AK7set9VnMEykugk8ZYnkXuqK41bX1dzlvKsAXHEjr8i2NZBld0buKhQLcGYEcwxnBgVTtC7eRGfXw==
-X-Received: by 2002:a1c:7c0b:0:b0:3e2:1dac:b071 with SMTP id
- x11-20020a1c7c0b000000b003e21dacb071mr178053wmc.13.1679505325582;
-        Wed, 22 Mar 2023 10:15:25 -0700 (PDT)
-Received: from atlantis.lan (255.red-79-146-124.dynamicip.rima-tde.net.
- [79.146.124.255])
-        by smtp.gmail.com with ESMTPSA id
- v10-20020a05600c470a00b003ee11ac2288sm8414333wmo.21.2023.03.22.10.15.24
-        (version=TLS1_3 cipher=TLS_AES_256_GCM_SHA384 bits=256/256);
-        Wed, 22 Mar 2023 10:15:25 -0700 (PDT)
-From: =?utf-8?q?=C3=81lvaro_Fern=C3=A1ndez_Rojas?=  <[email protected]>
-Cc: =?utf-8?q?=C3=81lvaro_Fern=C3=A1ndez_Rojas?=  <[email protected]>
-Subject: [PATCH v4 4/4] clk: bcm: Add BCM63268 timer clock and reset driver
-Date: Wed, 22 Mar 2023 18:15:15 +0100
-Message-Id: <[email protected]>
-X-Mailer: git-send-email 2.30.2
-In-Reply-To: <[email protected]>
-References: <[email protected]>
-MIME-Version: 1.0
-Precedence: bulk
-List-ID: <linux-clk.vger.kernel.org>
-X-Mailing-List: [email protected]
-
-Add driver for BCM63268 timer clock and reset controller.
-
-Signed-off-by: Álvaro Fernández Rojas <[email protected]>
----
- v4: add changes suggested by Stephen Boyd:
-  - Usage of of_device_get_match_data() isn't needed.
-  - Use devm_clk_hw_register_gate().
-  - Drop clk_hw_unregister_gate().
- v3: add missing <linux/io.h> include to fix build warning
- v2: add changes suggested by Stephen Boyd
-
- drivers/clk/bcm/Kconfig              |   9 ++
- drivers/clk/bcm/Makefile             |   1 +
- drivers/clk/bcm/clk-bcm63268-timer.c | 215 +++++++++++++++++++++++++++
- 3 files changed, 225 insertions(+)
- create mode 100644 drivers/clk/bcm/clk-bcm63268-timer.c
-
---- a/drivers/clk/bcm/Kconfig
-+++ b/drivers/clk/bcm/Kconfig
-@@ -37,6 +37,15 @@ config CLK_BCM_63XX_GATE
-         Enable common clock framework support for Broadcom BCM63xx DSL SoCs
-         based on the MIPS architecture
-+config CLK_BCM63268_TIMER
-+      bool "Broadcom BCM63268 timer clock and reset support"
-+      depends on BMIPS_GENERIC || COMPILE_TEST
-+      default BMIPS_GENERIC
-+      select RESET_CONTROLLER
-+      help
-+        Enable timer clock and reset support for Broadcom BCM63268 DSL SoCs
-+        based on the MIPS architecture.
-+
- config CLK_BCM_KONA
-       bool "Broadcom Kona CCU clock support"
-       depends on ARCH_BCM_MOBILE || COMPILE_TEST
---- a/drivers/clk/bcm/Makefile
-+++ b/drivers/clk/bcm/Makefile
-@@ -1,6 +1,7 @@
- # SPDX-License-Identifier: GPL-2.0
- obj-$(CONFIG_CLK_BCM_63XX)    += clk-bcm63xx.o
- obj-$(CONFIG_CLK_BCM_63XX_GATE)       += clk-bcm63xx-gate.o
-+obj-$(CONFIG_CLK_BCM63268_TIMER) += clk-bcm63268-timer.o
- obj-$(CONFIG_CLK_BCM_KONA)    += clk-kona.o
- obj-$(CONFIG_CLK_BCM_KONA)    += clk-kona-setup.o
- obj-$(CONFIG_CLK_BCM_KONA)    += clk-bcm281xx.o
---- /dev/null
-+++ b/drivers/clk/bcm/clk-bcm63268-timer.c
-@@ -0,0 +1,215 @@
-+// SPDX-License-Identifier: GPL-2.0
-+/*
-+ * BCM63268 Timer Clock and Reset Controller Driver
-+ *
-+ * Copyright (C) 2023 Álvaro Fernández Rojas <[email protected]>
-+ */
-+
-+#include <linux/clk-provider.h>
-+#include <linux/delay.h>
-+#include <linux/io.h>
-+#include <linux/of.h>
-+#include <linux/of_device.h>
-+#include <linux/platform_device.h>
-+#include <linux/reset-controller.h>
-+
-+#include <dt-bindings/clock/bcm63268-clock.h>
-+
-+#define BCM63268_TIMER_RESET_SLEEP_MIN_US     10000
-+#define BCM63268_TIMER_RESET_SLEEP_MAX_US     20000
-+
-+struct bcm63268_tclkrst_hw {
-+      void __iomem *regs;
-+      spinlock_t lock;
-+
-+      struct reset_controller_dev rcdev;
-+      struct clk_hw_onecell_data data;
-+};
-+
-+struct bcm63268_tclk_table_entry {
-+      const char * const name;
-+      u8 bit;
-+};
-+
-+static const struct bcm63268_tclk_table_entry bcm63268_timer_clocks[] = {
-+      {
-+              .name = "ephy1",
-+              .bit = BCM63268_TCLK_EPHY1,
-+      }, {
-+              .name = "ephy2",
-+              .bit = BCM63268_TCLK_EPHY2,
-+      }, {
-+              .name = "ephy3",
-+              .bit = BCM63268_TCLK_EPHY3,
-+      }, {
-+              .name = "gphy1",
-+              .bit = BCM63268_TCLK_GPHY1,
-+      }, {
-+              .name = "dsl",
-+              .bit = BCM63268_TCLK_DSL,
-+      }, {
-+              .name = "wakeon_ephy",
-+              .bit = BCM63268_TCLK_WAKEON_EPHY,
-+      }, {
-+              .name = "wakeon_dsl",
-+              .bit = BCM63268_TCLK_WAKEON_DSL,
-+      }, {
-+              .name = "fap1_pll",
-+              .bit = BCM63268_TCLK_FAP1,
-+      }, {
-+              .name = "fap2_pll",
-+              .bit = BCM63268_TCLK_FAP2,
-+      }, {
-+              .name = "uto_50",
-+              .bit = BCM63268_TCLK_UTO_50,
-+      }, {
-+              .name = "uto_extin",
-+              .bit = BCM63268_TCLK_UTO_EXTIN,
-+      }, {
-+              .name = "usb_ref",
-+              .bit = BCM63268_TCLK_USB_REF,
-+      }, {
-+              /* sentinel */
-+      }
-+};
-+
-+static inline struct bcm63268_tclkrst_hw *
-+to_bcm63268_timer_reset(struct reset_controller_dev *rcdev)
-+{
-+      return container_of(rcdev, struct bcm63268_tclkrst_hw, rcdev);
-+}
-+
-+static int bcm63268_timer_reset_update(struct reset_controller_dev *rcdev,
-+                              unsigned long id, bool assert)
-+{
-+      struct bcm63268_tclkrst_hw *reset = to_bcm63268_timer_reset(rcdev);
-+      unsigned long flags;
-+      uint32_t val;
-+
-+      spin_lock_irqsave(&reset->lock, flags);
-+      val = __raw_readl(reset->regs);
-+      if (assert)
-+              val &= ~BIT(id);
-+      else
-+              val |= BIT(id);
-+      __raw_writel(val, reset->regs);
-+      spin_unlock_irqrestore(&reset->lock, flags);
-+
-+      return 0;
-+}
-+
-+static int bcm63268_timer_reset_assert(struct reset_controller_dev *rcdev,
-+                              unsigned long id)
-+{
-+      return bcm63268_timer_reset_update(rcdev, id, true);
-+}
-+
-+static int bcm63268_timer_reset_deassert(struct reset_controller_dev *rcdev,
-+                                unsigned long id)
-+{
-+      return bcm63268_timer_reset_update(rcdev, id, false);
-+}
-+
-+static int bcm63268_timer_reset_reset(struct reset_controller_dev *rcdev,
-+                             unsigned long id)
-+{
-+      bcm63268_timer_reset_update(rcdev, id, true);
-+      usleep_range(BCM63268_TIMER_RESET_SLEEP_MIN_US,
-+                   BCM63268_TIMER_RESET_SLEEP_MAX_US);
-+
-+      bcm63268_timer_reset_update(rcdev, id, false);
-+      /*
-+       * Ensure component is taken out reset state by sleeping also after
-+       * deasserting the reset. Otherwise, the component may not be ready
-+       * for operation.
-+       */
-+      usleep_range(BCM63268_TIMER_RESET_SLEEP_MIN_US,
-+                   BCM63268_TIMER_RESET_SLEEP_MAX_US);
-+
-+      return 0;
-+}
-+
-+static int bcm63268_timer_reset_status(struct reset_controller_dev *rcdev,
-+                              unsigned long id)
-+{
-+      struct bcm63268_tclkrst_hw *reset = to_bcm63268_timer_reset(rcdev);
-+
-+      return !(__raw_readl(reset->regs) & BIT(id));
-+}
-+
-+static struct reset_control_ops bcm63268_timer_reset_ops = {
-+      .assert = bcm63268_timer_reset_assert,
-+      .deassert = bcm63268_timer_reset_deassert,
-+      .reset = bcm63268_timer_reset_reset,
-+      .status = bcm63268_timer_reset_status,
-+};
-+
-+static int bcm63268_tclk_probe(struct platform_device *pdev)
-+{
-+      struct device *dev = &pdev->dev;
-+      const struct bcm63268_tclk_table_entry *entry;
-+      struct bcm63268_tclkrst_hw *hw;
-+      struct clk_hw *clk;
-+      u8 maxbit = 0;
-+      int i, ret;
-+
-+      for (entry = bcm63268_timer_clocks; entry->name; entry++)
-+              maxbit = max(maxbit, entry->bit);
-+      maxbit++;
-+
-+      hw = devm_kzalloc(&pdev->dev, struct_size(hw, data.hws, maxbit),
-+                        GFP_KERNEL);
-+      if (!hw)
-+              return -ENOMEM;
-+
-+      platform_set_drvdata(pdev, hw);
-+
-+      spin_lock_init(&hw->lock);
-+
-+      hw->data.num = maxbit;
-+      for (i = 0; i < maxbit; i++)
-+              hw->data.hws[i] = ERR_PTR(-ENODEV);
-+
-+      hw->regs = devm_platform_ioremap_resource(pdev, 0);
-+      if (IS_ERR(hw->regs))
-+              return PTR_ERR(hw->regs);
-+
-+      for (entry = bcm63268_timer_clocks; entry->name; entry++) {
-+              clk = devm_clk_hw_register_gate(dev, entry->name, NULL, 0,
-+                                              hw->regs, entry->bit,
-+                                              CLK_GATE_BIG_ENDIAN,
-+                                              &hw->lock);
-+              if (IS_ERR(clk))
-+                      return PTR_ERR(clk);
-+
-+              hw->data.hws[entry->bit] = clk;
-+      }
-+
-+      ret = devm_of_clk_add_hw_provider(dev, of_clk_hw_onecell_get,
-+                                        &hw->data);
-+      if (ret)
-+              return ret;
-+
-+      hw->rcdev.of_node = dev->of_node;
-+      hw->rcdev.ops = &bcm63268_timer_reset_ops;
-+
-+      ret = devm_reset_controller_register(dev, &hw->rcdev);
-+      if (ret)
-+              dev_err(dev, "Failed to register reset controller\n");
-+
-+      return 0;
-+}
-+
-+static const struct of_device_id bcm63268_tclk_dt_ids[] = {
-+      { .compatible = "brcm,bcm63268-timer-clocks" },
-+      { /* sentinel */ }
-+};
-+
-+static struct platform_driver bcm63268_tclk = {
-+      .probe = bcm63268_tclk_probe,
-+      .driver = {
-+              .name = "bcm63268-timer-clock",
-+              .of_match_table = bcm63268_tclk_dt_ids,
-+      },
-+};
-+builtin_platform_driver(bcm63268_tclk);
diff --git a/target/linux/generic/pending-5.15/860-serial-8250_mtk-track-busclk-state-to-avoid-bus-error.patch b/target/linux/generic/pending-5.15/860-serial-8250_mtk-track-busclk-state-to-avoid-bus-error.patch
deleted file mode 100644 (file)
index c5db5d9..0000000
+++ /dev/null
@@ -1,61 +0,0 @@
-From 629c701fc39f1ada9416e0766a86729e83bde86c Mon Sep 17 00:00:00 2001
-Message-ID: <629c701fc39f1ada9416e0766a86729e83bde86c.1694465766.git.daniel@makrotopia.org>
-From: Daniel Golle <[email protected]>
-Date: Mon, 11 Sep 2023 21:27:44 +0100
-Subject: [PATCH] serial: 8250_mtk: track busclk state to avoid bus error
-To: Greg Kroah-Hartman <[email protected]>,
-    Jiri Slaby <[email protected]>,
-    Matthias Brugger <[email protected]>,
-    AngeloGioacchino Del Regno <[email protected]>,
-    Daniel Golle <[email protected]>,
-    John Ogness <[email protected]>,
-    Chen-Yu Tsai <[email protected]>,
-    Changqi Hu <[email protected]>,
-
-Commit e32a83c70cf9 ("serial: 8250-mtk: modify mtk uart power and
-clock management") introduced polling a debug register to make sure
-the UART is idle before disabling the bus clock. However, at least on
-some MediaTek SoCs access to that very debug register requires the bus
-clock being enabled. Hence calling the suspend function while already
-in suspended state results in that register access triggering a bus
-error. In order to avoid that, track the state of the bus clock and
-only poll the debug register if not already in suspended state.
-
-Fixes: e32a83c70cf9 ("serial: 8250-mtk: modify mtk uart power and clock management")
-Signed-off-by: Daniel Golle <[email protected]>
----
- drivers/tty/serial/8250/8250_mtk.c | 11 ++++++++++-
- 1 file changed, 10 insertions(+), 1 deletion(-)
-
---- a/drivers/tty/serial/8250/8250_mtk.c
-+++ b/drivers/tty/serial/8250/8250_mtk.c
-@@ -32,7 +32,7 @@
- #define MTK_UART_RXTRI_AD     0x14    /* RX Trigger address */
- #define MTK_UART_FRACDIV_L    0x15    /* Fractional divider LSB address */
- #define MTK_UART_FRACDIV_M    0x16    /* Fractional divider MSB address */
--#define MTK_UART_DEBUG0       0x18
-+#define MTK_UART_DEBUG0               0x18
- #define MTK_UART_IER_XOFFI    0x20    /* Enable XOFF character interrupt */
- #define MTK_UART_IER_RTSI     0x40    /* Enable RTS Modem status interrupt */
- #define MTK_UART_IER_CTSI     0x80    /* Enable CTS Modem status interrupt */
-@@ -418,13 +418,12 @@ static int __maybe_unused mtk8250_runtim
-       struct mtk8250_data *data = dev_get_drvdata(dev);
-       struct uart_8250_port *up = serial8250_get_port(data->line);
--      /* wait until UART in idle status */
--      while
--              (serial_in(up, MTK_UART_DEBUG0));
--
-       if (data->clk_count == 0U) {
-               dev_dbg(dev, "%s clock count is 0\n", __func__);
-       } else {
-+              /* wait until UART in idle status */
-+              while
-+                      (serial_in(up, MTK_UART_DEBUG0));
-               clk_disable_unprepare(data->bus_clk);
-               data->clk_count--;
-       }
diff --git a/target/linux/generic/pending-5.15/870-ARM-dts-nxp-imx7d-pico-add-cpu-supply-nodes.patch b/target/linux/generic/pending-5.15/870-ARM-dts-nxp-imx7d-pico-add-cpu-supply-nodes.patch
deleted file mode 100644 (file)
index 186b052..0000000
+++ /dev/null
@@ -1,43 +0,0 @@
-From 89a74fc5d367441bf4912e9158f0640ea3494b9e Mon Sep 17 00:00:00 2001
-From: Lech Perczak <[email protected]>
-Date: Fri, 17 Nov 2023 21:33:04 +0100
-Subject: [PATCH] ARM: dts: nxp: imx7d-pico: add cpu-supply nodes
-
-The PICO-IMX7D SoM has the usual power supply configuration using
-output sw1a of PF3000 PMIC, which was defined in downstream derivative
-of linux-imx (see link) in the sources for "Android Things" devkit.
-It is required to support CPU frequency scaling.
-
-Map the respective "cpu-supply" nodes of each core to sw1a of the PMIC.
-
-Enabling them causes cpufreq-dt, and imx-thermal drivers to probe
-successfully, and CPU frequency scaling to function.
-
-Link: https://android.googlesource.com/platform/hardware/bsp/kernel/nxp/imx-v4.1/+/o-iot-preview-5/arch/arm/boot/dts/imx7d-pico.dtsi#849
-
-Cc: Fabio Estevam <[email protected]>
-Cc: Shawn Guo <[email protected]>
-Cc: Sascha Hauer <[email protected]>
-
-Signed-off-by: Lech Perczak <[email protected]>
----
- arch/arm/boot/dts/imx7d-pico.dtsi | 8 ++++++++
- 1 file changed, 8 insertions(+)
-
---- a/arch/arm/boot/dts/imx7d-pico.dtsi
-+++ b/arch/arm/boot/dts/imx7d-pico.dtsi
-@@ -108,6 +108,14 @@
-       assigned-clock-rates = <0>, <32768>;
- };
-+&cpu0 {
-+      cpu-supply = <&sw1a_reg>;
-+};
-+
-+&cpu1 {
-+      cpu-supply = <&sw1a_reg>;
-+};
-+
- &ecspi3 {
-       cs-gpios = <&gpio4 11 GPIO_ACTIVE_LOW>;
-       pinctrl-names = "default";
diff --git a/target/linux/generic/pending-5.15/880-01-dt-bindings-leds-add-LED_FUNCTION_MOBILE-for-mobile-.patch b/target/linux/generic/pending-5.15/880-01-dt-bindings-leds-add-LED_FUNCTION_MOBILE-for-mobile-.patch
deleted file mode 100644 (file)
index 04c6efe..0000000
+++ /dev/null
@@ -1,37 +0,0 @@
-From 38eb5b3370c29515d2ce92adac2d6eba96f276f5 Mon Sep 17 00:00:00 2001
-From: INAGAKI Hiroshi <[email protected]>
-Date: Wed, 20 Mar 2024 15:32:18 +0900
-Subject: [PATCH v2 1/2] dt-bindings: leds: add LED_FUNCTION_MOBILE for mobile
- network
-
-Add LED_FUNCTION_MOBILE for LEDs that indicate status of mobile network
-connection. This is useful to distinguish those LEDs from LEDs that
-indicates status of wired "wan" connection.
-
-example (on stock fw):
-
-IIJ SA-W2 has "Mobile" LEDs that indicate status (no signal, too low,
-low, good) of mobile network connection via dongle connected to USB
-port.
-
-- no signal: (none, turned off)
--   too low: green:mobile & red:mobile (amber, blink)
--       low: green:mobile & red:mobile (amber, turned on)
--      good: green:mobile (turned on)
-
-Suggested-by: Hauke Mehrtens <[email protected]>
-Signed-off-by: INAGAKI Hiroshi <[email protected]>
----
- include/dt-bindings/leds/common.h | 1 +
- 1 file changed, 1 insertion(+)
-
---- a/include/dt-bindings/leds/common.h
-+++ b/include/dt-bindings/leds/common.h
-@@ -83,6 +83,7 @@
- #define LED_FUNCTION_INDICATOR "indicator"
- #define LED_FUNCTION_LAN "lan"
- #define LED_FUNCTION_MAIL "mail"
-+#define LED_FUNCTION_MOBILE "mobile"
- #define LED_FUNCTION_MTD "mtd"
- #define LED_FUNCTION_PANIC "panic"
- #define LED_FUNCTION_PROGRAMMING "programming"
diff --git a/target/linux/generic/pending-5.15/880-02-dt-bindings-leds-add-LED_FUNCTION_SPEED_-for-link-sp.patch b/target/linux/generic/pending-5.15/880-02-dt-bindings-leds-add-LED_FUNCTION_SPEED_-for-link-sp.patch
deleted file mode 100644 (file)
index e601481..0000000
+++ /dev/null
@@ -1,37 +0,0 @@
-From e22afe910afcfb51b6ba6a0ae776939959727f54 Mon Sep 17 00:00:00 2001
-From: INAGAKI Hiroshi <[email protected]>
-Date: Wed, 20 Mar 2024 15:59:06 +0900
-Subject: [PATCH v2 2/2] dt-bindings: leds: add LED_FUNCTION_SPEED_* for link
- speed on LAN/WAN
-
-Add LED_FUNCTION_SPEED_LAN and LED_FUNCTION_SPEED_WAN for LEDs that
-indicate link speed of ethernet ports on LAN/WAN. This is useful to
-distinguish those LEDs from LEDs that indicate link status (up/down).
-
-example:
-
-Fortinet FortiGate 30E/50E have LEDs that indicate link speed on each
-of the ethernet ports in addition to LEDs that indicate link status
-(up/down).
-
-- 1000 Mbps: green:speed-(lan|wan)-N
--  100 Mbps: amber:speed-(lan|wan)-N
--   10 Mbps: (none, turned off)
-
-Reviewed-by: Rob Herring <[email protected]>
-Signed-off-by: INAGAKI Hiroshi <[email protected]>
----
- include/dt-bindings/leds/common.h | 2 ++
- 1 file changed, 2 insertions(+)
-
---- a/include/dt-bindings/leds/common.h
-+++ b/include/dt-bindings/leds/common.h
-@@ -89,6 +89,8 @@
- #define LED_FUNCTION_PROGRAMMING "programming"
- #define LED_FUNCTION_RX "rx"
- #define LED_FUNCTION_SD "sd"
-+#define LED_FUNCTION_SPEED_LAN "speed-lan"
-+#define LED_FUNCTION_SPEED_WAN "speed-wan"
- #define LED_FUNCTION_STANDBY "standby"
- #define LED_FUNCTION_TORCH "torch"
- #define LED_FUNCTION_TX "tx"
diff --git a/target/linux/generic/pending-5.15/920-mangle_bootargs.patch b/target/linux/generic/pending-5.15/920-mangle_bootargs.patch
deleted file mode 100644 (file)
index b127d76..0000000
+++ /dev/null
@@ -1,71 +0,0 @@
-From: Imre Kaloz <[email protected]>
-Subject: init: add CONFIG_MANGLE_BOOTARGS and disable it by default
-
-Enabling this option renames the bootloader supplied root=
-and rootfstype= variables, which might have to be know but
-would break the automatisms OpenWrt uses.
-
-Signed-off-by: Imre Kaloz <[email protected]>
----
- init/Kconfig |  9 +++++++++
- init/main.c  | 24 ++++++++++++++++++++++++
- 2 files changed, 33 insertions(+)
-
---- a/init/Kconfig
-+++ b/init/Kconfig
-@@ -1814,6 +1814,15 @@ config EMBEDDED
-         an embedded system so certain expert options are available
-         for configuration.
-+config MANGLE_BOOTARGS
-+      bool "Rename offending bootargs"
-+      depends on EXPERT
-+      help
-+        Sometimes the bootloader passed bogus root= and rootfstype=
-+        parameters to the kernel, and while you want to ignore them,
-+        you need to know the values f.e. to support dual firmware
-+        layouts on the flash.
-+
- config HAVE_PERF_EVENTS
-       bool
-       help
---- a/init/main.c
-+++ b/init/main.c
-@@ -619,6 +619,29 @@ static inline void setup_nr_cpu_ids(void
- static inline void smp_prepare_cpus(unsigned int maxcpus) { }
- #endif
-+#ifdef CONFIG_MANGLE_BOOTARGS
-+static void __init mangle_bootargs(char *command_line)
-+{
-+      char *rootdev;
-+      char *rootfs;
-+
-+      rootdev = strstr(command_line, "root=/dev/mtdblock");
-+
-+      if (rootdev)
-+              strncpy(rootdev, "mangled_rootblock=", 18);
-+
-+      rootfs = strstr(command_line, "rootfstype");
-+
-+      if (rootfs)
-+              strncpy(rootfs, "mangled_fs", 10);
-+
-+}
-+#else
-+static void __init mangle_bootargs(char *command_line)
-+{
-+}
-+#endif
-+
- /*
-  * We need to store the untouched command line for future reference.
-  * We also need to store the touched command line since the parameter
-@@ -960,6 +983,7 @@ asmlinkage __visible void __init __no_sa
-       pr_notice("%s", linux_banner);
-       early_security_init();
-       setup_arch(&command_line);
-+      mangle_bootargs(command_line);
-       setup_boot_config();
-       setup_command_line(command_line);
-       setup_nr_cpu_ids();
diff --git a/target/linux/generic/pending-5.15/980-tools-thermal-tmon-Fix-compilation-warning-for-wrong.patch b/target/linux/generic/pending-5.15/980-tools-thermal-tmon-Fix-compilation-warning-for-wrong.patch
deleted file mode 100644 (file)
index 6a0a199..0000000
+++ /dev/null
@@ -1,51 +0,0 @@
-From a7a94ca21ac0f347f683d33c72b4aab57ce5eec3 Mon Sep 17 00:00:00 2001
-From: Florian Eckert <[email protected]>
-Date: Mon, 20 Nov 2023 11:13:20 +0100
-Subject: [PATCH] tools/thermal/tmon: Fix compilation warning for wrong format
-
-The following warnings are shown during compilation:
-
-tui.c: In function 'show_cooling_device':
- tui.c:216:40: warning: format '%d' expects argument of type 'int', but
-argument 7 has type 'long unsigned int' [-Wformat=]
-   216 |                         "%02d %12.12s%6d %6d",
-       |                                      ~~^
-       |                                        |
-       |                                        int
-       |                                      %6ld
- ......
-   219 |                         ptdata.cdi[j].cur_state,
-       |                         ~~~~~~~~~~~~~~~~~~~~~~~
-       |                                      |
-       |                                      long unsigned int
- tui.c:216:44: warning: format '%d' expects argument of type 'int', but
-argument 8 has type 'long unsigned int' [-Wformat=]
-   216 |                         "%02d %12.12s%6d %6d",
-       |                                          ~~^
-       |                                            |
-       |                                            int
-       |                                          %6ld
- ......
-   220 |                         ptdata.cdi[j].max_state);
-       |                         ~~~~~~~~~~~~~~~~~~~~~~~
-       |                                      |
-       |                                      long unsigned int
-
-To fix this, the correct string format must be used for printing.
-
-Signed-off-by: Florian Eckert <[email protected]>
----
- tools/thermal/tmon/tui.c | 2 +-
- 1 file changed, 1 insertion(+), 1 deletion(-)
-
---- a/tools/thermal/tmon/tui.c
-+++ b/tools/thermal/tmon/tui.c
-@@ -213,7 +213,7 @@ void show_cooling_device(void)
-                * cooling device instances. skip unused idr.
-                */
-               mvwprintw(cooling_device_window, j + 2, 1,
--                      "%02d %12.12s%6d %6d",
-+                      "%02d %12.12s%6lu %6lu",
-                       ptdata.cdi[j].instance,
-                       ptdata.cdi[j].type,
-                       ptdata.cdi[j].cur_state,